Ich habe eine gespeicherte Prozedur mit drei Parametern und ich habe versucht, die folgenden zu verwenden, um die Ergebnisse zurückzugeben:
context.Database.SqlQuery<myEntityType>("mySpName", param1, param2, param3);
Zuerst habe ich versucht, SqlParameter
-Objekte als Parameter zu verwenden, aber das hat nicht funktioniert und habe ein SqlException
mit der folgenden Meldung geworfen:
Die Prozedur oder Funktion 'mySpName' erwartet den Parameter '@ param1', der nicht angegeben wurde.
Meine Frage ist also, wie Sie diese Methode mit einer gespeicherten Prozedur verwenden können, die Parameter erwartet?
Vielen Dank.
Sie sollten die SqlParameter-Instanzen folgendermaßen bereitstellen:
context.Database.SqlQuery<myEntityType>(
"mySpName @param1, @param2, @param3",
new SqlParameter("param1", param1),
new SqlParameter("param2", param2),
new SqlParameter("param3", param3)
);
Sie können den Parameter "sql" auch als Formatbezeichner verwenden:
context.Database.SqlQuery<MyEntityType>("mySpName @param1 = {0}", param1)
Diese Lösung ist (nur) für SQL Server 2005
Ihr seid Lebensretter, aber wie @Dan Mork sagte, müsst ihr EXEC zum Mix hinzufügen. Was mich auslöste, war:
:
context.Database.SqlQuery<EntityType>(
"EXEC ProcName @param1, @param2",
new SqlParameter("param1", param1),
new SqlParameter("param2", param2)
);
return context.Database.SqlQuery<myEntityType>("mySpName {0}, {1}, {2}",
new object[] { param1, param2, param3 });
//Oder
using(var context = new MyDataContext())
{
return context.Database.SqlQuery<myEntityType>("mySpName {0}, {1}, {2}",
new object[] { param1, param2, param3 }).ToList();
}
//Oder
using(var context = new MyDataContext())
{
object[] parameters = { param1, param2, param3 };
return context.Database.SqlQuery<myEntityType>("mySpName {0}, {1}, {2}",
parameters).ToList();
}
//Oder
using(var context = new MyDataContext())
{
return context.Database.SqlQuery<myEntityType>("mySpName {0}, {1}, {2}",
param1, param2, param3).ToList();
}
Die meisten Antworten sind spröde, weil sie von der Reihenfolge der SP-Parameter abhängen. Es ist besser, die Parameter des Stored Proc zu benennen und diesen parametrisierte Werte zuzuweisen.
Damit Sie beim Aufrufen Ihres SP Named-Parameter verwenden können, ohne sich Gedanken über die Reihenfolge der Parameter zu machen
Verwenden von benannten SQL Server-Parametern mit ExecuteStoreQuery und ExecuteStoreCommand
Beschreibt den besten Ansatz. Besser als die Antwort von Dan Mork.
Z.B.:
var cmdText = "[DoStuff] @Name = @name_param, @Age = @age_param";
var sqlParams = new[]{
new SqlParameter("name_param", "Josh"),
new SqlParameter("age_param", 45)
};
context.Database.SqlQuery<myEntityType>(cmdText, sqlParams)
db.Database.SqlQuery<myEntityType>("exec GetNewSeqOfFoodServing @p0,@p1,@p2 ", foods_WEIGHT.NDB_No, HLP.CuntryID, HLP.ClientID).Single()
oder
db.Database.SqlQuery<myEntityType>(
"exec GetNewSeqOfFoodServing @param1, @param2",
new SqlParameter("param1", param1),
new SqlParameter("param2", param2)
);
oder
var cmdText = "exec [DoStuff] @Name = @name_param, @Age = @age_param";
var @params = new[]{
new SqlParameter("name_param", "Josh"),
new SqlParameter("age_param", 45)
};
db.Database.SqlQuery<myEntityType>(cmdText, @params)
oder
db.Database.SqlQuery<myEntityType>("mySpName {0}, {1}, {2}",
new object[] { param1, param2, param3 }).ToList();
Ich benutze diese Methode:
var results = this.Database.SqlQuery<yourEntity>("EXEC [ent].[GetNextExportJob] {0}", ProcessorID);
Ich mag es, weil ich einfach Guids und Datetimes einlege und SqlQuery die gesamte Formatierung für mich durchführt.
Die Antwort von @Tom Halladay ist richtig, mit der Erwähnung, dass Sie auch auf Nullwerte prüfen und DbNullable senden sollten, wenn die Parameter Null sind, da Sie eine Ausnahme wie erhalten würden
Die parametrisierte Abfrage '...' erwartet den Parameter '@parameterName', der nicht angegeben wurde.
So etwas hat mir geholfen
public static object GetDBNullOrValue<T>(this T val)
{
bool isDbNull = true;
Type t = typeof(T);
if (Nullable.GetUnderlyingType(t) != null)
isDbNull = EqualityComparer<T>.Default.Equals(default(T), val);
else if (t.IsValueType)
isDbNull = false;
else
isDbNull = val == null;
return isDbNull ? DBNull.Value : (object) val;
}
(Gutschrift für die Methode geht an https://stackoverflow.com/users/284240/tim-schmelter )
Dann benutze es wie folgt:
new SqlParameter("@parameterName", parameter.GetValueOrDbNull())
oder eine andere, einfachere, aber nicht generische Lösung wäre:
new SqlParameter("@parameterName", parameter??(object)DBNull.Value)
Ich hatte dieselbe Fehlermeldung beim Aufrufen einer gespeicherten Prozedur, die zwei Eingabeparameter verwendet und mit der SELECT-Anweisung 3 Werte zurückgibt, und löste das Problem wie unten in EF Code First Approach
SqlParameter @TableName = new SqlParameter()
{
ParameterName = "@TableName",
DbType = DbType.String,
Value = "Trans"
};
SqlParameter @FieldName = new SqlParameter()
{
ParameterName = "@FieldName",
DbType = DbType.String,
Value = "HLTransNbr"
};
object[] parameters = new object[] { @TableName, @FieldName };
List<Sample> x = this.Database.SqlQuery<Sample>("EXEC usp_NextNumberBOGetMulti @TableName, @FieldName", parameters).ToList();
public class Sample
{
public string TableName { get; set; }
public string FieldName { get; set; }
public int NextNum { get; set; }
}
UPDATE : Es sieht so aus, als würde bei SQL SERVER 2005 ein fehlendes EXEC-Schlüsselwort ein Problem verursachen. Damit es mit allen SQL-SERVER-Versionen funktioniert, habe ich meine Antwort aktualisiert und in der folgenden Zeile EXEC hinzugefügt
List<Sample> x = this.Database.SqlQuery<Sample>(" EXEC usp_NextNumberBOGetMulti @TableName, @FieldName", param).ToList();