Ошибка при попытке выполнить параметры хранимой процедуры модель Entity Framework EDMX в C # - PullRequest
0 голосов
/ 07 ноября 2019

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

Я получаю следующую ошибку

System.Data.SqlClient.SqlException
Параметризованный запрос '(@recordType nvarchar (12), @ lotCreation bit, @ licensePlateCreation' ожидает параметр '@lotManufactureDate' ', который не был предоставлен.

Вот код хранимой процедуры, edmxмодель создается, когда я вызываю хранимую процедуру из базы данных SQL Server, также здесь параметр с именем licensePlateLookupCode из хранимой процедуры допускает нулевые значения, но в коде созданной модели emdx она не отображается так, как будто она принимает нулевые значения - знаете ли вы, почему?

Это должно быть похоже на Nullable<string> licensePlateLookupCode, а не на string licensePlateLookupCode.

  public virtual int AddFeedbackRequestsAgentInsert(string recordType, 
     Nullable<bool> lotCreation, Nullable<bool> licensePlateCreation, 
     Nullable<int> finishedGoodLineId, Nullable<int> lotid, string 
     lotLookupCode, Nullable<System.DateTime> lotManufactureDate, 
     Nullable<System.DateTime> lotExpirationDate, Nullable<decimal> 
     packagedAmount, Nullable<int> packagingId, string 
     licensePlateLookupCode, Nullable<int> licensePlateId, Nullable<int> 
     licensePlateLocationId)
    {
        var recordTypeParameter = recordType != null ?
            new ObjectParameter("recordType", recordType) :
            new ObjectParameter("recordType", typeof(string));

        var lotCreationParameter = lotCreation.HasValue ?
            new ObjectParameter("lotCreation", lotCreation) :
            new ObjectParameter("lotCreation", typeof(bool));

        var licensePlateCreationParameter = licensePlateCreation.HasValue ?
            new ObjectParameter("licensePlateCreation", licensePlateCreation) :
            new ObjectParameter("licensePlateCreation", typeof(bool));

        var finishedGoodLineIdParameter = finishedGoodLineId.HasValue ?
            new ObjectParameter("finishedGoodLineId", finishedGoodLineId) :
            new ObjectParameter("finishedGoodLineId", typeof(int));

        var lotidParameter = lotid.HasValue ?
            new ObjectParameter("lotid", lotid) :
            new ObjectParameter("lotid", typeof(int));

        var lotLookupCodeParameter = lotLookupCode != null ?
            new ObjectParameter("lotLookupCode", lotLookupCode) :
            new ObjectParameter("lotLookupCode", typeof(string));

        var lotManufactureDateParameter = lotManufactureDate.HasValue ?
            new ObjectParameter("lotManufactureDate", lotManufactureDate) :
            new ObjectParameter("lotManufactureDate", typeof(System.DateTime));

        var lotExpirationDateParameter = lotExpirationDate.HasValue ?
            new ObjectParameter("lotExpirationDate", lotExpirationDate) :
            new ObjectParameter("lotExpirationDate", typeof(System.DateTime));

        var packagedAmountParameter = packagedAmount.HasValue ?
            new ObjectParameter("packagedAmount", packagedAmount) :
            new ObjectParameter("packagedAmount", typeof(decimal));

        var packagingIdParameter = packagingId.HasValue ?
            new ObjectParameter("packagingId", packagingId) :
            new ObjectParameter("packagingId", typeof(int));

        var licensePlateLookupCodeParameter = licensePlateLookupCode != null ?
            new ObjectParameter("licensePlateLookupCode", licensePlateLookupCode) :
            new ObjectParameter("licensePlateLookupCode", typeof(string));

        var licensePlateIdParameter = licensePlateId.HasValue ?
            new ObjectParameter("licensePlateId", licensePlateId) :
            new ObjectParameter("licensePlateId", typeof(int));

        var licensePlateLocationIdParameter = licensePlateLocationId.HasValue ?
            new ObjectParameter("licensePlateLocationId", licensePlateLocationId) :
            new ObjectParameter("licensePlateLocationId", typeof(int));

        return ((IObjectContextAdapter)this).ObjectContext.ExecuteFunction("AddFeedbackRequestsAgentInsert", recordTypeParameter, lotCreationParameter, licensePlateCreationParameter, finishedGoodLineIdParameter, lotidParameter, lotLookupCodeParameter, lotManufactureDateParameter, lotExpirationDateParameter, packagedAmountParameter, packagingIdParameter, licensePlateLookupCodeParameter, licensePlateIdParameter, licensePlateLocationIdParameter);
    }

