Thứ Ba, 3 tháng 9, 2013

Sử dụng Sqoop để ghi dữ liệu từ HDFS vào Informix, DB2 hoặc MySQL thông qua JDBC


Sqoop Apache Project là một Hadoop dựa trên JDBC nguồn mở cho tiện ích di chuyển dữ liệu của cơ sở dữ liệu. Ban đầu Sqoop đã được tạo ra trong một cuộc thi lập trình hackathon tại Cloudera và sau đó trở thành nguồn mở.
Việc di chuyển dữ liệu từ HDFS sang một cơ sở dữ liệu quan hệ là một trường hợp sử dụng phổ biến. HDFS và Map-Reduce rất giỏi làm công việc nặng. Đối với các truy vấn đơn giản hoặc một kho lưu trữ mặt sau cho một trang web, việc bắt giữ lại kết quả đầu ra Map-Reduce trong một kho lưu trữ quan hệ là một mẫu thiết kế tốt. Bạn có thể tránh chạy lại việc đếm từ của Map-Reduce bằng cách chỉ di chuyển các kết quả bằng Sqoop vào Informix và DB2. Bạn đã tạo ra dữ liệu về Twain và Cooper, bây giờ hãy di chuyển nó vào một cơ sở dữ liệu, như trong Liệt kê 11.

Liệt kê 11. Thiết lập driver JDBC
                 
#Sqoop needs access to the JDBC driver for every
# database that it will access
                
# please copy the driver for each database you plan to use for these exercises
# the MySQL database and driver are already installed in the virtual image
# but you still need to copy the driver to the sqoop/lib directory
                
#one time copy of jdbc driver to sqoop lib directory
$ sudo cp Informix_JDBC_Driver/lib/ifxjdbc*.jar /usr/lib/sqoop/lib/
$ sudo cp db2jdbc/db2jcc*.jar /usr/lib/sqoop/lib/
$ sudo cp /usr/lib/hive/lib/mysql-connector-java-5.1.15-bin.jar /usr/lib/sqoop/lib/
            

Các ví dụ được hiển thị trong các Liệt kê từ 12 đến 15 được trình bày cho từng cơ sở dữ liệu. Hãy đọc ngay vào ví dụ mà bạn quan tâm, gồm có Informix, DB2 hoặc MySQL. Đối với các chương trình cơ sở dữ liệu được viết theo nhiều ngôn ngữ lập trình, hãy giải trí với tất cả mọi ví dụ. Nếu cơ sở dữ liệu mà bạn chọn không có ở đây thì cũng không phải là một thách thức lớn để chạy các ví dụ mẫu ở những nơi khác.

Liệt kê 12. Những người dùng Informix: Sqoop ghi các kết quả đếm từ vào Informix
                 
# create a target table to put the data
# fire up dbaccess and use this sql 
# create table wordcount ( word char(36) primary key, n int);
                
# now run the sqoop command
# this is best put in a shell script to help avoid typos...
                
$ sqoop export -D sqoop.export.records.per.statement=1 \
--fields-terminated-by '\t' --driver com.informix.jdbc.IfxDriver \
--connect \
"jdbc:informix-sqli://myhost:54321/stores_demo:informixserver=i7;user=me;password=mypw" \
--table wordcount --export-dir /user/cloudera/HF.out
            


Liệt kê 13. Những người dùng Informix: Sqoop ghi các kết quả đếm từ vào Informix
                 
12/08/08 21:39:42 INFO manager.SqlManager: Using default fetchSize of 1000
12/08/08 21:39:42 INFO tool.CodeGenTool: Beginning code generation
12/08/08 21:39:43 INFO manager.SqlManager: Executing SQL statement: SELECT t.* 
FROM wordcount AS t WHERE 1=0
12/08/08 21:39:43 INFO manager.SqlManager: Executing SQL statement: SELECT t.* 
FROM wordcount AS t WHERE 1=0
12/08/08 21:39:43 INFO orm.CompilationManager: HADOOP_HOME is /usr/lib/hadoop
12/08/08 21:39:43 INFO orm.CompilationManager: Found hadoop core jar at: 
/usr/lib/hadoop/hadoop-0.20.2-cdh3u4-core.jar
12/08/08 21:39:45 INFO orm.CompilationManager: Writing jar file: 
/tmp/sqoop-cloudera/compile/248b77c05740f863a15e0136accf32cf/wordcount.jar
12/08/08 21:39:45 INFO mapreduce.ExportJobBase: Beginning export of wordcount
12/08/08 21:39:45 INFO manager.SqlManager: Executing SQL statement: SELECT t.* 
FROM wordcount AS t WHERE 1=0
12/08/08 21:39:46 INFO input.FileInputFormat: Total input paths to process : 1
12/08/08 21:39:46 INFO input.FileInputFormat: Total input paths to process : 1
12/08/08 21:39:46 INFO mapred.JobClient: Running job: job_201208081900_0012
12/08/08 21:39:47 INFO mapred.JobClient:  map 0% reduce 0%
12/08/08 21:39:58 INFO mapred.JobClient:  map 38% reduce 0%
12/08/08 21:40:00 INFO mapred.JobClient:  map 64% reduce 0%
12/08/08 21:40:04 INFO mapred.JobClient:  map 82% reduce 0%
12/08/08 21:40:07 INFO mapred.JobClient:  map 98% reduce 0%
12/08/08 21:40:09 INFO mapred.JobClient: Task Id : 
attempt_201208081900_0012_m_000000_0, Status : FAILED
java.io.IOException: java.sql.SQLException: 
    Encoding or code set not supported.
at ...SqlRecordWriter.close(AsyncSqlRecordWriter.java:187)
at ...$NewDirectOutputCollector.close(MapTask.java:540)
at org.apache.hadoop.mapred.MapTask.runNewMapper(MapTask.java:649)
at org.apache.hadoop.mapred.MapTask.run(MapTask.java:323)
at org.apache.hadoop.mapred.Child$4.run(Child.java:270)
at java.security.AccessController.doPrivileged(Native Method)
at javax.security.auth.Subject.doAs(Subject.java:396)
at ....doAs(UserGroupInformation.java:1177)
at org.apache.hadoop.mapred.Child.main(Child.java:264)
Caused by: java.sql.SQLException: Encoding or code set not supported.
at com.informix.util.IfxErrMsg.getSQLException(IfxErrMsg.java:413)
at com.informix.jdbc.IfxChar.toIfx(IfxChar.java:135)
at com.informix.jdbc.IfxSqli.a(IfxSqli.java:1304)
at com.informix.jdbc.IfxSqli.d(IfxSqli.java:1605)
at com.informix.jdbc.IfxS
12/08/08 21:40:11 INFO mapred.JobClient:  map 0% reduce 0%
12/08/08 21:40:15 INFO mapred.JobClient: Task Id : 
attempt_201208081900_0012_m_000000_1, Status : FAILED
java.io.IOException: java.sql.SQLException: 
    Unique constraint (informix.u169_821) violated.
at .mapreduce.AsyncSqlRecordWriter.write(AsyncSqlRecordWriter.java:223)
at .mapreduce.AsyncSqlRecordWriter.write(AsyncSqlRecordWriter.java:49)
at .mapred.MapTask$NewDirectOutputCollector.write(MapTask.java:531)
at .mapreduce.TaskInputOutputContext.write(TaskInputOutputContext.java:80)
at com.cloudera.sqoop.mapreduce.TextExportMapper.map(TextExportMapper.java:82)
at com.cloudera.sqoop.mapreduce.TextExportMapper.map(TextExportMapper.java:40)
at org.apache.hadoop.mapreduce.Mapper.run(Mapper.java:144)
at .mapreduce.AutoProgressMapper.run(AutoProgressMapper.java:189)
at org.apache.hadoop.mapred.MapTask.runNewMapper(MapTask.java:647)
at org.apache.hadoop.mapred.MapTask.run(MapTask.java:323)
at org.apache.hadoop.mapred.Child$4.run(Child.java:270)
at java.security.AccessController.doPrivileged(Native Method)
at javax.security.a
12/08/08 21:40:20 INFO mapred.JobClient: 
Task Id : attempt_201208081900_0012_m_000000_2, Status : FAILED
java.sql.SQLException: Unique constraint (informix.u169_821) violated.
at .mapreduce.AsyncSqlRecordWriter.write(AsyncSqlRecordWriter.java:223)
at .mapreduce.AsyncSqlRecordWriter.write(AsyncSqlRecordWriter.java:49)
at .mapred.MapTask$NewDirectOutputCollector.write(MapTask.java:531)
at .mapreduce.TaskInputOutputContext.write(TaskInputOutputContext.java:80)
at com.cloudera.sqoop.mapreduce.TextExportMapper.map(TextExportMapper.java:82)
at com.cloudera.sqoop.mapreduce.TextExportMapper.map(TextExportMapper.java:40)
at org.apache.hadoop.mapreduce.Mapper.run(Mapper.java:144)
at .mapreduce.AutoProgressMapper.run(AutoProgressMapper.java:189)
at org.apache.hadoop.mapred.MapTask.runNewMapper(MapTask.java:647)
at org.apache.hadoop.mapred.MapTask.run(MapTask.java:323)
at org.apache.hadoop.mapred.Child$4.run(Child.java:270)
at java.security.AccessController.doPrivileged(Native Method)
at javax.security.a
12/08/08 21:40:27 INFO mapred.JobClient: Job complete: job_201208081900_0012
12/08/08 21:40:27 INFO mapred.JobClient: Counters: 7
12/08/08 21:40:27 INFO mapred.JobClient:   Job Counters 
12/08/08 21:40:27 INFO mapred.JobClient:     SLOTS_MILLIS_MAPS=38479
12/08/08 21:40:27 INFO mapred.JobClient:     
Total time spent by all reduces waiting after reserving slots (ms)=0
12/08/08 21:40:27 INFO mapred.JobClient:     
Total time spent by all maps waiting after reserving slots (ms)=0
12/08/08 21:40:27 INFO mapred.JobClient:     Launched map tasks=4
12/08/08 21:40:27 INFO mapred.JobClient:     Data-local map tasks=4
12/08/08 21:40:27 INFO mapred.JobClient:     SLOTS_MILLIS_REDUCES=0
12/08/08 21:40:27 INFO mapred.JobClient:     Failed map tasks=1
12/08/08 21:40:27 INFO mapreduce.ExportJobBase: 
Transferred 0 bytes in 41.5758 seconds (0 bytes/sec)
12/08/08 21:40:27 INFO mapreduce.ExportJobBase: Exported 0 records.
12/08/08 21:40:27 ERROR tool.ExportTool: Error during export: Export job failed!
                
# despite the errors above, rows are inserted into the wordcount table
# one row is missing
# the retry and duplicate key exception are most likely related, but
# troubleshooting will be saved for a later article
                
# check how we did
# nothing like a "here document" shell script
                
$ dbaccess stores_demo - <<eoj
> select count(*) from wordcount;
> eoj
                
Database selected.
(count(*)) 
13837
1 row(s) retrieved.
Database closed.
            


Liệt kê 14. Những người dùng DB2: Sqoop ghi các kết quả đếm từ vào DB2
                 
# here is the db2 syntax
# create a destination table for db2
#
#db2 => connect to sample
#
#   Database Connection Information
#
# Database server        = DB2/LINUXX8664 10.1.0
# SQL authorization ID   = DB2INST1
# Local database alias   = SAMPLE
#
#db2 => create table wordcount ( word char(36) not null primary key , n int)
#DB20000I  The SQL command completed successfully.
#
                
sqoop export -D sqoop.export.records.per.statement=1 \
--fields-terminated-by '\t' \
--driver com.ibm.db2.jcc.DB2Driver \
--connect "jdbc:db2://192.168.1.131:50001/sample"  \
--username db2inst1 --password db2inst1 \
--table wordcount --export-dir /user/cloudera/HF.out 
                
12/08/09 12:32:59 WARN tool.BaseSqoopTool: Setting your password on the 
command-line is insecure. Consider using -P instead.
12/08/09 12:32:59 INFO manager.SqlManager: Using default fetchSize of 1000
12/08/09 12:32:59 INFO tool.CodeGenTool: Beginning code generation
12/08/09 12:32:59 INFO manager.SqlManager: Executing SQL statement: 
SELECT t.* FROM wordcount AS t WHERE 1=0
12/08/09 12:32:59 INFO manager.SqlManager: Executing SQL statement: 
SELECT t.* FROM wordcount AS t WHERE 1=0
12/08/09 12:32:59 INFO orm.CompilationManager: HADOOP_HOME is /usr/lib/hadoop
12/08/09 12:32:59 INFO orm.CompilationManager: Found hadoop core jar 
at: /usr/lib/hadoop/hadoop-0.20.2-cdh3u4-core.jar
12/08/09 12:33:00 INFO orm.CompilationManager: Writing jar 
file: /tmp/sqoop-cloudera/compile/5532984df6e28e5a45884a21bab245ba/wordcount.jar
12/08/09 12:33:00 INFO mapreduce.ExportJobBase: Beginning export of wordcount
12/08/09 12:33:01 INFO manager.SqlManager: Executing SQL statement: 
SELECT t.* FROM wordcount AS t WHERE 1=0
12/08/09 12:33:02 INFO input.FileInputFormat: Total input paths to process : 1
12/08/09 12:33:02 INFO input.FileInputFormat: Total input paths to process : 1
12/08/09 12:33:02 INFO mapred.JobClient: Running job: job_201208091208_0002
12/08/09 12:33:03 INFO mapred.JobClient:  map 0% reduce 0%
12/08/09 12:33:14 INFO mapred.JobClient:  map 24% reduce 0%
12/08/09 12:33:17 INFO mapred.JobClient:  map 44% reduce 0%
12/08/09 12:33:20 INFO mapred.JobClient:  map 67% reduce 0%
12/08/09 12:33:23 INFO mapred.JobClient:  map 86% reduce 0%
12/08/09 12:33:24 INFO mapred.JobClient:  map 100% reduce 0%
12/08/09 12:33:25 INFO mapred.JobClient: Job complete: job_201208091208_0002
12/08/09 12:33:25 INFO mapred.JobClient: Counters: 16
12/08/09 12:33:25 INFO mapred.JobClient:   Job Counters 
12/08/09 12:33:25 INFO mapred.JobClient:     SLOTS_MILLIS_MAPS=21648
12/08/09 12:33:25 INFO mapred.JobClient:     Total time spent by all 
reduces waiting after reserving slots (ms)=0
12/08/09 12:33:25 INFO mapred.JobClient:     Total time spent by all 
maps waiting after reserving slots (ms)=0
12/08/09 12:33:25 INFO mapred.JobClient:     Launched map tasks=1
12/08/09 12:33:25 INFO mapred.JobClient:     Data-local map tasks=1
12/08/09 12:33:25 INFO mapred.JobClient:     SLOTS_MILLIS_REDUCES=0
12/08/09 12:33:25 INFO mapred.JobClient:   FileSystemCounters
12/08/09 12:33:25 INFO mapred.JobClient:     HDFS_BYTES_READ=138350
12/08/09 12:33:25 INFO mapred.JobClient:     FILE_BYTES_WRITTEN=69425
12/08/09 12:33:25 INFO mapred.JobClient:   Map-Reduce Framework
12/08/09 12:33:25 INFO mapred.JobClient:     Map input records=13838
12/08/09 12:33:25 INFO mapred.JobClient:     Physical memory (bytes) snapshot=105148416
12/08/09 12:33:25 INFO mapred.JobClient:     Spilled Records=0
12/08/09 12:33:25 INFO mapred.JobClient:     CPU time spent (ms)=9250
12/08/09 12:33:25 INFO mapred.JobClient:     Total committed heap usage (bytes)=42008576
12/08/09 12:33:25 INFO mapred.JobClient:     Virtual memory (bytes) snapshot=596447232
12/08/09 12:33:25 INFO mapred.JobClient:     Map output records=13838
12/08/09 12:33:25 INFO mapred.JobClient:     SPLIT_RAW_BYTES=126
12/08/09 12:33:25 INFO mapreduce.ExportJobBase: Transferred 135.1074 KB 
in 24.4977 seconds (5.5151 KB/sec)
12/08/09 12:33:25 INFO mapreduce.ExportJobBase: Exported 13838 records.                
                
