几个配置让Drill更像Mysql

by 司马顿 | 2022年3月30日 下午6:22

对于csv文件,很多人用excel打开它,然后用excel内置函数来操作数据。

我不喜欢界面化的东西,一般在linux shell里来操作这些数据。

对csv的处理,不管spark, hive, 还是drill, impala都是可以的,这些工具都提供了一个SQL引擎来访问csv,你可以编写sql语句来访问数据。

显然,drill是最方便的。其他工具有如下问题:

相对来说,drill开箱即用,足够灵巧。它不需要定义schema,可以自由读取多种外部文件格式。虽然它也可以部署成分布式服务,但你只把它当作一个工具,用起来也很不错。

登陆linux服务器,运行drill-embedded打开本机的一个drill实例。然后,可以从浏览器访问drill的web管理端口:http://xx.xx.xx.xx:8047/

进入web页面后,稍微调整几个设置,让drill用起来更像Mysql。谁让我们都很熟悉Mysql呢?

如下图,在顶部Storage栏目,点击dfs的update按钮:

我们在这里定义本地文件系统的路径,以及目标文件(比如csv)的加载格式。

点击进去后,是一个Json文件,需要手工编辑这个Json文件。

首先在workspace里增加一节内容,对应用户的家目录的路径,这个路径用于放置输入文件。如下:

"workspaces": {
    "tmp": {
      "location": "/tmp",
      "writable": true,
      "defaultInputFormat": null,
      "allowAccessOutsideWorkspace": false
    },
    "root": {
      "location": "/",
      "writable": false,
      "defaultInputFormat": null,
      "allowAccessOutsideWorkspace": false
    },
    "pyh": {
      "location": "/home/pyh/tmp",
      "writable": false,
      "defaultInputFormat": null,
      "allowAccessOutsideWorkspace": false
    }
  },

上述加粗的内容,就是新增的路径。这个路径,在drill里对应着database的概念。比如,在drill shell里,可以如下访问这个database:

use dfs.pyh;

这里的dfs是默认的存储插件名称,pyh就是数据库的名称。在drill里,路径对应着database名称,输入文件对应着table名称。

接着,继续编写上述Json,找到csv文件定义,修改如下:

    "csv": {
      "type": "text",
      "extensions": [
        "csv"
      ],
      "extractHeader": true
    },

上述加粗的字体,就是新增的。表示对于csv文件,可以infer header,也就是从输入文件的第一行去infer header。当然,这就要求输入的csv文件第一行包含header名称。

如果不做上述修改的话,drill里每行的输出就是一个数组,列的内容挤在这个数组里,不伦不类的。而修改后,drill就自动把每行按照csv的分隔符拆开,并且自动按拆开的内容组装成列,看起来跟Mysql一样。

现在回到drill shell,执行相应的查询,如下:

apache drill (dfs.pyh)> use dfs.pyh;
+------+-------------------------------------+
|  ok  |               summary               |
+------+-------------------------------------+
| true | Default schema changed to [dfs.pyh] |
+------+-------------------------------------+
1 row selected (0.122 seconds)
apache drill (dfs.pyh)> select * from `people.csv` limit 3;
+--------------+-----------+--------+---------+-----------------------------+
|     name     |   born    |  sex   |   tel   |             job             |
+--------------+-----------+--------+---------+-----------------------------+
| Romeo V.F.   | 1973-4-10 | Male   | 5158581 | Delivery Truck Driver       |
| Preston D.I. | 1974-8-2  | Male   | 3719958 | Home Health Aide            |
| Ophelia D.A. | 1972-9-14 | Female | 9417846 | Maintenance & Repair Worker |
+--------------+-----------+--------+---------+-----------------------------+
3 rows selected (0.177 seconds)

你看,这就跟Mysql一模一样了。参考上篇博客,我们也可以执行更复杂的查询:

apache drill (dfs.pyh)> select job,count(*) as dd from `people.csv` group by job order by dd desc limit 10;
+--------------------------------------+-----+
|                 job                  | dd  |
+--------------------------------------+-----+
| School Counselor                     | 231 |
| Customer Service Representative      | 231 |
| Veterinary Technologist & Technician | 230 |
| Insurance Agent                      | 229 |
| Clinical Social Worker               | 227 |
| Financial Advisor                    | 225 |
| Accountant                           | 225 |
| Carpenter                            | 223 |
| HR Specialist                        | 222 |
| Painter                              | 221 |
+--------------------------------------+-----+
10 rows selected (0.208 seconds)

因为drill的操作是内存映射,这个过程是很快的。当然,缺点是比较耗内存,一个drill实例,默认就要求4G内存,挺消耗资源。

对于csv的操作,spark也很快。但spark的确不如drill方便,它的SQL是基于dataframe的,要从dataframe才能生成一个sql对象。作为对比,spark的优势还在于对非结构化数据的处理(RDD引擎),以及流处理的能力。对于高度结构化数据,drill甚至更为强大。

而在SQL引擎表现上,drill和spark比较类似,性能也接近。各自都有一个优化器,负责sql语句解析与优化(逻辑计划、物理计划),以及执行规划。它们的执行规划甚至都是类似的,只是概念不同而已,如下表对比:

总体上,对于高度结构化的数据,drill是个不错的查询引擎,性能很好。稍微配置下,就跟传统的Mysql很像,用起来顺手。

Source URL: https://smart.postno.de/archives/3723