Здесь я вызываю эту хранимую процедуру, а затем выполняю ее после того, как пользователь щелкнет кнопку Отправить. кнопка, я получаю сообщение об ошибке для параметров lotmanufacturer и lotexpiration date, потому что они NULLS, я думаю, но в фактической хранимой процедуре базы данных яt может принимать нули или нет

    private void Btn_Submit_Click(object sender, EventArgs e)
    {
        // db context variable
        var context = _manufacturingDbContext;

        // ** Variables to insert to FootPrint stored procedure datex_footprint_integration.AddFeedbackRequestsAgentInsert with Record Type (FinishedGood)
        const string recordType = "FinishedGood";
        const bool lotCreation = false;
        const bool licensePlateCreation = true;           
        var finishedGoodLineId = context.FinishedGoodLineIdByOrderAndFinishedGoodAndLot(Cmb_MfgOrder.Text, Cmb_FgLookupCode.Text, Cmb_LotLookupCode.Text).FirstOrDefault();         
        var lotId = context.LotIdByManufacturingOrderAndFinishedGood(Cmb_MfgOrder.Text, Cmb_FgLookupCode.Text,Cmb_LotLookupCode.Text).FirstOrDefault();
        var doNotCreateLot = null;
        DateTime? lotManufactureDate = null;
        DateTime? lotExpirationDate = null;
        var packagedAmount = Convert.ToDecimal(Txt_PackagedAmount.Text);
        const int packagedId = 3;
        var licensePlateLookupCode = Txt_LicensePlateLookupCode.Text;
        int? licensePlateId = null;
        const int licensePlateLocationId = 51372;            

        // Call SQL Server SPROC dbo.AddFeedbackRequestsAgentInsert and enter data to FootPrint Task

        context.Database.ExecuteSqlCommand("EXEC dbo.AddFeedbackRequestsAgentInsert " +
                                           "@recordType, @lotCreation, @licensePlateCreation, @finishedGoodLineId, @lotid, @lotLookupCode, @lotManufactureDate," +
                                           "@lotExpirationDate, @packagedAmount, @packagingId, @licensePlateLookupCode, @licensePlateId, @licensePlateLocationId",
                             new SqlParameter("@recordType", recordType),
                                            new SqlParameter("@lotCreation", lotCreation),
                                            new SqlParameter("@licensePlateCreation", licensePlateCreation),
                                            new SqlParameter("@finishedGoodLineId", finishedGoodLineId),
                                            new SqlParameter("@lotid", lotId),
                                            new SqlParameter("@lotLookupCode", doNotCreateLot),
                                            new SqlParameter("@lotManufactureDate", lotManufactureDate),
                                            new SqlParameter("@lotExpirationDate", lotExpirationDate),
                                            new SqlParameter("@packagedAmount", packagedAmount),
                                            new SqlParameter("@packagingId", packagedId),
                                            new SqlParameter("@licensePlateLookupCode", licensePlateLookupCode),
                                            new SqlParameter("@licensePlateId", licensePlateId),
                                            new SqlParameter("@licensePlateLocationId", licensePlateLocationId)
                                            );

        context.SaveChanges();
}

Вот фактическая хранимая процедура - как вы можете видеть @lotManufactureDate и @lotExpirationDate действительно разрешают нули:

CREATE PROCEDURE [dbo].[AddFeedbackRequestsAgentInsert]
         @recordType NVARCHAR(30),
         @lotCreation BIT,
         @licensePlateCreation BIT,
         @finishedGoodLineId INT,
         @lotid INT NULL,
         @lotLookupCode NVARCHAR(256) NULL,
         @lotManufactureDate DATETIME NULL,
         @lotExpirationDate DATETIME NULL,
         @packagedAmount DECIMAL(28,8),
         @packagingId INT,
         @licensePlateLookupCode NVARCHAR(256) NULL,
         @licensePlateId INT NULL,
         @licensePlateLocationId INT NULL

Итак, я неНе понимаю, почему я получаю эту ошибку ожидаемого, когда я передаю эти 2 параметра даты с нулевыми датами, то же самое происходит, если параметр lotlookupcode, если я передаю ноль, я получаю ту же ошибку, которая ожидает lotlookupcode. Можете ли вы увидеть, в чем может быть проблема здесь?

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

