Сборка таблиц из разных файлов Excel с помощью Power Query

Постановка задачи

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

Предположим, что у нас есть вот такая папка, в которой содержится несколько файлов с данными из филиалов-городов:

Файлы для сборки

Количество файлов роли не играет и может меняться в будущем. В каждом файле есть лист с именем Продажи, где расположена таблица с данными:

Данные в книгах

Количество строк (заказов) в таблицах, само-собой, разное, но набор столбцов везде стандартный.

Задача: собрать данные из всех файлов в одну книгу с последующим автоматическим обновлением при добавлении-удалении файлов-городов или строк в таблицах. По итоговой консолидированной таблице затем можно будет строить любые отчеты, сводные таблицы, фильтровать-сортировать данные и т.д. Главное - суметь собрать.

Подбираем оружие

Для решения нам потребуется последняя версия Excel 2016 (в нее нужный функционал уже встроен по умолчанию) или предыдущие версии Excel 2010-2013 с установленной бесплатной надстройкой Power Query от Microsoft (скачать ее можно здесь). Power Query - это супергибкий и супермощный инструмент для загрузки в Excel данных из внешнего мира с последующей их зачисткой и обработкой. Power Query поддерживает практически все существующие источники данных - от текстовых файлов до SQL и даже Facebook :)

Если у вас нет Excel 2013 или 2016, то дальше можно не читать (шучу). В более древних версиях Excel подобную задачу можно реализовать только программированием макроса на Visual Basic (что весьма непросто для начинающих) или монотонным ручным копированием (что долго и порождает ошибки).

Шаг 1. Импортируем один файл как образец

Для начала давайте импортируем данные из одной книги в качестве примера, чтобы Excel "подхватил идею". Для этого создайте новую пустую книгу и...

  • если у вас Excel 2016, то откройте вкладку Данные и выберите Создать запрос - Из файла - Из книги (Data - New Query- From file - From Excel)
  • если у вас Excel 2010-2013 с установленной надстройкой Power Query, то откройте вкладку Power Query и выберите на ней Из файла - Из книги (From file - From Excel)
Затем в открывшемся окне переходим в нашу папку с отчетами и выбираем любой из файлов-городов (не играет роли какой именно, т.к. они все типовые). Через пару секунд должно появиться окно Навигатор, где нужно в левой части выбрать требуемый нам лист (Продажи), а в правой отобразится его содержимое:

Навигатор Power Query

Если нажать в правом нижнем углу этого окна кнопку Загрузить (Load), то таблица будет сразу импортирована на лист в исходном виде. Для одиночного файла - это хорошо, но нам нужно загрузить много таких файлов, поэтому мы пойдем немного другим путем и жмем кнопку Правка (Edit). После этого должен в отдельном окне отобразиться редактор запросов Power Query с нашими данными из книги:

Редактор запросов Power Query

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

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

Для примера, давайте добавим к нашей таблице столбец с текстовым названием месяца, чтобы потом проще было строить отчеты сводных таблиц. Для этого щелкните правой кнопкой мыши по заголовку столбца Дата и выберите команду Дублировать столбец (Duplicate Column), а затем щелкните правой кнопкой мыши по заголовку появившегося столбца-дубликата и выберите команды Преобразование - Месяц - Название месяца:

Добавление столбца с месяцем

Должен образоваться новый столбец с текстовыми названиями месяца для каждой строки. Дважды щелкнув по заголовку столбца, его можно переименовать из Копия Дата в более удобное Месяц, например.

Новый столбец
Если в каких-то столбцах программа не совсем корректно распознала тип данных, то ей можно помочь, щелкнув по значку формата в левой части каждого столбца:

Преобразование форматов данных в столбцах

Исключить строки с ошибками или пустые строки, а также ненужных менеджеров или заказчиков можно с помощью простого фильтра:

Фильтрация данных в Power Query

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

Шаги преобразований

Легко и изящно, не правда ли?

