Запрос к нейросети в Power Query

Сегодня будем делать простую, но классную штуку - научим Power Query выполнять запросы к нейросетям для обработки и анализа загруженных данных. Делать это будем на примере DeepSeek - она в России пока ещё работает без VPN, стоит недорого, а по качеству отстаёт от флагманов в лице OpenAI или Claude не так сильно. Кроме того, весь разобранный далее процесс и код подключения можно легко адаптировать к любой другой нейросети - принципы у всех плюс-минус одинаковые.

Для примера вот такую таблицу с криво и неполно записанными адресами и предположим, что нам необходимо извлечь из них в отдельный столбец только город:

Исходные данные для анализа

Обратите внимание, насколько у нас тут всё запущено: Санкт-Петербург в нескольких вариантах, город может быть в начале адреса или в конце, с "г." и без, а где-то есть только почтовый индекс. Плюс некоторые названия написаны не полностью (В.Новгород) или с ошибками (Чилябинск).

Подобная задача практически невыполнима встроенными средствами Power Query (если только у вас нет полного справочника со всеми вариантами написания всех городов), но для ИИ это будет вполне по силам. 

Рассмотрим весь процесс по шагам.

Шаг 1. Получаем API-ключ ИИ

Тут всё стандартно.

  1. Регистрируемся на сайте DeepSeek, если вы ещё этого не сделали.
  2. В личном кабинете в разделе Top up пополняем аккаунт хотя бы на 2-5$, чтобы иметь возможность использовать запросы по API. Для пополнения потребуется нероссийская банковская карта. Если её нет, то можно выпустить виртуальную карту или воспользоваться услугами посредников или специализированных платёжных сервисов.
  3. Там же в разделе API keys создаем API-ключ - длинную буквенно-цифровую последовательность, выполняющую роль вашего идентификатора при обращении к нейросети. Ключ желательно скопировать и сохранить где-нибудь в надёжном месте, т.к. показывается он вам только единожды при создании, а потом будет скрыт. Скомпрометированный ключ, который случайно узнал кто-то посторонний, всегда можно удалить, а вместо него создать новый. 
  4. В разделе Usage в будущем можно контролировать расход средств и остаток на счёте.

Шаг 2. Пишем M-функцию запроса к нейросети в Power Query

В языке М, который работает "под капотом" у Power Query содержится более 700 встроенных функций, но готовой функции запроса к нейросетям там пока нет. Так что нам придётся написать её самостоятельно.
Чтобы начать "с чистого листа" в Microsoft Excel выбираем команды Данные - Получить данные - Из других источников - Пустой запрос (Data - Get data - From other sources - Blank query). Затем на вкладке Просмотр жмём на кнопку Расширенный редактор (View - Advanced Editor), чтобы перейти к исходному коду запроса на языке М. Стираем всё, что увидим в открывшемся окне и копируем-вставляем туда следующий М-код:

(Instruction, SourceData, Temp) =>
let
apiKey = "ТУТ ДОЛЖЕН БЫТЬ ВАШ API-КЛЮЧ",

//формируем запрос
prompt = 
    Json.FromValue(
        [
            model = "deepseek-chat", 
            messages = {
                [ role = "system", content = Instruction ], 
                [ role = "user", content = SourceData ]
            }, 
            temperature = Temp
        ]
        ), 

//делаем запрос к ИИ и получаем ответ
response = 
    Json.Document(
        Web.Contents(
            "https://api.deepseek.com/chat/completions",
            [
                Headers = [ #"Content-Type" = "application/json", #"Authorization" = "Bearer " & apiKey ], 
                Content = prompt
            ]
        )
    ),
result = response[choices]{0}[message][content]
in 
result

Убеждаемся в нижней части окна, что не найдено ошибок и жмём на кнопку Готово. После этого можно назвать созданный запрос (точнее говоря, уже функцию) любым подходящим образом - например, AskDeepSeek. При необходимости к исходному коду функции всегда можно будет вернуться, нажав на ту же кнопку Расширенный редактор (Advanced Editor).

Если вам неохота разбираться с механикой его работы, то можете сразу переходить к следующему шагу - применению этого кода к нашим данным. Если же вам интересно, как, на самом деле, это работает, то давайте поясню.

Технически, этот М-код - это не обыкновенный запрос Power Query (который надо вручную обновлять), а функция. От запроса она отличается тем, что получает на входе какие-то данные в качестве аргументов, что-то с ними делает и возвращает результат своей работы нам обратно. Т.е. всё примерно также, как у привычных нам экселевских функций.

В данном случае у этой функции будет три аргумента:

  • Instruction - инструкция, которую мы даём ИИ (например, "извлеки название города из адреса")
  • SourceData - исходные данные, которые мы передаём ИИ на обработку
  • Temperature - необязательный аргумент, задающий температуру запроса - дробное число в интервале 0..2, определяющее степень креативности ИИ-модели (0 - сухо и чётко, 2 - графоманский бред )

В начале кода мы задаём в переменной apiKey наш ключ API, полученный на сайте модели.

После этого в переменной prompt с помощью М-функции Json.FromValue мы формируем запрос для нейросети в формате JSON, где задаются все необходимые исходные данные и параметры генерации: выбранная модель, инструкция, исходные данные на обработку и температура запроса.

Затем при помощи М-функции Web.Contents мы выполняем веб-запрос к ИИ-модели, используя наш ключ из переменной apiKey и собранный запрос с параметрами из переменной prompt.

ИИ возвращает ответ также в формате JSON, который мы читаем с помощью функции Json.Document и помещаем в переменную response. Кроме, собственно, ответа там будет содержаться много сопутствующей технической информации, так что далее мы выуживаем только текстовый ответ модели и помещаем его в переменную result. Её затем и возвращаем как результат всей функции после оператора in.

Я намеренно сделал этот код максимально простым, чтобы вы ухватили суть. При желании, в него, конечно же, можно внести массу улучшений и украшений: добавить обработку ошибок от сервера, сохранять API-ключ не открытым текстом в коде, а брать из внешнего txt-файла и т.д. Можете заняться этим потом при желании :)

