更多更新在javaeye http://bupt04406.iteye.com/blog/1096504
CliDriver
初始化过程
CliDriver.main 是 Cli 的入口
(1) 解析(Parse)args,放入cmdLine,处理 –hiveconf var=val 用于增加或者覆盖hive/hadoop配置,设置到System的属性中。
(2) 配置log4j,加载hive-log4j.properties里的配置信息。
(3)创建一个HiveConf,设置hiveJar= hive-exec-1.1.2.jar ,初始化加载hive-default.xml、 hive-site.xml。
(4) 创建一个CliSessionState(SessionState)
(5) 处理-S, -e, -f, -h等信息,保存在SessionState中。如果是-h,打印提示信息,并退出。
(6) –hiveconf var=val 设置的属性设置到HiveConf中。
(7) ShimLoader,load HadoopShims
(8) –hiveconf var=val 设置的属性设置到HiveConf中。
(9) CliSessionState设置到SessionState中,创建一个hive_job_log_ xxx文件(用于记录Hive的一些操作信息)保存到SessionState的hiveHist 。
(10) 创建CliDriver.
(11) 如果是–e,执行命令并退出,如果是-f,执行文件中的命令并退出。
(12)创建ConsoleReader,读取用户输入,遇到“;”为一个完整的命令,执行该命令(CliDriver.processLine ),接着读取处理用户的输入。用户输入的命令记录在user.home/.hivehistory文件中。
处理运行过程
CliDriver.processLine 去掉命令末尾的;,
CliDriver.processCmd
Split命令,分析第一个单词:
(1)如果是quit或者exit,退出。
(2)source,执行文件中的HiveQL
(3)!,执行命令,如!ls,列出当前目录的文件信息。
(4)list,列出jar/file/archive。
(5)如果是其他,则生成调用相应的CommandProcessor处理。
CommandProcessor
CommandProcessorFactory
(1)set SetProcessor,设置修改参数,设置到SessionState的HiveConf里。
(2)dfs DfsProcessor,使用hadoop的 FsShell运行hadoop的命令。
(3)add AddResourceProcessor 添加到SessionState的resource_map里,运行提交job的时候会写入 Hadoop的Distributed Cache。
(4)delete DeleteResourceProcessor从SessionState的resource_map里删除。
(5)其他 Driver
Driver
Driver.run(String command) // 处理一条命令
{
int ret = compile(command); // 分析命令,生成Task。
ret = execute(); // 运行Task。
}
Driver.compile
Driver.compile(String command) // 处理一条命令
{
(1) Parser(antlr):HiveQL->AbstractSyntaxTree(AST)
ParseDriver pd = new ParseDriver();
ASTNode tree = pd.parse(command, ctx);
(2) SemanticAnalyzer
BaseSemanticAnalyzer sem = SemanticAnalyzerFactory.get(conf, tree);
// Do semantic analysis and plan generation
sem.analyze(tree, ctx);
}
Parser是:
使用antlr,语法规则是 Hive.g
ql/src/java目录下面的:org.apache.hadoop.hive.ql. ParseDriver
SemanticAnalyzerFactory/SemanticAnalyzer
多种SemanticAnalyzer:
(1)ExplainSemanticAnalyzer(会调用SemanticAnalyzer获得相应信息)
explain 某条HiveSQL时调用
EXPLAIN [EXTENDED] query
(2)LoadSemanticAnalyzer
LOAD DATA [LOCAL] INPATH 'filepath' [OVERWRITE] INTO TABLE tablename [PARTITION (partcol1=val1, partcol2=val2 ...)]
(3)DDLSemanticAnalyzer
SHOW TABLES、DROP TABLE、DESC TABLE等时
(4)FunctionSemanticAnalyzer
CREATE/DROP FUNCTION
(5)SemanticAnalyzer
select 等
(6)其他SemanticAnalyzer,Hive-0.6、0.7只有上面5种,trunk里面针对新功能新特性添加了相应的SemanticAnalyzer
Driver.execute
Driver.execute() // 运行命令生成的Task(一个或多个)
{
}
核心之一:SemanticAnalyzer
ql/src/java目录下面的: org.apache.hadoop.hive.ql.SemanticAnalyzer
SemanticAnalyzer. analyzeInternal(ASTNode ast)
{
doPhase1(child, qb, initPhase1Ctx());//分析AST树
getMetaData(qb); //从数据库中获得表的信息
Operator sinkOp = genPlan(qb);// AST-〉operator trees
Optimizer optm = new Optimizer();
pCtx = optm.optimize();// 优化 operator trees -〉operator trees
// At this point we have the complete operator tree
// from which we want to find the reduce operator
genMapRedTasks(qb); // operator trees-〉MapReduce Tasks
}
Hive原理分析:
(1) 从HQL语句到AST的转化过程是很机械,使用ANTLR,根据Hive.g的语法分析规则,生成AST。
(2) 从AST转化到QB,再到DAG图不是那么很容易明白,所以需要理清楚一下。
AST-〉QB就是把AST里面的一些信息和子查询分析出来,如所有涉及的表和表的别名(如果这条HQL查询语句中没有为表取别名,那么取别名为表名)的对应关系保存到QB的aliasToTabs,目标表(目标表即输出的table)的子AST。where子句,select子句,join子句,等一些子查询的AST分析出来,保存起来。
QBMetaData是查询相关的元数据信息,如所有源表(源表即从哪些表取得输入数据)到该表的Table关联。表的Table用来记录Table有哪些字段,各个字段的类型,表的分隔符等等信息。目标表名(存放输出结果的表)到表的Table的关联,目标表可以有多个,因为输出可能是写入多个表。
QB-〉DAG图的转化过程。
从QB生成operator,从生成的QB中的子查询生成Operator并保存记录它们之间的父子关系,还可能插入一些operator,这些operator是一些必要的辅助功能。
后面需要对这个DAG图,即operator图进行拆分,生成一些mapreduce作业(job),如有一个map阶段可能有多个operator,完成这些operator的功能,如某个Job的map执行多个operator,TableScanOperator是第一个operator,从读取一个表的数据开始(一条一条记录,record),在接着可能就是跟据where生成的operator(FilterOperator),过滤哪些不符合规则的记录(record,key/value),在接着是执行根据select生成的Select Operator(该operator选择仅需要的字段,过滤无关的字段,从而减少中间数据),最后是一个Reduce Output Operator,该operator完成map的输出,生成中间key和value。
作业的reduce也是可以执行多个operator的。
从QB生成的Operator里面有父子关系,生成mapreduce时,会对这个具有父子关系的operator图进行切分,生成一个个阶段,有些阶段是mapreduce作业,这些作业执行多个operator的功能。
ReduceSinkOperator是map的最后一个Operator,因为该operator需要生成一个map的输出,即输出key和输出value。
核心之二:ExecDriver
/home/tianzhao/apache/hive-0.6.0/build/hadoopcore/hadoop-0.19.1/bin/hadoop jar /home/tianzhao/apache/hive-0.6.0/build/ql/hive-exec-0.6.0.jar org.apache.hadoop.hive.ql.exec.ExecDriver -plan /tmp/hive-tianzhao/hive_2011-05-31_09-30-02_222_4000721282829102058/plan5577504731701425227.xml -jobconf datanucleus.connectionPoolingType=DBCP
使用hadoop jar hive-exec-0.6.0.jar org.apache.hadoop.hive.ql.exec.ExecDriver提交job给hadoop,作业的信息诸如operator等信息序列化到了 -plan plan5577504731701425227.xml里面。
ExecMapper、ExecReducer在configure(JobConf job)运行的时候会反序列化出来。
hive提交给hadoop的MapReduce作业,map阶段运行ExecMapper,reduce阶段运行ExecReducer。
add jar/add file/add archive,这些archive、jar和文件会写入 Distributed Cache里面。在MapTask和ReduceTask运行的时候读取调用。 写入Distributed Cache参考ExecDriver。
......