Шаг 2. Преобразуем наш запрос в функцию

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

В редакторе запросов перейдите на вкладку Просмотр и нажмите кнопку Расширенный редактор (View - Advanced Editor). Должно открыться окно, где все наши предыдущие действия будут записаны в виде кода на языке М. Обратите внимание, что в коде жестко прописан путь к файлу, который мы импортировали для примера:

Исходный код

Теперь аккуратно вносим пару правок:

Измененный код

Смысл их прост: первая строка (filepath)=> превращает нашу процедуру в функцию с аргументом filepath, а ниже мы меняем фиксированный путь на значение этой переменной. 

Все. Жмем на Готово и должны увидеть вот это:

Созданная функция

Не пугайтесь, что пропали данные - на самом деле все ОК, все так и должно выглядеть :) Мы успешно создали нашу пользовательскую функцию, где запомнился весь алгоритм импорта и обработки данных без привязки к конкретному файлу. Осталось дать ей более понятное имя (например getData) на панели справа в поле Имя и можно жать Главная - Закрыть и загрузить (Home - Close and Load). Обратите внимание, что в коде жестко прописан путь к файлу, который мы импортировали для примера.. Вы вернетесь в основное окно Microsoft Excel, но справа должна появиться панель с созданным подключением к нашей функции:

Подключение к функции

Шаг 3. Собираем все файлы

Все самое сложное - позади, осталась приятная и легкая часть. Идем на вкладку Данные - Создать запрос - Из файла - Из папки (Data - New Query - From file - From folder) или, если у вас Excel 2010-2013, аналогично на вкладку Power Query. В появившемся окне указываем папку, где лежат все наши исходные файлы-города и жмем ОК. Следующим шагом должно открыться окно, где будут перечислены все найденные в этой папке (и ее подпапках) файлы Excel и детализация по каждому из них:

Импорт всех файлов Excel из заданной папки

Жмем Изменить (Edit) и опять попадаем в знакомое окно редактора запросов.

Теперь нужно добавить к нашей таблице еще один столбец с нашей созданной функцией, которая "вытянет" данные из каждого файла. Для этого идем на вкладку Добавить столбец - Пользовательский столбец (Add Column - Add Custom Column) и в появившемся окне вводим нашу функцию getData, указав для ее в качестве аргумента полный путь к каждому файлу:

Дополнительный столбец

После нажатия на ОК созданный столбец должен добавиться к нашей таблице справа.

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

А теперь "вау-момент" - щелкнем мышью по значку со своенным стрелками в правом верхнем углу добавленного столбца с нашей функцией:

Подгружаем данные в пользовательский столбец

... снимаем флажок Использовать исходное имя столбца как префикс (Use original column name as prefix)и жмем ОК. И наша функция подгрузит и обработает данные из каждого файла, следуя записанному алгоритму и собрав все в общую таблицу:

Собранные данные

Для полной красоты можно еще убрать расширения .xlsx из первого столбца с именами файлов - стандартной заменой на "ничего" (правой кнопкой мыши по заголовку столбца - Заменить) и переименовать этот столбец в Город. А также подправить формат данных в столбце с датой.

Все! Жмем на Главной - Закрыть и загрузить (Home - Close & Load). Все собранные запросом данные по всем городам будут выгружены на текущий лист Excel в формате "умной таблицы":

Собранные данные

Созданное подключение и нашу функцию сборки не нужно никак отдельно сохранять - они сохраняются вместе с текущим файлом обычным образом.

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

P.S.

Поправка. После январских обновлений 2017 года Power Query научился собирать Excel'евские книги сам, т.е. не нужно больше делать отдельную функцию - это происходит автоматически. Таким образом второй шаг из этой статьи уже не нужен и весь процесс становится заметно проще:

  1. Выбрать Создать запрос - Из файла - Из папки - Выбрать папку - ОК
  2. После появления списка файлов нажать Изменить
  3. В окне редактора запросов развернуть двойной стрелкой столбец Binary и выбрать имя листа, который нужно взять из каждого файла

