[TOC]
# Sqoop簡介及安裝
## 1 概述
> sqoop是apache旗下一款“Hadoop和關系數據庫服務器之間傳送數據”的工具。
1) 導入數據:MySQL,Oracle導入數據到Hadoop的HDFS、HIVE、HBASE等數據存儲系統;
2) 導出數據:從Hadoop的文件系統中導出數據到關系數據庫

## 2 工作機制
> 將導入或導出命令翻譯成mapreduce程序來實現
> 在翻譯出的mapreduce中主要是對inputformat和outputformat進行定制
## 3 sqoop實戰及原理
### 3.1 sqoop安裝
> 安裝sqoop的前提是已經具備java和hadoop的環境
1) 下載并解壓
~~~
最新版下載地址http://ftp.wayne.edu/apache/sqoop/1.4.6/
~~~
2) 修改配置文件
~~~
$ cd $SQOOP_HOME/conf
$ mv sqoop-env-template.sh sqoop-env.sh
~~~
> 打開sqoop-env.sh并編輯下面幾行:
~~~
export HADOOP_COMMON_HOME=/home/hadoop/apps/hadoop-2.6.1/
export HADOOP_MAPRED_HOME=/home/hadoop/apps/hadoop-2.6.1/
export HIVE_HOME=/home/hadoop/apps/hive-1.2.1
~~~
3) 加入mysql的jdbc驅動包
~~~
cp ~/app/hive/lib/mysql-connector-java-5.1.28.jar $SQOOP_HOME/lib/
~~~
4) 驗證啟動
~~~
$ cd $SQOOP_HOME/bin
$ sqoop-version
~~~
> 預期的輸出:
~~~
15/12/17 14:52:32 INFO sqoop.Sqoop: Running Sqoop version: 1.4.6
Sqoop 1.4.6 git commit id 5b34accaca7de251fc91161733f906af2eddbe83
Compiled by abe on Fri Aug 1 11:19:26 PDT 2015
~~~
> 到這里,整個Sqoop安裝工作完成。
## 4 Sqoop的數據導入
> “導入工具”導入單個表從RDBMS到HDFS。表中的每一行被視為HDFS的記錄。所有記錄都存儲為文本文件的文本數據(或者Avro、sequence文件等二進制數據)
### 4.1 語法
> 下面的語法用于將數據導入HDFS。
~~~
$sqoop import (generic-args) (import-args)
~~~
### 4.2 示例
1) 表數據
> 在mysql中有一個庫userdb中三個表:emp, emp_add和emp_contact
> 表emp:


2) 導入表表數據到HDFS
> 下面的命令用于從MySQL數據庫服務器中的emp表導入HDFS
~~~
$bin/sqoop import \
--connect jdbc:mysql://hdp-node-01:3306/test \
--username root \
--password root \
--table emp --m 1
~~~
> 如果成功執行,那么會得到下面的輸出。
~~~
14/12/22 15:24:54 INFO sqoop.Sqoop: Running Sqoop version: 1.4.5
14/12/22 15:24:56 INFO manager.MySQLManager: Preparing to use a MySQL streaming resultset.
INFO orm.CompilationManager: Writing jar file: /tmp/sqoop-hadoop/compile/cebe706d23ebb1fd99c1f063ad51ebd7/emp.jar
-----------------------------------------------------
O mapreduce.Job: map 0% reduce 0%
14/12/22 15:28:08 INFO mapreduce.Job: map 100% reduce 0%
14/12/22 15:28:16 INFO mapreduce.Job: Job job_1419242001831_0001 completed successfully
-----------------------------------------------------
-----------------------------------------------------
14/12/22 15:28:17 INFO mapreduce.ImportJobBase: Transferred 145 bytes in 177.5849 seconds (0.8165 bytes/sec)
14/12/22 15:28:17 INFO mapreduce.ImportJobBase: Retrieved 5 records.
~~~
> 為了驗證在HDFS導入的數據,請使用以下命令查看導入的數據
~~~
$ $HADOOP_HOME/bin/hadoop fs -cat /user/hadoop/emp/part-m-00000
~~~
> emp表的數據和字段之間用逗號(,)表示。
~~~
1201, gopal, manager, 50000, TP
1202, manisha, preader, 50000, TP
1203, kalil, php dev, 30000, AC
1204, prasanth, php dev, 30000, AC
1205, kranthi, admin, 20000, TP
~~~
3) 導入關系表到HIVE
~~~
bin/sqoop import --connect jdbc:mysql://hdp-node-01:3306/test --username root --password root --table emp --hive-import --m 1
~~~
> 導入到HDFS指定目錄
> 在導入表數據到HDFS使用Sqoop導入工具,我們可以指定目標目錄。
> 以下是指定目標目錄選項的Sqoop導入命令的語法。
~~~
--target-dir <new or exist directory in HDFS>
~~~
> 下面的命令是用來導入emp_add表數據到'/queryresult'目錄。
~~~
bin/sqoop import \
--connect jdbc:mysql://hdp-node-01:3306/test \
--username root \
--password root \
--target-dir /queryresult \
--table emp --m 1
~~~
> 下面的命令是用來驗證 /queryresult 目錄中 emp_add表導入的數據形式。
~~~
$HADOOP_HOME/bin/hadoop fs -cat /queryresult/part-m-*
~~~
> 它會用逗號(,)分隔emp_add表的數據和字段。
~~~
1201, 288A, vgiri, jublee
1202, 108I, aoc, sec-bad
1203, 144Z, pgutta, hyd
1204, 78B, oldcity, sec-bad
1205, 720C, hitech, sec-bad
~~~
4) 導入表數據子集
> 我們可以導入表的使用Sqoop導入工具,"where"子句的一個子集。它執行在各自的數據庫服務器相應的SQL查詢,并將結果存儲在HDFS的目標目錄。
> where子句的語法如下。
~~~
--where <condition>
~~~
> 下面的命令用來導入emp_add表數據的子集。子集查詢檢索員工ID和地址,居住城市為:Secunderabad
~~~
bin/sqoop import \
--connect jdbc:mysql://hdp-node-01:3306/test \
--username root \
--password root \
--where "city ='sec-bad'" \
--target-dir /wherequery \
--table emp_add --m 1
~~~
> 按需導入
~~~
bin/sqoop import \
--connect jdbc:mysql://hdp-node-01:3306/test \
--username root \
--password root \
--target-dir /wherequery2 \
--query 'select id,name,deg from emp WHERE id>1207 and $CONDITIONS' \
--split-by id \
--fields-terminated-by '\t' \
--m 1
~~~
> 下面的命令用來驗證數據從emp_add表導入/wherequery目錄
~~~
$HADOOP_HOME/bin/hadoop fs -cat /wherequery/part-m-*
~~~
> 它用逗號(,)分隔 emp_add表數據和字段。
~~~
1202, 108I, aoc, sec-bad
1204, 78B, oldcity, sec-bad
1205, 720C, hitech, sec-bad
~~~
5) 增量導入
> 增量導入是僅導入新添加的表中的行的技術。
> 它需要添加‘incremental’, ‘check-column’, 和 ‘last-value’選項來執行增量導入。
> 下面的語法用于Sqoop導入命令增量選項。
~~~
--incremental <mode>
--check-column <column name>
--last value <last check column value>
~~~
> 假設新添加的數據轉換成emp表如下:
> 1206, satish p, grp des, 20000, GR
> 下面的命令用于在EMP表執行增量導入。
~~~
bin/sqoop import \
--connect jdbc:mysql://hdp-node-01:3306/test \
--username root \
--password root \
--table emp --m 1 \
--incremental append \
--check-column id \
--last-value 1205
~~~
> 以下命令用于從emp表導入HDFS emp/ 目錄的數據驗證。
~~~
$ $HADOOP_HOME/bin/hadoop fs -cat /user/hadoop/emp/part-m-*
~~~
> 它用逗號(,)分隔 emp_add表數據和字段。
~~~
1201, gopal, manager, 50000, TP
1202, manisha, preader, 50000, TP
1203, kalil, php dev, 30000, AC
1204, prasanth, php dev, 30000, AC
1205, kranthi, admin, 20000, TP
1206, satish p, grp des, 20000, GR
~~~
> 下面的命令是從表emp 用來查看修改或新添加的行
~~~
$ $HADOOP_HOME/bin/hadoop fs -cat /emp/part-m-*1
~~~
> 這表示新添加的行用逗號(,)分隔emp表的字段。
~~~
1206, satish p, grp des, 20000, GR
~~~
## 5 Sqoop的數據導出
> 將數據從HDFS導出到RDBMS數據庫
> 導出前,目標表必須存在于目標數據庫中。
1. 默認操作是從將文件中的數據使用INSERT語句插入到表中
2. 更新模式下,是生成UPDATE語句更新表數據
> 語法
> 以下是export命令語法。
~~~
$ sqoop export (generic-args) (export-args)
~~~
> 示例
> 數據是在HDFS 中“EMP/”目錄的emp_data文件中。所述emp_data如下:
~~~
1201, gopal, manager, 50000, TP
1202, manisha, preader, 50000, TP
1203, kalil, php dev, 30000, AC
1204, prasanth, php dev, 30000, AC
1205, kranthi, admin, 20000, TP
1206, satish p, grp des, 20000, GR
~~~
1) 首先需要手動創建mysql中的目標表
~~~
$ mysql
mysql> USE db;
mysql> CREATE TABLE employee (
id INT NOT NULL PRIMARY KEY,
name VARCHAR(20),
deg VARCHAR(20),
salary INT,
dept VARCHAR(10));
~~~
2) 然后執行導出命令
~~~
bin/sqoop export \
--connect jdbc:mysql://hdp-node-01:3306/test \
--username root \
--password root \
--table emp2 \
--export-dir /user/hadoop/emp/
~~~
3) 驗證表mysql命令行。
~~~
mysql>select * from employee;
~~~
> 如果給定的數據存儲成功,那么可以找到數據在如下的employee表。
~~~
+------+--------------+-------------+-------------------+--------+
| Id | Name | Designation | Salary | Dept |
+------+--------------+-------------+-------------------+--------+
| 1201 | gopal | manager | 50000 | TP |
| 1202 | manisha | preader | 50000 | TP |
| 1203 | kalil | php dev | 30000 | AC |
| 1204 | prasanth | php dev | 30000 | AC |
| 1205 | kranthi | admin | 20000 | TP |
| 1206 | satish p | grp des | 20000 | GR |
+------+--------------+-------------+-------------------+--------+
~~~
## 6 Sqoop作業
> 注:Sqoop作業——將事先定義好的數據導入導出任務按照指定流程運行
> 語法
> 以下是創建Sqoop作業的語法。
~~~
$ sqoop job (generic-args) (job-args)
[-- [subtool-name] (subtool-args)]
$ sqoop-job (generic-args) (job-args)
[-- [subtool-name] (subtool-args)]
~~~
> 創建作業(--create)
> 在這里,我們創建一個名為myjob,這可以從RDBMS表的數據導入到HDFS作業。
~~~
bin/sqoop job --create myimportjob -- import --connect jdbc:mysql://hdp-node-01:3306/test --username root --password root --table emp --m 1
~~~
> 該命令創建了一個從db庫的employee表導入到HDFS文件的作業。
> 驗證作業 (--list)
~~~
‘--list’ 參數是用來驗證保存的作業。下面的命令用來驗證保存Sqoop作業的列表。
~~~
~~~
$ sqoop job --list
~~~
> 它顯示了保存作業列表。
~~~
Available jobs:
myjob
~~~
> 檢查作業(--show)
~~~
‘--show’ 參數用于檢查或驗證特定的工作,及其詳細信息。以下命令和樣本輸出用來驗證一個名為myjob的作業。
~~~
~~~
$ sqoop job --show myjob
~~~
> 它顯示了工具和它們的選擇,這是使用在myjob中作業情況。
~~~
Job: myjob
Tool: import Options:
----------------------------
direct.import = true
codegen.input.delimiters.record = 0
hdfs.append.dir = false
db.table = employee
...
incremental.last.value = 1206
...
~~~
> 執行作業 (--exec)
> ‘--exec’ 選項用于執行保存的作業。下面的命令用于執行保存的作業稱為myjob。
~~~
$ sqoop job --exec myjob
~~~
> 它會顯示下面的輸出。
~~~
10/08/19 13:08:45 INFO tool.CodeGenTool: Beginning code generation
...
~~~
?
## 7 Sqoop的原理
### 概述
> Sqoop的原理其實就是將導入導出命令轉化為mapreduce程序來執行,sqoop在接收到命令后,都要生成mapreduce程序
> 使用sqoop的代碼生成工具可以方便查看到sqoop所生成的java代碼,并可在此基礎之上進行深入定制開發
> 代碼定制
> 以下是Sqoop代碼生成命令的語法:
~~~
$ sqoop-codegen (generic-args) (codegen-args)
$ sqoop-codegen (generic-args) (codegen-args)
~~~
> 示例:以USERDB數據庫中的表emp來生成Java代碼為例。
> 下面的命令用來生成導入
~~~
$ sqoop-codegen \
--import
--connect jdbc:mysql://localhost/userdb \
--username root \
--table emp
~~~
> 如果命令成功執行,那么它就會產生如下的輸出。
~~~
14/12/23 02:34:40 INFO sqoop.Sqoop: Running Sqoop version: 1.4.5
14/12/23 02:34:41 INFO tool.CodeGenTool: Beginning code generation
……………….
14/12/23 02:34:42 INFO orm.CompilationManager: HADOOP_MAPRED_HOME is /usr/local/hadoop
Note: /tmp/sqoop-hadoop/compile/9a300a1f94899df4a9b10f9935ed9f91/emp.java uses or overrides a deprecated API.
Note: Recompile with -Xlint:deprecation for details.
14/12/23 02:34:47 INFO orm.CompilationManager: Writing jar file: /tmp/sqoop-hadoop/compile/9a300a1f94899df4a9b10f9935ed9f91/emp.jar
~~~
> 驗證: 查看輸出目錄下的文件
~~~
$ cd /tmp/sqoop-hadoop/compile/9a300a1f94899df4a9b10f9935ed9f91/
$ ls
emp.class
emp.jar
emp.java
~~~
> 如果想做深入定制導出,則可修改上述代碼文件
- hadoop
- linux基礎
- Linux入門
- Linux進階
- shell
- Zookeeper
- Zookeeper簡介及部署
- Zookeeper使用及API
- Redis
- Redis簡介安裝部署
- Redis使用及API
- Java高級增強
- Java多線程增強
- Maven簡介及搭建
- Hive
- Hive簡介及安裝
- Hive操作
- HIve常用函數
- Hive數據類型
- Flume
- Flume簡介及安裝
- flume 攔截器(interceptor)
- azkaban
- azKaban簡介及安裝
- Sqoop
- Sqoop簡介及安裝
- HDFS
- HDFS原理
- HDFS操作API
- MAPREDUCE原理
- MAPREDUCE圖片資源
- MAPREDUCE加強
- HBASE
- HBASE簡介及安裝
- HBASE操作及API
- HBASE內部原理
- Storm
- Storm簡介及安裝
- Storm原理
- kafka
- kafka簡介及安裝
- kafka常用操作及API
- kafka原理
- kafka配置詳解
- Scala
- Scala簡介及安裝
- Scala基礎語法
- Scala實戰