Статьи

Как анализировать высокодинамичные наборы данных с помощью Apache Drill

Сегодняшние данные являются динамическими и управляемыми приложениями. Рост новой эры бизнес-приложений, обусловленный такими отраслевыми тенденциями, как веб / социальные сети / мобильные устройства / IOT, генерирует наборы данных с новыми типами данных и новыми моделями данных. Эти приложения являются итеративными, и связанные с ними модели данных обычно являются полуструктурированными, не содержат схем и постоянно развиваются. Полуструктурированный, где элемент может быть сложным / вложенным, и без схемы с его способностью разрешать изменяющиеся поля в каждой отдельной строке и постоянно развиваться, где поля часто добавляются и удаляются для удовлетворения бизнес-требований. Другими словами, современные наборы данных касаются не только объема и скорости, но также разнообразия и изменчивости.

Apache Drill , первый в отрасли движок SQL без схемы для Hadoop и NoSQL , позволяет бизнес-пользователям самостоятельно запрашивать динамические наборы данных, такие как JSON, в режиме самообслуживания, используя знакомые наборы навыков SQL и инструменты BI. С Apache Drill требуется всего несколько минут, чтобы получить представление о любом типе данных, в отличие от недель и месяцев с традиционными подходами.

Позвольте мне продемонстрировать это на небольшом примере. Набор данных, использованный в этом примере, взят из набора данных регистрации Yelp .

Набор данных регистрации Yelp имеет следующую структуру (это описание взято из приведенного выше сайта Yelp для справки):

01
02
03
04
05
06
07
08
09
10
11
12
13
check-in
{
    'type': 'checkin',
    'business_id': (encrypted business id),
    'checkin_info': {
        '0-0': (number of checkins from 00:00 to 01:00 on all Sundays),
        '1-0': (number of checkins from 01:00 to 02:00 on all Sundays),
        ...
        '14-4': (number of checkins from 14:00 to 15:00 on all Thursdays),
        ...
        '23-6': (number of checkins from 23:00 to 00:00 on all Saturdays)
    }, # if there was no checkin for a hour-day block it will not be in the dataset
}

Стоит повторить комментарий сверху # if there was no checkin for a hour-day block it will not be in the dataset . Это означает, что имена элементов, которые вы видите в “checkin_info” , неизвестны заранее и могут варьироваться для каждой строки. Это простой, но очень мощный пример высокодинамичных данных. Если нам нужно проанализировать это с использованием любой другой технологии SQL на Hadoop, нам нужно сначала представить этот набор данных в плоской реляционной структуре, что может быть дорогостоящим и занимать много времени.

Но с Drill это очень просто. ETL / выравнивание не требуется. Посмотрим, как это делается.

Шаг 1: Сначала загрузите Drill на свой компьютер и начните через несколько минут

Обратите внимание, что Drill может быть установлен локально на вашем рабочем столе (это называется встроенным режимом). Тебе не нужен Hadoop .

Шаг 2: Запустите SQLLine, предварительно упакованное приложение на основе JDBC с Drill

  • bin / sqlline -u jdbc: drill: zk = local

Шаг 3: Начните анализировать данные, используя SQL

Во-первых, давайте посмотрим на набор данных:

1
2
3
4
5
6
7
0: jdbc:drill:zk=local> select * from dfs.`/users/nrentachintala/Downloads/yelp/yelp_academic_dataset_checkin.json` limit 2;
+--------------+------------+-------------+
| checkin_info |    type    | business_id |
+--------------+------------+-------------+
| {"3-4":1,"13-5":1,"6-6":1,"14-5":1,"14-6":1,"14-2":1,"14-3":1,"19-0":1,"11-5":1,"13-2":1,"11-6":2,"11-3":1,"12-6":1,"6-5":1,"5-5":1,"9-2":1,"9-5":1,"9-6":1,"5-2":1,"7-6":1,"7-5":1,"7-4":1,"17-5":1,"8-5":1,"10-2":1,"10-5":1,"10-6":1} | checkin    | JwUE5GmEO-sH1FuwJgKBlQ |
| {"6-6":2,"6-5":1,"7-6":1,"7-5":1,"8-5":2,"10-5":1,"9-3":1,"12-5":1,"15-3":1,"15-5":1,"15-6":1,"16-3":1,"10-0":1,"15-4":1,"10-4":1,"8-2":1} | checkin    | uGykseHzyS5xAMWoN6YUqA |
+--------------+------------+-------------+

