2014-09-19 2 views
-1

Я попытался реализовать некоторый динамический SQL для создания курсора в качестве расширения простого запроса SELECT. Курсор используется как способ печати значений GROUPED, возвращаемых из SELECT в виде сообщения в SQL Server Management Studio (вроде визуальной сводки данных). Цель этого подхода состоит в том, что половина задач связана и половина помогает мне понять, как динамический SQL может быть разработан. Код гласит:Ошибка компиляции - Динамический SQL

DECLARE @Focus VARCHAR(10); 
SET @Focus = 'Completed'; /* User input event focus {Started, Completed} */ 
DECLARE @PeriodStartDate DATE, @PeriodEndDate DATE; 
SET @PeriodStartDate = '04/01/2014'; 
SET @PeriodEndDate = GETDATE(); 
DECLARE @sql VARCHAR(MAX); 
SET @sql = 
     'SELECT ' + 
     'CASE DATEPART(M, ' + '[Event ' + CASE @Focus 
               WHEN 'Started' THEN 'Start' 
               WHEN 'Completed' THEN 'End' 
               END + ' Date]) ' + 
     ' WHEN 1 THEN ''January'' ' + 
     ' WHEN 2 THEN ''February'' ' + 
     ' WHEN 3 THEN ''March'' ' + 
     ' WHEN 4 THEN ''April'' ' + 
     ' WHEN 5 THEN ''May'' ' + 
     ' WHEN 6 THEN ''June'' ' + 
     ' WHEN 7 THEN ''July'' ' + 
     ' WHEN 8 THEN ''August'' ' + 
     ' WHEN 9 THEN ''September'' ' + 
     ' WHEN 10 THEN ''October'' ' + 
     ' WHEN 11 THEN ''November'' ' + 
     ' WHEN 12 THEN ''December'' ' + 
     ' END AS [Event ' + @Focus + ' Month], ' + 
     ' COUNT([Unique ID]) AS [Number of Events] ' + 
     ' FROM [udf_Events](' + @Focus + ', ' + CAST(@PeriodStartDate AS VARCHAR) + ', ' + CAST(@PeriodEndDate AS VARCHAR) + ') ' + 
     ' GROUP BY ' + 
     ' DATEPART(M, ' + '[Event ' + CASE @Focus 
              WHEN 'Started' THEN 'Start' 
              WHEN 'Completed' THEN 'End' 
              END + ' Date]) ' + 
     ' ORDER BY ' + 
     ' DATEPART(M, ' + '[Event ' + CASE @Focus 
              WHEN 'Started' THEN 'Start' 
              WHEN 'Completed' THEN 'End' 
              END + ' Date]) ' 
;            
DECLARE Results CURSOR 
FOR 
    SELECT 
     @sql; 

Сообщение об ошибке я получаю:

Msg 16924, уровень 16, состояние 1, строка 71 Cursorfetch: Число переменных, объявленных в INTO список должен соответствовать выбранный столбцов.

Через борется с проблемой и пытается выполнить запрос как ЗЕЬЕСТ (удаление сложности курсора) с помощью EXEC (@sql) сообщение об ошибке гласит:

Неверное имя столбца ' Завершено.

.. Это заставляет меня думать, что проблема заключается в выражении CASE в первом выбранном поле. udf_Events является встроенной табличной функцией с тремя аргументами. В частности, в нем есть столбцы [Дата начала события] и [Дата окончания события], которые являются значениями, которые курсор пытается выполнить.

+0

'Msg 16924, уровень 16, состояние 1, строка 71 Cursorfetch' не показывать в своем коде,' вероятно завершило читать '[Событие Завершена месяц]', простой PRINT @SQL должен помочь найти проблему, поэтому она читается как «найти мой тип» - вопрос – bummi

+0

Проблема не в CursorFetch, поэтому проблема все еще возникает, когда @sql выполняется невежественно для любого созданного курсора , Также не нужно было размещать код курсора. – cope

+0

В этом случае 'Invalid column name 'Completed'' vs.PRINT @SQL - это мой вопрос о типографии и подходит для OT - проблема, которая больше не может быть воспроизведена или простая типографская. – bummi

ответ

0

Попробуйте это ... несколько ' пропали без вести в запросе

DECLARE @Focus VARCHAR(10); 
SET @Focus = 'Completed'; /* User input event focus {Started, Completed} */ 

DECLARE @temp VARCHAR(500); 
IF(@Focus = 'Completed') 
SET @temp = '[Event End Date]' 
ELSE 
SET @temp = '[Event Start Date]' 

DECLARE @PeriodStartDate DATE, @PeriodEndDate DATE; 
SET @PeriodStartDate = '04/01/2014'; 
SET @PeriodEndDate = GETDATE(); 
DECLARE @sql VARCHAR(MAX); 
SET @sql = 
     'SELECT ' + 
     'CASE DATEPART(M, ' + @temp + ')' + 
     ' WHEN 1 THEN ''January'' ' + 
     ' WHEN 2 THEN ''February'' ' + 
     ' WHEN 3 THEN ''March'' ' + 
     ' WHEN 4 THEN ''April'' ' + 
     ' WHEN 5 THEN ''May'' ' + 
     ' WHEN 6 THEN ''June'' ' + 
     ' WHEN 7 THEN ''July'' ' + 
     ' WHEN 8 THEN ''August'' ' + 
     ' WHEN 9 THEN ''September'' ' + 
     ' WHEN 10 THEN ''October'' ' + 
     ' WHEN 11 THEN ''November'' ' + 
     ' WHEN 12 THEN ''December'' ' + 
     ' END AS [Event ' + @Focus + ' Month], ' + 
     ' COUNT([Unique ID]) AS [Number of Events] ' + 
     ' FROM [udf_Events](''' + @Focus + ''', ''' + CAST(@PeriodStartDate AS VARCHAR) + ''', ''' + CAST(@PeriodEndDate AS VARCHAR) + ''') ' + 
     ' GROUP BY ' + 
     ' DATEPART(M, ' + @temp + ')' + 
     ' ORDER BY ' + 
     ' DATEPART(M, ' + @temp + ')';     

print @sql 
0

Вы не процитировать даты в вызове udf_Events, так что вы в конечном итоге с

[udf_Events](Completed, 2014-04-01, 2014-09-19) 

вместо

[udf_Events](Completed, '2014-04-01', '2014-09-19') 

Исправление состоит в том, чтобы изменить линию

' FROM [udf_Events](' + @Focus + ', ' + CAST(@PeriodStartDate AS VARCHAR) + ', ' + CAST(@PeriodEndDate AS VARCHAR) + ') ' + 

в

' FROM [udf_Events](' + @Focus + ', ''' + CAST(@PeriodStartDate AS VARCHAR) + ''', ''' + CAST(@PeriodEndDate AS VARCHAR) + ''') ' + 

Это сказало, если параметры в udf_Events являются datetimes, то я бы рассмотреть вопрос об изменении формата YYYYMMDD, как это однозначно. Для этого вы можете использовать CONVERT(char(8), <date>, 112), где <date> - это дата, которую нужно преобразовать.

т.е.

' FROM [udf_Events](' + @Focus + ', ''' + CONVERT(char(8), @PeriodStartDate, 112) + ''', ''' + CONVERT(char(8), @PeriodEndDate, 112) + ''') ' + 
Смежные вопросы