Sqlserver
 sql >> Database >  >> RDS >> Sqlserver

Errore "Deve dichiarare la variabile scalare" quando si passa un parametro con valori di tabella a un'istruzione SQL con parametri

Per prima cosa:non ho idea di dove stai ottenendo il tableName e columnName , ma se sono forniti dall'utente, questo è aperto a SQL injection. Come minimo, usa QUOTENAME() per garantire che non venga iniettato alcun codice effettivo.

In secondo luogo, non stai effettivamente utilizzando il TVP. Il codice che hai dice solo IN (@IDTable) che non è il modo in cui usi un TVP.

Un TVP è solo una variabile di tabella e dovrebbe essere utilizzata come qualsiasi altra tabella:

protected virtual void DoDeleteRecords(List<Guid> ids)
{   
    if (ids.Count == 0)
        return;
    DataTable tvp = new DataTable();
    tvp.Columns.Add("Id", typeof(Guid));

    foreach (Guid id in ids)
        tvp.Rows.Add(id);

    const string sql = @"
DELETE FROM table
WHERE idColumnName IN (SELECT * FROM @IDTable);
";

    using(SqlConnection connection = new SqlConnection(CoreSettings.ConnectionString))
    using(SqlCommand command = new SqlCommand(sql, connection))
    {
        command.Parameters.Add(
            new SqlParameter("@IDTable", SqlDbType.Structured)
        {
            Value = tvp,
            Direction = ParameterDirection.Input,
            TypeName = "dbo.IDList"
        });

        connection.Open();
        command.ExecuteNonQuery();
    }
}