Подтвердить что ты не робот

Сохраненная процедура или функция ожидает параметра, который не поставляется

Я пытаюсь вставить данные в базу данных SQL Server, вызвав хранимую процедуру, но я получаю сообщение об ошибке

Процедура или функция "SHOWuser" ожидает параметра "@userID", который не был предоставлен.

Моя хранимая процедура называется SHOWuser. Я проверил его полностью и никаких параметров не было.

Мой код:

public void SHOWuser(string userName, string password, string emailAddress, List<int> preferences)
{
        SqlConnection dbcon = new SqlConnection(conn);

        try
        { 
            SqlCommand cmd = new SqlCommand();

            cmd.Connection = dbcon;
            cmd.CommandType = System.Data.CommandType.StoredProcedure;
            cmd.CommandText = "SHOWuser";

            cmd.Parameters.AddWithValue("@userName", userName);
            cmd.Parameters.AddWithValue("@password", password);
            cmd.Parameters.AddWithValue("@emailAddress", emailAddress);

            dbcon.Open();

            int i = Convert.ToInt32(cmd.ExecuteScalar());

            cmd.Parameters.Clear();
            cmd.CommandText = "tbl_pref";

            foreach (int preference in preferences)
            {
                cmd.Parameters.Clear();
                cmd.Parameters.AddWithValue("@userID", Convert.ToInt32(i));
                cmd.Parameters.AddWithValue("@preferenceID", Convert.ToInt32(preference));

                cmd.ExecuteNonQuery();
            }
        }
        catch (Exception)
        {
            throw;
        }
        finally
        {
            dbcon.Close();
        }

а хранимая процедура:

ALTER PROCEDURE [dbo].[SHOWuser]
(
    @userName varchar(50),
    @password nvarchar(50),
    @emailAddress nvarchar(50)
)
AS
BEGIN
    INSERT INTO tbl_user(userName, password, emailAddress) 
    VALUES (@userName, @password, @emailAddress)

    SELECT
        tbl_user.userID, tbl_user.userName,
        tbl_user.password, tbl_user.emailAddress, 
        STUFF((SELECT ',' + preferenceName 
               FROM tbl_pref_master
               INNER JOIN tbl_preferences ON tbl_pref_master.preferenceID = tbl_preferences.preferenceID
               WHERE tbl_preferences.userID = tbl_user.userID
               FOR XML PATH ('')), 1, 1, ' ' ) AS Preferences
    FROM
        tbl_user

    SELECT SCOPE_IDENTITY();
END

Это вторая хранимая процедура tbl_pref, которая используется в той же функции:

ALTER PROCEDURE [dbo].[tbl_pref]
    @userID int,
    @preferenceID int
AS
BEGIN
    INSERT INTO tbl_preferences(userID, preferenceID) 
    VALUES (@userID, @preferenceID)
END
4b9b3361

Ответ 1

Ваша хранимая процедура ожидает 5 параметров ввода

@userID int, 
@userName varchar(50), 
@password nvarchar(50), 
@emailAddress nvarchar(50), 
@preferenceName varchar(20) 

Итак, вы должны добавить все 5 параметров к этому вызову SP:

    cmd.CommandText = "SHOWuser";
    cmd.Parameters.AddWithValue("@userID",userID);
    cmd.Parameters.AddWithValue("@userName", userName);
    cmd.Parameters.AddWithValue("@password", password);
    cmd.Parameters.AddWithValue("@emailAddress", emailAddress);
    cmd.Parameters.AddWithValue("@preferenceName", preferences);
    dbcon.Open();

PS: Не понятно, для чего предназначены эти параметры. Вы не используете эти параметры в своем теле SP, чтобы ваш SP выглядел следующим образом:

ALTER PROCEDURE [dbo].[SHOWuser] AS BEGIN ..... END

Ответ 2

В моем случае я получил это исключение, даже если все значения параметров были правильно поставлены, но тип команды не был указан:

cmd.CommandType = System.Data.CommandType.StoredProcedure;

Это явно не так в вопросе выше, но описание исключения в этом случае не очень ясное, поэтому я решил указать это.

Ответ 3

Я столкнулся с этим вопросом вчера, но ни одно из решений здесь не работало точно, однако они указали мне в правильном направлении.

Наше приложение - это инструмент рабочего процесса, написанный на С#, и, в упрощенном виде, содержит несколько хранимых процедур в базе данных, а также таблицу метаданных о каждом параметре, используемом каждой хранимой процедурой (имя, порядок, тип данных, размер, и т.д.), что позволяет нам создавать столько новых хранимых процедур, сколько нам нужно, не меняя С#.

Анализ проблемы показал, что наш код устанавливал все правильные параметры в объекте SqlCommand, однако, как только он был выполнен, он выдал ту же ошибку, что и OP.

Дальнейший анализ показал, что некоторые параметры имели значение null. Поэтому я должен сделать вывод, что объекты SqlCommand игнорируют любой объект SqlParameter в их коллекции .Parameters со значением null.

Есть два решения этой проблемы, которые я нашел.

  • В наших хранимых процедурах укажите значение по умолчанию для каждого параметра, поэтому от @Parameter int до @Parameter int = NULL (или какого-либо другого значения по умолчанию, если требуется).

  • В нашем коде, который генерирует отдельные объекты SqlParameter, назначая DBNull.Value вместо null, где предполагаемое значение представляет собой SQL null делает трюк.

Исходный кодер перешел, и код был первоначально написан с учетом решения 1, и, взвесив преимущества обоих, я думаю, что я придерживаюсь решения 1. Намного проще указать значение по умолчанию для специфической хранимой процедуры при ее записи, а не всегда null, как определено в коде.

Надеюсь, что это поможет кому-то.

Ответ 4

В моем случае он возвращал один выходной параметр и не возвращал какое-либо значение.
Поэтому он изменил его на

param.Direction = ParameterDirection.Output;
command.ExecuteScalar();

а затем он выбрасывал ошибку размера. поэтому пришлось также установить размер

SqlParameter param = new SqlParameter("@Name",SqlDbType.NVarChar);
param.Size = 10;

Ответ 5

В моем случае я получил ошибку на выходном параметре, даже если я правильно его установил на стороне С#, я понял, что забыл дать значение по умолчанию для вывода параметра в хранимой процедуре

ALTER PROCEDURE [dbo].[test]
(
                @UserID int,
                @ReturnValue int = 0 output --Previously I had @ReturnValue int output
)