TSQL Inserting records from XML string

前端 未结 1 1253
無奈伤痛
無奈伤痛 2021-01-22 03:54

I have a SQL query that is inserting records into a table from an XML string that I pass to it. The string could contain 1 node or multiple so each one is a new record.

1条回答
  •  轻奢々
    轻奢々 (楼主)
    2021-01-22 04:29

    Given the clarification of this statement in the question:

    For each trainer, I need to also insert a record into that table but it needs to have the last inserted record id of the segment.

    being (as found in the comments on the question):

    There would be a total of 4 records inserted into the trainer table, 2 have the segment id of 1 and the other 2 with the segment id of 2.

    The following will insert this data into related tables that have auto-incrementing IDs. In the sample data, I varied the EmpID values slightly to make it clearer that it is indeed working as expected.

    DECLARE @DocumentID INT, @ImportData XML;
    
    SET @ImportData = N'
    
        
          
             9
             641
             12
             21
             10/10/2014
             
                
                   HUS123
                
                
                   Dan123
                
             
          
        
        
          
             9
             641
             12
             21
             10/25/2014
             
                
                   HUS1234
                
                
                   Dan1234
                
             
          
       
    ';
    
    
    DECLARE @Segment TABLE (SegmentId INT NOT NULL IDENTITY(1, 1) PRIMARY KEY,
                            TrainingEventID INT NOT NULL, -- Unique
                            LocaleID INT NOT NULL, -- Unique
                            NumOfTeammates INT,
                            NonProdHrs INT,
                            SegmentDate DATE); -- Unique
    -- Ideally create UNIQUE INDEX with the 3 fields noted above
    DECLARE @Trainer TABLE (TrainerId INT NOT NULL IDENTITY(1, 1) PRIMARY KEY,
                            SegmentID INT NOT NULL, -- FK to Segment.SegmentID
                            EmpID VARCHAR(50) NOT NULL);
    
    EXEC sp_xml_preparedocument @DocumentID OUTPUT, @ImportData;
    
    -- First pass: extract "Segment" rows
    INSERT INTO @Segment
                (TrainingEventID, LocaleID, NumOfTeammates, NonProdHrs, SegmentDate)
       SELECT TrainingEventID, LocaleID, NumOfTeammates, NonProdHrs, SegmentDate
       FROM   OPENXML (@DocumentID, N'/root/data/segment', 2) 
                 WITH (TrainingEventID   INT  './trainingEventID/text()', 
                       LocaleID          INT  './localeID/text()',
                       NumOfTeammates    INT  './numOfTeammates/text()',
                       NonProdHrs        INT  './nonProdHrs/text()',
                       SegmentDate       DATE './segmentDate/text()');
    
    
    -- Second pass: extract "Trainer" rows
    INSERT INTO @Trainer (SegmentID, EmpID)
       SELECT seg.SegmentID, trnr.EmpID
       FROM   OPENXML (@DocumentID, N'/root/data/segment/trainers/trainer', 2) 
                 WITH (TrainingEventID   INT         '../../trainingEventID/text()',
                       LocaleID          INT         '../../localeID/text()',
                       SegmentDate       DATE        '../../segmentDate/text()',
                       EmpID             VARCHAR(50) './empID/text()') trnr
       INNER JOIN @Segment seg
               ON seg.[TrainingEventID] = trnr.[TrainingEventID]
              AND seg.[LocaleID] = trnr.[LocaleID]
              AND seg.[SegmentDate] = trnr.[SegmentDate];
    
    
    EXEC sp_xml_removedocument @DocumentID;
    -------------------
    
    SELECT * FROM @Segment ORDER BY [SegmentID];
    SELECT * FROM @Trainer ORDER BY [SegmentID];
    

    Output:

    SegmentId   TrainingEventID   LocaleID   NumOfTeammates   NonProdHrs   SegmentDate
    1           9                 641        12               21           2014-10-10
    2           9                 641        12               21           2014-10-25
    
    TrainerId   SegmentID   EmpID
    1           1           HUS123
    2           1           Dan123
    3           2           HUS1234
    4           2           Dan1234
    

    References:

    • OPENXML
    • sp_xml_preparedocument
    • sp_xml_removedocument

    0 讨论(0)
提交回复
热议问题