Шаг 3. Применяем функцию

Осталось самое простое и интересное - применить созданную функцию для решения нашей рабочей задачи.

Конвертируем исходную таблицу с кривыми адресами в динамическую "умную" таблицу сочетанием клавиш Ctrl+T и загружаем в Power Query командой Данные - Из таблицы/диапазона или щёлкнув по таблице правой кнопкой мыши - Получить данные из таблицы/диапазона.

Затем применяем нашу функцию, выбрав на вкладке Добавление столбца команду Вызвать настраиваемую функцию (Add column - Invoke Custom function). В открывшемся окне задаём её аргументы:

Аргументы функции API-запроса к нейросети

После нажатия на OK наш Power Query ненадолго задумается. Или надолго - зависит от объема исходных данных. У меня уходило около 1 сек на каждую строку в среднем. Но, рано или поздно, выдаст нам результаты ИИ-запроса в новом столбце:

Результаты запроса

Красота :)

Другие нейросети

При желании приведённый выше код можно легко адаптировать под другие нейросети - большинство из них сейчас поддерживают единый стандарт API-запроса, который мы использовали выше. Например, для запроса не к DeepSeek, а к OpenAI ChatGPT в коде необходимо будет поменять:

  • адрес подключения в первом аргументе функции Web.Contents на https://api.openai.com/v1/chat/completions
  • название модели в переменной prompt - например, на "gpt-4o-mini"
  • API-ключ в переменной apiKey
Обычно все эти параметры можно легко найти на сайте соответствующей нейросети.

Дисклеймер

И пожалуйста не забывайте два важных момента:

  • Любая нейросеть может ошибаться и выдумывать факты (особенно при высоких значениях температуры), поэтому внимательно проверяйте полученные результаты.
  • Используя любую нейросеть, вы отправляете в каждом запросе свои данные на её сервер для обработки. Если это чувствительная информация (персональные или корпоративные данные и т.п.), то лучше рассмотреть вариант с развёртыванием локальной нейросети на вашем ПК (например, с помощью LM Studio или Ollama) для решения подобных задач.

Ссылки по теме



20.02.2026 18:01:31
Если просто скормить картинку deepseek, то вторую строку он определяет как один адрес в отличие от алисы, гугла, гигачата. Гугл справился быстрее всех. За пример спасибо!
25.02.2026 12:25:12
Всем добрый день! Я воспользовался сервисом https/globalapi.ru/dashboard/ для подключения к DeepSeek. Подключаясь через него можно заметно экономить на комиссии при оплате. Код для подключения  
                                                                                     (Instruction, SourceData, Temp) => 
let 
    apiKey = "Ваш ключ", 
    baseUrl = [url=https://llm.globalapi.ru/v1]"https/llm.globalapi.ru/v1"[/url], 
 
    // Формируем тело запроса с правильной структурой 
    requestBody = Text.FromBinary(Json.FromValue([ 
     model = "deepseek-chat", 
     messages = { 
      [role = "system", content = Instruction], 
      [role = "user", content = SourceData] 
     }, 
     temperature = Temp, 
     stream = false 
    &#93), 
 
    // Отправляем запрос 
    response = Json.Document( 
     Web.Contents( 
      baseUrl, 
      [ 
          Headers = [ 
           #"Content-Type" = "application/json", 
           #"Authorization" = "Bearer " & apiKey 
          ], 
          Content = Text.ToBinary(requestBody), 
          RelativePath = "/chat/completions" 
      ] 
     ) 
    ), 
 
    // Извлекаем ответ 
    result = response[choices]{0}[message][content] 
in 
    result
25.02.2026 22:17:56
Большое спасибо Николаю и Денису.

Вставляю Верный код Дениса, так как у него при копировании кода в двух местах (двоеточие и слеш, а также скобка) автозаменились на эмодзи:

(Instruction, SourceData, Temp) =>
let
  apiKey = "Ваш Ключ с сайта GlobalAPI",
  baseUrl = "https://llm.globalapi.ru/v1",

  // Формируем тело запроса с правильной структурой
  requestBody = Text.FromBinary(
Json.FromValue(
    [
model = "deepseek-chat",
messages = {
   [role = "system", content = Instruction],
   [role = "user", content = SourceData]
},
temperature = Temp,
   stream = false
]
                       ) ),

  // Отправляем запрос
  response =
 Json.Document(
Web.Contents(
   baseUrl,
[
  Headers = [
#"Content-Type" = "application/json",
#"Authorization" = "Bearer " & apiKey
  ],
  Content = Text.ToBinary(requestBody),
  RelativePath = "/chat/completions"
]
)
  ),

  // Извлекаем ответ
  result = response[choices]{0}[message][content]
in
  result
Наверх