MySQL 8.0: CTE С неисполнением двух подразделов

#mysql #percona

#mysql #percona

Вопрос:

Percona MySQL 8.0.15-5

Всем привет, не могли бы вы помочь мне с проблемой?

Я хочу переписать запрос с использованием временной таблицы в CTE, используя ‘with’. Этот запрос должен выполнять блокировку данных из одной таблицы в другую.

Рабочий процесс следующий: мы выбираем пакет данных, вставляем его в целевую таблицу, затем выбираем максимальный идентификатор из этого пакета, сохраняем его и при дальнейшем вызове процедуры выбор данных начинается с этого идентификатора.

‘with’ хорошо подходит в этом случае, чтобы не создавать временную таблицу. Я написал следующий запрос:

   insert ignore quotes
  (
    time,
    symbol,
    server,
    bid,
    ask,
    last,
    volume
  )
  WITH temp AS 
  (
    SELECT
      q.id,
      q.`time`,
      q.symbol,
      q.server,
      q.bid,
      q.ask,
      q.last,
      q.volume,
      q.created_at
    FROM
      `old.quotes2` q
    WHERE
      q.id > id
    ORDER BY
      q.id asc
    LIMIT
      write_limit
  ), m AS (SELECT @max := MAX(t.id) max FROM temp t) -- m subclause not executed
  SELECT
    t.time,
    `search_or_add_of_symbol_id_from_name`(t.symbol) symbol,
    `search_of_server_id_from_name`(lower(t.server)) server,
    t.bid,
    t.ask,
    t.last,
    t.volume
  FROM temp t
  

MySQL не выполняет второй запрос, называемый m, вероятно, из-за того, что я не использую его в будущем. Чтобы решить эту проблему, я должен добавить дополнительное условие «присоединиться» к основному «выбрать».

Возможно ли заставить MySQL выполнить подраздел ‘m’? Может быть, есть какой-либо намек, который заставит оптимизатор выполнить подпункт ‘m’?

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

1. Разве вы не можете просто выполнить отдельный запрос для сохранения максимального идентификатора пакета?

2. в этом случае вам нужно создать временную таблицу, которую я специально выбрал CTE, чтобы не создавать временную таблицу

Ответ №1:

Попробуйте:

Вариант 0:

 INSERT ...
WITH
  temp AS (...),
  m AS (...)
SELECT ...
FROM temp JOIN m;
  

Вариант 1:

 INSERT ...
WITH
  temp AS (...),
  m AS (...)
SELECT ...
FROM temp, m;
  

Вариант 2:

 INSERT ...
WITH
  temp AS (...)
SELECT ...
FROM temp, (...) m;