Spark常見錯誤問題匯總
在執(zhí)行insert 語句時報錯,堆棧信息為:FileSystem closed。常常出現(xiàn)在ThriftServer里面。
原因:由于hadoop FileSystem.get 獲得的FileSystem會從緩存加載,如果多線程一個線程closedFileSystem會導致該BUG
解決方法:hdfs存在不從緩存加載的解決方式,在hdfs-site.xml 配置 fs.hdfs.impl.disable.cache=true即可
在執(zhí)行Spark過程中拋出:Failed to bigdata010108:33381,caused by:java.nio.channels.unresolvedAdderssException
原因:該原因是由于hosts未配置,導致不識別
解決方法:修改相應的機器的host即可
在執(zhí)行Sparksql操作orc類型的表時拋出:java.lang.IndexOutOfBoundsException 或者 java.lang.NullPointerException
原因:分區(qū)或者表下存在空的orc文件。該BUG在Spark2.3.0之后才修復
解決方法:規(guī)避解決。修改ORC的默認分割策略為:hive.exec.orc.split.strategy=BI進行解決。Orc的分split有3種策略(ETL、BI、HYBIRD),默認是HYBIRD(混合模式,根據(jù)文件大小和文件個數(shù)自動選擇ETL還是BI模式),BI模式是按照文件個數(shù)來分split
Spark2.1.0不支持永久函數(shù),這是由于Spark2.2.0之前不支持讀取hdfs上面的jar包。
Saprk-sql和ThriftServer使用時報錯:Java.net.socketTimeOutException:read time out
原因:是由于hivemetastore過于繁忙或者gc導致連接超時
解決方法:spark-sql解決:hive.metastore.client.socket.timeout將該參數(shù)調(diào)大。ThriftServer解決辦法:在獲得一個Connection之前加上:DriverManager.setLoginTimeout(100)
操作snappy壓縮的表時拋出:java.lang.RuntimeException: native snappy library not available: this version of libhadoop was built without snappy support.
原因:是由于沒有在java.library.path上加上snappy庫
解決方法:修改spark-default.conf配置文件加上:spark.executor.extraLibraryPath /data/Install/hadoop/lib/native 或者spark.executor.extraJavaOptions -Djava.library.path=/data/Install/hadoop/lib/native
Spark-sql在執(zhí)行時將一個很小的文件拆分成了20個task進行運行,導致運行速度太慢。
原因:是由于HaddopRDD生成過程中partitions是會拿參數(shù)mapreduce.job.maps ,或mapred.map.tasks(20)和spark默認分區(qū)數(shù)(2)做最大值比較,所以導致默認為20
解決方法:修改該參數(shù)就可以將task降下來。
ThriftServer登錄異常:javax.security.sasl.AuthenticationException: Error validating LDAP user
原因:是由于密碼錯誤或者LDAP服務異常
解決方法:解決密碼和驗證問題
使用jdbc的方式連接到ThriftServer,可以執(zhí)行類似與show tabls的等操作,但是不能執(zhí)行select相關的操作:java.io.IOException: Failed to create local dir in /tmp/blockmgr-adb70127-0a28-4256-a205-c575acc74f9d/06.
原因:用戶很久沒使用ThriftServer導致系統(tǒng)清理了該上級目錄或者用戶根本就對該目錄沒有寫權限
解決方法:重啟ThriftServer和設置目錄權限:spark.local.dir
在Spark SQL中運行的SQL語句過于復雜的話,會出現(xiàn) java.lang.StackOverflowError 異常
原因:這是因為程序運行的時候 Stack 大小大于 JVM 的設置大小
解決方法:通過在啟動 Spark-sql 的時候加上 --driver-java-options “-Xss10m” 選項解決這個問題
INSERT INTO重復執(zhí)行出現(xiàn):Unable to move source hdfs://bigdata05/tmp/hive-hduser1101_hive_2017-09-11_14-50-56_038_2358196375683362770-82/-ext-10000/part-00000 to destination hdfs://bigdata05/user/hive
原因:該問題是2.1.0的Bug,在Spark2.1.1中已經(jīng)解決2.1.0。
解決方法:2.1.0規(guī)避辦法INSERT OVERWRITE不帶分區(qū)重復執(zhí)行不會出現(xiàn)問題
執(zhí)行大數(shù)據(jù)量的join等操作時出現(xiàn):1.Missing an output location for shuffle;2.Failed to connect to bigdata030015/100.103.131.13:38742; 3.FileNotFoundException……(not such file or directory)。4.Container killed on request. Exit code is 143
原因:shuffle分為shuffle write和shuffle read兩部分。shuffle write的分區(qū)數(shù)由上一階段的RDD分區(qū)數(shù)控制,shuffle read的分區(qū)數(shù)則是由Spark提供的一些參數(shù)控制。shuffle write可以簡單理解為類似于saveAsLocalDiskFile的操作,將計算的中間結(jié)果按某種規(guī)則臨時放到各個executor所在的本地磁盤上。
shuffle read的時候數(shù)據(jù)的分區(qū)數(shù)則是由spark提供的一些參數(shù)控制。可以想到的是,如果這個參數(shù)值設置的很小,同時shuffle read的量很大,那么將會導致一個task需要處理的數(shù)據(jù)非常大。結(jié)果導致JVM crash(OOM),從而導致取shuffle數(shù)據(jù)失敗,同時executor也丟失了,看到Failed to connect to host的錯誤,也就是executor lost的意思。有時候即使不會導致JVM crash也會造成長時間的gc
解決方法:1. 調(diào)優(yōu)sql。
2.SparkSQL和DataFrame的join,group by等操作通過spark.sql.shuffle.partitions控制分區(qū)數(shù),默認為200,根據(jù)shuffle的量以及計算的復雜度提高這個值。
3.Rdd的join,groupBy,reduceByKey等操作,通過spark.default.parallelism控制shuffle read與reduce處理的分區(qū)數(shù),設置大一點。
4.通過提高executor的內(nèi)存設置spark.executor.memory適當提高executor的memory值。
5.判斷join過程中是否存在數(shù)據(jù)傾斜的問題:可以參考鏈接:https://tech.meituan.com/spark-tuning-pro.html
Sparksql使用過程中Executor端拋出:java.lang.OutOfMemoryError: GC overhead limit exceeded
原因:這是由于大部分事件都在GC,導致OOM。
解決方法:加大執(zhí)行器內(nèi)存,修改GC策略spark.executor.extraJavaOptions -XX:+UseG1GC
hiveserver2和SparkThriftServer使用操作orc表的時候報錯A用戶無法訪問B用戶的目錄。
原因:這是由于orc 在進行Split過沖中會進行用戶緩存。ORC在hive1.2.1時的BUG,在hive2.X和Spark2.3.X版本后進行了解決
解決方法:暫時規(guī)避方法比較暴力,1、先使用超級用戶進行第一次查詢,導致緩存的用戶為超級用戶。2、設置hive.fetch.task.conversion=none不進行緩存
spark-sql在使用過程中小數(shù)據(jù)量查詢很慢,查看sparkUI顯示每個Task處理都很快,但是都隔了3秒進行調(diào)度導致整體很慢。
原因:這是由于數(shù)據(jù)本地性導致的,默認spark.locality.wait為3秒
解決方法:設置該參數(shù)為0即可加快速度,只有在數(shù)據(jù)量較小的情況下才建議這樣設置。
on yarn啟動spark-sql 和spark-submit時出現(xiàn):java.lang.NoClassDefFoundError: com/sun/jersey/api/client/config/ClientConfig
原因:和yarn相關Jersey包沖突
解決方法:配置上–conf spark.hadoop.yarn.timeline-service.enabled=false
在使用Spark過程中出現(xiàn):java.io.IOException: No space left on device
原因:一般是由于Spark的tmp目錄滿了導致
解決方法:可以將該目錄空間設置大點,支持按逗號分割多個目錄:spark.local.dir
超出最大結(jié)果集:is bigger than spark.driver.maxResultSize (2.0GB)
原因:spark.driver.maxResultSize默認配置為1G
解決方法:調(diào)大該參數(shù)即可
常見OOM:java.lang.OutOfMemoryError: Java heap space
原因:1、數(shù)據(jù)量太大,申請的Executor資源不足以支撐。2.單分區(qū)的數(shù)據(jù)量過大,和分區(qū)數(shù)過多導致執(zhí)行task和job存儲的信息過多導致Driver OutOfMemoryError
解決方法:1、盡量不要使用collect操作。2、查看數(shù)據(jù)是否有傾斜,增加shuffle的并行度,加大Executor內(nèi)存
由Executor的FullGC引起Executor lost,task失敗,各種超時:Futures timed out after【120S】
原因:一般是由于Executor處理數(shù)據(jù)量過大如傾斜導致,從而使Executor full gc導致時間超時,Executor 和 task 的lost
解決方法:1、如果通過查看Executor的日志是full GC導致,適當調(diào)優(yōu)SQL,加大Executor內(nèi)存。2、如果沒有fullGC考慮提高:spark.network.timeout
jar包版本沖突時:java.lang.ClassNotFoundException: XXX
原因:一般可能是用戶jar和Spark jar沖突
解決方法:1、最好和Spark相關的jar進行適配。2、如果不行可以使用參數(shù):spark.driver.userClassPathFirst和spark.executor.userClassPathFirst 設置為true
進行shuffle拋出:Shuffle Fetch Failed: OOM
原因:Shuffle fetch階段開啟的fetch數(shù)據(jù)量過大導致
解決方法:1、加大Executor內(nèi)存。2、將參數(shù)spark.reduce.maxSizeInFlight調(diào)小,默認48M
shuffle報org.apache.spark.shuffle.FetchFailedException: Direct buffer memory
原因:堆外內(nèi)存不夠?qū)е拢苯觾?nèi)存
解決方法:增大JVM 參數(shù)-XX:MaxDirectMemorySize(如:spark.executor.extraJavaOptions = -XX:MaxDirectMemorySize=xxxm)
集群節(jié)點異常導致Spark job失敗,如磁盤只讀。
原因:Spark 是一個高性能、容錯的分布式計算框架,一旦它知道某個計算所在的機器出現(xiàn)問題會依據(jù)之前生成的 lineage 重新在這臺機器上調(diào)度這個 Task,如果超過失敗次數(shù)就會導致job失敗。
解決方法:Spark有黑名單機制,在超出一定次數(shù)的失敗后不會往該節(jié)點或者Executor調(diào)度Task。設置相應Black參數(shù):spark.blacklist.enabled=true
driver python和Executor Python版本不一致問題
原因:pyspark要求所有的Executor運行的python版本一致
解決方法:指定python的運行路徑:spark.pyspark.python /data/Install/Anaconda2Install/Anaconda3-5.1.0/bin/python 或者 env配置上:export PYSPARK_PYTHON=/data/Install/Anaconda2Install/Anaconda3-5.1.0/bin/python;export PYSPARK_DRIVER_PYTHON=/data/Install/Anaconda2Install/Anaconda3-5.1.0/bin/python
Pyspark使用過程中出現(xiàn):RDD時出現(xiàn)序列化pickle.load(obj)報錯,EOFError。有時可以,在local也可以。
原因:在on yarn時,機器上也有安裝相關的Spark。導致包沖突
解決方法:刪除nodeManager上的Spark安裝路徑就可以解決
運行RDD操作時報Randomness of hash of string should be disabled via PYTHONHASHSEED mean in pyspark
原因:這是由于各個Executor的Hash隨機值不一樣導致。
解決方法:只需要指定各Executor的PYTHONHASHSEED環(huán)境變量即可如:–conf spark.executorEnv.PYTHONHASHSEED=321
消費kafka時,第一個job讀取了現(xiàn)有所有的消息,導致第一個Job處理過久甚至失敗
原因:auto.offset.reset設置為了earliest 從最早的offset開始進行消費,也沒有設置spark.streaming.kafka.maxRatePerPartition參數(shù)
解決方法:指定從之前開始消費的數(shù)據(jù)開始:設置offsetRange。并將參數(shù)設置為:auto.offset.reset=latest 設置Spark每個分區(qū)的速率。
盡量使用高性能算子
使用reduceByKey/aggregateByKey替代groupByKey
使用mapPartitions替代普通map
使用foreachPartitions替代foreach
使用filter之后進行coalesce操作
使用repartitionAndSortWithinPartitions替代repartition與sort類操作
Streaming如果存在多個Batch延遲時,消費不過來。有時會報出:Hbase相關的異常如:RegionTooBusyException
原因:Streaming在進行處理時如果單個Batch讀取的數(shù)據(jù)多,會導致計算延遲甚至導致存儲組件性能壓力
解決方法:1、如果是計算延遲試著調(diào)整讀取速率如:spark.streaming.kafka.maxRatePerPartition參數(shù) 2、調(diào)優(yōu)存儲組件的性能 3、開啟Spark的反壓機制:spark.streaming.backpressure.enabled,該參數(shù)會自動調(diào)優(yōu)讀取速率。但是如果設置了spark.streaming.receiver.maxRate 或 spark.streaming.kafka.maxRatePerPartition,那么最后到底接收多少數(shù)據(jù)取決于三者的最小值
消費kafka時,讀取消息報錯:OffsetOutOfRangeException
原因:讀取的offsetRange超出了Kafka的消息范圍,如果是小于也就是kafka保存的消息已經(jīng)被處理掉了(log.retention.hours)。或者超出Kafka現(xiàn)有的offset
解決方法:在讀取offset時先進行校正,拿到offset的earliestOffset 和lastestOffset
Kafka抖動導致No leader found
kafka變更或者其他原因?qū)е?/span>
解決方法:設置 spark.streaming.kafka.maxRetries 大于1
