Временная таблица и набор переменных mysql — ОБНОВЛЕНИЯ

#mysql #sql #database #syntax #backend

Вопрос:

Я хочу как создать временную таблицу, так и использовать переменную. Я ознакомился с документацией и считаю, что синтаксис правильный, но объединение их вместе приводит к ошибке.

Моя цель-создать переменную даты, которая всегда будет на 1 год раньше now() и заполнит мою временную таблицу строками с шагом в один месяц до настоящего момента. Любая помощь была бы очень признательна.

Ошибка:

 "Error: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'SET @start_date = DATEADD(year, -1 ,GETDATE())nn  WHILE @start_date < GETD' at line 4"
 

Вот мое заявление SQL.

 
        CREATE TEMPORARY TABLE helper(
          date datetime not null
          );

        SET @start_date = DATEADD(year, -1 ,GETDATE())

        WHILE @start_date < GETDATE()
        BEGIN
          INSERT INTO helper VALUES (@start_date)
          SELECT @start_date = DATEADD(MONTH, 1, @start_date)
        
        END
 

обновление 1

с помощью этого кода я все еще получаю синтаксическую ошибку

      CREATE TEMPORARY TABLE helper(
          date datetime not null
        );
          
        insert into helper (date)
          with recursive cte as (
            select curdate() - interval 12 month as date
            union all
            select date   interval 1 month
            from cte
            where date < curdate()
          )
          select date from cte;

          select * from helper;
 

ошибка

  "Error: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'insert into helper (date)n          with recursive cte as (n            select c' at line 4",
 

ОБНОВЛЕНИЕ 2

Я изменил синтаксис на этот. Я все еще получаю ошибки, но, похоже, это ближе к MySQL 5.7

  `
          CREATE TEMPORARY TABLE helper(
            date datetime not null
          );

          CREATE PROCEDURE dowhile()
          BEGIN
          DECLARE date datetime DEFAULT SUBDATE(curdate(), interval 12 month);
            WHILE date < curDate() DO
              INSERT INTO helper VALUES(date);
              SET date = date   interval 1 month;
            END WHILE;
          END;
          DELIMITER;

          CALL dowhile()

          SELECT date_format(log.entry_stamp, '%Y-%M') AS 'date', COUNT(log.element_id) as count FROM dm_log log
          INNER JOIN dm_element el
          ON el.element_id = log.element_id
          WHERE ? = el.dm_id
          LEFT OUTER JOIN helper h
          ON h.date = log.date
          GROUP BY date
          ORDER BY date;

          DROP TEMPORARY TABLE helper; 
             `
 

Ошибка

 "Error: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'CREATE PROCEDURE dowhile()n          BEGINn          DECLARE date datetime DEFAU' at line 4",
 

Ответ №1:

Вы можете использовать рекурсивный CTE вместо WHILE цикла:

 insert into helper (date)
    with recursive cte as (
          select curdate() - interval 12 month as date
          union all
          select date   interval 1 month
          from cte
          where date < curdate()
         )
    select date from cte;
 

Вот скрипка db<>.

Обратите внимание, что MySQL не используется getdate() . И не поддерживает while циклы за пределами программных блоков. И не имеет формы с тремя аргументами dateadd() . Похоже, вы путаете MySQL с SQL Server.

В более ранних версиях вам, вероятно, потребуется четко указать значения:

 insert into helper (date)
    select curdate() union all
    select curdate() - interval 1 month union all
    . . .;
 

Комментарии:

1. Спасибо вам за ваш ответ. Я обновил свой вопрос с помощью предоставленного вами кода, так как я все еще получаю синтаксическую ошибку с новым кодом. Хотя я вижу, что ваш работает с dbfiddle.

2. @helper12345 . . . Какую версию MySQL вы используете? Рекурсивные CTE доступны с версии 8.0.

3. Если бы я использовал синтаксис, который работал бы с предыдущей версией, есть ли такой, который делал бы то же самое?

4. Я ошибся, это 5.7. Существует ли анологичный синтаксис для 5.7?