Обратите внимание, что Drill позволяет напрямую запрашивать данные в файлах JSON. Вам не нужно определять какие-либо предварительные определения схемы в хранилище Hive. Кроме того, обратите внимание, что имена элементов в столбце checkin_info отличаются между первой и второй строкой.

Drill предоставляет функцию KVGen (Key Value Generator), которая полезна при работе со сложными данными, которые содержат произвольные карты, состоящие из динамических и неизвестных имен элементов, таких как checkin_info . KVGen превращает динамическую карту в массив пар ключ-значение, где ключи представляют имена динамических элементов.

Давайте применим KVGen к элементу checkin_info для генерации пар ключ-значение.

1
2
3
4
5
6
7
0: jdbc:drill:zk=local> select kvgen(checkin_info) checkins from dfs.`/users/nrentachintala/Downloads/yelp/yelp_academic_dataset_checkin.json` limit 2;
+------------+
|  checkins  |
+------------+
| [{"key":"3-4","value":1},{"key":"13-5","value":1},{"key":"6-6","value":1},{"key":"14-5","value":1},{"key":"14-6","value":1},{"key":"14-2","value":1},{"key":"14-3","value":1},{"key":"19-0","value":1},{"key":"11-5","value":1},{"key":"13-2","value":1},{"key":"11-6","value":2},{"key":"11-3","value":1},{"key":"12-6","value":1},{"key":"6-5","value":1},{"key":"5-5","value":1},{"key":"9-2","value":1},{"key":"9-5","value":1},{"key":"9-6","value":1},{"key":"5-2","value":1},{"key":"7-6","value":1},{"key":"7-5","value":1},{"key":"7-4","value":1},{"key":"17-5","value":1},{"key":"8-5","value":1},{"key":"10-2","value":1},{"key":"10-5","value":1},{"key":"10-6","value":1}] |
| [{"key":"6-6","value":2},{"key":"6-5","value":1},{"key":"7-6","value":1},{"key":"7-5","value":1},{"key":"8-5","value":2},{"key":"10-5","value":1},{"key":"9-3","value":1},{"key":"12-5","value":1},{"key":"15-3","value":1},{"key":"15-5","value":1},{"key":"15-6","value":1},{"key":"16-3","value":1},{"key":"10-0","value":1},{"key":"15-4","value":1},{"key":"10-4","value":1},{"key":"8-2","value":1}] |
+------------+

Drill предоставляет еще одну функцию для работы со сложными данными, которая называется «Flatten», чтобы разбить список пар «ключ-значение», полученных из «KVGen», на отдельные строки для дальнейшего применения к ним аналитических функций.

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
0: jdbc:drill:zk=local> select flatten(kvgen(checkin_info)) checkins from dfs.`/users/nrentachintala/Downloads/yelp/yelp_academic_dataset_checkin.json` limit 20;
+------------+
|  checkins  |
+------------+
| {"key":"3-4","value":1} |
| {"key":"13-5","value":1} |
| {"key":"6-6","value":1} |
| {"key":"14-5","value":1} |
| {"key":"14-6","value":1} |
| {"key":"14-2","value":1} |
| {"key":"14-3","value":1} |
| {"key":"19-0","value":1} |
| {"key":"11-5","value":1} |
| {"key":"13-2","value":1} |
| {"key":"11-6","value":2} |
| {"key":"11-3","value":1} |
| {"key":"12-6","value":1} |
| {"key":"6-5","value":1} |
| {"key":"5-5","value":1} |
| {"key":"9-2","value":1} |
| {"key":"9-5","value":1} |
| {"key":"9-6","value":1} |
| {"key":"5-2","value":1} |
| {"key":"7-6","value":1} |
+------------+

Обратите внимание, что Drill позволяет нам применять функции KVGen и Flatten к наборам данных на лету, не требуя предварительного определения схем и не требуя сохранения в промежуточных форматах. Это мощная функция, которая может сэкономить недели и месяцы задержек, прежде чем получить ценность из данных.

