2014-06-30 62 views
1

我對delphi/sql server有個小問題。我有一個SP來自存儲過程的返回值在delphi中總是爲空

GO 
/****** Object: StoredProcedure [dbo].[sp_adaugaUser] Script Date: 6/30/2014 12:33:52 PM ******/ 
SET ANSI_NULLS ON 
GO 
SET QUOTED_IDENTIFIER ON 
GO 
-- ============================================= 
-- Author:  <Author,,Name> 
-- Create date: <Create Date,,> 
-- Description: <Description,,> 
-- ============================================= 
ALTER PROCEDURE [dbo].[sp_adaugaUser] 
    -- Add the parameters for the stored procedure here 
    @User varchar(50), 
    @Password varchar(32)--, 
    -- @errMesaj varchar(50) 
AS 
BEGIN 
declare @sUser varchar(50), 
     @sPassword varchar(32), 
     @errMesaj varchar(100), 
     @exists bit, 
     @exists2 bit; 
set @sUser = LTRIM(RTRIM(@User)) 
set @sPassword = LTRIM(RTRIM(@Password)) 


    -- SET NOCOUNT ON added to prevent extra result sets from 
    -- interfering with SELECT statements. 
    SET NOCOUNT ON; 

    select @exists = COUNT(*) from sys.server_principals where name = @sUser 
    select @exists2 = COUNT(*) from sys.database_principals where name = @sUser 
    -- Insert statements for procedure here 
    if @exists = 1 begin 
     if @exists2 = 1 set @errMesaj = 1 --'Userul deja exista' 
       else begin 
       exec ('CREATE USER [' + @sUser + '] FOR LOGIN [' + @sUser + ']') 
       set @errMesaj = 2 --'S-a creat userul pentru login deja existent' 
       end 
        end 
      else begin 
         exec(' CREATE LOGIN [' + @sUser + '] WITH PASSWORD = ''' [email protected] + ''' 
           CREATE USER [' + @sUser + '] FOR LOGIN [' + @sUser+']') 
         set @errMesaj = 3 --'S-a creat user si login' 
         end 

RETURN @errMesaj 
END 

此SP將登錄名和用戶添加到服務器/數據庫中...並根據它做了什麼返回消息。

在Delphi我已經得到了有3個參數的TADOStoredProcedure:

1:@user - ftString,pdInput 2:@Password - ftString,pdInput 1:@errMesaj - ftString,pdReturnValue

我叫TADOStoredProcedure這樣的:

procedure TdataModule1.AdaugaUser(user, password : string); // procedura ce apeleaza o SP din BD pentru adaugarea de useri 
begin 
    sp_adaugaUser.Parameters.ParamByName('@User').Value := user; 
    sp_adaugaUser.Parameters.ParamByName('@Password').Value := password; 
    sp_adaugaUser.Prepared := true ; 
    try 
    sp_adaugaUser.ExecProc; 
    finally 
    sp_adaugaUser.Prepared := false ; 
    sp_vizualizare_useri.Close; 
    sp_vizualizare_useri.Open; 
    test := sp_adaugaUser.Parameters.ParamByName('@errMesaj').Value; 
    end; 

end; 

,但由於某種原因,當我調試測試的值總是null,爲什麼呢?

錯誤:enter image description here

+0

你有例外嗎?似乎執行用戶沒有權限創建登錄名或用戶 – deterministicFail

+0

我已經獲得了許可,我是100%,因爲我正在用sa用戶連接到SQL。我更新了錯誤圖片的帖子。 – CiucaS

+0

如果SQL Server允許您像上面那樣更改存儲過程,我確實感到很驚訝。我會期待一個錯誤消息,因爲RETURN應該返回一個整數值 - 不是varchar。 –

回答

5

如果你想描述你將不得不與OUTPUT定義它使用的參數@errMesaj。

ALTER PROCEDURE [dbo].[sp_adaugaUser] 
    -- Add the parameters for the stored procedure here 
    @User varchar(50), 
    @Password varchar(32), 
    @errMesaj varchar(100) OUTPUT 
AS 

SQLServer的過程的結果值被限制爲整數Return Data from a Stored Procedure

一個例子來顯示不同possibilies可能看起來像這樣:

Alter PROCEDURE [dbo].[sp_adaugaUser] 
    -- Add the parameters for the stored procedure here 
    @User varchar(50), 
    @Password varchar(32), 
    @errMesaj varchar(100) OUTPUT 
AS 
BEGIN 
declare @sUser varchar(50), 
     @sPassword varchar(32), 
     @ReturnCode int, 
     @exists bit, 
     @exists2 bit; 
set @sUser = LTRIM(RTRIM(@User)) 
set @sPassword = LTRIM(RTRIM(@Password)) 


    -- SET NOCOUNT ON added to prevent extra result sets from 
    -- interfering with SELECT statements. 
    SET NOCOUNT ON; 

    select @exists = COUNT(*) from sys.server_principals where name = @sUser 
    select @exists2 = COUNT(*) from sys.database_principals where name = @sUser 
    -- Insert statements for procedure here 
    if @exists = 1 begin 
     if @exists2 = 1 
      begin 
       set @errMesaj = 'Userul deja exista' 
       set @ReturnCode = 1 
      end 
       else begin 
       exec ('CREATE USER [' + @sUser + '] FOR LOGIN [' + @sUser + ']') 
       set @errMesaj = 'S-a creat userul pentru login deja existent' 
       set @ReturnCode = 2 
       end 
        end 
      else begin 
         exec(' CREATE LOGIN [' + @sUser + '] WITH PASSWORD = ''' [email protected] + ''' 
           CREATE USER [' + @sUser + '] FOR LOGIN [' + @sUser+']') 
         set @errMesaj = 'S-a creat user si login' 
         set @ReturnCode = 2 
         end 

    Return @ReturnCode 
END 

用於呼叫

最小Delphi代碼
sp_adaugaUser.Parameters.ParamByName('@User').Value := user; 
    sp_adaugaUser.Parameters.ParamByName('@Password').Value := password; 
    sp_adaugaUser.ExecProc; 
    Showmessage(sp_adaugaUser.Parameters.ParamByName('@errMesaj').Value); 
    Showmessage(IntToStr(sp_adaugaUser.Parameters.ParamByName('@RETURN_VALUE').Value)); 

使用TAdoStoredProc for sp_adaugaUser您的參數TER值應該是這樣的

enter image description hereenter image description here

你所得到的錯誤是因爲在 test := sp_adaugaUser.Parameters.ParamByName('@errMesaj').Value;值爲NULL不能轉換爲字符串。

+0

我得到了同樣的錯誤...即使我在SQL中添加@errMesaj作爲OUTPUT變量。 – CiucaS

+0

只是省略'RETURN @ errMesaj'結果值預計是一個整數。 – bummi

+0

您是否必須在調用sp的查詢中包含OUT? – MartynA