И все! Песня!

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



Страницы: 1  2  3  4  
24.04.2018 10:15:42
спасибо
15.06.2018 08:57:58
Кто-нибудь знает как обновить Power Query 2016, пишет что у меня не последняя версия...э
24.06.2018 19:34:29
Спс, мне очень помогло
26.06.2018 15:44:17
Использовал успешно PQ для преобразования таблиц и столкнулся с задачей склеить несколько файлов в один. Следуя этому алгоритму на 3 этапе загружается корректно только файл, загруженный на 1 этапе. Ошибка: Expression.Error: The key didn't match any rows in the table

Не подскажете, что можно сделать?
09.07.2018 07:32:12
Добрый день, Николай!
Возможно ли изменить уже записанную функцию? Или надо все заново делать?
Поняла, что удалила некоторые колонки, которые в целом могут понадобиться в будущем для сводной таблицы.
09.07.2018 11:17:05
Уже нашла :-)
Добрый день, Николай!
После склейки столбцов с путем и именем в новом столбце для всех книг кроме одной (той с которой на первом этапе делали настройки) вместо "table" пишет ошибку "error"
В запросе "" произошла ошибка. Expression.Error: Ключу не соответствует ни одна строка в таблице.
Сведения:
   Key=Record
   Table=Table.
В чем может быть причина?
20.07.2018 10:59:02
Не видя ваших исходных файлов и запроса - сказать невозможно. Миллион причин разных.
26.07.2018 07:53:50
Добрый день,

Настроила power query для нескольких файлов. Доступ в папки и файлы открыт для всех сотрудников. Но папки и файлы хранятся не на общем сервере, доступ открыт через dropbox. Соответственно, адрес линка у каждого сотрудника отличается.
C:\Users\имя сотрудника\Dropbox (название компании)\название папки\сам файл

Все прекрасно работает, НО только с моего компьютера. Пока я не внесу обновления, ни один сотрудник не увидит обновления и также не может вносить никакие данные, тк они все равно не попадут в сводный файл, тк линки с других компьютеров не работают. Это и понятно, тк адрес ссылки отличается по имени. К тому же постоянно выскакивает уведомление, что линки не найдены.

Подскажите, как быть, наверное, можно как-то настроить  и изменить адрес source, чтобы другие коллеги могли не только видеть последние обновления, но и также работать с файлами и вносить изменения.

Заранее благодарю

Екатерина
05.09.2018 21:43:16
Добрый вечер. Делаю все по инструкции, запрос создал, когда хочу подгрузить с источника возникает ошибка. Ссылка скриншота https://dropmefiles.com/Evnuj
19.09.2018 14:06:57
Ну, вот и подошёл я к пределу возможностей Power Query :(: всего-то ему нужно 3 (три!) файла собрать в одну таблицу, а он мне выдаёт OutOfMemory :).

Да и объёмы-то несильно большие этих файлов: один 49,9, другой 36,6, а третий 47,4 мега всего... Вот пытаюсь их Повером этим собрать, а он "падает"... Да и таблички там несильно здоровые: 341 столбец на максимум 64300 строк.
Придётся отдельно с каждым файлом возиться
12.12.2018 09:03:18
Всем привет,
Насколько я понимаю данный подход может работать в одном файле с разными вкладками. Но если вкладки имеют различные названия, как поставить переменную имени вкладки в функцию?
17.12.2018 15:14:30
Все бы хорошо с консолидацией из папки, огорчает, что при переименовании Source.Name например, при использовании в качестве заголовков первой строки, в шапку переходит название файла. Если этот файл из папки удалить или добавить файл с именем, который по алфавиту следует ранее чем первый, получаем ошибку...Запрос не находит имя файла и все - крах консолидации!
19.01.2019 20:07:51
Здравствуйте Уважаемый Николай. Подскажите а можно ли примерно таким же образом менять заранее подготовленные веб-запросы ? вот пример:
let
   Источник = Json.
  in
   #"Измененный тип"

