使用外键插入数据

Insert Data with Foreign Keys

我有两个 table 与外键约束相连。每个 table 都有一个主键(ProductID,BaseProductID),它是一个自动递增的标识列。 每个 BaseProduct 在导入过程中只有 1 个 Product。

BaseProduct
- BaseProductID
- BaseProductName

Product
- ProductID
- BaseProductID
- ProductName

我尝试从具有相同表但不同种子值的不同数据库向两个 table 中插入行。我不想保留源数据库中的 ID。

有没有办法在一条语句中做到这一点?

编辑

Select 会是

Select ProductName FROM @SourceProduct 
WHERE Not ProductName  in (
select ProductName   FROM @TargetBaseProduct
)

我尝试了 Giorgi 的解决方案,它很接近,但是

的匹配
tgt.BaseProductID = src.BaseProductID

如果目标已经有 BaseProductID = 1 的条目,则导致不插入 BaseProductID = 1 的源行的结果。

DECLARE @SourceBaseProduct TABLE
    (
      BaseProductID INT ,
      BaseProductName NVARCHAR(MAX)
    )
DECLARE @SourceProduct TABLE
    (
      ProductID INT ,
      BaseProductID INT ,
      ProductName NVARCHAR(MAX)
    )

DECLARE @TargetBaseProduct TABLE
    (
      BaseProductID INT IDENTITY(1, 1) ,
      BaseProductName NVARCHAR(MAX)
    )
DECLARE @TargetProduct TABLE
    (
      ProductID INT IDENTITY(1, 1) ,
      BaseProductID INT ,
      ProductName NVARCHAR(MAX)
    )


INSERT  INTO @SourceBaseProduct
VALUES  ( 1, 'BaseProduct1' ),
        ( 2, 'BaseProduct2' ),
        ( 4, 'BaseProduct3' )
INSERT  INTO @SourceProduct
VALUES  ( 3, 1, 'Product1' ),
        ( 9, 2, 'Product2' ),
        ( 27, 4, 'Product3' )

INSERT  INTO @TargetBaseProduct
(

      BaseProductName 
      )
VALUES  ( 'Existing Product Base' )

INSERT  INTO @TargetProduct(
 BaseProductID  ,
      ProductName)
VALUES  (  @@IDENTITY, 'Existing Product' )

MERGE INTO @TargetBaseProduct tgt
USING
    ( SELECT    sbp.BaseProductID ,
                sbp.BaseProductName ,
                sp.ProductName
      FROM      @SourceBaseProduct sbp
                JOIN @SourceProduct sp ON sp.BaseProductID = sbp.BaseProductID
    ) AS src
ON tgt.BaseProductID = src.BaseProductID
WHEN NOT MATCHED BY TARGET THEN
    INSERT VALUES ( src.BaseProductName )
OUTPUT
    Inserted.BaseProductID ,
    src.ProductName
    INTO @TargetProduct(BaseProductID, ProductName);


SELECT  * FROM    @TargetBaseProduct
SELECT  * FROM    @TargetProduct

输出

BaseProductID   BaseProductName
1               Existing Product Base
2               BaseProduct2
3               BaseProduct3


ProductID   BaseProductID   ProductName
1           1               Existing Product
2           2               Product2
3           3               Product3

预期结果

BaseProductID   BaseProductName
1               Existing Product Base
2               BaseProduct1
3               BaseProduct2
4               BaseProduct3


ProductID   BaseProductID   ProductName
1           1               Existing Product
2           2               Product1
3           3               Product2
4           4               Product3

编辑

使用

ON 1 = 0

按照 Giorgi 的建议给出了正确的结果

如果我没猜错,MERGE:

DECLARE @SourceBaseProduct TABLE
    (
      BaseProductID INT ,
      BaseProductName NVARCHAR(MAX)
    )
DECLARE @SourceProduct TABLE
    (
      ProductID INT ,
      BaseProductID INT ,
      ProductName NVARCHAR(MAX)
    )

DECLARE @TargetBaseProduct TABLE
    (
      BaseProductID INT IDENTITY(1, 1) ,
      BaseProductName NVARCHAR(MAX)
    )
DECLARE @TargetProduct TABLE
    (
      ProductID INT IDENTITY(1, 1) ,
      BaseProductID INT ,
      ProductName NVARCHAR(MAX)
    )


INSERT  INTO @SourceBaseProduct
VALUES  ( 1, 'BaseProduct1' ),
        ( 2, 'BaseProduct2' ),
        ( 4, 'BaseProduct3' )
INSERT  INTO @SourceProduct
VALUES  ( 3, 1, 'Product1' ),
        ( 9, 2, 'Product2' ),
        ( 27, 4, 'Product3' )



MERGE INTO @TargetBaseProduct tgt
USING
    ( SELECT    sbp.BaseProductID ,
                sbp.BaseProductName ,
                sp.ProductName
      FROM      @SourceBaseProduct sbp
                JOIN @SourceProduct sp ON sp.BaseProductID = sbp.BaseProductID
    ) AS src
ON tgt.BaseProductID = src.BaseProductID
WHEN NOT MATCHED BY TARGET THEN
    INSERT VALUES ( src.BaseProductName )
OUTPUT
    Inserted.BaseProductID ,
    src.ProductName
    INTO @TargetProduct(BaseProductID, ProductName);


SELECT  * FROM    @TargetBaseProduct
SELECT  * FROM    @TargetProduct

输出:

BaseProductID   BaseProductName
1               BaseProduct1
2               BaseProduct2
3               BaseProduct3


ProductID   BaseProductID   ProductName
1           1               Product1
2           2               Product2
3           3               Product3

编辑:如果您也想插入现有行,则更改

ON tgt.BaseProductID = src.BaseProductID

ON 1 = 0