Теперь при выводе сглаженных данных мы можем использовать все стандартные функции SQL, такие как фильтры, агрегаты и сортировка. Давайте посмотрим на несколько примеров.

Получить общее количество проверок, зарегистрированных в наборе данных Yelp

1
2
3
4
5
6
7
8
0: jdbc:drill:zk=local> select sum(checkintbl.checkins.`value`)  as TotalCheckins from (
. . . . . . . . . . . >  select flatten(kvgen(checkin_info)) checkins from dfs.`/users/nrentachintala/Downloads/yelp/yelp_academic_dataset_checkin.json` ) checkintbl
. . . . . . . . . . . >  ;
+---------------+
| TotalCheckins |
+---------------+
| 4713811       |
+---------------+

Получите количество проверок специально для воскресных полуночников

1
2
3
4
5
6
7
0: jdbc:drill:zk=local> select sum(checkintbl.checkins.`value`) as SundayMidnightCheckins from (
. . . . . . . . . . . >  select flatten(kvgen(checkin_info)) checkins from dfs.`/users/nrentachintala/Downloads/yelp/yelp_academic_dataset_checkin.json` ) checkintbl where checkintbl.checkins.key='23-0';
+------------------------+
| SundayMidnightCheckins |
+------------------------+
| 8575                   |
+------------------------+

Получить количество проверок в день недели

01
02
03
04
05
06
07
08
09
10
11
12
13
0: jdbc:drill:zk=local> select `right`(checkintbl.checkins.key,1) WeekDay,sum(checkintbl.checkins.`value`) TotalCheckins from (
. . . . . . . . . . . >  select flatten(kvgen(checkin_info)) checkins from dfs.`/users/nrentachintala/Downloads/yelp/yelp_academic_dataset_checkin.json`  ) checkintbl group by `right`(checkintbl.checkins.key,1) order by TotalCheckins;
+------------+---------------+
|  WeekDay   | TotalCheckins |
+------------+---------------+
| 1          | 545626        |
| 0          | 555038        |
| 2          | 555747        |
| 3          | 596296        |
| 6          | 735830        |
| 4          | 788073        |
| 5          | 937201        |
+------------+---------------+

Получить количество проверок в час дня

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
0: jdbc:drill:zk=local> select  substr(checkintbl.checkins.key,1,strpos(checkintbl.checkins.key,'-')-1) as HourOfTheDay ,sum(checkintbl.checkins.`value`) TotalCheckins from (
. . . . . . . . . . . >  select flatten(kvgen(checkin_info)) checkins from dfs.`/users/nrentachintala/Downloads/yelp/yelp_academic_dataset_checkin.json` ) checkintbl group by  substr(checkintbl.checkins.key,1,strpos(checkintbl.checkins.key,'-')-1) order by TotalCheckins;
+--------------+---------------+
| HourOfTheDay | TotalCheckins |
+--------------+---------------+
| 3            | 20357         |
| 4            | 21076         |
| 2            | 28116         |
| 5            | 33842         |
| 1            | 45467         |
| 6            | 54174         |
| 0            | 74127         |
| 7            | 96329         |
| 23           | 102009        |
| 8            | 130091        |
| 22           | 140338        |
| 9            | 162913        |
| 21           | 211949        |
| 10           | 220687        |
| 15           | 261384        |
| 14           | 276188        |
| 16           | 292547        |
| 20           | 293783        |
| 13           | 328373        |
| 11           | 338675        |
| 17           | 374186        |
| 19           | 385381        |
| 12           | 399797        |
| 18           | 422022        |
+--------------+---------------+

Как вы можете видеть выше, Drill позволяет легко просматривать как структурированные, так и полуструктурированные данные без какого-либо предварительного управления схемами или ETL.

Более подробное руководство о том, как Drill работает с JSON и другими сложными форматами данных, читайте в разделе Анализ данных JSON Yelp с помощью Apache Drill: https://cwiki.apache.org/confluence/display/DRILL/Analyzing+Yelp+JSON+Data+ с + Apache + Drill

Чтобы узнать больше о Drill, пожалуйста, обратитесь к следующим ресурсам:

Ссылка: Как анализировать высокодинамичные наборы данных с помощью Apache Drill от нашего партнера по JCG Neeraja Rentachintala в блоге Mapr .