Prosedur atau fungsi tersimpan mengharapkan parameter yang tidak disediakan

Saya mencoba memasukkan data ke dalam database SQL Server dengan memanggil stored procedure, tetapi saya mendapatkan error

Prosedur atau fungsi 'SHOWuser' mengharapkan parameter '@userID', yang tidak disediakan.

Prosedur tersimpan saya disebut SHOWuser. Saya telah memeriksanya secara menyeluruh dan tidak ada parameter yang hilang.

Kode saya adalah:

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();
        }

dan prosedur yang tersimpan adalah:

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

Ini adalah prosedur tersimpan kedua tbl_pref yang digunakan dalam fungsi yang sama:

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

Dalam kasus saya, saya menerima pengecualian ini bahkan ketika semua nilai parameter diberikan dengan benar tetapi jenis perintah tidak ditentukan:

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

Ini jelas bukan kasus dalam pertanyaan di atas, tetapi deskripsi pengecualian tidak terlalu jelas dalam kasus ini, jadi saya memutuskan untuk menentukannya.

Komentar (3)

Saya menemukan masalah ini kemarin, tetapi tidak ada solusi di sini yang bekerja dengan tepat, namun mereka mengarahkan saya ke arah yang benar.

Aplikasi kami adalah alat alur kerja yang ditulis dalam C # dan, terlalu disederhanakan, memiliki beberapa prosedur tersimpan pada database, serta tabel metadata tentang setiap parameter yang digunakan oleh setiap prosedur tersimpan (nama, urutan, tipe data, ukuran, dll), memungkinkan kami untuk membuat sebanyak mungkin prosedur tersimpan baru yang kami butuhkan tanpa harus mengubah C #.

Analisis masalah menunjukkan bahwa kode kami menetapkan semua parameter yang benar pada objek SqlCommand, namun setelah dieksekusi, kode itu melemparkan kesalahan yang sama seperti yang didapat OP.

Analisis lebih lanjut mengungkapkan bahwa beberapa parameter memiliki nilai null. Oleh karena itu, saya harus menarik kesimpulan bahwa objek SqlCommand mengabaikan objek SqlParameter apa pun dalam koleksi .Parameters mereka dengan nilai null.

Ada dua solusi untuk masalah ini yang saya temukan.

  1. Dalam prosedur tersimpan kita, berikan nilai default untuk setiap parameter, jadi dari @Parameter int ke @Parameter int = NULL (atau nilai default lainnya sesuai kebutuhan).

  2. Dalam kode kita yang menghasilkan objek SqlParameter individual, menetapkan DBNull.Value bukan null di mana nilai yang dimaksudkan adalah SQL NULL melakukan trik.

Pembuat kode asli telah pindah dan kode awalnya ditulis dengan Solusi 1 dalam pikiran, dan setelah menimbang manfaat dari keduanya, saya pikir saya akan tetap menggunakan Solusi 1. Jauh lebih mudah untuk menentukan nilai default untuk prosedur tersimpan tertentu saat menulisnya, daripada selalu menjadi NULL seperti yang didefinisikan dalam kode.

Semoga itu membantu seseorang.

Komentar (3)
Larutan

Prosedur tersimpan Anda mengharapkan 5 parameter sebagai input

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

Jadi, Anda harus menambahkan semua 5 parameter ke panggilan SP ini:

    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: Tidak jelas untuk apa parameter ini. Anda tidak menggunakan parameter-parameter ini di badan SP Anda sehingga SP Anda akan terlihat seperti:

ALTER PROCEDURE [dbo].[SHOWuser] AS BEGIN ..... END
Komentar (6)