什么是Oozie?如何使用Oozie?蒟蒻博主带你快速上手Oozie!

写在前面: 博主是一名软件工程系大数据应用开发专业大二的学生,昵称来源于《爱丽丝梦游仙境》中的Alice和自己的昵称。作为一名互联网小白,写博客一方面是为了记录自己的学习历程,一方面是希望能够帮助到很多和自己一样处于起步阶段的萌新。由于水平有限,博客中难免会有一些错误,有纰漏之处恳请各位大佬不吝赐教!个人小站:http://alices.ibilibili.xyz/ , 博客主页:https://alice.blog.csdn.net/
尽管当前水平可能不及各位大佬,但我还是希望自己能够做得更好,因为一天的生活就是一生的缩影。我希望在最美的年华,做最好的自己

        本篇博客,博主为大家介绍的是Oozie,一种运行在hadoop平台上的工作流调度引擎。如果看完后有点收获,不妨给博主一个大大的赞|ू・ω・` )
        
在这里插入图片描述


Oozie

1、简介

        Oozie是运行在hadoop平台上的一种工作流调度引擎,它可以用来调度与管理hadoop任务,如,MapReduce、Pig等。

在这里插入图片描述

Oozie的组件介绍

        workFlow:工作流,定义工作流任务的执行,主要由一个个的action组成,每个action都是一个任务,在xml中进行配置即可

        Coordinator :协作器,可以理解为工作流的协调器,可以将多个工作流协调成一个工作流来进行处理。也是oozie当中的定时任务调度的模块

        Bundle :捆,束。多个Coordinator 的抽象,可以通过bundle将多个Coordinator 进行组装集合起来,形成一个bundle

        可以发现它们三者之间的关系类似于套娃
在这里插入图片描述
        如果还是不能给你留下深刻的印象,可以参照下面这个图,绝对的通俗易懂
在这里插入图片描述

2、架构

在这里插入图片描述
        从oozie的架构图中,可以看到所有的任务都是通过oozie生成相应的任务客户端,并通过任务客户端来提交相应的任务。

3、安装

        因为Oozie的安装步骤实在繁琐,这里就不详细演示说明了。想知道具体安装步骤的朋友,可以自行Google/百度。

        如果已经安装好了Oozie,可以通过web页面进行查看详情。

        http://bd001:11000/oozie/
在这里插入图片描述

        看到类似的效果,说明我们的Oozie就安装成功了。

4、使用

        正式开始使用之前,需要申明一点,本次试验所使用的虚拟机主机名为bd001,并且是单节点的,所以下面步骤中所需要配置的文件里的主机名均为bd001。

        如果有跟着操作的朋友,请以自己的集群的实际情况为准!

4.1 使用oozie调度shell脚本

        oozie安装好了之后,需要测试oozie的功能是否完整好使,官方已经给我们带了各种测试案例,我们可以通过官方提供的各种案例来对oozie进行调度。

第一步:解压官方提供的调度案例

        oozie自带了各种案例,我们可以使用oozie自带的各种案例来作为模板,所以我们这里先把官方提供的各种案例给解压出来。

cd /export/servers/oozie-4.1.0-cdh5.14.0
tar -zxf oozie-examples.tar.gz

        解压完毕,可以发现examples文件夹就是我们想要的。
在这里插入图片描述

第二步:创建工作目录

        在任意地方创建一个oozie的工作目录,以后调度任务的配置文件全部放到oozie的工作目录当中去。

        这里直接在oozie的安装目录下面创建工作目录。

cd /export/servers/oozie-4.1.0-cdh5.14.0
mkdir oozie_works
第三步:拷贝任务模板到工作目录当中去

        任务模板以及工作目录都准备好了之后,我们把shell的任务模板拷贝到我们oozie的工作目录当中去。

cd /export/servers/oozie-4.1.0-cdh5.14.0
cp -r examples/apps/shell/ oozie_works/
第四步:随意准备一个shell脚本
cd /export/servers/oozie-4.1.0-cdh5.14.0
vim oozie_works/shell/hello.sh

注意:这个脚本一定要是在我们oozie工作路径下的shell路径下的位置

#!/bin/bash
echo "hello world" >> /export/servers/hello_oozie.txt
第五步:修改模板下的配置文件

修改job.properties

cd /export/servers/oozie-4.1.0-cdh5.14.0/oozie_works/shell

vim job.properties

nameNode=hdfs://bd001:8020
jobTracker=bd001:8032
queueName=default
examplesRoot=oozie_works
oozie.wf.application.path=${nameNode}/user/${user.name}/${examplesRoot}/shell
EXEC=hello.sh

修改workflow.xml
vim workflow.xml

<workflow-app xmlns="uri:oozie:workflow:0.4" name="shell-wf">
<start to="shell-node"/>
<action name="shell-node">
    <shell xmlns="uri:oozie:shell-action:0.2">
        <job-tracker>${jobTracker}</job-tracker>
        <name-node>${nameNode}</name-node>
        <configuration>
            <property>
                <name>mapred.job.queue.name</name>
                <value>${queueName}</value>
            </property>
        </configuration>
        <exec>${EXEC}</exec>
        <!-- <argument>my_output=Hello Oozie</argument> -->
        <file>/user/root/oozie_works/shell/${EXEC}#${EXEC}</file>

        <capture-output/>
    </shell>
    <ok to="end"/>
    <error to="fail"/>
</action>
<decision name="check-output">
    <switch>
        <case to="end">
            ${wf:actionData('shell-node')['my_output'] eq 'Hello Oozie'}
        </case>
        <default to="fail-output"/>
    </switch>
</decision>
<kill name="fail">
    <message>Shell action failed, error message[${wf:errorMessage(wf:lastErrorNode())}]</message>
</kill>
<kill name="fail-output">
    <message>Incorrect output, expected [Hello Oozie] but was [${wf:actionData('shell-node')['my_output']}]</message>
</kill>
<end name="end"/>
</workflow-app>
第六步:上传调度任务到hdfs上面去

注意:上传的hdfs目录为/user/root,因为我们hadoop启动的时候使用的是root用户,如果hadoop启动的是其他用户,那么就上传到/user/其他用户。

cd /export/servers/oozie-4.1.0-cdh5.14.0
hdfs dfs -put oozie_works/ /user/root
第七步:执行调度任务

        通过oozie的命令来执行调度任务

cd /export/servers/oozie-4.1.0-cdh5.14.0
bin/oozie job -oozie http://bd001:11000/oozie -config oozie_works/shell/job.properties  -run

从监控界面可以看到任务执行成功了
在这里插入图片描述
查看hadoop的19888端口,我们会发现,oozie启动了一个MR的任务去执行shell脚本
在这里插入图片描述
在这里插入图片描述

4.2 使用oozie调度hive

第一步:拷贝hive的案例模板
cd /export/servers/oozie-4.1.0-cdh5.14.0
cp -ra examples/apps/hive2/ oozie_works/
第二步:编辑hive模板

这里使用的是hiveserver2来进行提交任务,需要注意我们要将hiveserver2的服务给启动起来

hive --service hiveserver2 &
hive --service metastore  &

修改job.properties

cd /export/servers/oozie-4.1.0-cdh5.14.0/oozie_works/hive2
vim job.properties
nameNode=hdfs://bd001:8020
jobTracker=bd001:8032
queueName=default
jdbcURL=jdbc:hive2://bd001:10000/default
examplesRoot=oozie_works

oozie.use.system.libpath=true
# 配置我们文件上传到hdfs的保存路径 实际上就是在hdfs 的/user/root/oozie_works/hive2这个路径下
oozie.wf.application.path=${nameNode}/user/${user.name}/${examplesRoot}/hive2

修改workflow.xml
vim workflow.xml

<?xml version="1.0" encoding="UTF-8"?>
<workflow-app xmlns="uri:oozie:workflow:0.5" name="hive2-wf">
    <start to="hive2-node"/>

    <action name="hive2-node">
        <hive2 xmlns="uri:oozie:hive2-action:0.1">
            <job-tracker>${jobTracker}</job-tracker>
            <name-node>${nameNode}</name-node>
            <prepare>
                <delete path="${nameNode}/user/${wf:user()}/${examplesRoot}/output-data/hive2"/>
                <mkdir path="${nameNode}/user/${wf:user()}/${examplesRoot}/output-data"/>
            </prepare>
            <configuration>
                <property>
                    <name>mapred.job.queue.name</name>
                    <value>${queueName}</value>
                </property>
            </configuration>
            <jdbc-url>${jdbcURL}</jdbc-url>
            <script>script.q</script>
            <param>INPUT=/user/${wf:user()}/${examplesRoot}/input-data/table</param>
            <param>OUTPUT=/user/${wf:user()}/${examplesRoot}/output-data/hive2</param>
        </hive2>
        <ok to="end"/>
        <error to="fail"/>
    </action>

    <kill name="fail">
        <message>Hive2 (Beeline) action failed, error message[${wf:errorMessage(wf:lastErrorNode())}]</message>
    </kill>
    <end name="end"/>
</workflow-app>

编辑hivesql文件
vim script.q

DROP TABLE IF EXISTS test;
CREATE EXTERNAL TABLE default.test (a INT) STORED AS TEXTFILE LOCATION '${INPUT}';
insert into test values(10);
insert into test values(20);
insert into test values(30);
第三步:上传工作文件到hdfs
cd /export/servers/oozie-4.1.0-cdh5.14.0/oozie_works
hdfs dfs -put hive2/ /user/root/oozie_works/
第四步:执行oozie的调度
cd /export/servers/oozie-4.1.0-cdh5.14.0
bin/oozie job -oozie http://bd001:11000/oozie -config oozie_works/hive2/job.properties  -run
第五步:查看调度结果

在这里插入图片描述

在这里插入图片描述

4.3 使用oozie调度MR任务

第一步:准备MR执行的数据

        我们这里通过oozie调度一个MR的程序的执行,MR的程序可以是自己写的,也可以是hadoop工程自带的,我们这里就选用hadoop工程自带的MR程序来运行wordcount的示例。

        准备以下数据上传到HDFS的/oozie/input路径下去。

hdfs dfs -mkdir -p /oozie/input
vim wordcount.txt
hello   world   hadoop
spark   hive    hadoop

将数据上传到hdfs对应目录

hdfs dfs -put wordcount.txt /oozie/input

第二步:执行官方测试案例
hadoop jar /export/servers/hadoop-2.6.0-cdh5.14.0/share/hadoop/mapreduce/hadoop-mapreduce-examples-2.6.0-cdh5.14.0.jar   wordcount  /oozie/input/  /oozie/output

在这里插入图片描述

第三步:准备调度的资源

        将需要调度的资源都准备好放到一个文件夹下面去,包括jar包,job.properties,以及workflow.xml。

        拷贝MR的任务模板

cd /export/servers/oozie-4.1.0-cdh5.14.0
cp -ra examples/apps/map-reduce/   oozie_works/

        删掉MR任务模板lib目录下自带的jar包

cd /export/servers/oozie-4.1.0-cdh5.14.0/oozie_works/map-reduce/lib
rm -rf oozie-examples-4.1.0-cdh5.14.0.jar
第三步:拷贝的jar包到对应目录

        从上一步的删除当中,可以看到需要调度的jar包存放在了
/export/servers/oozie-4.1.0-cdh5.14.0/oozie_works/map-reduce/lib这个目录下,所以我们把我们需要调度的jar包也放到这个路径下即可

cp /export/servers/hadoop-2.6.0-cdh5.14.0/share/hadoop/mapreduce/hadoop-mapreduce-examples-2.6.0-cdh5.14.0.jar /export/servers/oozie-4.1.0-cdh5.14.0/oozie_works/map-reduce/lib/
第四步:修改配置文件

修改job.properties
cd /export/servers/oozie-4.1.0-cdh5.14.0/oozie_works/map-reduce

vim job.properties

nameNode=hdfs://bd001:8020
jobTracker=bd001:8032
queueName=default
examplesRoot=oozie_works

oozie.wf.application.path=${nameNode}/user/${user.name}/${examplesRoot}/map-reduce/workflow.xml
outputDir=/oozie/output
inputdir=/oozie/input

修改workflow.xml

cd /export/servers/oozie-4.1.0-cdh5.14.0/oozie_works/map-reduce
vim workflow.xml
<?xml version="1.0" encoding="UTF-8"?>
<!--
  Licensed to the Apache Software Foundation (ASF) under one
  or more contributor license agreements.  See the NOTICE file
  distributed with this work for additional information
  regarding copyright ownership.  The ASF licenses this file
  to you under the Apache License, Version 2.0 (the
  "License"); you may not use this file except in compliance
  with the License.  You may obtain a copy of the License at
  
       http://www.apache.org/licenses/LICENSE-2.0
  
  Unless required by applicable law or agreed to in writing, software
  distributed under the License is distributed on an "AS IS" BASIS,
  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  See the License for the specific language governing permissions and
  limitations under the License.
-->
<workflow-app xmlns="uri:oozie:workflow:0.5" name="map-reduce-wf">
    <start to="mr-node"/>
    <action name="mr-node">
        <map-reduce>
            <job-tracker>${jobTracker}</job-tracker>
            <name-node>${nameNode}</name-node>
            <prepare>
                <delete path="${nameNode}/${outputDir}"/>
            </prepare>
            <configuration>
                <property>
                    <name>mapred.job.queue.name</name>
                    <value>${queueName}</value>
                </property>
				<!--  
                <property>
                    <name>mapred.mapper.class</name>
                    <value>org.apache.oozie.example.SampleMapper</value>
                </property>
                <property>
                    <name>mapred.reducer.class</name>
                    <value>org.apache.oozie.example.SampleReducer</value>
                </property>
                <property>
                    <name>mapred.map.tasks</name>
                    <value>1</value>
                </property>
                <property>
                    <name>mapred.input.dir</name>
                    <value>/user/${wf:user()}/${examplesRoot}/input-data/text</value>
                </property>
                <property>
                    <name>mapred.output.dir</name>
                    <value>/user/${wf:user()}/${examplesRoot}/output-data/${outputDir}</value>
                </property>
				-->
				
				   <!-- 开启使用新的API来进行配置 -->
                <property>
                    <name>mapred.mapper.new-api</name>
                    <value>true</value>
                </property>

                <property>
                    <name>mapred.reducer.new-api</name>
                    <value>true</value>
                </property>

                <!-- 指定MR的输出key的类型 -->
                <property>
                    <name>mapreduce.job.output.key.class</name>
                    <value>org.apache.hadoop.io.Text</value>
                </property>

                <!-- 指定MR的输出的value的类型-->
                <property>
                    <name>mapreduce.job.output.value.class</name>
                    <value>org.apache.hadoop.io.IntWritable</value>
                </property>

                <!-- 指定输入路径 -->
                <property>
                    <name>mapred.input.dir</name>
                    <value>${nameNode}/${inputdir}</value>
                </property>

                <!-- 指定输出路径 -->
                <property>
                    <name>mapred.output.dir</name>
                    <value>${nameNode}/${outputDir}</value>
                </property>

                <!-- 指定执行的map类 -->
                <property>
                    <name>mapreduce.job.map.class</name>
                    <value>org.apache.hadoop.examples.WordCount$TokenizerMapper</value>
                </property>

                <!-- 指定执行的reduce类 -->
                <property>
                    <name>mapreduce.job.reduce.class</name>
                    <value>org.apache.hadoop.examples.WordCount$IntSumReducer</value>
                </property>
				<!--  配置map task的个数 -->
                <property>
                    <name>mapred.map.tasks</name>
                    <value>1</value>
                </property>

            </configuration>
        </map-reduce>
        <ok to="end"/>
        <error to="fail"/>
    </action>
    <kill name="fail">
        <message>Map/Reduce failed, error message[${wf:errorMessage(wf:lastErrorNode())}]</message>
    </kill>
    <end name="end"/>
</workflow-app>
第五步:上传调度任务到hdfs对应目录
cd /export/servers/oozie-4.1.0-cdh5.14.0/oozie_works
hdfs dfs -put map-reduce/ /user/root/oozie_works/
第六步:执行调度任务

执行调度任务,然后通过oozie的11000端口进行查看任务结果

cd /export/servers/oozie-4.1.0-cdh5.14.0
bin/oozie job -oozie http://bd001:11000/oozie -config oozie_works/map-reduce/job.properties -run

在这里插入图片描述
查看集群上输出文件的内容
在这里插入图片描述


小结

        本篇博客主要为大家带来了Oozie的简介,架构,以及基本操作的分享。感兴趣的朋友可以有空多多练习,有任何疑问可以随时后台联系博主哟(^U^)ノ~YO

        如果以上过程中出现了任何的纰漏错误,烦请大佬们指正😅

        受益的朋友或对大数据技术感兴趣的伙伴记得点赞关注支持一波🙏

在这里插入图片描述

Alice菌 CSDN认证博客专家 CSDN博客专家 大数据学者 追梦人
00后大数据学者,坚信技术成就自我。
个人原创公众号【猿人菌】,每日更新大数据干货,欢迎上车!
一天的生活就是一生的缩影。在最美的年华,做最好的自己!
©️2020 CSDN 皮肤主题: 代码科技 设计师:Amelia_0503 返回首页