简体   繁体   English

带OUTPUT子句的SQL Server BULK INSERT

[英]SQL Server BULK INSERT with OUTPUT clause

I'm working on a pet project that will allow me to store my game collection in a DB and write notes on those games. 我正在开发一个宠物项目,该项目使我可以将自己的游戏收藏存储在数据库中并为这些游戏写笔记。 The single entries of games has been coded by inserting desired variables into my game_information table and outputting the PK (identity) of the newly created row from that table, so I can insert it into my game_notes table along with the note. 通过将所需的变量插入到我的game_information表中并从该表中输出新创建的行的PK(标识),已经对游戏的单个条目进行了编码,因此我可以将其与笔记一起插入到我的game_notes表中。

var id = db.QueryValue("INSERT INTO Game_Information (gamePrice, name, edition) output Inserted.gameId VALUES (@0, @1, @2)", gamePrice, name, edition); 
db.Execute("INSERT INTO Game_Notes(gameId, notes, noteDate) VALUES (@0, @1, @2)", id, notes, noteDate);

I'm now playing with uploading data in bulk via csv but how can I write a BULK INSERT that would output all PKs of the newly created rows, so I can inserted them into my second table ( game_notes ) along with a variable called notes? 我现在正在通过csv批量上传数据,但是我该如何编写一个BULK INSERT来输出新创建的行的所有PK,因此我可以将它们与第二个表( game_notes )以及一个称为notes的变量一起插入?

At the moment I have the following: 目前,我有以下内容:

  • Stored Procedure that reads .csv and uses BULK INSERT to dump information into a view of game_information 读取.csv并使用批量BULK INSERT将信息转储到game_information视图中的存储过程

     @FileName nvarchar(200) AS BEGIN DECLARE @sql nvarchar(MAX); SET @sql = 'BULK INSERT myview FROM ''mycsv.csv'' WITH ( FIELDTERMINATOR = '','', ROWTERMINATOR = ''\\n'', FIRSTROW = 2 )' EXEC(@sql) END 

C# code that creates set up in WebMatrix 在WebMatrix中创建设置的C#代码

if ((IsPost) && (Request.Files[0].FileName!=" "))
{
                var fileSavePath = "";
                var uploadedFile = Request.Files[0];
                fileName = Path.GetFileName(uploadedFile.FileName);

                uploadedFile.SaveAs(//path +filename); 
                var command = "EXEC Procedure1 @FileName = @0"; 
                db.Execute(command, //path +filename); 
                File.Delete(//path +filename); 
}

Which allows for csv records to be inserted into game_information . 允许将csv记录插入game_information

If this isn't feasible with BULK INSERT , would something along the lines of be a valid solution to attempt? 如果使用BULK INSERT可行,那么是否有可能是尝试的有效解决方案?

BULK INSERT into a temp_table

INSERT from temp_table to my game_information table
OUTPUT the game_Ids from the INSERT as an array(?)

then INSERT the Ids along with note into game_notes. 

I've also been looking at OPENROWSET but I'm unsure if that will allow for what I'm trying to accomplish. 我也一直在关注OPENROWSET但不确定是否OPENROWSET我的要求。 Feedback on this is greatly appreciated. 对此表示感谢。

You have a few different options. 您有几种选择。

  1. Bulk inserting into a temp table and then copying information into your permanent tables is definitely a valid solution. 批量插入临时表,然后将信息复制到永久表中绝对是有效的解决方案。 However, based on what you're trying to do I don't see the need for a temp table. 但是,根据您要执行的操作,我看不到需要临时表。 Just bulk import into game_information, SELECT your ID's to your application, and then do your update of game_notes. 只需批量导入game_information中,选择您的ID至您的应用程序,然后更新game_notes。

  2. Another option would be to insert your keys. 另一种选择是插入您的密钥。 You can allow for IDENTITY_INSERT to be on for your tables and just have your keys as part of the CSV file. 您可以允许IDENTITY_INSERT在您的表上启用,而仅将密钥作为CSV文件的一部分。 See here: https://msdn.microsoft.com/en-ca/library/ms188059.aspx?f=255&MSPPError=-2147217396 . 参见此处: https : //msdn.microsoft.com/zh-cn/library/ms188059.aspx?f=255&MSPPError=-2147217396 If you did this then you could do a BULK INSERT into your Game_information table, and then do a second BULK INSERT into your secondary tables by using a different CSV file. 如果这样做,则可以对Game_information表进行批量插入,然后通过使用其他CSV文件对辅助表进行第二次批量插入。 Be sure to re-enable key constraints and turn IDENTITY_INSERT off after its finished. 确保重新启用键约束,并在完成后关闭IDENTITY_INSERT。

If you need more particular control over the data you're selecting from the CSV file then you can use OPENROWSET but there's not enough details in your post to comment further. 如果您需要对从CSV文件中选择的数据进行更具体的控制,则可以使用OPENROWSET,但是您的帖子中没有足够的详细信息可以进一步评论。

Thank your for your input womp. 多谢您的协助。 I was able to get the desired results by amending my BULK INSERT as follows: 我可以通过如下修改BULK INSERT来获得所需的结果:

BEGIN

DECLARE @sql nvarchar(MAX);
SET @sql=   
'CREATE TABLE #Temp (--define table--)

 BULK INSERT #Temp   --Bulk into my temp table--
 FROM '+char(39)+@FileName+char(39)+' 
 WITH
(
  FIELDTERMINATOR = '','',
  ROWTERMINATOR = ''\n'',
  FIRSTROW = 2

)

    INSERT myDB.dbo.game_information(gamePrice, name, edition, date)
    OUTPUT INSERTED.gameId, INSERTED.Date INTO myDB.dbo.game_notes(gameId, noteDate)
    SELECT gamePrice, name, edition, date
    FROM #Temp'

EXEC(@sql)
END    

This placed the correct ids into game_notes and left the Note column of the table as Null for those entries. game_notes正确的ID放入game_notes并将这些条目的表的Note列留为Null Which meant I could run a simple 这意味着我可以运行一个简单的

"UPDATE game_notes SET Notes = @0 WHERE Notes IS NULL";

To push the desired note into the correct rows. 将所需的音符推入正确的行。 I'm executing this and the stored bulk procedure in the same If (IsPost) , so I feel like I'm protected from the wrong accidental note updates. 我正在同一If (IsPost)执行此操作,并执行了存储的批量过程,所以我感觉自己可以防止错误的意外注释更新。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM