Apache Tajo 简明教程
Apache Tajo - Introduction
Distributed Data Warehouse System
数据仓库是一种关系型数据库,其设计主要用于查询和分析,而不是用于事务处理。它是一个面向主题、集成、随时间变化且不易失的数据集合。这些数据可帮助分析师在组织中做出明智决策,但关系数据量逐日增加。
为了克服这些挑战,分布式数据仓库系统跨多个数据存储库共享数据,目的是用于联机分析处理 (OLAP)。每个数据仓库可能属于一个或多个组织。它执行负载平衡和可扩展性。元数据进行复制并集中分布。
Apache Tajo 是一款分布式数据仓库系统,它使用 Hadoop 分布式文件系统 (HDFS) 作为存储层,并拥有自己的查询执行引擎,而不是 MapReduce 框架。
Overview of SQL on Hadoop
Hadoop 是一个开放源码框架,允许在分布式环境中存储和处理大数据。它非常快速且强大。但是,Hadoop 的查询能力有限,因此可以在 Hadoop 上使用 SQL 来进一步提升其性能。这允许用户通过简单的 SQL 命令与 Hadoop 进行交互。
SQL on Hadoop 的一些应用程序示例包括 Hive、Impala、Drill、Presto、Spark、HAWQ 和 Apache Tajo。
What is Apache Tajo
Apache Tajo 是一个关系型分布式数据处理框架。它旨在实现低延迟和可扩展的临时查询分析。
-
Tajo 支持标准 SQL 和各种数据格式。大多数 Tajo 查询无需进行任何修改即可执行。
-
Tajo 具有 fault-tolerance 针对失败的任务进行重启机制和可扩展查询重写引擎。
-
Tajo 执行必要的 ETL (Extract Transform and Load process) 操作,以汇总存储在 HDFS 上的大型数据集。它是 Hive/Pig 之外的另一种选择。
Tajo 的最新版本提高了与 Java 程序以及第三方数据库(例如 Oracle 和 PostGreSQL)的连接性。
Features of Apache Tajo
Apache Tajo 具有以下功能:
-
超强的可扩展性和优化的性能
-
Low latency
-
User-defined functions
-
Row/columnar storage processing framework.
-
与 HiveQL 和 Hive MetaStore 兼容
-
简单的数据流程和容易维护。
Benefits of Apache Tajo
Apache Tajo 提供了以下好处:
-
Easy to use
-
Simplified architecture
-
Cost-based query optimization
-
Vectorized query execution plan
-
Fast delivery
-
简单的 I/O 机制并支持各种类型的存储。
-
Fault tolerance
Apache Tajo - Architecture
下图描绘了 Apache Tajo 的架构。
下表详细描述了每个组件。
S.No. |
Component & Description |
1 |
Client Client 提交 SQL 语句到 Tajo Master 以获取结果。 |
2 |
Master Main 是主守护进程。它负责查询规划,并且是工作者的协调器。 |
3 |
Catalog server 维护表和索引描述。它嵌入在 Master 守护进程中。编目服务器使用 Apache Derby 作为存储层,并通过 JDBC 客户端进行连接。 |
4 |
Worker Master 节点将任务分配给工作器节点。TajoWorker 处理数据。随着 TajoWorkers 数量的增加,处理能力也会线性增加。 |
5 |
Query Master Tajo master 将查询分配给 Query Master。Query Master 负责控制分布式执行计划。它启动 TaskRunner 并将任务计划为 TaskRunner。Query Master 的主要作用是监视正在运行的任务并将其报告给 Master 节点。 |
6 |
Node Managers 管理工作器节点的资源。它决定将请求分配给该节点。 |
7 |
TaskRunner 充当本地查询执行引擎。它用于运行和监视查询过程。TaskRunner 一次处理一个任务。它具有以下三个主要属性 - 逻辑计划 - 创建该任务的执行块。段 - 输入路径、偏移量范围和模式。获取 URI |
8 |
Query Executor 它用于执行查询。 |
9 |
Storage service 将底层数据存储连接到 Tajo。 |
Apache Tajo - Installation
要安装 Apache Tajo,您的系统上必须安装以下软件 −
-
Hadoop 版本 2.3 或更高版本
-
Java 版本 1.7 或更高版本
-
Linux or Mac OS
现在,让我们继续按照以下步骤安装 Tajo。
Verifying Java installation
希望您已在您的计算机上安装了 Java 8 版本。现在,您只需要通过验证来继续进行。
若要验证,使用以下命令 -
$ java -version
如果计算机上已成功安装 Java,您将可以看到已安装 Java 的当前版本。如果尚未安装 Java,请按照以下步骤在您的计算机上安装 Java 8。
Download JDK
访问以下链接下载 JDK 的最新版本,然后下载最新版本。
最新版本是 JDK 8u 92 文件是 “jdk-8u92-linux-x64.tar.gz” 。请在您的计算机上下载文件。之后,解压缩文件并将它们移动到特定目录。现在,设置 Java 替代方案。最后,您的计算机上已安装了 Java。
Verifying Hadoop Installation
您已经在您的系统上安装了 Hadoop 。现在,使用以下命令对其进行验证 -
$ hadoop version
如果您的设置一切正常,则您将可以看到 Hadoop 的版本。如果尚未安装 Hadoop,请访问以下链接下载并安装 Hadoop - https://www.apache.org
Apache Tajo Installation
Apache Tajo 提供了两种执行模式 - 本地模式和完全分布模式。在验证 Java 和 Hadoop 安装后,请继续执行以下步骤在您的计算机上安装 Tajo 集群。本地模式 Tajo 实例需要非常简单的配置。
访问以下链接下载 Tajo 的最新版本 - https://www.apache.org/dyn/closer.cgi/tajo
现在,您可以在您的计算机上下载文件 “tajo-0.11.3.tar.gz” 。
Set Environment Variable
将以下更改添加到 “conf/tajo-env.sh” 文件
$ cd tajo-0.11.3
$ vi conf/tajo-env.sh
# Hadoop home. Required
export HADOOP_HOME = /Users/path/to/Hadoop/hadoop-2.6.2
# The java implementation to use. Required.
export JAVA_HOME = /path/to/jdk1.8.0_92.jdk/
此处,您必须向 “tajo-env.sh” 文件指定 Hadoop 和 Java 路径。在更改完成后,保存文件并退出终端。
Start Tajo Server
要启动 Tajo 服务器,执行以下命令 -
$ bin/start-tajo.sh
您将收到类似于以下内容的响应 -
Starting single TajoMaster
starting master, logging to /Users/path/to/Tajo/tajo-0.11.3/bin/../
localhost: starting worker, logging to /Users/path/toe/Tajo/tajo-0.11.3/bin/../logs/
Tajo master web UI: http://local:26080
Tajo Client Service: local:26002
现在,键入命令 “jps” 查看正在运行的守护程序。
$ jps
1010 TajoWorker
1140 Jps
933 TajoMaster
Apache Tajo - Configuration Settings
Tajo 的配置基于 Hadoop 的配置系统。本章详细说明了 Tajo 配置设置。
Distributed Mode Configuration
分布式模式设置在 Hadoop 分布式文件系统 (HDFS) 上运行。让我们按照步骤配置 Tajo 分布式模式设置。
tajo-site.xml
此文件可在 /path/to/tajo/conf 目录中获取,可作为其他 Tajo 模块的配置。要以分布式模式访问 Tajo,请对 “tajo-site.xml” 应用以下更改。
<property>
<name>tajo.rootdir</name>
<value>hdfs://hostname:port/tajo</value>
</property>
<property>
<name>tajo.master.umbilical-rpc.address</name>
<value>hostname:26001</value>
</property>
<property>
<name>tajo.master.client-rpc.address</name>
<value>hostname:26002</value>
</property>
<property>
<name>tajo.catalog.client-rpc.address</name>
<value>hostname:26005</value>
</property>
Master Node Configuration
Tajo 将 HDFS 用作主要的存储类型。其配置如下,且应当将其添加到 “tajo-site.xml” 中。
<property>
<name>tajo.rootdir</name>
<value>hdfs://namenode_hostname:port/path</value>
</property>
Catalog Configuration
如果您要自定义目录服务,请将 $path/to/Tajo/conf/catalogsite.xml.template 复制到 $path/to/Tajo/conf/catalog-site.xml 中,并根据需要添加任何以下配置。
例如,如果您使用 “Hive catalog store” 访问 Tajo,则其配置应如下所示 −
<property>
<name>tajo.catalog.store.class</name>
<value>org.apache.tajo.catalog.store.HCatalogStore</value>
</property>
如果您需要存储 MySQL 目录,则应用以下更改 −
<property>
<name>tajo.catalog.store.class</name>
<value>org.apache.tajo.catalog.store.MySQLStore</value>
</property>
<property>
<name>tajo.catalog.jdbc.connection.id</name>
<value><mysql user name></value>
</property>
<property>
<name>tajo.catalog.jdbc.connection.password</name>
<value><mysql user password></value>
</property>
<property>
<name>tajo.catalog.jdbc.uri</name>
<value>jdbc:mysql://<mysql host name>:<mysql port>/<database name for tajo>
?createDatabaseIfNotExist = true</value>
</property>
同样,您可以在此配置文件中注册 Tajo 支持的其他目录。
Worker Configuration
默认情况下,TajoWorker 将临时数据存储在本地文件系统中。它在 “tajo-site.xml” 文件中定义,如下所示 −
<property>
<name>tajo.worker.tmpdir.locations</name>
<value>/disk1/tmpdir,/disk2/tmpdir,/disk3/tmpdir</value>
</property>
要增加每个工作程序资源运行任务的能力,请选择以下配置 −
<property>
<name>tajo.worker.resource.cpu-cores</name>
<value>12</value>
</property>
<property>
<name>tajo.task.resource.min.memory-mb</name>
<value>2000</value>
</property>
<property>
<name>tajo.worker.resource.disks</name>
<value>4</value>
</property>
要让 Tajo 服务器以专用的模式运行,请选择以下配置 −
<property>
<name>tajo.worker.resource.dedicated</name>
<value>true</value>
</property>
Apache Tajo - Shell Commands
在本章中,我们将详细了解 Tajo Shell 命令。
要执行 Tajo shell 命令,您需要使用以下命令启动 Tajo 服务器和 Tajo shell −
Meta Commands
现在让我们讨论 Meta Commands 。Tsql 元命令以反斜杠 (‘\’) 开头。
Session Variables
Tajo 客户端通过一个唯一的会话 ID 连接到 Master。会话在客户端断开连接或过期前有效。
下面的命令用于列出所有会话变量。
Query
default> \set
Result
'SESSION_LAST_ACCESS_TIME' = '1470206387146'
'CURRENT_DATABASE' = 'default'
‘USERNAME’ = 'user'
'SESSION_ID' = 'c60c9b20-dfba-404a-822f-182bc95d6c7c'
'TIMEZONE' = 'Asia/Kolkata'
'FETCH_ROWNUM' = '200'
‘COMPRESSED_RESULT_TRANSFER' = 'false'
\set key val 将使用值 val 设置名为 key 的会话变量。例如,
Query
default> \set ‘current_database’='default'
Result
usage: \set [[NAME] VALUE]
在此,您可以在 \set 命令中分配键和值。如果您需要还原更改,请使用 \unset 命令。
Apache Tajo - Data Types
要在 Tajo shell 中执行查询,请打开您的终端并移动到已安装的 Tajo 目录,然后键入以下命令:
$ bin/tsql
您现在将看到响应,如下面的程序所示:
default>
您现在可以执行查询。否则您可通过 Web 控制台应用程序将查询运行到下列 URL: http://localhost:26080/
Primitive Data Types
Apache Tajo 支持下列基本数据类型列表:
S.No. |
Data type & Description |
1 |
integer 用于存储具有 4 字节存储的整数。 |
2 |
tinyint 微小整数为 1 字节 |
3 |
smallint 用于存储小尺寸 2 字节整数。 |
4 |
bigint 大范围整数具有 8 字节存储。 |
5 |
boolean Returns true/false. |
6 |
real 用于存储实值。大小为 4 字节。 |
7 |
float 具有 4 或 8 字节存储空间的浮点精度值。 |
8 |
double 存储在 8 字节中的双精度值。 |
9 |
char[(n)] Character value. |
10 |
varchar[(n)] Variable-length non-Unicode data. |
11 |
number Decimal values. |
12 |
binary Binary values. |
13 |
date 日历日期(年、月、日)。 Example − DATE '2016-08-22' |
14 |
time 一天中的时间(时、分、秒、毫秒),没有时区。该类型的值解析后在会话时区呈现。 |
15 |
timezone 一天中的时间(时、分、秒、毫秒),有时区。此类型的值使用值中的时区呈现。 Example − TIME '01:02:03.456 Asia/kolkata' |
16 |
timestamp 即时时间,其中包括没有时区的日期和时间。 Example − TIMESTAMP '2016-08-22 03:04:05.321' |
17 |
text Variable-length Unicode text. |
Apache Tajo - Operators
以下运算符用于 Tajo 中执行所需操作。
S.No. |
Operator & Description |
1 |
Arithmetic operators Presto 支持诸如 +、-、*、/、% 的算术运算符。 |
2 |
Relational operators <、>、⇐、>=、=、<> |
3 |
Logical operatorsAND, OR, NOT |
4 |
String operatorsThe ‘ |
' 运算符执行字符串连接。 |
|
5 |
Range operators 范围运算符用于测试特定范围内的值。Tajo 支持 BETWEEN、IS NULL、IS NOT NULL 运算符。 |
Apache Tajo - Math Functions
数学函数在数学公式上运行。下表详细描述了函数列表。
S.No. |
Function & Description |
1 |
abs(x) 返回 x 的绝对值。 |
2 |
cbrt(x) 返回 x 的立方根。 |
3 |
ceil(x) 返回四舍五入到最接近整数的 x 值。 |
4 |
floor(x) 返回向下舍入到最接近整数的 x 值。 |
5 |
pi() 返回圆周率 π。结果值将以双精度浮点值返回。 |
6 |
radians(x) 将角度 x 由度转换成弧度。 |
7 |
degrees(x) 返回 x 的度数。 |
8 |
pow(x,p) 返回值为“p”的 x 次方。 |
9 |
div(x,y) 返回给定的两个 x、y 整数值的除法结果。 |
10 |
exp(x) 返回欧拉数 e 的 n 次方。 |
11 |
sqrt(x) 返回 x 的平方根。 |
12 |
sign(x) 返回 x 的符号函数,即如果参数为 0,则返回 −0,如果参数大于 0,则返回 1,如果参数小于 0,则返回 −1。 |
13 |
mod(n,m) 返回 n 除以 m 的模(余)。 |
14 |
round(x) 返回 x 的舍入值。 |
15 |
cos(x)Returns the cosine value(x). |
16 |
asin(x) 返回反正弦值 (x)。 |
17 |
acos(x) 返回反正切值 (x)。 |
18 |
atan(x) 返回反正切值 (x)。 |
19 |
atan2(y,x) 返回反正切值 (y/x)。 |
Data Type Functions
下表列出了 Apache Tajo 中可用的数据类型函数。
S.No. |
Function & Description |
1 |
to_bin(x) 返回整数的二进制表示形式。 |
2 |
to_char(int,text)Converts integer to string. |
3 |
to_hex(x) 将 x 值转换为十六进制。 |
Apache Tajo - String Functions
下表列出 Tajo 中的字符串函数。
Apache Tajo - DateTime Functions
Apache Tajo 支持以下 DateTime 函数。
Apache Tajo - JSON Functions
JSON 函数在以下表格中列出:
S.No. |
Function & Description |
1 |
json_extract_path_text(js on text, json_path text) 从 JSON 字符串中基于 JSON 路径提取 JSON 字符串。 |
2 |
json_array_get(json_array text, index int4) 返回 JSON 数组中指定索引位置的元素。 |
3 |
json_array_contains(json_ array text, value any) 判断给定值是否存在于 JSON 数组中。 |
4 |
json_array_length(json_ar ray text) 返回 json 数组的长度。 |
Apache Tajo - Database Creation
Apache Tajo - Table Management
表是某个数据源的逻辑视图。它包含逻辑模式、分区、URL 和各种属性。Tajo 表可以是 HDFS 中的目录、单个文件、某个 HBASE 表或某个 RDBMS 表。
Tajo 支持以下两种类型的表 −
-
external table
-
internal table
External Table
外部表在创建表时需要 location 属性。例如,如果你的数据已作为文本/JSON 文件或 HBASE 表存在,你可以将它注册为 Tajo 外部表。
以下查询是外部表创建的示例。
create external table sample(col1 int,col2 text,col3 int) location ‘hdfs://path/to/table';
在此,
-
External keyword − 这用于创建外部表,用于在指定位置创建表。
-
Sample 指代表名称。
-
Location − 它是 HDFS、Amazon S3、HBASE 或本地文件系统的目录。要为目录分配 location 属性,请使用以下 URI 示例 − HDFS − hdfs://localhost:port/path/to/table Amazon S3 − s3://bucket-name/table local file system − [role="bare"] [role="bare"]file:///path/to/table Openstack Swift − swift://bucket-name/table
Table Properties
外部表具有以下属性 −
-
TimeZone − 用户可以指定时区以读取或写入表。
-
Compression format − 用于压缩数据大小。例如,text/json 文件使用 compression.codec 属性。
Tablespace
表空间用于定义存储系统中的位置。它仅支持内部表。你可以按名称访问表空间。每个表空间可以使用不同的存储类型。如果你不指定表空间,Tajo 则在根目录中使用默认表空间。
Tablespace Configuration
你在 Tajo 中有 “conf/tajo-site.xml.template” 。复制此文件并将其重命名为 “storagesite.json” 。此文件会充当表空间的配置。Tajo 数据格式使用以下配置 −
HDFS Configuration
$ vi conf/storage-site.json {
"spaces": {
"${tablespace_name}": {
"uri": “hdfs://localhost:9000/path/to/Tajo"
}
}
}
Tablespace Creation
只能从另一个表中访问 Tajo 的内部表记录。你可以使用表空间对其进行配置。
Syntax
CREATE TABLE [IF NOT EXISTS] <table_name> [(column_list)] [TABLESPACE tablespace_name]
[using <storage_type> [with (<key> = <value>, ...)]] [AS <select_statement>]
在此,
-
IF NOT EXISTS − 如果尚未创建同名表,此配置可以避免出错。
-
TABLESPACE − 此子句用于分配表空间名称。
-
Storage type − Tajo 数据支持文本、JSON、HBase、Parquet、序列文件和 ORC 等格式。
-
AS select statement − 从另一个表中选择记录。
Configure Tablespace
启动 Hadoop 服务并打开文件 “conf/storage-site.json” ,然后添加以下更改 −
$ vi conf/storage-site.json {
"spaces": {
“space1”: {
"uri": “hdfs://localhost:9000/path/to/Tajo"
}
}
}
在此,Tajo 将引用来自 HDFS 位置的数据, space1 是表空间名称。如果您没有启动 Hadoop 服务,则无法注册表空间。
Data formats
Tajo 支持数据格式。让我们详细逐一了解每种格式。
Creating Table
default> create external table customer(id int,name text,address text,age int)
using text with('text.delimiter'=',') location ‘file:/Users/workspace/Tajo/customers.csv’;
在此, “customers.csv” 文件引用位于 Tajo 安装目录中的逗号分隔值文件。
要使用文本格式创建内部表,请使用以下查询 −
default> create table customer(id int,name text,address text,age int) using text;
在上述查询中,您尚未分配任何表空间,因此它将使用 Tajo 的默认表空间。
JSON
Apache Tajo 支持 JSON 格式来查询数据。Tajo 将 JSON 对象视为 SQL 记录。一个对象等于 Tajo 表中的一行。让我们考虑“array.json”如下 −
$ hdfs dfs -cat /json/array.json {
"num1" : 10,
"num2" : "simple json array",
"num3" : 50.5
}
在创建此文件后,切换到 Tajo shell,然后键入以下查询,以使用 JSON 格式创建表。
Apache Tajo - SQL Statements
在上一章中,您已经了解如何在 Tajo 中创建表。本章说明 Tajo 中的 SQL 语句。
Create Table Statement
在转移到创建表之前,请按如下方法在 Tajo 安装目录路径中创建一个文本文件“students.csv” −
students.csv
Id |
Name |
Address |
Age |
Marks |
1 |
Adam |
23 New Street |
21 |
90 |
2 |
Amit |
12 Old Street |
13 |
95 |
3 |
Bob |
10 Cross Street |
12 |
80 |
4 |
David |
15 Express Avenue |
12 |
85 |
5 |
Esha |
20 Garden Street |
13 |
50 |
6 |
Ganga |
25 North Street |
12 |
55 |
7 |
Jack |
2 Park Street |
12 |
60 |
8 |
Leena |
24 South Street |
12 |
70 |
9 |
Mary |
5 West Street |
12 |
75 |
10 |
Peter |
16 Park Avenue |
12 |
95 |
在文件创建后,转到终端并逐个启动 Tajo 服务器和 Shell。
Create Database
使用以下命令创建新数据库 −
Query
default> create database sampledb;
OK
连接到刚刚创建的数据库“sampledb”。
default> \c sampledb
You are now connected to database "sampledb" as user “user1”.
然后,按如下方法在“sampledb”中创建表 −
Insert Table Statement
Tajo 使用以下语法将记录插入表。
Syntax
create table table1 (col1 int8, col2 text, col3 text);
--schema should be same for target table schema
Insert overwrite into table1 select * from table2;
(or)
Insert overwrite into LOCATION '/dir/subdir' select * from table;
Tajo 的插入语句与 SQL 的 INSERT INTO SELECT 语句类似。
Add Column
如需在“students”表中插入新列,请键入以下语法 −
Alter table <table_name> ADD COLUMN <column_name> <data_type>
Set Property
此属性用于更改表的属性。
Query
sampledb> ALTER TABLE students SET PROPERTY 'compression.type' = 'RECORD',
'compression.codec' = 'org.apache.hadoop.io.compress.Snappy Codec' ;
OK
在此,分配压缩类型和编解码器属性。
如需更改文本分隔符属性,请使用以下 −
Result
上述查询将生成以下结果。
sampledb> \d students
table name: sampledb.students
table uri: file:/tmp/tajo-user1/warehouse/sampledb/students
store type: TEXT
number of rows: 10
volume: 228 B
Options:
'compression.type' = 'RECORD'
'timezone' = 'Asia/Kolkata'
'text.null' = '\\N'
'compression.codec' = 'org.apache.hadoop.io.compress.SnappyCodec'
'text.delimiter' = ','
schema:
id INT4
name TEXT
addr TEXT
age INT4
mark INT4
grade TEXT
以上结果显示可以使用“SET”属性来更改表的属性。
Select Statement
SELECT 语句用于从数据库中选择数据。
Select 语句的语法如下 -
SELECT [distinct [all]] * | <expression> [[AS] <alias>] [, ...]
[FROM <table reference> [[AS] <table alias name>] [, ...]]
[WHERE <condition>]
[GROUP BY <expression> [, ...]]
[HAVING <condition>]
[ORDER BY <expression> [ASC|DESC] [NULLS (FIRST|LAST)] [, …]]
Order By Clause
ORDER BY 子句用于根据一列或多列以升序或降序对数据进行排序。Tajo 数据库默认按升序对查询结果进行排序。
Create Index Statement
CREATE INDEX 语句用于在表中创建索引。索引用于快速检索数据。当前版本仅支持存储在 HDFS 上的纯文本格式的索引。
Result
上述查询将生成以下结果。
id
———————————————
要查看已为该列分配的索引,请键入以下查询。
default> \d mytable
table name: default.mytable
table uri: file:/Users/deiva/workspace/Tajo/students.csv
store type: TEXT
number of rows: unknown
volume: 307 B
Options:
'timezone' = 'Asia/Kolkata'
'text.null' = '\\N'
'text.delimiter' = ','
schema:
id INT4
name TEXT
address TEXT
age INT4
mark INT4
Indexes:
"student_index" TWO_LEVEL_BIN_TREE (id ASC NULLS LAST )
此处,TWO_LEVEL_BIN_TREE 方法在 Tajo 中默认使用。
Aggregate & Window Functions
本章详细说明了聚合和窗口函数。
Aggregation Functions
聚合函数从一组输入值生成单个结果。下表详细描述了聚合函数列表。
S.No. |
Function & Description |
1 |
AVG(exp) 对数据源中所有记录的列求平均值。 |
2 |
CORR(expression1, expression2) 返回一组数值对之间的相关系数。 |
3 |
COUNT()Returns the number rows. |
4 |
MAX(expression) 返回所选列的最大值。 |
5 |
MIN(expression) 返回所选列的最小值。 |
6 |
SUM(expression) 返回给定列的总和。 |
7 |
LAST_VALUE(expression) 返回给定列的最后值。 |
Window Function
窗口函数针对一组行执行,并为查询中的每一行返回一个单值。术语窗口表示供函数使用的行集。
查询中的窗口函数使用 OVER() 子句定义窗口。
OVER() 子句具有以下功能 −
-
定义窗口分区,以便形成行组。(PARTITION BY 子句)
-
对分区中的行进行排序。(ORDER BY 子句)
下表详细描述了窗口函数。
Function |
Return type |
Description |
int |
返回当前行的等级(带间隙)。 |
|
int |
返回它所在分区中的当前行,从 1 开始计数。 |
|
Same as input type |
返回当前行所在分区内,根据偏移行数,对行求值的结果。如果不存在这样的行,则将返回默认值。 |
|
Same as input type |
返回当前行所在分区内,根据偏移行数,对行求值的结果。 |
|
Same as input type |
返回输入行的第一个值。 |
|
Same as input type |
返回输入行的最后一个值。 |
Apache Tajo - SQL Queries
本章解释了以下重要的查询。
-
Predicates
-
Explain
-
Join
让我们继续并执行查询。
Predicates
谓词是一种用于评估 true/false 值和 UNKNOWN 的表达式。谓词用于 WHERE 子句和 HAVING 子句以及需要布尔值的其他结构的搜索条件中。
IN predicate
确定要测试的表达式的值是否与子查询或列表中的任何值匹配。子查询是一个普通的 SELECT 语句,其结果集为一列一或多行。此列或列表中的所有表达式必须与要测试的表达式具有相同的数据类型。
Syntax
IN::=
<expression to test> [NOT] IN (<subquery>)
| (<expression1>,...)
Query
select id,name,address from mytable where id in(2,3,4);
Result
上述查询将生成以下结果。
id, name, address
-------------------------------
2, Amit, 12 old street
3, Bob, 10 cross street
4, David, 15 express avenue
该查询返回 mytable 中 id 为 2、3 和 4 的学生的记录。
Query
select id,name,address from mytable where id not in(2,3,4);
Result
上述查询将生成以下结果。
id, name, address
-------------------------------
1, Adam, 23 new street
5, Esha, 20 garden street
6, Ganga, 25 north street
7, Jack, 2 park street
8, Leena, 24 south street
9, Mary, 5 west street
10, Peter, 16 park avenue
上述查询返回来自 mytable 的记录,其中学生不在 2、3 和 4 中。
Like Predicate
LIKE 谓词比较第一个表达式中为计算字符串值而指定字符串(称为要测试的值)与在第二个字符串中定义的模式,用于计算字符串值。
该模式可包含任何形式的通配符,例如:
-
下划线符号(_),可用于替换要测试的值中的任何单个字符。
-
百分比符号(%),可替换要测试的值中的零个或多个字符的任何字符串。
Syntax
LIKE::=
<expression for calculating the string value>
[NOT] LIKE
<expression for calculating the string value>
[ESCAPE <symbol>]
Query
select * from mytable where name like ‘A%';
Result
上述查询将生成以下结果。
id, name, address, age, mark
-------------------------------
1, Adam, 23 new street, 12, 90
2, Amit, 12 old street, 13, 95
查询返回那些以“A”开头的学生姓名,来自 mytable 的记录。
Query
select * from mytable where name like ‘_a%';
Result
上述查询将生成以下结果。
id, name, address, age, mark
——————————————————————————————————————-
4, David, 15 express avenue, 12, 85
6, Ganga, 25 north street, 12, 55
7, Jack, 2 park street, 12, 60
9, Mary, 5 west street, 12, 75
查询返回那些以“a ”为第二个字符开头的学生姓名,来自 mytable 的记录。
Using NULL Value in Search Conditions
现在让我们了解如何在搜索条件中使用 NULL 值。
Syntax
Predicate
IS [NOT] NULL
Query
select name from mytable where name is not null;
Result
上述查询将生成以下结果。
name
-------------------------------
Adam
Amit
Bob
David
Esha
Ganga
Jack
Leena
Mary
Peter
(10 rows, 0.076 sec, 163 B selected)
在此,结果为 true,故它从表格中返回所有名称。
Query
现在让我们检查带有 NULL 条件的查询。
default> select name from mytable where name is null;
Result
上述查询将生成以下结果。
name
-------------------------------
(0 rows, 0.068 sec, 0 B selected)
Explain
Explain 用于获取查询执行计划。它显示了语句的逻辑和全局计划执行。
Logical Plan Query
explain select * from mytable;
explain
-------------------------------
=> target list: default.mytable.id (INT4), default.mytable.name (TEXT),
default.mytable.address (TEXT), default.mytable.age (INT4), default.mytable.mark (INT4)
=> out schema: {
(5) default.mytable.id (INT4), default.mytable.name (TEXT), default.mytable.address (TEXT),
default.mytable.age (INT4), default.mytable.mark (INT4)
}
=> in schema: {
(5) default.mytable.id (INT4), default.mytable.name (TEXT), default.mytable.address (TEXT),
default.mytable.age (INT4), default.mytable.mark (INT4)
}
Result
上述查询将生成以下结果。
查询结果显示了给定表的逻辑计划格式。逻辑计划返回以下三个结果:
-
Target list
-
Out schema
-
In schema
Global Plan Query
explain global select * from mytable;
explain
-------------------------------
-------------------------------------------------------------------------------
Execution Block Graph (TERMINAL - eb_0000000000000_0000_000002)
-------------------------------------------------------------------------------
|-eb_0000000000000_0000_000002
|-eb_0000000000000_0000_000001
-------------------------------------------------------------------------------
Order of Execution
-------------------------------------------------------------------------------
1: eb_0000000000000_0000_000001
2: eb_0000000000000_0000_000002
-------------------------------------------------------------------------------
=======================================================
Block Id: eb_0000000000000_0000_000001 [ROOT]
=======================================================
SCAN(0) on default.mytable
=> target list: default.mytable.id (INT4), default.mytable.name (TEXT),
default.mytable.address (TEXT), default.mytable.age (INT4), default.mytable.mark (INT4)
=> out schema: {
(5) default.mytable.id (INT4), default.mytable.name (TEXT),default.mytable.address (TEXT),
default.mytable.age (INT4), default.mytable.mark (INT4)
}
=> in schema: {
(5) default.mytable.id (INT4), default.mytable.name (TEXT), default.mytable.address (TEXT),
default.mytable.age (INT4), default.mytable.mark (INT4)
}
=======================================================
Block Id: eb_0000000000000_0000_000002 [TERMINAL]
=======================================================
(24 rows, 0.065 sec, 0 B selected)
Result
上述查询将生成以下结果。
在此,全局计划显示执行块 ID、执行顺序及其信息。
Joins
SQL 连接用于将来自两个或多个表的行合并在一起。以下是不同类型的 SQL 连接:
-
Inner join
-
{ LEFT | RIGHT | FULL } OUTER JOIN
-
Cross join
-
Self join
-
Natural join
考虑以下两个表,以执行连接操作。
Inner Join
内部连接从两个表中选择所有行,当两个表中的列之间有匹配项时。
Syntax
SELECT column_name(s) FROM table1 INNER JOIN table2 ON table1.column_name = table2.column_name;
Query
default> select c.age,c1.empid from customers c inner join customer_order c1 on c.id = c1.id;
Result
上述查询将生成以下结果。
age, empid
-------------------------------
21, 101
23, 102
22, 103
22, 104
33, 105
查询匹配两个表中的五列。因此,它返回第一个表中匹配的行年龄。
Left Outer Join
左外联接保留“左表”中的所有行,而不管是否有与“右表”中的某行匹配的行。
Query
select c.name,c1.empid from customers c left outer join customer_order c1 on c.id = c1.id;
Result
上述查询将生成以下结果。
name, empid
-------------------------------
customer1, 101
customer2, 102
customer3, 103
customer4, 104
customer5, 105
customer6,
在此示例中,左外联接返回来自 customers(左表)表的 name 列行和来自 customer_order(右表)表中的 empid 列匹配的行。
Right Outer Join
右外联接保留“右表”中的所有行,而不管是否有与“左表”中的某行匹配的行。
Query
select c.name,c1.empid from customers c right outer join customer_order c1 on c.id = c1.id;
Result
上述查询将生成以下结果。
name, empid
-------------------------------
customer1, 101
customer2, 102
customer3, 103
customer4, 104
customer5, 105
在此示例中,右外联接返回来自 customer_order(右表)表的 empid 行和来自 customers 表的与 name 列匹配的行。
Full Outer Join
全外联接保留来自左表和右表的所有行。
Query
select * from customers c full outer join customer_order c1 on c.id = c1.id;
Result
上述查询将生成以下结果。
该查询返回来自 customers 表和 customer_order 表的所有匹配行和不匹配行。
Cross Join
这会返回来自两个或更多联接表的记录集的笛卡尔积。
Syntax
SELECT * FROM table1 CROSS JOIN table2;
Query
select orderid,name,address from customers,customer_order;
Result
上述查询将生成以下结果。
上述查询返回表的笛卡尔积。
Natural Join
自然联接未使用任何比较运算符。它不会像笛卡尔积那样连接。只有当两个关系之间存在至少一个公共属性时,我们才能执行自然联接。
Syntax
SELECT * FROM table1 NATURAL JOIN table2;
Query
select * from customers natural join customer_order;
Result
上述查询将生成以下结果。
在此示例中,存在列 id,它是这两个表之间的公共属性。使用该公共属性, Natural Join 联接这两个表。
Self Join
SQL 自联接用于将一个表连接到它自身,就像该表是两个表一样,在 SQL 语句中临时重命名至少一个表。
Syntax
SELECT a.column_name, b.column_name...
FROM table1 a, table1 b
WHERE a.common_filed = b.common_field
Query
default> select c.id,c1.name from customers c, customers c1 where c.id = c1.id;
Result
上述查询将生成以下结果。
id, name
-------------------------------
1, customer1
2, customer2
3, customer3
4, customer4
5, customer5
6, customer6
该查询将客户表连接到它自身。
Apache Tajo - Storage Plugins
Tajo 支持多种存储格式。要注册存储插件配置,您应该将更改添加到配置文件 “storage-site.json”。
storage-site.json
结构定义如下 −
{
"storages": {
“storage plugin name“: {
"handler": "${class name}”, "default-format": “plugin name"
}
}
}
每个存储实例均通过 URI 进行标识。
Apache Tajo - Integration with HBase
Apache Tajo 支持 HBase 集成。这使我们能够在 Tajo 中访问 HBase 表。HBase 是一个分布式面向列的数据库,建立在 Hadoop 文件系统之上。它是 Hadoop 生态系统的一部分,提供对 Hadoop 文件系统中数据的随机实时读/写访问。需要执行以下步骤来配置 HBase 集成。
Set Environment Variable
将以下更改添加到“conf/tajo-env.sh”文件中。
$ vi conf/tajo-env.sh
# HBase home directory. It is opitional but is required mandatorily to use HBase.
# export HBASE_HOME = path/to/HBase
在您包含 HBase 路径后,Tajo 将 HBase 库文件设置为类路径。
Create an External Table
使用以下语法创建一个外部表 −
CREATE [EXTERNAL] TABLE [IF NOT EXISTS] <table_name> [(<column_name> <data_type>, ... )]
USING hbase WITH ('table' = '<hbase_table_name>'
, 'columns' = ':key,<column_family_name>:<qualifier_name>, ...'
, 'hbase.zookeeper.quorum' = '<zookeeper_address>'
, 'hbase.zookeeper.property.clientPort' = '<zookeeper_client_port>')
[LOCATION 'hbase:zk://<hostname>:<port>/'] ;
要访问 HBase 表,您必须配置表空间位置。
在此,
-
Table − 设置 hbase 原始表名。如果您想创建一个外部表,该表必须存在于 HBase 上。
-
Columns − 键指 HBase 行键。列条目的数量需要等于 Tajo 表列的数量。
-
hbase.zookeeper.quorum − 设置 zookeeper 仲裁地址。
-
hbase.zookeeper.property.clientPort − 设置 zookeeper 客户机端口。
Query
CREATE EXTERNAL TABLE students (rowkey text,id int,name text)
USING hbase WITH ('table' = 'students', 'columns' = ':key,info:id,content:name')
LOCATION 'hbase:zk://<hostname>:<port>/';
这里,位置路径字段设置 zookeeper 客户机端口 ID。如果您不设置端口,Tajo 将引用 hbase-site.xml 文件的属性。
Create Table in HBase
您可以使用 “hbase shell” 命令启动 HBase 交互 shell,如下面的查询所示。
Query
/bin/hbase shell
Result
上述查询将生成以下结果。
hbase(main):001:0>
Steps to Query HBase
要查询 HBase,您应该完成以下步骤 −
Step 1 − 将以下命令管道化到 HBase shell 中以创建一个 “tutorial” 表。
Query
hbase(main):001:0> create ‘students’,{NAME => ’info’},{NAME => ’content’}
put 'students', ‘row-01', 'content:name', 'Adam'
put 'students', ‘row-01', 'info:id', '001'
put 'students', ‘row-02', 'content:name', 'Amit'
put 'students', ‘row-02', 'info:id', '002'
put 'students', ‘row-03', 'content:name', 'Bob'
put 'students', ‘row-03', 'info:id', ‘003'
Step 2 − 现在,在 hbase shell 中发出以下命令以将数据加载到表中。
main):001:0> cat ../hbase/hbase-students.txt | bin/hbase shell
Step 3 − 现在,返回 Tajo shell 并执行以下命令以查看表的元数据 −
default> \d students;
table name: default.students
table path:
store type: HBASE
number of rows: unknown
volume: 0 B
Options:
'columns' = ':key,info:id,content:name'
'table' = 'students'
schema:
rowkey TEXT
id INT4
name TEXT
Step 4 − 要从表中获取结果,请使用以下查询 −
Query
default> select * from students
Result
上述查询将获取以下结果 −
rowkey, id, name
-------------------------------
row-01, 001, Adam
row-02, 002, Amit
row-03 003, Bob
Apache Tajo - Integration with Hive
Apache Tajo - OpenStack Swift Integration
Swift 是一个分布式且一致的对象/blob 存储。Swift 提供云存储软件,以便您可以使用简单的 API 存储和检索大量数据。Tajo 支持 Swift 集成。
以下是 Swift 集成的前提条件 −
-
Swift
-
Hadoop
Core-site.xml
对 Hadoop “core-site.xml” 文件添加以下更改 −
<property>
<name>fs.swift.impl</name>
<value>org.apache.hadoop.fs.swift.snative.SwiftNativeFileSystem</value>
<description>File system implementation for Swift</description>
</property>
<property>
<name>fs.swift.blocksize</name>
<value>131072</value>
<description>Split size in KB</description>
</property>
这将用于 Hadoop 访问 Swift 对象。完成所有更改后,移动到 Tajo 目录以设置 Swift 环境变量。
Apache Tajo - JDBC Interface
Apache Tajo 提供 JDBC 接口来连接和执行查询。我们可以使用相同的 JDBC 接口从基于 Java 的应用程序连接 Tajo。本节让我们来了解如何使用 JDBC 接口连接 Tajo 并执行我们示例 Java 应用程序中的命令。
Download JDBC Driver
访问以下链接下载 JDBC 驱动程序 − http://apache.org/dyn/closer.cgi/tajo/tajo-0.11.3/tajo-jdbc-0.11.3.jar 。
现在,您的计算机已经下载了“tajo-jdbc-0.11.3.jar”文件。
Connect to Tajo
Apache Tajo 以单个 jar 文件的形式提供 JDBC 驱动程序,并且可以 @ /path/to/tajo/share/jdbc-dist/tajo-jdbc-0.11.3.jar 获得此文件。
连接 Apache Tajo 的连接字符串格式如下−
jdbc:tajo://host/
jdbc:tajo://host/database
jdbc:tajo://host:port/
jdbc:tajo://host:port/database
在此,
-
host − TajoMaster 的主机名。
-
port − 服务器正在监听的端口号。默认端口号为 26002。
-
database − 数据库名称。默认数据库名称为 default。
Java Application
让我们了解一下 Java 应用程序。
Coding
import java.sql.*;
import org.apache.tajo.jdbc.TajoDriver;
public class TajoJdbcSample {
public static void main(String[] args) {
Connection connection = null;
Statement statement = null;
try {
Class.forName("org.apache.tajo.jdbc.TajoDriver");
connection = DriverManager.getConnection(“jdbc:tajo://localhost/default");
statement = connection.createStatement();
String sql;
sql = "select * from mytable”;
// fetch records from mytable.
ResultSet resultSet = statement.executeQuery(sql);
while(resultSet.next()){
int id = resultSet.getInt("id");
String name = resultSet.getString("name");
System.out.print("ID: " + id + ";\nName: " + name + "\n");
}
resultSet.close();
statement.close();
connection.close();
}catch(SQLException sqlException){
sqlException.printStackTrace();
}catch(Exception exception){
exception.printStackTrace();
}
}
}
可以使用以下命令编译和运行该应用程序。
Apache Tajo - Custom Functions
Apache Tajo 支持自定义/用户定义函数 (UDF)。自定义函数可以在 Python 中创建。
自定义函数就是带装饰符 “@output_type(<tajo sql datatype>)” 的普通 Python 函数,如下所示 −
@ouput_type(“integer”)
def sum_py(a, b):
return a + b;
带 UDF 的 Python 脚本可以通过在 “tajosite.xml” 中添加以下配置来注册。
<property>
<name>tajo.function.python.code-dir</name>
<value>file:///path/to/script1.py,file:///path/to/script2.py</value>
</property>
一旦脚本被注册,重新启动集群,UDF 将立即在 SQL 查询中可用,如下所示 −
select sum_py(10, 10) as pyfn;
Apache Tajo 也支持用户定义聚合函数,但不支持用户定义窗口函数。