можно ли как то в полуавтоматическом режиме вводить данные в поле веб запроса, чтобы каждый раз не менять?
18.02.2019 20:55:13
Посмотрите, плиз, статью про параметризацию путей в Power Query - то же самое можно и с веб-запросами делать.
20.01.2019 15:55:51
Использование функции и обновление.
Не зависимо от обновления PQ позволяет собрать данные из книги или из папки.
А если в книгах подлежащих консолидации может быть разное количество листов?
Для приведенного примера: Продажи, Продажи2011, Продажи2012 ... и т. д
Запросом к книге собираю все листы имеющиеся в книге (путем незначительной корректировки запроса к одному листу, что описано например в ютубе).
Затем по приведенной методике делаю функцию, которая собирает все листы в книге.
Затем запросом к папке с подстановкой функции собираю все книги в папке.
Результат - сборка всех книг из папки и всех листов из этих книг.
Исходные листы д.б. таблицами, иначе при консолидации диапазонов надо будет как-то удалять лишние строки с заголовками.
30.01.2019 11:28:54
Для чего проставляется флажек add this data to the data mode привыгрузке данных, собранных в Power Query, в таблицу?
Потом из этой таблицы строится Pivot. Может да данном этапе надо проставлять флажек add this data to the data mode?
18.02.2019 20:51:50
Этот флажок нужен для загрузки результатов запроса в надстройку Power Pivot (а не в обычную сводную таблицу).
11.02.2019 10:32:03
Добрый день!

Подскажите, пожалуйста, возможно ли после загрузки запроса, сделать дополнительный столбец для ручного заполнения, чтобы при обновлении запроса, введенная информация была привязана к своей строке?
18.02.2019 20:53:28
Самый простой вариант - подтянуть нужные данные к результатам выгрузки той же функцией ВПР (VLOOKUP).
19.02.2019 10:01:27
Николай, подскажите, пожалуйста, можно ли "зафиксировать" ширины столбцов в итоговой таблице? То есть, получается так, что после того, как собраны все данные, таблица отформатирована (установлены ширины столбцов, при необходимости в заголовке установлено "Переносить текст" и т.д.), при обновлении данных всё это "рушится": ширины столбцов увеличиваются непомерно.
27.02.2019 10:59:02
Юрий, попробуйте щелкнуть правой по таблице с результатами запроса на листе - Таблица - Свойства внешних данных и поиграть с галочками в группе отвечающей за форматирование.
05.03.2019 16:55:19
Браво!
Бис!
А ларчик просто открывался. Когда знаешь, тогда всё легко :)
СПАСИБО!!!
26.02.2019 10:54:48
А чего мой комент удаляют?

Это полезный материал, но я просил помочь с проблемой=>

В запросе "" произошла ошибка. Expression.Error: Ключу не соответствует ни одна строка в таблице.
Сведения:
   Key=Record
   Table=Table

