3. 开发环境搭建:Hadoop集群安装、Eclipse/IDEA配置、Maven项目构建

好,咱们直接进入正题。开发环境搭建这事儿,说难不难,说简单吧,坑也不少。我见过太多同学卡在这一步,代码写好了,环境跑不起来,那叫一个憋屈。今天我就把这几年的经验捋一捋,带你一步步把环境搭好。

3.1 Hadoop集群安装——别急着上生产环境

我个人习惯,学习阶段用伪分布式就够了。说白了,就是一台机器模拟出集群的效果。你想想看,咱们学MapReduce,重点是编程模型和调优思路,不是运维。真要在三台机器上折腾,光SSH免密登录就能让你怀疑人生。

3.1.1 前置准备

  • JDK 1.8+:Hadoop 2.x/3.x 都依赖JDK。我建议用Oracle JDK 8,OpenJDK也行,但版本别太新。
  • SSH免密登录:伪分布式也需要。因为Hadoop的守护进程之间通过SSH通信。
  • 用户:别用root跑Hadoop。我吃过这个亏,权限问题能让你排查一整天。
⚠️ 我曾经... 在CentOS 7上直接用root解压Hadoop,结果启动DataNode时一直报权限拒绝。后来才发现,Hadoop默认不允许root用户启动。嗯,从那以后我都是新建一个hadoop用户。

3.1.2 安装步骤(伪分布式)

  1. 下载Hadoop安装包(我推荐3.3.6版本,稳定且兼容性好)。
  2. 解压到 /usr/local/hadoop
  3. 配置 etc/hadoop/hadoop-env.sh,设置 JAVA_HOME
  4. 配置 core-site.xmlhdfs-site.xmlmapred-site.xmlyarn-site.xml

这里我贴一份我常用的配置,你直接复制改改路径就行:

<!-- core-site.xml -->
<configuration>
    <property>
        <name>fs.defaultFS</name>
        <value>hdfs://localhost:9000</value>
    </property>
</configuration>

<!-- hdfs-site.xml -->
<configuration>
    <property>
        <name>dfs.replication</name>
        <value>1</value>  <!-- 伪分布式副本数设为1 -->
    </property>
</configuration>

<!-- mapred-site.xml -->
<configuration>
    <property>
        <name>mapreduce.framework.name</name>
        <value>yarn</value>
    </property>
</configuration>

<!-- yarn-site.xml -->
<configuration>
    <property>
        <name>yarn.nodemanager.aux-services</name>
        <value>mapreduce_shuffle</value>
    </property>
</configuration>
💡 小技巧: 格式化NameNode之前,确认一下 dfs.namenode.name.dir 指向的目录存在且有写权限。我见过有人格式化失败,就是因为目录没创建。

3.2 Eclipse/IDEA配置——选对工具,事半功倍

说实话,Eclipse和IDEA我都用过。早期做MapReduce开发,Eclipse配合Hadoop插件确实方便。但现在我更推荐IDEA,原因很简单:Maven集成更好,代码提示更智能。

3.2.1 IDEA配置要点

  • 安装Big Data Tools插件:这个插件能直接连接HDFS,浏览文件系统。我在项目中经常用它查看中间结果,比命令行方便多了。
  • 配置JDK:Project Structure -> SDKs,指向你安装的JDK 1.8。
  • 添加Hadoop依赖:别手动导jar包,用Maven管理。

重点来了: 很多同学在IDEA里跑MapReduce程序,会报 ClassNotFoundException。这是因为Hadoop的jar包没打到运行环境里。解决办法:在pom.xml里把Hadoop依赖的scope设为 provided,然后打包成jar丢到集群上跑。本地调试的话,用 LocalJobRunner 模式。

3.3 Maven项目构建——标准化你的工程

Maven这东西,说白了就是帮你管理jar包依赖和构建流程。我刚开始学MapReduce时,手动下载Hadoop的jar包,一个个加到classpath里,那叫一个痛苦。后来用了Maven,世界清净了。

3.3.1 创建Maven项目

在IDEA里新建Maven项目,groupId填你的包名,artifactId填项目名。然后修改pom.xml,加入Hadoop依赖:

<dependencies>
    <dependency>
        <groupId>org.apache.hadoop</groupId>
        <artifactId>hadoop-client</artifactId>
        <version>3.3.6</version>
        <scope>provided</scope>  <!-- 运行时由集群提供 -->
    </dependency>
    <dependency>
        <groupId>org.apache.hadoop</groupId>
        <artifactId>hadoop-common</artifactId>
        <version>3.3.6</version>
    </dependency>
</dependencies>
⚠️ 注意版本一致性: 所有Hadoop相关的jar包版本必须一致。我曾经混用过3.2.0的hadoop-client和3.3.0的hadoop-common,结果运行时抛出 NoSuchMethodError。排查了半天才发现是版本冲突。

3.3.2 打包与提交

写一个简单的WordCount程序,然后执行 mvn clean package。生成的jar包在target目录下。提交到集群的命令:

hadoop jar target/wordcount-1.0.jar com.example.WordCount /input /output

这里有个坑:输出目录不能已存在。Hadoop会报 FileAlreadyExistsException。我习惯在代码里加一段逻辑,如果输出目录存在就删除它:

FileSystem fs = FileSystem.get(conf);
Path outputPath = new Path(args[1]);
if (fs.exists(outputPath)) {
    fs.delete(outputPath, true);
}
💡 避坑指南: 如果你在Windows上开发,提交到Linux集群时,注意换行符问题。Windows的 \r\n 在Linux下会被当成两个字符。我建议在pom.xml里配置 maven-compiler-pluginencoding 为UTF-8,并且用 mvn clean package -DskipTests 跳过测试,加快打包速度。

3.4 验证环境——跑通第一个程序

环境搭好了,怎么验证?我的做法是:写一个最简单的MapReduce程序,统计文本文件的行数。为什么选这个?因为逻辑简单,能快速验证HDFS读写、Map和Reduce阶段是否正常。

启动Hadoop集群:

start-dfs.sh
start-yarn.sh

上传测试文件:

hdfs dfs -put /path/to/test.txt /input

运行你的WordCount程序。如果控制台输出 Job succeeded,恭喜你,环境搭建完成!

最后说一句: 环境搭建是MapReduce学习的第一道坎。跨过去,后面就顺畅了。我当年搭环境花了两天,各种报错。现在回想起来,其实都是些小问题——路径写错了、端口没开、防火墙没关。你只要按步骤来,遇到问题多看看日志,基本都能解决。

好,这一章就到这里。下一章咱们开始写真正的MapReduce代码,到时候我会分享一些我在项目中踩过的坑,保证让你少走弯路。