介绍
本实验重点介绍 Hive 的配置和基本操作,旨在帮助具有一定 SQL 基础的学生理解 Hive 的架构、基本部署和使用方法。
请自行输入文档中的所有示例代码,尽量不要直接复制粘贴代码。只有这样,你才能更熟悉代码。如果遇到问题,请仔细查阅文档,或者可以前往论坛寻求帮助和交流。
本实验重点介绍 Hive 的配置和基本操作,旨在帮助具有一定 SQL 基础的学生理解 Hive 的架构、基本部署和使用方法。
请自行输入文档中的所有示例代码,尽量不要直接复制粘贴代码。只有这样,你才能更熟悉代码。如果遇到问题,请仔细查阅文档,或者可以前往论坛寻求帮助和交流。
Apache Hive 是一个构建在 Hadoop 之上的数据仓库软件包,用于通过类似 SQL 的查询来查询和分析大规模数据集。它通过为用户提供熟悉的 SQL 接口,简化了大数据的数据聚合、即席查询和分析。以下是 Hive 的架构和关键特性概述:
HCatalog
,以及用于运行 MapReduce 任务、Pig 查询或通过 REST API 与 Hive 元数据交互的 WebHCat
。page_views
表)。Hive 专为数据仓库任务设计,而非在线事务处理(OLTP),重点关注可扩展性、性能、可靠性和容错性。它支持多种输入格式,并可以通过不同格式的连接器进行扩展。理解 Hive 的架构、数据单元和数据类型对于充分利用其在大数据分析中的能力至关重要。
本节重点介绍下载与目录设置、环境变量设置、元数据库配置、Hive 系统参数以及初始化元数据库。
首先,你需要切换到 hadoop
用户以执行后续操作。双击打开桌面上的 Xfce 终端,并输入以下命令:
su - hadoop
提示:用户 hadoop
的密码是 hadoop
。
然后使用 wget
命令下载最新稳定版本的 Hive。这里我们选择了 Hive 的 2.3.3 版本:
sudo wget https://labexfile.oss-us-west-1.aliyuncs.com/courses/144/apache-hive-2.3.3-bin.tar.gz
接下来,你需要解压下载的安装包。在终端中输入以下命令:
tar -zxvf apache-hive-2.3.3-bin.tar.gz
使用 sudo 权限将解压后的目录移动到 /opt
目录。如果不使用 sudo 权限,你可能无法写入 /opt
目录:
sudo mv /home/hadoop/apache-hive-2.3.3-bin /opt/hive-2.3.3
移动目录后,你需要将 Hive 目录的所有者更改为 hadoop
用户及其用户组。请在终端中输入以下命令:
sudo chown -R hadoop:hadoop /opt/hive-2.3.3
提示:你可以打开另一个终端以 sudo 权限执行上述操作。
labex:~/ $ ls -al /opt/
total 24
drwxrwxr-x 10 hadoop hadoop 4096 Mar 3 12:01 hive-2.3.3
...
在目录设置完成后,你需要设置 Hive 的环境变量,以便 HIVE_HOME
指向其安装目录。
首先使用 vim
编辑器打开 hadoop
用户的 .bashrc
文件。在终端中输入以下命令:
vim /home/hadoop/.bashrc
在文件末尾添加以下内容。PATH
需要根据当前实验环境的实际情况进行修改。$PATH
表达式用于引用现有内容。直接在 PATH
环境变量的末尾添加 :$HIVE_HOME/bin
:
export HIVE_HOME=/opt/hive-2.3.3
export PATH=$PATH:$HIVE_HOME/bin
编辑完成后保存文件并退出编辑器。然后使用 source
命令激活上述环境变量。
在本实验中,我们已经预装了 Hive,因此你不需要执行 source
环境变量的操作,但在实际安装中,此步骤需要根据具体情况完成。
这是一个 Hive 配置过程,在此步骤中,你可以仅查看而无需动手操作,因为我们在实验中已经预配置了一个 Hive,并且预安装了 Hive,你可以使用 which hive
命令查看。但文件的创建仍然需要执行,因为这是我们判断你是否通过测试的凭证。
在正式使用 Hive 之前,你需要设置其元数据存储。默认情况下,Hive 将元信息存储在嵌入式 Derby 数据库中。其在磁盘上的存储位置由 Hive 配置文件 conf/hive-default.xml
中的配置项 javax.jdo.option.ConnectionURL
决定。默认情况下,此位置为 ./metastore_db
。
但在本实验中,我们将使用 MySQL 作为元数据的存储。因此,你需要修改 Hive 的配置文件。
使用 vim
编辑器创建并打开此配置文件:
vim /opt/hive-2.3.3/conf/hive-site.xml
<configuration>
<property>
<name>javax.jdo.option.ConnectionURL</name>
<value>jdbc:mysql://localhost:3306/hive_metastore1?createDatabaseIfNotExist=true</value>
</property>
<property>
<name>javax.jdo.option.ConnectionDriverName</name>
<value>com.mysql.cj.jdbc.Driver</value>
</property>
<property>
<name>javax.jdo.option.ConnectionUserName</name>
<value>hiveuser1</value>
</property>
<property>
<name>javax.jdo.option.ConnectionPassword</name>
<value>123qweQWE...</value>
</property>
</configuration>
编辑完上述配置项后,保存文件并退出编辑器。
通过 sudo mysql
启动 MySQL 服务器,并创建数据库 hive_metastore
:
CREATE DATABASE hive_metastore1;
CREATE USER 'hiveuser1'@'localhost' IDENTIFIED BY '123qweQWE...';
GRANT ALL PRIVILEGES ON hive_metastore1.* TO 'hiveuser1'@'localhost';
FLUSH PRIVILEGES;
exit;
然后下载 MySQL JDBC 驱动程序并将其复制到 /opt/hive-2.3.3/lib
目录:
cp /usr/local/hive/lib/mysql-connector-j-8.3.0.jar /opt/hive-2.3.3/lib
在元数据库配置完成后,你需要设置 Hive 的内部配置项,以标识 Hadoop 的位置、内部配置文件路径等。
首先使用 cp
命令复制设置模板以使其生效。请在终端中输入以下命令:
cp /opt/hive-2.3.3/conf/hive-env.sh.template /opt/hive-2.3.3/conf/hive-env.sh
然后使用 vim
编辑器打开 hive-env.sh
文件:
vim /opt/hive-2.3.3/conf/hive-env.sh
在第 48 行,将 HADOOP_HOME
设置为 Hadoop 的安装路径:
HADOOP_HOME=/home/hadoop/hadoop
编辑完上述配置项后,保存文件并退出编辑器。
当所有配置工作完成后,你可以开始初始化元数据库。
由于后续使用的数据将存储在 HDFS 上,你需要提前启动 HDFS。请在终端中输入以下命令以启动 HDFS:
start-dfs.sh
start-yarn.sh
你需要输入 jps
来查看服务状态:
hadoop:~/ $ jps [17:31:43]
8960 Jps
3153 NodeManager
2823 SecondaryNameNode
3017 ResourceManager
2570 DataNode
2428 NameNode
如果你是第一次使用 Hadoop,需要删除 Hadoop 数据并使用 hdfs namenode -format
进行初始化。
在本实验中,我们已经使用预安装的 Hive 初始化了元数据库。当然,如果你想初始化刚刚下载的 Hive,可以使用以下命令:
/opt/hive-2.3.3/bin/schematool -initSchema -dbType mysql
Initialization script completed
schemaTool completed
在这里,如果你是第一次初始化刚刚下载的 Hive,你需要将 ~/.bashrc
中的 HIVE_HOME
路径更改为刚刚安装的 Hive 路径,并执行 source
。我的建议是不要这样做,因为我们后续的 Hive 测试都是基于预安装的 Hive!
当提示信息显示初始化已完成时,你可以使用 hive
命令进入其命令行。请在终端中输入以下命令:
hive
提示:直接输入 hive
会进入我们预安装的 Hive shell,添加绝对路径后你将进入刚刚设置的 Hive shell!
Hive Session ID = 3eee2693-175d-4452-82d2-47f1b639d9d5
Logging initialized using configuration in jar:file:/usr/local/hive/lib/hive-common-3.1.3.jar!/hive-log4j2.properties Async: true
Hive-on-MR is deprecated in Hive 2 and may not be available in the future versions. Consider using a different execution engine (i.e. spark, tez) or using Hive 1.X releases.
Hive Session ID = 68d0d345-92c3-4eb1-8393-7ee34f56363f
hive>
接下来我们将学习 Hive 中的一些基本操作。除了本节中提到的一些操作语句外,所有 Hive 语句都可以在其 语言手册 中找到。你可以在完成本节后尝试更多语句。
首先你需要获取一些数据。本节实验使用的数据主要是模拟 NginX 服务器的日志文件,可用于分析网站的页面浏览量。
请重新打开一个终端,并在终端中输入以下命令以下载示例数据:
su hadoop
cd ~
wget http://labfile.oss-cn-hangzhou.aliyuncs.com/courses/567/log_example.csv
然后将文件上传到 HDFS:
hdfs dfs -mkdir -p /user/data/staging/page_view
hdfs dfs -put /home/hadoop/log_example.csv /user/data/staging/page_view
获取数据后的第一件事是创建表。如果你想为上述数据创建一个 page_view
表,需要在 Hive 命令行中输入以下语句:
CREATE TABLE page_view(viewTime INT, userid BIGINT,
Page_url STRING, referrer_url STRING,
Ip STRING COMMENT 'IP Address of the User')
COMMENT 'This is the page view table'
PARTITIONED BY(dt STRING, country STRING)
STORED AS SEQUENCEFILE;
在此示例中,表中的每一列都被分配了适当的类型。并且,我们可以在列和表级别附加注释。此外,PARTITIONED BY
子句定义了一个与数据列不同的分区列。分区列不与数据列一起存储。当你以这种方式指定分区列时,换行符将用作每行的分隔符。
如果数据不是上述格式,你可以参数化字段分隔符,如下例所示:
以下语句仅用于演示目的,无需在 hive
shell 中输入。
CREATE TABLE page_view1(viewTime INT, userid BIGINT,
Page_url STRING, referrer_url STRING,
Ip STRING COMMENT 'IP Address of the User')
COMMENT 'This is the page view table'
PARTITIONED BY(dt STRING, country STRING)
ROW FORMAT DELIMITED
FIELDS TERMINATED BY '1'
STORED AS SEQUENCEFILE;
由于行分隔符由 Hadoop 系统中的分隔符决定,而不是由 Hive 决定,因此我们无法手动更改行分隔符。
通常,列数据确定的表存储在桶中,这将有助于高效地对数据集查询进行采样。如果没有桶,即使可以完成表的随机采样,也无法在整个数据扫描过程中实现高效采样。以下示例展示了如何在 userid
列上为 page_view
表启用桶存储。
以下语句仅用于演示目的,无需在 hive
shell 中输入。
CREATE TABLE page_view2(viewTime INT, userid BIGINT,
Page_url STRING, referrer_url STRING,
Ip STRING COMMENT 'IP Address of the User')
COMMENT 'This is the page view table'
PARTITIONED BY(dt STRING, country STRING)
CLUSTERED BY(userid) SORTED BY(viewTime) INTO 32 BUCKETS
ROW FORMAT DELIMITED
FIELDS TERMINATED BY '1'
COLLECTION ITEMS TERMINATED BY '2'
MAP KEYS TERMINATED BY '3'
STORED AS SEQUENCEFILE;
在上面的示例中,表中的 userid
列通过哈希函数聚合为 32 个桶。在每个桶中,数据按 viewTime
升序排序。这种组织数据的方法允许用户有效地对聚合列(这里是 userid
列)进行采样,而排序功能使数据管理者能够通过更好的数据结构更高效地评估查询。
以下语句仅用于演示目的,无需在 hive
shell 中输入。
CREATE TABLE page_view3(viewTime INT, userid BIGINT,
Page_url STRING, referrer_url STRING,
Friends ARRAY<BIGINT>, properties MAP<STRING, STRING>,
Ip STRING COMMENT 'IP Address of the User')
COMMENT 'This is the page view table'
PARTITIONED BY(dt STRING, country STRING)
CLUSTERED BY(userid) SORTED BY(viewTime) INTO 32 BUCKETS
ROW FORMAT DELIMITED
FIELDS TERMINATED BY '1'
COLLECTION ITEMS TERMINATED BY '2'
MAP KEYS TERMINATED BY '3'
STORED AS SEQUENCEFILE;
在上面的示例中,表中每行的格式是根据字段名称和类型定义的,与其他编程语言中的类型定义非常相似。请注意,表名和列名不区分大小写。IP Address of the User
和下面的 COMMENT
语句表明我们可以在列和表级别添加注释。此外,PARTITIONED BY
子句定义了与数据列不同的分区列。如前所述,实际上它们并不存储数据。CLUSTERED BY
子句指定使用哪一列来创建多少个桶。ROW FORMAT DELIMITED
子句指定如何在 Hive 表中存储行。对于分隔格式,此语句指定如何确定字段的终止符号、集合(数组或映射)中项目的终止符号以及确定映射键的终止符号,其中数字采用 ASCII 编码。STORED AS SEQUENCEFILE
表示数据以二进制格式(特别是 Hadoop 的 SequenceFile
类型)存储在 HDFS 上。其中,ROW FORMAT
和 STORED AS
子句中的设置是 Hive 当前使用的默认值。因此,我们在最初创建表的语句中没有明确写出它们。
如果你想列出仓库中的现有表,可以使用以下语句:
SHOW TABLES;
如果有很多表,上述语句将生成大量返回信息。你可以通过指定前缀来缩小范围。例如,如果你想列出前缀为 page
的表,可以使用以下语句:
SHOW TABLES 'page.*';
此语句中的匹配规则与正则表达式语法相同,句点(.
)表示通配符。
如果你想列出表的分区,请使用以下语句。如果表不是分区表,则不会返回任何信息:
SHOW PARTITIONS page_view;
如果你想列出表的列和列类型,可以使用 DESCRIBE
语句:
DESCRIBE page_view;
如果你想列出表的列和所有其他属性,需要添加 EXTENDED
关键字。这将打印大量信息,通常用于调试:
DESCRIBE EXTENDED page_view;
如果你想重命名现有表,请使用带有 RENAME TO
的 ALTER TABLE
语句。如果已存在具有新名称的表,则会返回错误:
ALTER TABLE page_view RENAME TO new_page_view;
查看结果:
hive> ALTER TABLE page_view RENAME TO new_page_view;
OK
Time taken: 0.124 seconds
hive> show tables;
OK
new_page_view
...
Time taken: 0.021 seconds, Fetched: 4 row(s)
我们还可以重命名现有表的列。但需要注意的是,你必须使用相同的列类型,并在每个现有列中包含一条记录:
ALTER TABLE new_page_view REPLACE COLUMNS (viewTime INT, userid BIGINT, page_url STRING, referrer_url STRING, ipaddr STRING COMMENT 'IP Address of the User');
此外,你可以向现有表添加新列:
ALTER TABLE new_page_view ADD COLUMNS (new_column INT COMMENT 'a new int column');
请注意,模式中的更改(例如添加列)将保留表的旧分区的模式,以防止其成为分区表。所有访问这些列并在旧分区上运行的查询都会隐式返回这些列的 null 值或指定的默认值。
由于 Hive 被设计为数据仓库,数据的销毁始终是负面的。因此,删除表的操作有点繁琐。在表上使用 DROP
命令将隐式删除在该表上构建的任何索引。
你可以使用以下命令删除表:
DROP TABLE new_page_view;
在 Hive 中,加载数据和查询数据是两个不同的操作。本文档描述了如何将数据加载到 Hive 表中。
有几种方法可以将数据加载到 Hive 表中。用户可以创建指向 HDFS 中特定位置的外部表。在这种用法中,用户可以使用 HDFS 的 put
或 copy
命令将数据文件复制到指定位置,并创建一个指向该位置的表。该表将包含所有相关的 行格式 信息。
创建完成后,用户可以转换数据并将其插入到任何其他 Hive 表中。我们一开始就将 log_example.csv
文件上传到 HDFS 并将其重命名为 page_view
。如果我们想将其加载到相应分区的 page_view
表中,可以使用以下命令。
首先创建一个外部表并将其与指定文件关联:
CREATE EXTERNAL TABLE page_view_stg(viewTime INT, userid BIGINT,
Page_url STRING, referrer_url STRING,
Ip STRING COMMENT 'IP Address of the User',
Country STRING COMMENT 'country of origin')
COMMENT 'This is the staging page view table'
ROW FORMAT DELIMITED FIELDS TERMINATED BY '44' LINES TERMINATED BY '\n' STORED AS TEXTFILE
LOCATION '/user/data/staging/page_view';
然后创建一个 page_view
表用于数据的最终存储:
CREATE TABLE page_view(viewTime INT, userid BIGINT,
Page_url STRING, referrer_url STRING,
Ip STRING COMMENT 'IP Address of the User')
COMMENT 'This is the page view table'
PARTITIONED BY(dt STRING, country STRING)
STORED AS SEQUENCEFILE;
最后,将数据从外部表插入到 page_view
表中:
FROM page_view_stg pvs
INSERT OVERWRITE TABLE page_view
PARTITION(dt='2015-05-17', country='us')
SELECT pvs.viewTime, pvs.userid, pvs.page_url, pvs.referrer_url, pvs.ip
WHERE pvs.country = 'us';
数据加载到 HDFS 然后再加载到 page_view
表可能需要几分钟时间。
...
Loading data to table default.page_view partition (dt=2015-05-17, country=us)
MapReduce Jobs Launched:
Stage-Stage-1: Map: 1 Reduce: 1 Cumulative CPU: 6.31 sec HDFS Read: 369021 HDFS Write: 22943 SUCCESS
Total MapReduce CPU Time Spent: 6 seconds 310 msec
OK
Time taken: 25.304 seconds
插入数据后,我们可以进行简单的查询。这与常见的 SQL 语句类似。在 Hive 命令行界面中输入以下语句:
SELECT * FROM page_view WHERE userid = 0 LIMIT 10;
返回的信息是查询到的记录:
hive> select * from page_view;
OK
NULL 490 /downloads/product_1 /archives/webroot 217.168.17.5 2015-05-17 us
NULL 490 /downloads/product_2 /archives/webroot 217.168.17.5 2015-05-17 us
NULL 3316 /downloads/product_2 /archives/webroot 217.168.17.5 2015-05-17 us
...
如果你想了解更多 Hive 操作语句,可以阅读以下扩展内容:
当你使用完毕后,可以使用 quit
命令退出 Hive 命令行界面:
quit;
当然,别忘了关闭 HDFS 服务。在终端中输入以下命令:
stop-yarn.sh
stop-dfs.sh
本节介绍了 Hive 的架构、安装部署以及基本的 HQL 语句。同时,我们还学习了如何使用示例数据进行数据导入。
提到的主要内容有:
总的来说,作为一个数据仓库软件包,Hive 的功能需要进一步探索。请保持主动查阅技术资料的习惯,并继续学习以下课程。