What is the best way to achieve this
实现这一目标的最佳方法是什么?
INSERT INTO @TableName (@ColumnNames)
EXEC sp_executesql @SQLResult;
Where @TableName
, @ColumnNames
, @SQLResult
are varchar
variables
其中@ TableName,@ ColumnNames,@ SQLResult是varchar变量
I am trying to avoid do a separate insert for each table.
我试图避免为每个表单独插入。
3 个解决方案
#1
1
The best way is to write (or generate) all reqiured procedures for all table. 23 tables times 4 procedures (insert, update, delete and select) that can be generated automatically is nothing in dev time and pain compared to the so called "generic solution".
最好的方法是为所有表编写(或生成)所有重新安装的过程。与所谓的“通用解决方案”相比,23个表时间可以自动生成的4个过程(插入,更新,删除和选择)没有任何开发时间和痛苦。
It's a path to poor perfomance, unreadable code, sql injection hazard and countless debuging hours.
这是一条通向性能差,代码难以辨认,sql注入危险和无数次调试时间的途径。
#2
0
First of all I appreciate all your comments. And I agree that SQL dynamic is a pain to debug (Thanks God, management studio has this possibility). And, of course there are hundreds of different solutions
首先,我感谢你的所有评论。我同意SQL动态是一个痛苦的调试(感谢上帝,管理工作室有这种可能性)。当然,还有数百种不同的解决方案
I solved it in this way finally, more or less I try to explain why this solution of SQL dynamic. The client uses xlsx spreadsheets to enter certain data, so I read the spreadsheets and I insert the (data depends on the spreadsheet to insert into the proper table). Later the data in the tables are exported to XML to send a third party sofware.
我终于以这种方式解决了它,或多或少我尝试解释为什么这个SQL动态解决方案。客户端使用xlsx电子表格输入某些数据,因此我阅读电子表格并插入(数据取决于电子表格插入到正确的表格中)。稍后,表中的数据将导出为XML以发送第三方软件。
SET @SEL = N'';
DECLARE sel_cursor CURSOR
FOR (SELECT sc.name as field
FROM sys.objects so INNER JOIN sys.columns sc ON so.[object_id]=sc.[object_id]
WHERE so.name= @TableName and sc.name not in ('InitDate', 'EndDate', 'Version', 'Status'));
SET @SEL = ''; set @i = 0;
OPEN sel_cursor
FETCH NEXT FROM sel_cursor INTO @field
WHILE @@FETCH_STATUS = 0
BEGIN
set @sel = @sel + ', '+ @field
set @i = 1;
FETCH NEXT FROM sel_cursor INTO @field
END
CLOSE sel_cursor;
DEALLOCATE sel_cursor;
SET @SQL = N''
SET @SQL = @SQL + N'SELECT * INTO XLImport FROM OPENROWSET'
SET @SQL = @SQL + N'('
SET @SQL = @SQL + N'''Microsoft.ACE.OLEDB.12.0'''+','
SET @SQL = @SQL + N'''Excel 12.0 Xml; HDR=YES;'
SET @SQL = @SQL + N'Database='+@file +''''+ ','
SET @SQL = @SQL + N'''select * from ['+ @SheetName + '$]'''+');'
EXEC sp_executesql @SQL
SET @SQL = N'';
SET @SQL = @SQL + N'
SELECT '+''''+CAST(@initDate AS VARCHAR(10))+'''' +', '+ ''''+CAST(@endDate AS VARCHAR(10))+''''
+ ', '+ CAST(@version AS VARCHAR(2)) +', ' +''''+@status+''''
+ @SEL
+' FROM DBO.XLImport '
DECLARE cols_cursor CURSOR
FOR (Select COLUMN_NAME From INFORMATION_SCHEMA.COLUMNS where table_name = @tableName);
SET @SEL = ''; set @i = 0;
OPEN cols_cursor
FETCH NEXT FROM cols_cursor INTO @field
WHILE @@FETCH_STATUS = 0
BEGIN
set @sel = @sel + @field + ', '
set @i = 1;
FETCH NEXT FROM cols_cursor INTO @field
END
CLOSE cols_cursor;
DEALLOCATE cols_cursor;
SET @SEL = LEFT(@SEL, LEN(@SEL) - 1) -- remove last ,
SET @SQL = N''
SET @SQL = @SQL + N'SELECT * INTO XLImport FROM OPENROWSET'
SET @SQL = @SQL + N'('
SET @SQL = @SQL + N'''Microsoft.ACE.OLEDB.12.0'''+','
SET @SQL = @SQL + N'''Excel 12.0 Xml; HDR=YES;'
SET @SQL = @SQL + N'Database='+@file +''''+ ','
SET @SQL = @SQL + N'''select * from ['+ @SheetName + '$]'''+');'
EXEC sp_executesql @SQL
SET @SQLString =
N'INSERT INTO '+ @TableName + '('+ @SEL +') ' + @SQL;
EXEC sp_executesql @SQLString
#3
0
Use EXECUTE sp_executesql @sql
, here is example:
使用EXECUTE sp_executesql @sql,这里是示例:
create proc sp_DynamicExcuteStore
@TableName varchar(50),
@ColumnNames varchar(50),
@SQLResult varchar(max)
as
declare @sql nvarchar(max) = '
INSERT INTO '+@TableName+' ('+@ColumnNames+')
EXEC sp_executesql '+@SQLResult
EXECUTE sp_executesql @sql
go
create proc sp_test
as
select 'test' + convert(varchar,RAND())
go
CREATE TABLE [dbo].[Test](
[text1] [nvarchar](500) NULL
) ON [PRIMARY]
GO
DECLARE @return_value int
EXEC @return_value = [dbo].[sp_DynamicExcuteStore]
@TableName = N'Test',
@ColumnNames = N'text1',
@SQLResult = N'proc_test'
SELECT 'Return Value' = @return_value
GO
SELECT TOP 1000 [text1]
FROM [test].[dbo].[Test]
#1
1
The best way is to write (or generate) all reqiured procedures for all table. 23 tables times 4 procedures (insert, update, delete and select) that can be generated automatically is nothing in dev time and pain compared to the so called "generic solution".
最好的方法是为所有表编写(或生成)所有重新安装的过程。与所谓的“通用解决方案”相比,23个表时间可以自动生成的4个过程(插入,更新,删除和选择)没有任何开发时间和痛苦。
It's a path to poor perfomance, unreadable code, sql injection hazard and countless debuging hours.
这是一条通向性能差,代码难以辨认,sql注入危险和无数次调试时间的途径。
#2
0
First of all I appreciate all your comments. And I agree that SQL dynamic is a pain to debug (Thanks God, management studio has this possibility). And, of course there are hundreds of different solutions
首先,我感谢你的所有评论。我同意SQL动态是一个痛苦的调试(感谢上帝,管理工作室有这种可能性)。当然,还有数百种不同的解决方案
I solved it in this way finally, more or less I try to explain why this solution of SQL dynamic. The client uses xlsx spreadsheets to enter certain data, so I read the spreadsheets and I insert the (data depends on the spreadsheet to insert into the proper table). Later the data in the tables are exported to XML to send a third party sofware.
我终于以这种方式解决了它,或多或少我尝试解释为什么这个SQL动态解决方案。客户端使用xlsx电子表格输入某些数据,因此我阅读电子表格并插入(数据取决于电子表格插入到正确的表格中)。稍后,表中的数据将导出为XML以发送第三方软件。
SET @SEL = N'';
DECLARE sel_cursor CURSOR
FOR (SELECT sc.name as field
FROM sys.objects so INNER JOIN sys.columns sc ON so.[object_id]=sc.[object_id]
WHERE so.name= @TableName and sc.name not in ('InitDate', 'EndDate', 'Version', 'Status'));
SET @SEL = ''; set @i = 0;
OPEN sel_cursor
FETCH NEXT FROM sel_cursor INTO @field
WHILE @@FETCH_STATUS = 0
BEGIN
set @sel = @sel + ', '+ @field
set @i = 1;
FETCH NEXT FROM sel_cursor INTO @field
END
CLOSE sel_cursor;
DEALLOCATE sel_cursor;
SET @SQL = N''
SET @SQL = @SQL + N'SELECT * INTO XLImport FROM OPENROWSET'
SET @SQL = @SQL + N'('
SET @SQL = @SQL + N'''Microsoft.ACE.OLEDB.12.0'''+','
SET @SQL = @SQL + N'''Excel 12.0 Xml; HDR=YES;'
SET @SQL = @SQL + N'Database='+@file +''''+ ','
SET @SQL = @SQL + N'''select * from ['+ @SheetName + '$]'''+');'
EXEC sp_executesql @SQL
SET @SQL = N'';
SET @SQL = @SQL + N'
SELECT '+''''+CAST(@initDate AS VARCHAR(10))+'''' +', '+ ''''+CAST(@endDate AS VARCHAR(10))+''''
+ ', '+ CAST(@version AS VARCHAR(2)) +', ' +''''+@status+''''
+ @SEL
+' FROM DBO.XLImport '
DECLARE cols_cursor CURSOR
FOR (Select COLUMN_NAME From INFORMATION_SCHEMA.COLUMNS where table_name = @tableName);
SET @SEL = ''; set @i = 0;
OPEN cols_cursor
FETCH NEXT FROM cols_cursor INTO @field
WHILE @@FETCH_STATUS = 0
BEGIN
set @sel = @sel + @field + ', '
set @i = 1;
FETCH NEXT FROM cols_cursor INTO @field
END
CLOSE cols_cursor;
DEALLOCATE cols_cursor;
SET @SEL = LEFT(@SEL, LEN(@SEL) - 1) -- remove last ,
SET @SQL = N''
SET @SQL = @SQL + N'SELECT * INTO XLImport FROM OPENROWSET'
SET @SQL = @SQL + N'('
SET @SQL = @SQL + N'''Microsoft.ACE.OLEDB.12.0'''+','
SET @SQL = @SQL + N'''Excel 12.0 Xml; HDR=YES;'
SET @SQL = @SQL + N'Database='+@file +''''+ ','
SET @SQL = @SQL + N'''select * from ['+ @SheetName + '$]'''+');'
EXEC sp_executesql @SQL
SET @SQLString =
N'INSERT INTO '+ @TableName + '('+ @SEL +') ' + @SQL;
EXEC sp_executesql @SQLString
#3
0
Use EXECUTE sp_executesql @sql
, here is example:
使用EXECUTE sp_executesql @sql,这里是示例:
create proc sp_DynamicExcuteStore
@TableName varchar(50),
@ColumnNames varchar(50),
@SQLResult varchar(max)
as
declare @sql nvarchar(max) = '
INSERT INTO '+@TableName+' ('+@ColumnNames+')
EXEC sp_executesql '+@SQLResult
EXECUTE sp_executesql @sql
go
create proc sp_test
as
select 'test' + convert(varchar,RAND())
go
CREATE TABLE [dbo].[Test](
[text1] [nvarchar](500) NULL
) ON [PRIMARY]
GO
DECLARE @return_value int
EXEC @return_value = [dbo].[sp_DynamicExcuteStore]
@TableName = N'Test',
@ColumnNames = N'text1',
@SQLResult = N'proc_test'
SELECT 'Return Value' = @return_value
GO
SELECT TOP 1000 [text1]
FROM [test].[dbo].[Test]