Mon SqlParameter ne passe pas NULL correctement
-
06-09-2019 - |
Question
J'ai cette C # qui a formulaire en ligne dispose d'une boîte de sélecteur de date. Si la date est fixée à rien (la valeur par défaut) Je veux passer NULL à la base de données. Cela se produit dans ma requête paramétrée.
SqlParameter CMActionDate = new SqlParameter();
CMActionDate.ParameterName = "@ActionDate";
if (ActionDate.Equals(""))
{
CMActionDate.Value = System.Data.SqlTypes.SqlDateTime.Null;
}
else
{
CMActionDate.Value = ActionDate;
}
Quand je tourne le débogage, je vois que la date est en effet « » il va dans l'instruction IF et définit la actiondate.value à {NULL} comme je pense qu'il devrait.
Cependant.
Quand il va alors exécuter le nonquery, je clique sur la loupe et voir ceci:
UPDATE table SET [action_date] = '' WHERE [id] = 2488
Ce que je voudrais voir est la suivante:
UPDATE table SET [action_date] = 'Null' WHERE [id] = 2488
Depuis la action_date n'a jamais vraiment à NULL obtient, alors la valeur dans le champ datetime revient à « 01/01/1900 12:00:00 AM » et c'est une douleur en elle-même.
Je l'ai essayé d'installer CMActionDate.Value aux valeurs suivantes en vain (je reçois le même résultat que ci-dessus.):
- DBNull.Value;
- "NULL";
- SqlDateTime.Null;
- null;
Aide.
EDIT
Peut-être que je n'étais pas clair? Oui, bien sûr, la requête paramétrisé ressemble à ceci:
"UPDATE CM_Codebase SET [action_date] = '" + @ActionDate + "' WHERE [id] = " + @CM_id + "";
Mais quand je suis débogage cette chose dans VS, je mets un point d'arrêt avant droit ExecuteNonQuery (); afin que je puisse voir le SQL qu'il essaie d'exécuter. Il est là que je vois le SQL et d'en voir le bit où action_date = « ».
Est-ce que l'aide?
La solution
Vous ne devriez pas voir non plus « » ou « nulle ». Si vous utilisez des requêtes paramétrées correctement, il devrait ressembler à ceci:
Tableau UPDATE SET [action_date] = @ActionDate WHERE [id] = @ID
point entier d'une requête paramétrée est que la valeur de paramètre réelle est jamais substitué directement dans la chaîne de requête.
Votre code de requête devrait ressembler à ceci:
string sql = "UPDATE table SET [action_date]= @ActionDate WHERE [id]= @CM_id";
using (var cn = new SqlConnection("your connection string here."))
using (var cmd = new SqlCommand(sql, cn))
{
cmd.Parameters.Add("@ActionDate", SqlDbTypes.DateTime).Value =
ActionDate.Equals("")? DBNull.Value : DateTime.Parse(ActionDate);
cmd.Parameters.Add("@CM_id", SqlDbTypes.Int).Value = 2488;
cn.Open();
cmd.ExecuteNonQuery();
}
Le résultat de ce code est que vos paramètres de requête sont envoyés au serveur en tant que données. À aucun moment dans votre code C # vous jamais être en mesure de voir la chaîne de requête avec vos données de substitution dans: il est envoyé au serveur séparément.
Cela empêche toute possibilité de le serveur exécutant une valeur de paramètre code en raison d'une erreur dans votre désinfectante valeur de paramètre. Les données sont complètement séparées, et n'a pas besoin d'être aseptisé pour ce contexte, en premier lieu. Il permet également au serveur de mise en cache et réutiliser le plan d'exécution de la requête, ce qui entraîne dans un (petit) coup de pouce de la performance.
Autres conseils
Votre requête doit montrer paramétré
UPDATE table SET [action_date] = @ActionDate WHERE [id] = @id
Et la valeur du paramètre doit avoir une valeur équivalente nulle.
Votre sql est
"UPDATE CM_Codebase SET [action_date] = '" + @ActionDate + "'
WHERE [id] = " + @CM_id + "";
Ce qui ne fait pas vraiment de sens. Vous devez laisser sql remplacer le @ActionDate et @CM_ID, ne pas construire une requête SQL dynamique.
Votre sql doit être littéralement:
String sql = "UPDATE table SET [action_date] = @ActionDate WHERE [id] = @CM_id"
Il ne faut pas concaténation de chaînes autour des variables et ils ne devraient pas être entre guillemets doubles.
Votre requête certainement ne ressemble pas à ceux affichés.
Votre @parameter doit être à l'intérieur de votre chaîne, afin d'être lu correctement. Vous voyez ActionDate = « » parce que @ActionDate n'existe pas, le plus probable.
Vous avez besoin de quelque chose comme
string sql = "UPDATE CM_Codebase SET [action_date] = @ActionDate WHERE [id] = @CM_id";
Notez qu'il n'y a pas concaténation de chaîne en cours.