1 Hive的数据导入
1.1 使用load语句
语法
LOAD DATA [LOCAL] INPATH ‘filepath’ [OVERWRITE]
INTO TABLE tablename [PARTITION (partcoll=val1,partcol2=val2…)]
说明:
[LOCAL] 是否从linux本地去取文件。加上local是从linux读取文件,不加local是从hdfs中读取文件
[OVERWRITE] 是否要覆盖表中原来的数据
示例:
将student01.txt数据导入t3表
hive> load data local inpath '/root/hadoop_practice/student01.txt' into table t3;
将/root/hadoop_practice下所有的数据文件导入到t3表中,并且覆盖原来的数据
hive> load data local inpath '/root/hadoop_practice/' overwrite into table t3;
将HDFS中,/student/student01.txt 导入到t3表
hive> load data inpath '/student/student01.txt' overwrite into table t3;
1.2 使用sqoop导入数据
1.2.1 安装配置sqoop
官网下载sqoop
wget https://mirrors.tuna.tsinghua.edu.cn/apache/sqoop/1.4.6/sqoop-1.4.6.bin__hadoop-0.23.tar.gz
解压
tar -zxvf sqoop-1.4.6.bin__hadoop-0.23.tar.gz
配置变量(配置Hadoop的环境变量)
export HADOOP_COMMON_HOME=/usr/hadoop/hadoop-2.7.4/
export HADOOP_MAPRED_HOME=/usr/hadoop/hadoop-2.7.4/
复制jdbc驱动到sqoop-1.4.6.bin__hadoop-0.23/lib下
cp /usr/share/java/mysql-connector-java.jar /root/sqoop-1.4.6.bin__hadoop-0.23/lib
1.2.2 利用sqoop将mysql中的表导入的hdfs中
将mysql数据库中的user表导入到hdfs中的/sqoop/user下
./sqoop import --connect jdbc:mysql://192.168.162.177:3306/mysql --username root --password root --table user -m 1 --target-dir '/sqoop/user'
注意:jdbc:mysql://192.168.162.177:3306/mysql 中不要使用localhost,使用ip地址
导出完成后生成的hdfs文件
内容:
1.2.2 利用sqoop将mysql中的表导入的Hive中 ,并制定表名
问题:为什么当hive中表名为user的时候,无法对user表进行操作?
./sqoop import --hive-import --connect jdbc:mysql://192.168.162.177:3306/mysql --username root --password root --table user -m 1 --columns 'User,Password' --hive-table user1
1.2.3 利用sqoop将mysql中的表导入到Hive中,并使用where条件
./sqoop import --hive-import --connect jdbc:mysql://192.168.162.177:3306/mysql --username root --password root --table user -m 1 --columns 'Host,User,Password' --hive-table user2 --where "Host='localhost'";
注意:条件语句的引号
1.2.4 利用sqoop将mysql中的表导入到Hive中,并使用查询语句
问题:(未解决) 条件查询不到,总是报错
./sqoop import --hive-import --connect jdbc:mysql://192.168.162.177:3306/mysql --username root --password root -m 1 --query 'SELECT * FROM user WHERE Host="localhost" AND $CONDITIONS ' --target-dir '/sqoop/user3' --hive-table user3;
1.2.5 利用sqoop将hive中的数据导入mysql
问题:数据类型不匹配 string
./sqoop export --connect jdbc:mysql://192.168.162.177:3306/mysql --username root --password root -m 1 --table t3 --export-dir /user/hive/warehouse/t3;
2 Hive的数据查询
2.1 基础查询
2.2 简单查询的Fetch Task 功能。
配置方式:
- set hive.fetch.task.conversion=more;
- hive –hiveconf hive.fetch.task.conversion=more
- 修改hive-site.xml文件
2.3 在查询中使用过滤
2.4 在查询中使用排序 ORDER BY
3 Hive 中的函数
内置函数 自定义函数
3.1 数学函数
round(reg1,reg2)
reg1 表示要处理的数据
reg2 表示保留小数点后的位数
hive> select round(45.926,2),round(45.926,1),round(45.926,0),round(45.926,-1),round(45.926,-2);
OK
45.93 45.9 46 50 0
Time taken: 1.646 seconds, Fetched: 1 row(s)
hive> select ceil(45.9);
OK
46
Time taken: 0.275 seconds, Fetched: 1 row(s)
hive> select floor(45.9);
OK
45
Time taken: 0.732 seconds, Fetched: 1 row(s)
3.2 字符函数
hive> select lower('Hello World');
OK
hello world
Time taken: 0.626 seconds, Fetched: 1 row(s)
hive> select upper('Hello World');
OK
HELLO WORLD
Time taken: 0.67 seconds, Fetched: 1 row(s)
hive> select length('Hello World');
OK
11
Time taken: 0.251 seconds, Fetched: 1 row(s)
hive> select concat ('Hello','World');
OK
HelloWorld
Time taken: 0.703 seconds, Fetched: 1 row(s)
补充: 与java中的substring、js中的substring、substr区别
java和js中都有substring方法用来截取字符串
用法:字符串.substring(起始位置从零开始、结束位置)
js中有substr方法
用法: 字符串.substr(起始位置从零开始、截取长度)
substr(a,b) 从a中,第b位开始取,取右边所有的字符串
substr(a,b,c) 从a中,第b位开始取,取右边c个字符串
hive> select substr('Hello world',3);
OK
llo world
Time taken: 0.676 seconds, Fetched: 1 row(s)
hive> select trim(' Hello World' );
OK
Hello World
Time taken: 0.337 seconds, Fetched: 1 row(s)
hive> select lpad('abc',10,'*');
OK
*******abc
Time taken: 0.625 seconds, Fetched: 1 row(s)
hive> select rpad('abc',10,'*');
OK
abc*******
Time taken: 0.663 seconds, Fetched: 1 row(s)
3.2 收集函数
hive> select size(map(1,'Tom',2,'Mary'));
OK
2
Time taken: 0.853 seconds, Fetched: 1 row(s)
3.3 转换函数
hive> select cast(1 as bigint);
OK
1
Time taken: 0.373 seconds, Fetched: 1 row(s)
hive> select cast(1 as float);
OK
1.0
Time taken: 0.669 seconds, Fetched: 1 row(s)
3.4 日期函数
hive> select to_date('2017-11-23 16:48:21');
OK
2017-11-23
Time taken: 0.711 seconds, Fetched: 1 row(s)
hive> select year('2017-11-23 16:48:21');
OK
2017
Time taken: 0.647 seconds, Fetched: 1 row(s)
hive> select month('2017-11-23 16:48:21');
OK
11
Time taken: 0.413 seconds, Fetched: 1 row(s)
hive> select day('2017-11-23 16:48:21');
OK
23
Time taken: 0.174 seconds, Fetched: 1 row(s)
hive> select weekofyear('2017-11-23 16:48:21');
OK
47
Time taken: 0.688 seconds, Fetched: 1 row(s)
hive> select datediff('2017-11-23 16:48:21','2014-11-23 17:00:52');
OK
1096
Time taken: 0.306 seconds, Fetched: 1 row(s)
hive> select date_add('2017-11-23 16:48:21',2);
OK
2017-11-25
Time taken: 0.216 seconds, Fetched: 1 row(s)
hive> select date_sub('2017-11-23 16:48:21',2);
OK
2017-11-21
Time taken: 0.614 seconds, Fetched: 1 row(s)
3.5 条件函数
3.6 聚合函数
3.7 表生成函数
hive> select explode(map(1,'Tom',2,'Mary',3,'Mell'));
OK
1 Tom
2 Mary
3 Mell
Time taken: 0.36 seconds, Fetched: 3 row(s)
5 Hive 表连接
6 Hive 子查询
7 Hive的Java客户端和自定义函数
7.1 启动Hive远程服务
hiveserver2
7.2 JDBC 客户端
7.3 代码实现
7.3.1 IDEA使用Maven创建一个项目
7.3.2 pom引入依赖
<dependencies>
<!--日志依赖-->
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>1.7.12</version>
</dependency>
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-core</artifactId>
<version>1.1.1</version>
</dependency>
<!--实现slf4j接口并整合-->
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
<version>1.1.1</version>
</dependency>
<!--hive jdbc 依赖-->
<dependency>
<groupId>org.apache.hive</groupId>
<artifactId>hive-jdbc</artifactId>
<version>2.3.2</version>
</dependency>
</dependencies>
引入依赖之后Reimport maven project
7.3.3 配置logback日志
在resource下创建logback.xml
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<jmxConfigurator/>
<!--
将日志打印到控制台
-->
<appender name="console" class="ch.qos.logback.core.ConsoleAppender">
<layout class="ch.qos.logback.classic.PatternLayout">
<Pattern>%date [%thread] %-5level %logger{25} - %msg%n</Pattern>
</layout>
</appender>
<!--
level:设置日志级别,大小写无关:TRACE, DEBUG, INFO, WARN, ERROR, ALL 和 OFF,不能设置为INHERITED或者同义词NULL。默认是DEBUG
ref:日志信息交给已经配置好的名为"console"的appender处理,appender将信息打印到控制台
-->
<root level="INFO">
<appender-ref ref="console"/>
</root>
</configuration>
7.3.4 创建jdbc连接工具类
在java下创建 org.hive.demo.untils包,然后在包下创建JDBCUtils类
package org.hive.demo.utils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.Statement;
/**
* Hive JDBC 连接工具类
* Created by shirukai on 2017/11/23.
*/
public class JDBCUtils {
private static Logger logger = LoggerFactory.getLogger("JDBCUtils");
private static String url = "jdbc:hive2://192.168.162.177:10000/default";
public static String user = "root";
public static String pass = "root";
//获取连接
public static Connection getConnection(){
try {
return DriverManager.getConnection(url,user,pass);
} catch (Exception e) {
logger.error(e.getMessage(), e);
}
return null;
}
//释放资源
public static void release(Connection conn, Statement st, ResultSet rs){
if (rs != null){
try {
rs.close();
} catch (Exception e) {
logger.error(e.getMessage(), e);
}finally {
rs = null;
}
}
if (st != null){
try {
st.close();
} catch (Exception e) {
logger.error(e.getMessage(), e);
}finally {
st = null;
}
}
if (conn != null){
try {
conn.close();
} catch (Exception e) {
logger.error(e.getMessage(), e);
}finally {
conn = null;
}
}
}
}
7.3.4 创建hive测试类
创建org.hive.demo.hive包,然后创建HiveJDBCDemo类
package org.hive.demo.hive;
import org.hive.demo.utils.JDBCUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.Statement;
/**
*
* Created by shirukai on 2017/11/23.
*/
public class HiveJDBCDemo {
private static Logger logger = LoggerFactory.getLogger("HiveJDBCDemo");
public static void main(String[] args){
Connection conn = null;
Statement st = null;
ResultSet rs = null;
String sql = "select * from t3";
try {
//获取连接
conn = JDBCUtils.getConnection();
//创建运行环境
st = conn.createStatement();
//运行HQL
rs = st.executeQuery(sql);
while (rs.next()){
logger.info("rs={}",rs.getString(1));
}
} catch (Exception e) {
logger.error(e.getMessage(), e);
}finally {
JDBCUtils.release(conn,st,rs);
}
}
}
7.3.5 运行main方法
7.3.6 出现如下错误的解决方法
报错:root is not allowed to impersonate root
修改 hadoop的配置文件 core-site.xml ,加入以下内容,修改完成后重启hadoop服务
<property>
<name>hadoop.proxyuser.root.hosts</name>
<value>*</value>
</property>
<property>
<name>hadoop.proxyuser.root.groups</name>
<value>*</value>
</property>
参考资料:https://www.waitig.com/user-root-is-not-allowed-to-impersonate-anonymous.html
7.3.7 注意版本问题
加载HiveServer2 JDBC驱动程序。从1.2.0版开始,不再需要使用Class.forName()来显式加载JDBC驱动程序。
如:
Class.forName("org.apache.hive.jdbc.HiveDriver");
通过Connection
使用JDBC驱动程序创建对象来连接到数据库。
Connection cnct = DriverManager.getConnection("jdbc:hive2://<host>:<port>", "<user>", "<password>");
8 Hive Thrift客户端
(……)
9 hive 自定义函数
- Hive的自定义函数(UDF):User Defined Function
- 可以直接应用于select语句,对查询结果做格式化处理后,再输出内容。
Hive自定义函数的实现细节
- 自定义UDF需要继承org.apache.hadoop.hive.ql.UDF
- 需要实现evaluate函数,evaluate函数支持重载
Hive自定义函数的部署运行
- 把程序打包放到目标机器上去
- 进入hive客户端,添加jar包
add jar /root/training/udfjar/udf_test.jar
- 创建临时函数
CREATE TEMPORARY FUNCTION <函数名>
AS'Java类名'
自定义函数案例
拼加两个字符串
创建 ConcatString类
package org.hive.demo.hive;
import org.apache.hadoop.hive.ql.exec.UDF;
import org.apache.hadoop.io.Text;
public class ConcatString extends UDF {
public Text evaluate(Text a,Text b){
return new Text(a.toString()+"***"+b.toString());
}
}
利用 Eclipse将ConcatString类导出成jar包
导出jar后上传到linux
进入hive客户端,添加jar包
hive> add jar /root/concatstring.jar;
Added [/root/concatstring.jar] to class path
Added resources: [/root/concatstring.jar]
创建临时函数
hive> create temporary function myconcat as 'org.hive.demo.hive.ConcatString';
OK
Time taken: 0.183 seconds
测试
hive> select myconcat('Hello','Word');
OK
Hello***Word
Time taken: 3.523 seconds, Fetched: 1 row(s)
10 总结
为什么要使用hive呢?
hive是一个数据仓库,用来支持我们的OLAP的应用,hive的数据仓库是建立咋Hadoop集群之上的,它的数据是存放在HDFS系统中,在hive中执行的操作会转换成MapReduce作业进行提交运行。我们的Hive也支持类似SQL的语言,即HQL。Hive采用元数据对表进行管理,元数据有三种存放模式:嵌入模式、本地模式、远程模式。hive提供了非常强大的编程接口:JDBC、客户端、自定义函数。这就是我们学习的Hive。
学习自:慕课网《走进大数据之Hive入门、进阶》