# check on the results...
#
#db2 => select count(*) from wordcount 
#
#1          
#-----------
#      13838
#
#  1 record(s) selected.
#
#
            


Liệt kê 15. Những người dùng MySQL: Sqoop ghi các kết quả đếm từ vào MySQL
                 
# if you don't have Informix or DB2 you can still do this example
# mysql - it is already installed in the VM, here is how to access
                
# one time copy of the JDBC driver
                
sudo cp /usr/lib/hive/lib/mysql-connector-java-5.1.15-bin.jar /usr/lib/sqoop/lib/
                
# now create the database and table
                
$ mysql -u root
Welcome to the MySQL monitor.  Commands end with ; or \g.
Your MySQL connection id is 45
Server version: 5.0.95 Source distribution
                
Copyright (c) 2000, 2011, Oracle and/or its affiliates. All rights reserved.
                
Oracle is a registered trademark of Oracle Corporation and/or its
affiliates. Other names may be trademarks of their respective
owners.
                
Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.
                
mysql> create database mydemo;
Query OK, 1 row affected (0.00 sec)
                
mysql> use mydemo
Database changed
mysql> create table wordcount ( word char(36) not null primary key, n int);
Query OK, 0 rows affected (0.00 sec)
                
mysql> exit
Bye
                
# now export
                
$ sqoop export --connect jdbc:mysql://localhost/mydemo \
--table wordcount --export-dir /user/cloudera/HF.out \
--fields-terminated-by '\t' --username root               
            

Không có nhận xét nào:

Đăng nhận xét