Я вызываю эту функцию из хранимой процедуры функции импорта браузера модели, когда я битакнопка «Отправить» Я ничего не получаю в базе данных, если параметры выглядят корректно на основе модели emdx и хранимой процедуры?

    var context = _manufacturingDbContext;


    const string recordType = "FinishedGood";
    const bool lotCreation = false;
    const bool licensePlateCreation = true;           
    var finishedGoodLineId = context.FinishedGoodLineIdByOrderAndFinishedGoodAndLot(Cmb_MfgOrder.Text, Cmb_FgLookupCode.Text, Cmb_LotLookupCode.Text).FirstOrDefault();         
    var lotId = context.LotIdByManufacturingOrderAndFinishedGood(Cmb_MfgOrder.Text, Cmb_FgLookupCode.Text,Cmb_LotLookupCode.Text).FirstOrDefault();
    var doNotCreateLot = null;
    DateTime? lotManufactureDate = null;
    DateTime? lotExpirationDate = null;
    var packagedAmount = Convert.ToDecimal(Txt_PackagedAmount.Text);
    const int packagedId = 3;
    var licensePlateLookupCode = Txt_LicensePlateLookupCode.Text;
    int? licensePlateId = null;
    const int licensePlateLocationId = 51372;    


        //calling stored procedure and send data to sproc based on the variables above
        context.AddFeedbackRequestsAgentInsert(recordType, lotCreation, licensePlateCreation, finishedGoodLineId,
            lotId, lot, lotManufactureDate, lotExpirationDate, packagedAmount, packagedId, licensePlateLookupCode,
            licensePlateId, licensePlateLocationId);

}

Ответы [ 3 ]

0 голосов
/ 07 ноября 2019

Вы можете вызвать AddFeedbackRequestsAgentInsert метод, сгенерированный EF напрямую, и передать ему параметры. Возможно, вам не нужно будет вызывать ontext.Database.ExecuteSqlCommand

, если вы хотите использовать ontext.Database.ExecuteSqlCommand, вы можете использоватьприведенный ниже код для передачи значения NULL в параметрах даты, которые могут иметь значение NULL *

        new SqlParameter("@lotManufactureDate", lotManufactureDate.HasValue ? lotManufactureDate : DBNull.Value),
        new SqlParameter("@lotManufactureDate", lotExpirationDate.HasValue ? lotExpirationDate : DBNull.Value),

ИЛИ

        new SqlParameter("@lotManufactureDate", lotManufactureDate.HasValue ? lotManufactureDate : default(DateTime)),
        new SqlParameter("@lotManufactureDate", lotExpirationDate.HasValue ? lotExpirationDate : default(DateTime)),
0 голосов
/ 07 ноября 2019

Это мой ответ, все, что мне нужно было сделать, это исправить некоторую часть моего хранимого заготовки sql, и самое важное, что мне просто нужно было вызвать мою функцию импорта, созданную из модели emdx, и добавить в нее правильные параметры после проверки данных в базе данных. правильно вставляет на основе решения кода, любой вопрос, если вы видите лучший подход, пожалуйста, дайте мне знать.

    public void ExecuteStoredProcedure()
    {
        try
        {
            // db context variable
            var context = _manufacturingDbContext;

            const string recordType = "FinishedGood";
            const bool lotCreation = false;
            const bool licensePlateCreation = true;
            var finishedGoodLineId = context.FinishedGoodLineIdByOrderAndFinishedGoodAndLot(Cmb_MfgOrder.Text, Cmb_FgLookupCode.Text, Cmb_LotLookupCode.Text).FirstOrDefault();
            var lotId = context.LotIdByManufacturingOrderAndFinishedGood(Cmb_MfgOrder.Text, Cmb_FgLookupCode.Text, Cmb_LotLookupCode.Text).FirstOrDefault();
            string lot = null;
            DateTime? lotManufactureDate = null;
            DateTime? lotExpirationDate = null;
            var packagedAmount = Convert.ToDecimal(Txt_PackagedAmount.Text);
            const int packagedId = 3;
            var licensePlateLookupCode = Txt_LicensePlateLookupCode.Text;
            int? licensePlateId = null;
            const int licensePlateLocationId = 51372;


            // Call SQL Server SPROC datex_footprint_integration.AddFeedbackRequestsAgentInsert and enter data to FootPrint Task
            var run = context.AddFeedbackRequestsAgentInsert(recordType, lotCreation, licensePlateCreation, finishedGoodLineId,
                lotId, "", lotManufactureDate, lotExpirationDate, packagedAmount, packagedId, licensePlateLookupCode,
                licensePlateId, licensePlateLocationId);
            context.SaveChanges();
        }
        catch (Exception e)
        {
            MessageBox.Show(e.Message);
            throw;
        }       
    }
0 голосов
/ 07 ноября 2019

Итак, вы обновили Stored Proc в базе данных, но ваши модели данных не знают об этих изменениях. Что вам нужно сделать, так это обновить Entity FW в вашем приложении .net. 1- Обновить (обновить) EDMX из базы данных ..

enter image description here

2- Щелкните правой кнопкой мыши по концептуальной модели (mode.context.tt) и (model.tt) и нажмите (запустить пользовательский инструмент) .., который обновит ваши модели данных, сопоставленные с C #, чтобы увидеть эти добавленные новые параметры.

enter image description here

...