Хотя все делал по написанному  
27.02.2019 10:52:53
Удаляю, потому что в нём нет смысла. Если бы делали "по написанному", то все бы работало. Если не работает - значит что-то делаете не так, логично? Но понять, что именно вы делаете неправильно из вашего комментария или приведенной ошибки нереально.
Хотите качественной помощи - пришлите мне ваш файл с ошибочным запросом на почту или спросите на форуме (приложив, опять же, файл).
ОК? :)
26.02.2019 13:02:57
Добрый день! Николай, спасибо за урок!
Помогите, пожалуйста, понять почему PQ загружает только первые 100 строк из исходного листа+1 строка шапка, а 102 строка - многоточие. Т.е. показывает, что данные есть но больше 100 строк не загружает.
27.02.2019 11:00:07
Наталья, не видя вашего файла с исходными данными и вашего запроса - не смогу сказать. Шлите на почту - посмотрю как будет минутка, ОК?
26.03.2019 19:06:01
Подскажите, пожалуйста, есть ли возможность подобным образом, имея фиксированное количество строк, добавлять условные "города" по столбцам?
В этом примере получается, есть фиксированное количество столбцов и города по строкам (т.е. наоборот, сделать транспоринирование)
07.05.2019 16:50:59
Добрый день. Подскажите, пжлст, у меня MS Office 2019 Pro, но почему то в редакторе отсутствует доп.контекстное меню для "Месяца" и я не могу получить из колонки Дата название месяца (как описано в статье), далее нет значков для колонок для быстрого определения формата. Это зависит от версии редактора? Как-то нужно его обновить?
И вопрос № 2, подскажите, пжлст, как получить текстовое название месяца из колонки Дата без меню (ну т.е. имею в виду код).
Спасибо!
11.05.2019 11:37:04
Да, вам нужно обновить Power Query - для этого просто нужно обновить весь Excel через Файл - Учетная запись - Обновить.
Если формулой, то будет =Date.ToText(колонка_с_датой, "MMMM")
28.05.2019 10:46:15
Приветствую всех!
В одном файле появилась проблема: при обновлении данных в PQ и в сводных таблицах выскакивает сообщение "Нам не удалось загрузить модель данных. Возможно, модель данных в этой книге повреждена." И больше никаких сведений. При этом само обновление после нажатия кнопки Ок в этом сообщении дальше проходит успешно (?), но, может быть, что-то не так обновляется?
Где нужно покопаться, чтобы найти это самое "повреждение"?

P. S. Хорошо, что делал резервные копии этого файла. При использовании резервной копии такое сообщение не появляется.
29.01.2020 08:00:58
Добрый день, подскажите Вы нашли ответ на Вашу проблему?! У меня такая ж проблема. Спасибо.
03.02.2020 20:26:13
Да, решил с помощью форума. PQ в этом был не виноват. Это в Сводных у меня был косяк. А ввиду того, что при обновлении данных через PQ обновлялись и данные на других листах и на этом листе через формулы, выскакивало это сообщение.
06.06.2019 18:18:39
Добрый день!
При попытке создать пользовательский столбец, выдает ошибку:
"Ошибка выражения :Имя "getData" не распознано. Убедитесь, что оно написано верно"
Формула:  =getData([Folder Path]&[Name])

Вопрос снят, я разобрался;)
26.06.2019 11:43:45
Добрый день!
Подскажите, пожалуйста, как изменить универсальный запрос getData из инструкции, чтобы помимо любой книги из указанной папки, он так же распознавал лист с любым названием из той или иной книги, с целью избежать ошибки, уже озвученной ранее на данном форуме, а именно:
An error occurred in the ‘’ query. Expression.Error: The key matched more than one row in the table.Details:    Key=Record    Table=Table
Заранее большое спасибо за ответ
26.06.2019 12:31:21
Нашла ответ самостоятельно о том, как решить данную проблему:
Ее можно наглядно увидеть по ссылке
После применения данного шага на этапе формирования запроса "GetData" Error в Пользовательском столбце пропадает.
Вызвана она, скорее всего, в большинстве случаев именно привязкой к названию листа, с которого запрос считывает наши данные.
06.02.2020 13:22:47
Добрый день!
Подскажите, пожалуйста, какой именно шаг нужно применить.
Моя проблема в том, название листов, с которых нужно собирать данные, отличаются, При этом порядковый номер листа всегда одинаковый.
29.07.2019 07:58:45
Как можно сделать тоже самое только с файлами csv?
13.09.2019 14:37:26
Кстати, Николай, случайно наткнулся на интересный фокус как преобразовать запрос в функцию чисто мышиным клацаньем без использования расширенного редактора. На форуме выкладывал описание. При этом создается функция, в которой текст кода связан с исходным запросом, т.е. когда меняешь текст запроса, меняется и сама функция. Для отладки сложных функций очень удобный инструмент.
Страницы: 1  2  3  4  
Наверх