Мне было интересно, есть ли способ сделать это в MS SQL Server 2005:
DECLARE @theDate varchar(60)
SET @theDate = '''2010-01-01'' AND ''2010-08-31 23:59:59'''
SELECT AdministratorCode,
SUM(Total) as theTotal,
SUM(WOD.Quantity) as theQty,
AVG(Total) as avgTotal,
(SELECT SUM(tblWOD.Amount)
FROM tblWOD
JOIN tblWO on tblWOD.OrderID = tblWO.ID
WHERE tblWO.Approved = '1'
AND tblWO.AdministratorCode = tblWO.AdministratorCode
AND tblWO.OrderDate BETWEEN @theDate
)
... etc
Возможно ли это сделать?
sql
sql-server
sql-server-2005
tsql
dynamic-sql
StealthRT
источник
источник
Ответы:
Это возможно, но требует использования динамического SQL.
Я рекомендую прочитать Проклятие и благословение динамического SQL, прежде чем продолжить ...
DECLARE @theDate varchar(60) SET @theDate = '''2010-01-01'' AND ''2010-08-31 23:59:59''' DECLARE @SQL VARCHAR(MAX) SET @SQL = 'SELECT AdministratorCode, SUM(Total) as theTotal, SUM(WOD.Quantity) as theQty, AVG(Total) as avgTotal, (SELECT SUM(tblWOD.Amount) FROM tblWOD JOIN tblWO on tblWOD.OrderID = tblWO.ID WHERE tblWO.Approved = ''1'' AND tblWO.AdministratorCode = tblWO.AdministratorCode AND tblWO.OrderDate BETWEEN '+ @theDate +')' EXEC(@SQL)
Динамический SQL - это просто оператор SQL, составленный в виде строки перед выполнением. Так происходит обычная конкатенация строк. Динамический SQL требуется всякий раз, когда вы хотите сделать что-то недопустимое в синтаксисе SQL, например:
EXEC sp_executesql
позволяет использовать параметры bind / preparestatement, поэтому вам не нужно беспокоиться об экранировании одинарных кавычек / etc для атак с использованием SQL-инъекций.источник
DECLARE @theDate DATETIME SET @theDate = '2010-01-01'
Затем измените свой запрос, чтобы использовать эту логику:
источник
Использование EXEC
Вы можете использовать следующий пример для построения оператора SQL.
DECLARE @sqlCommand varchar(1000) DECLARE @columnList varchar(75) DECLARE @city varchar(75) SET @columnList = 'CustomerID, ContactName, City' SET @city = '''London''' SET @sqlCommand = 'SELECT ' + @columnList + ' FROM customers WHERE City = ' + @city EXEC (@sqlCommand)
Использование sp_executesql
Используя этот подход, вы можете гарантировать, что значения данных, передаваемые в запрос, являются правильными типами данных, и избежать использования дополнительных кавычек.
DECLARE @sqlCommand nvarchar(1000) DECLARE @columnList varchar(75) DECLARE @city varchar(75) SET @columnList = 'CustomerID, ContactName, City' SET @city = 'London' SET @sqlCommand = 'SELECT ' + @columnList + ' FROM customers WHERE City = @city' EXECUTE sp_executesql @sqlCommand, N'@city nvarchar(75)', @city = @city
Справка
источник
Я отмечу, что в статье, связанной с самым популярным ответом «Проклятие и благословения динамического SQL», автор заявляет, что ответ - не использовать динамический SQL. Прокрутите почти до конца, чтобы увидеть это.
Из статьи: «Правильный метод - распаковать список в таблицу с пользовательской функцией или хранимой процедурой».
Конечно, когда список находится в таблице, вы можете использовать соединение. Я не мог напрямую комментировать самый популярный ответ, поэтому просто добавил этот комментарий.
источник