spark程序开发中出现 java.lang.ClassNotFoundException的处理

开发spark程序中出现异常总结出如下:

一.通过idea开发spark程序,运行scala文件时候出现错误

Caused by: java.lang.ClassNotFoundException: xxx.WordCount$$anonfun$2
	at java.net.URLClassLoader.findClass(URLClassLoader.java:382)
	at java.lang.ClassLoader.loadClass(ClassLoader.java:424)
	at java.lang.ClassLoader.loadClass(ClassLoader.java:357)
	at java.lang.Class.forName0(Native Method)
	at java.lang.Class.forName(Class.java:348)
    ......

这种情况出现的原因是程序找不到 WordCount 的编译文件,针对这种情况有两个原因:

1.该.scala文件并未放在scala目录下
如果是java和scala文件混合的项目,通过mvn clean package打成jar包的时候,jar包中并不一定会有编译好的scala的class文件,简而言之就是没有WordCount$$anonfun$2.class文件!

解决:main目录右键新建目录scala,然后右键 Mark Diretory as -> Sources root 即可,然后将需要执行的scala文件放置其中即可,项目重新build一下,在target文件夹中可以看到WordCount.scala文件。

编译成功之后,通过maven插件打jar包,建议通过 maven-jar-plugin中的jar:jar双击生成。然后通过编译工具(可以解压出来)查看是否把java和scala代码打包成功:也就是文件中是否有WordCount$$anonfun$2.class文件!

2.并未指定运行jar包位置
运行程序,发现依然报同样的错误,这可能是生成jar包的位置程序并不知道 (-。-!) 没办法,在配置参数中加上jar包的绝对路径即可!

解决:在配置参数中加上jar包的路径,通过 .setJars(Array(“path2jar”))即可,这里需要注意的是jar包的位置是你本地开发环境的地址,而不是集群环境上的地址!

val conf: SparkConf = new SparkConf()
      .setAppName("WordCount")
      .setMaster("spark://master_ip:7077")
      .setJars(Array("/home/xxx/WordCount.jar")) //需要加上去的
val sc = new SparkContext(conf)

然后运行,终于成功啦!

19/12/26 19:48:06 INFO DAGScheduler: ResultStage 1 (collect at WordCount.scala:20) finished in 0.145 s
19/12/26 19:48:06 INFO DAGScheduler: Job 0 finished: collect at WordCount.scala:20, took 2.280499 s
(are,2)
(how,1)
(map,3)
(hello,4)
(yarn,1)
(what,1)
(now,1)
(reduce,1)
(world,1)
(job,4)
(you,2)
(hadoop,3)
(bad,2)
(good,2)
(doing,1)

上述这种是通过idea远程访问spark集群的方式运行程序,这样可以前期调试更改和测试代码。

二.在spark集群上运行jar包时候报错

[root@hadoop000 master]# spark-submit --class WordCount --master spark://master_ip:7077 /opt/hadoop/lib/WordCount.jar 

这种情况出现的原因与上面第一个的处理基本相同:

Caused by: java.lang.ClassNotFoundException: xxx.WordCount$$anonfun$2
	at java.net.URLClassLoader.findClass(URLClassLoader.java:382)
	at java.lang.ClassLoader.loadClass(ClassLoader.java:424)
	at java.lang.ClassLoader.loadClass(ClassLoader.java:357)
	at java.lang.Class.forName0(Native Method)
	at java.lang.Class.forName(Class.java:348)
    ......

解决方法与上面相同,并且程序里面可以不用指定jar包的位置。稍有区别的是 /opt/hadoop/lib/WordCount.jar 这里的jar包是集群环境中的位置。至此问题解决

你可能感兴趣的:(问题解决)