Hive入门
Posted 杀智勇双全杀
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Hive入门相关的知识,希望对你有一定的参考价值。
Hive入门(一)
Hive与HDFS的数据映射
集群启动
先启动HDFS:
start-dfs.sh
然后启动YARN:
start-yarn.sh
之前已经配置好了Hive,在node3
直接启动即可:
cd /export/server/hive-2.1.0-bin/
bin/hive
Hive对象
上一篇中已经在node1:50070
查看过Hive会在HDFS文件系统中存储各种数据。
数据库
事实上,Hive创建的每个数据库都对应HDFS中的某个目录。目录的名字是:数据库名.db
。
在启动Hive的命令行:
hive> show databases;
OK
default
Time taken: 1.027 seconds, Fetched: 1 row(s)
hive> create database aaa;
OK
Time taken: 0.242 seconds
可以用浏览器在node1:50070
看到:
新建的数据库会存放在之前配置好的仓库路径内。/user/hive/warehouse
是之前配置的仓库路径。
表
每张表会在数据库对应的目录下建立一个与表同名的目录。
在启动Hive的命令行:
hive> select current_database();
OK
default
Time taken: 1.834 seconds, Fetched: 1 row(s)
可以看到当前使用的数据库是default【这是废话。。。之前也只有这个数据库】。
在启动Hive的命令行:
hive> show tables;
OK
tb_house
tb_word
tb_word2
Time taken: 0.041 seconds, Fetched: 3 row(s)
可以看到:
表的数据
表的数据映射的是HDFS上的文件。
进入到目录后可以看到文件(建表时被Hive搬到仓库路径的文件)。
元数据映射
在启动Hive的命令行:
select * from tb_word2
后Hive可以找到这个表对应的数据并展示在命令行。使用ctrl+c
,多按几次结束。exit;
退出hive。
看看mysql中存储了写啥玩意儿:
mysql> show databases;
+--------------------+
| Database |
+--------------------+
| information_schema |
| hivemetadata |
| itcast_shop |
| mysql |
| performance_schema |
+--------------------+
5 rows in set (0.00 sec)
mysql> use hivemetadata
Reading table information for completion of table and column names
You can turn off this feature to get a quicker startup with -A
Database changed
mysql> show tables;
+---------------------------+
| Tables_in_hivemetadata |
+---------------------------+
| AUX_TABLE |
| BUCKETING_COLS |
| CDS |
| COLUMNS_V2 |
| COMPACTION_QUEUE |
| COMPLETED_COMPACTIONS |
| COMPLETED_TXN_COMPONENTS |
| DATABASE_PARAMS |
| DBS |
| DB_PRIVS |
| DELEGATION_TOKENS |
| FUNCS |
| FUNC_RU |
| GLOBAL_PRIVS |
| HIVE_LOCKS |
| IDXS |
| INDEX_PARAMS |
| KEY_CONSTRAINTS |
| MASTER_KEYS |
| NEXT_COMPACTION_QUEUE_ID |
| NEXT_LOCK_ID |
| NEXT_TXN_ID |
| NOTIFICATION_LOG |
| NOTIFICATION_SEQUENCE |
| NUCLEUS_TABLES |
| PARTITIONS |
| PARTITION_EVENTS |
| PARTITION_KEYS |
| PARTITION_KEY_VALS |
| PARTITION_PARAMS |
| PART_COL_PRIVS |
| PART_COL_STATS |
| PART_PRIVS |
| ROLES |
| ROLE_MAP |
| SDS |
| SD_PARAMS |
| SEQUENCE_TABLE |
| SERDES |
| SERDE_PARAMS |
| SKEWED_COL_NAMES |
| SKEWED_COL_VALUE_LOC_MAP |
| SKEWED_STRING_LIST |
| SKEWED_STRING_LIST_VALUES |
| SKEWED_VALUES |
| SORT_COLS |
| TABLE_PARAMS |
| TAB_COL_STATS |
| TBLS |
| TBL_COL_PRIVS |
| TBL_PRIVS |
| TXNS |
| TXN_COMPONENTS |
| TYPES |
| TYPE_FIELDS |
| VERSION |
| WRITE_SET |
+---------------------------+
57 rows in set (0.00 sec)
好吧。。。还不少。。。
先看下DBS
表的内容(Hive支持大小写关键字):
mysql> SELECT * FROM DBS;
+-------+-----------------------+----------------------------------------------+---------+------------+------------+
| DB_ID | DESC | DB_LOCATION_URI | NAME | OWNER_NAME | OWNER_TYPE |
+-------+-----------------------+----------------------------------------------+---------+------------+------------+
| 1 | Default Hive database | hdfs://node1:8020/user/hive/warehouse | default | public | ROLE |
| 6 | NULL | hdfs://node1:8020/user/hive/warehouse/aaa.db | aaa | root | USER |
+-------+-----------------------+----------------------------------------------+---------+------------+------------+
2 rows in set (0.00 sec)
原来这货存储了Hive中所有数据库的信息。
再看下TBLS
表的内容:
mysql> SELECT * FROM TBLS;
+--------+-------------+-------+------------------+-------+-----------+-------+----------+---------------+--------------------+--------------------+
| TBL_ID | CREATE_TIME | DB_ID | LAST_ACCESS_TIME | OWNER | RETENTION | SD_ID | TBL_NAME | TBL_TYPE | VIEW_EXPANDED_TEXT | VIEW_ORIGINAL_TEXT |
+--------+-------------+-------+------------------+-------+-----------+-------+----------+---------------+--------------------+--------------------+
| 1 | 1619879908 | 1 | 0 | root | 0 | 1 | tb_word | MANAGED_TABLE | NULL | NULL |
| 2 | 1619880547 | 1 | 0 | root | 0 | 2 | tb_word2 | MANAGED_TABLE | NULL | NULL |
| 3 | 1619882149 | 1 | 0 | root | 0 | 3 | tb_house | MANAGED_TABLE | NULL | NULL |
+--------+-------------+-------+------------------+-------+-----------+-------+----------+---------------+--------------------+--------------------+
3 rows in set (0.00 sec)
原来这货存储了Hive中所有表的信息。SD_ID
是个神马玩意儿?不妨看看SDS
表:
mysql> SELECT * FROM SDS;
+-------+-------+------------------------------------------+---------------+---------------------------+------------------------------------------------+-------------+------------------------------------------------------------+----------+
| SD_ID | CD_ID | INPUT_FORMAT | IS_COMPRESSED | IS_STOREDASSUBDIRECTORIES | LOCATION | NUM_BUCKETS | OUTPUT_FORMAT | SERDE_ID |
+-------+-------+------------------------------------------+---------------+---------------------------+------------------------------------------------+-------------+------------------------------------------------------------+----------+
| 1 | 1 | org.apache.hadoop.mapred.TextInputFormat | | | hdfs://node1:8020/user/hive/warehouse/tb_word | -1 | org.apache.hadoop.hive.ql.io.HiveIgnoreKeyTextOutputFormat | 1 |
| 2 | 2 | org.apache.hadoop.mapred.TextInputFormat | | | hdfs://node1:8020/user/hive/warehouse/tb_word2 | -1 | org.apache.hadoop.hive.ql.io.HiveIgnoreKeyTextOutputFormat | 2 |
| 3 | 3 | org.apache.hadoop.mapred.TextInputFormat | | | hdfs://node1:8020/user/hive/warehouse/tb_house | -1 | org.apache.hadoop.hive.ql.io.HiveIgnoreKeyTextOutputFormat | 3 |
+-------+-------+------------------------------------------+---------------+---------------------------+------------------------------------------------+-------------+------------------------------------------------------------+----------+
3 rows in set (0.00 sec)
原来SD_ID是个外键。。。
那么真相其实很简单:
所有Hive中数据库、表与HDFS的映射关系都存储在元数据中,Hive服务端会读取元数据找到这张表对应的HDFS数据的路径从而找到该文件。
数据库就是HDFS目录,表也是HDFS目录(数据库目录深一层),表的数据是指向的HDFS文件(再深入一层)。
还可以安装hive-standalone-metastore-3.0.0,这货是Hive的精简版,只保留了Hive中将文件映射为Hive表的功能(阉割了转换为MapReduce的功能)。
Hive转换MapReduce
功能映射
select 1 from 2 where 3 group by 4 having 5 order by 6 limit 7
Hive与MySQL的执行顺序基本一致。。。
1出的内容决定了Hive的SQL执行后再结果中显示的列的字段及对应的内容。
这种完整的SQL语句当然是按五大阶段的MapReduce来跑的。。。
MapReduce阶段 | SQL参数 |
---|---|
Input | 2 |
Map | 1,3 |
Shuffle | 4,6 |
Reduce | 5,7 |
Output | 保存SQL |
由于不一定会保存,Output阶段可能并不会保存到文件。
执行解析
使用exit退出MySQL,重新进入Hive。
hive> explain select region,count(*) as numb from tb_house where region != '浦东' group by region order by numb;
OK
STAGE DEPENDENCIES:
Stage-1 is a root stage
Stage-2 depends on stages: Stage-1
Stage-0 depends on stages: Stage-2
STAGE PLANS:
Stage: Stage-1
Map Reduce
Map Operator Tree:
TableScan
alias: tb_house
Statistics: Num rows: 22259 Data size: 2225948 Basic stats: COMPLETE Column stats: NONE
Filter Operator
predicate: (region <> '浦东') (type: boolean)
Statistics: Num rows: 22259 Data size: 2225948 Basic stats: COMPLETE Column stats: NONE
Group By Operator
aggregations: count()
keys: region (type: string)
mode: hash
outputColumnNames: _col0, _col1
Statistics: Num rows: 22259 Data size: 2225948 Basic stats: COMPLETE Column stats: NONE
Reduce Output Operator
key expressions: _col0 (type: string)
sort order: +
Map-reduce partition columns: _col0 (type: string)
Statistics: Num rows: 22259 Data size: 2225948 Basic stats: COMPLETE Column stats: NONE
value expressions: _col1 (type: bigint)
Reduce Operator Tree:
Group By Operator
aggregations: count(VALUE._col0)
keys: KEY._col0 (type: string)
mode: mergepartial
outputColumnNames: _col0, _col1
Statistics: Num rows: 11129 Data size: 1112923 Basic stats: COMPLETE Column stats: NONE
File Output Operator
compressed: false
table:
input format: org.apache.hadoop.mapred.SequenceFileInputFormat
output format: org.apache.hadoop.hive.ql.io.HiveSequenceFileOutputFormat
serde: org.apache.hadoop.hive.serde2.lazybinary.LazyBinarySerDe
Stage: Stage-2
Map Reduce
Map Operator Tree:
TableScan
Reduce Output Operator
key expressions: _col1 (type: bigint)
sort order: +
Statistics: Num rows: 11129 Data size: 1112923 Basic stats: COMPLETE Column stats: NONE
value expressions: _col0 (type: string)
Reduce Operator Tree:
Select Operator
expressions: VALUE._col0 (type: string), KEY.reducesinkkey0 (type: bigint)
outputColumnNames: _col0, _col1
Statistics: Num rows: 11129 Data size: 1112923 Basic stats: COMPLETE Column stats: NONE
File Output Operator
compressed: false
Statistics: Num rows: 11129 Data size: 1112923 Basic stats: COMPLETE Column stats: NONE
table:
input format: org.apache.hadoop.mapred.SequenceFileInputFormat
output format: org.apache.hadoop.hive.ql.io.HiveSequenceFileOutputFormat
serde: org.apache.hadoop.hive.serde2.lazy.LazySimpleSerDe
Stage: Stage-0
Fetch Operator
limit: -1
Processor Tree:
ListSink
Time taken: 2.284 seconds, Fetched: 69 row(s)
其中,explain
是用于查看执行计划的,换句话说,explain开头的供Hive执行的SQL语句并不会真正运行并计算,只是展示下预期的运行过程。<>
代表不等于。
此例中显示总共会划分为3步。运行次序有严格的依赖性,必须先运行Stage-1
(使用了region作K2),然后是Stage-2
,最后是Stage-0
。_col0
, _col1
则是个数。
metastore
功能
metastore字面意思就是元数据存储。
Hive中的元数据记录了Hive中所有对象信息:数据库信息、表信息、字段信息。
Hive中的元数据重点记录了Hive表与HDFS文件的映射关系。每次创建表关联文件,Hive都会自动创建表的元数据。每次查询表的数据,Hive都会从元数据中获取表对应的HDFS信息。
三种方式
嵌入式数据库
Local/Embedded Metastore Database (Derby),存储在derby中。Apache Derby是个完全用java编写的数据库,类似sqlite,免配置C/S即可使用。
本地数据库
存储在本地MySQL中,直接访问。
远程Metastore服务
存储在MySQL中,但是是通过一个进程来进行访问。
两个位置
默认位置
Hive自带的Derby数据库。不能共享,不能启动多个实例,一般不用。
自定义位置
自定义将元数据存储在其他数据库中。MySQL、Oracle之类的普通数据库都可以,∵MySQL免费,∴一般存储在MySQL中。
共享
Hive默认是转换为MapReduce程序,但是眼下MapReduce性能堪忧将近淘汰,显然大概率不会使用Hive来实现数据仓库中的分布式计算。SparkSQL、Impala、Presto等工具更快,性能更好,语法都兼容Hive的语法,应该让这些更先进的框架能够访问Hive的数据。
只需要读取Hive元数据就能知道Hive有哪些表,中间可能需要解析元数据。但是很多框架都需要访问Hive的元数据,都自行封装代码解析元数据就会导致程序冗余。
metastore服务
Java有JDBC
访问数据库,C#可以使用ADO.NET
和ASP.NET
访问SQL server
,Hive则是提供了metastore服务
来实现元数据共享服务。metastore服务专门负责管理Hive的元数据,并且接受所有需要访问元数据的请求。
metastore配置
为了避免出错,先quit;
退出Hive,然后关掉多余的进程。jps
查看3个节点确保进程杀干净。
stop-dfs.sh
stop-yarn.sh
没有杀掉的进程可以考虑kill -9
。
cd /export/server/hive-2.1.0-bin/conf
vim hive-site.xml
找个空位按o
向下插入:
<property>
<name>hive.metastore.uris</name>
<value>thrift://node3:9083</value>
</property>
记得:wq
保存。这一步设置了metastore
是通过node3的9083端口
访问。
metastore启动
由于配置了Metastore,Hive已经不再能够直接访问MySQL中的元数据,以后必须先启动metastore,再启动Hive的服务端。
不服可以试试直接启动Hive,会报错:
Caused by: java.net.ConnectException: 拒绝连接 (Connection refused)
metastore服务已经不再允许Hive自行连接MySQL访问元数据,它要全权管理。
老老实实正常启动:
cd /export/server/hive-2.1.0-bin/
hive --service metastore
有时候一次启动不成功,只好多来几次。。。
由于这货是个前台程序,会一直霸占命令行。。。没办法操作了。。。先去虚拟机:
手敲一遍。。。先把Hive启动。或者新建个命令行窗口启动。当然还是启动不了的!!!
使用:
netstat -atunlp |grep 9083
发现metastore服务启动成功:
[root@node3 hive-2.1.0-bin]# netstat -atunlp |grep 9083
tcp 0 0 0.0.0.0:9083 0.0.0.0:* LISTEN 3820/java
仔细检查,是报错:
The reported blocks 50 has reached the threshold 0.9990 of total blocks 50. The number of live datanodes 3 has reached the minimum number 0. In safe mode extension. Safe mode will be turned off automatically in 2 seconds.
不开启HDFS和YARN就会因为分布式存储空间达到0.9990以上的占有率【这句话当然是废话。。。】,从而不能写入HDFS文件,只好进入了安全模式。。。
启动HDFS:
start-dfs.sh
启动YARN:
start-yarn.sh
要多等一会儿。。。然后使用Hive
命令即可成功启动Hive。
虚拟机使用jps查看进程:
发现有2个RunJar,一个5265,一个3820。显然3820的这个RunJar先启动,它是metastore服务,5265的RunJar后启动,它是Hive的进程。
一波三折!!!
还有很长的路要走:Hive入门(二)
以上是关于Hive入门的主要内容,如果未能解决你的问题,请参考以下文章
Hive函数入门--案例:UDF实现手机号加密--代码实现与效果演示