如何 return 一个id并直接在另一个存储过程中使用它?

How to return an id and use it directly in another stored procedure?

我要他的存储过程return插入的id

ALTER PROCEDURE [dbo].[InsertAddress_DBO]
    @Name VARCHAR(50)
AS
BEGIN
    SET NOCOUNT ON;

    INSERT INTO [dbo].[Address]([Address_Name])
    OUTPUT INSERTED.Address_Id
    VALUES (@Name)
END

这个一样

ALTER PROCEDURE [dbo].[InsertDocumentation_DBO]
    @Texte VARCHAR(50)
AS
BEGIN
    SET NOCOUNT ON;

    INSERT INTO [dbo].[Documentation]([Documentation_Text])
    OUTPUT inserted.Documentation_Id
    VALUES (@Texte)
END

而这个是为了使用它们和 return 她自己的 - 比如使用插入的id作为参数放入下一个存储过程

ALTER PROCEDURE [dbo].[InsertEstablishmentByStrings_DBO]
    @Establishment_Name VARCHAR(50),
    @Address_Name VARCHAR(50),
    @Documentation_Text VARCHAR(50)
AS
BEGIN
    SET NOCOUNT ON;

    DECLARE @Address_ID INT ,
            @Documentation_ID INT 

    EXEC @Address_ID = [dbo].[InsertAddress_DBO] 
                       @Name = "rue de la banchiesserie 85 Golback"

    EXEC @Documentation_ID = [dbo].[InsertDocumentation_DBO] 
                             @Texte = "né en 55555 restaurant fabuleux"

    INSERT INTO [dbo].[Establishment]([Establishment_Name],[Address_Id],[Documentation_Id])
    OUTPUT inserted.Establishment_Id
    VALUES (@Establishment_Name,@Address_ID,@Documentation_ID)
END

但是,我总是会出错,因为存储过程在我执行时 return 没有 ID。

我的代码有什么问题?

我想获得可以在我必须执行的每个存储过程中反复使用的代码。我已经尝试了@@Identity、缩进、作用域……都没有用。

如果您想 return 从存储过程到 SQL 查询执行的上下文,您可以使用 return 语句或输出参数。我建议您使用第二个选项。第一个通常用于 return 过程执行状态。

ALTER PROCEDURE [dbo].[InsertAddress_DBO]
    @Name VARCHAR(50),
    @Address_ID INT OUTPUT
AS
BEGIN
    SET NOCOUNT ON;

    INSERT INTO [dbo].[Address]([Address_Name])
    VALUES (@Name)
    SET @Address_ID = SCOPE_IDENTITY()
END

您可以在外部过程中使用 returned 值

ALTER PROCEDURE [dbo].[InsertEstablishmentByStrings_DBO]
    @Establishment_Name VARCHAR(50),
    @Address_Name VARCHAR(50),
    @Documentation_Text VARCHAR(50)
AS
BEGIN
    SET NOCOUNT ON;

    DECLARE @Address_ID INT ,
        @Documentation_ID INT 

    EXEC [dbo].[InsertAddress_DBO] 
        @Address_ID = @Address_ID OUTPUT,
        @Name = "rue de la banchiesserie 85 Golback"

     ...
END

您使用的 OUTPUT INSERTED 子句不会return将数据发送到查询执行上下文,而是将它们发送到输出流。

您的存储过程应如下所示,使用 OUTPUT 参数,而不是尝试使用结果集使用 RETURN 值 (which should never contain data)。另外[不要][把][一切][放在][正方形][方括号][除非][你][有][到],[因为][所有][它][做][是][妨碍] [可读性],并且不要用“双引号”将字符串文字括起来,因为这在 T-SQL.

中有其他含义
CREATE OR ALTER PROCEDURE dbo.InsertAddress_DBO
    @Name       varchar(50),
    @Address_Id int OUTPUT
AS
BEGIN
    SET NOCOUNT ON;

    INSERT dbo.Address(Address_Name)
      VALUES (@Name);
      
    SELECT @Address_Id = SCOPE_IDENTITY();
END
GO

CREATE OR ALTER PROCEDURE dbo.InsertDocumentation_DBO
    @Texte  varchar(50),
    @Doc_Id int OUTPUT
AS
BEGIN
    SET NOCOUNT ON;

    INSERT dbo.Documentation(Documentation_Text)
      VALUES (@Texte);
      
    SELECT @Doc_Id = SCOPE_IDENTITY();
END
GO

现在,您的主程序可以这样做:

CREATE OR ALTER PROCEDURE dbo.InsertEstablishmentByStrings_DBO
    @Establishment_Name varchar(50),
    @Address_Name       varchar(50),
    @Documentation_Text varchar(50)
AS
BEGIN
    SET NOCOUNT ON;

    DECLARE @Address_ID INT ,
            @Documentation_ID INT 

    EXEC dbo.InsertAddress_DBO 
         @Name = @Address_Name,
         @Address_Id = @Address_ID OUTPUT;

    EXEC dbo.InsertDocumentation_DBO 
         @Texte = Documentation_Text,
         @Doc_Id = @Documentation_ID OUTPUT;

    INSERT dbo.Establishment
    (Establishment_Name, Address_Id, Documentation_Id)
    OUTPUT inserted.Establishment_Id, 
           inserted.Address_ID, inserted.Documentation_ID
    VALUES (@Establishment_Name,@Address_ID,@Documentation_ID);
END
GO

你这样称呼它:

EXEC dbo.InsertEstablishmentByStrings_DBO
  @Establishment_Name = 'Gaston''s',
  @Address_Name       = 'rue de la banchiesserie 85 Golback',
  @Documentation_Text = 'né en 55555 restaurant fabuleux';

得到这样的结果:

Establishment_Id Address_ID Documentation_ID
1 1 1