Конфигурисање Спарк-а на ИАРН-у

Хабр, здраво! Јуче на састанак посвећен Апацхе Спарк-у, од момака из Рамблер&Цо, било је доста питања учесника везаних за конфигурисање овог алата. Одлучили смо да кренемо његовим стопама и поделимо своје искуство. Тема није лака - зато вас позивамо да поделите своје искуство у коментарима, можда и ми нешто погрешно разумемо и користимо.

Мали увод у то како користимо Спарк. Имамо тромесечни програм „Специјалист за велике податке“, а током другог модула наши учесници раде на овом инструменту. Сходно томе, наш задатак, као организатора, је да припремимо кластер за коришћење у оваквом случају.

Посебност наше употребе је да број људи који истовремено раде на Спарку може бити једнак целој групи. На пример, на семинару, када сви покушавају нешто у исто време и понављају за нашим учитељем. А ово није много - понекад и до 40 људи. Вероватно нема много компанија у свету које се суочавају са таквим случајем употребе.

Затим ћу вам рећи како и зашто смо одабрали одређене параметре конфигурације.

Почнимо од самог почетка. Спарк има 3 опције за покретање на кластеру: самостално, користећи Месос и користећи ИАРН. Одлучили смо да изаберемо трећу опцију јер нам је то имало смисла. Већ имамо хадооп кластер. Наши учесници су већ добро упознати са његовом архитектуром. Хајде да користимо ПРЕДУ.

spark.master=yarn

Даље занимљивије. Свака од ове 3 опције постављања има 2 опције распоређивања: клијент и кластер. Заснован документација и разним линковима на Интернету, можемо закључити да је клијент погодан за интерактивни рад - на пример, преко јупитер нотебоок-а, а кластер погоднији за производна решења. У нашем случају, били смо заинтересовани за интерактивни рад, дакле:

spark.deploy-mode=client

Генерално, од сада ће Спарк некако радити на ИАРН-у, али то нам није било довољно. Пошто имамо програм о великим подацима, понекад учесницима није било довољно онога што се добија у оквиру равномерног сечења ресурса. А онда смо пронашли занимљиву ствар - динамичку алокацију ресурса. Укратко, поента је следећа: ако имате тежак задатак и кластер је слободан (на пример, ујутру), онда коришћење ове опције Спарк вам може дати додатне ресурсе. Нужда се тамо рачуна по лукавој формули. Нећемо улазити у детаље - ради добро.

spark.dynamicAllocation.enabled=true

Поставили смо овај параметар и након покретања Спарк се срушио и није се покренуо. Тако је, јер сам то морао да прочитам документација пажљивије. У њему се наводи да да би све било у реду потребно је и да омогућите додатни параметар.

spark.shuffle.service.enabled=true

Зашто је то потребно? Када наш посао више не захтева толико ресурса, Спарк би требало да их врати у заједнички базен. Фаза која одузима највише времена у скоро сваком МапРедуце задатку је фаза Схуффле. Овај параметар вам омогућава да сачувате податке који се генеришу у овој фази и у складу са тим ослободите извршиоце. А извршилац је процес који све обрачунава на радника. Има одређени број процесорских језгара и одређену количину меморије.

Овај параметар је додат. Чинило се да све функционише. Постало је приметно да су учесницима заправо дато више ресурса када су им били потребни. Али појавио се још један проблем - у неком тренутку су се други учесници пробудили и такође су желели да користе Спарк, али тамо је све било заузето и они су били незадовољни. Могу се разумети. Почели смо да гледамо документацију. Испоставило се да постоји низ других параметара који се могу користити за утицај на процес. На пример, ако је извршитељ у режиму приправности, након којег времена се могу узети ресурси из њега?

spark.dynamicAllocation.executorIdleTimeout=120s

У нашем случају, ако ваши извршиоци не ураде ништа два минута, молимо вас да их вратите у заједнички базен. Али овај параметар није увек био довољан. Било је јасно да особа већ дуже време ништа не ради, а ресурси се не ослобађају. Испоставило се да постоји и посебан параметар - после ког времена изабрати извршиоце који садрже кеширане податке. Подразумевано, овај параметар је био бесконачност! Исправили смо то.

spark.dynamicAllocation.cachedExecutorIdleTimeout=600s

То јест, ако ваши извршиоци не раде ништа 5 минута, дајте их у заједнички базен. У овом режиму, брзина пуштања и издавања ресурса за велики број корисника постала је пристојна. Количина незадовољства је смањена. Али одлучили смо да идемо даље и ограничимо максималан број извршилаца по апликацији – у суштини по учеснику програма.

spark.dynamicAllocation.maxExecutors=19

Сада су, наравно, незадовољни на другој страни – „кластер мирује, а ја имам само 19 извршилаца“, али шта можете, треба нам нека исправна равнотежа. Не можете учинити све срећним.

И још једна мала прича везана за специфичности нашег случаја. Некако је неколико људи закаснило на практичан час, а Варница из неког разлога није почела за њих. Погледали смо количину бесплатних ресурса - изгледа да постоји. Варница би требало да почне. Срећом, до тада је документација већ била додата у подкортекс негде, а ми смо се сетили да када се покрене, Спарк тражи порт на коме ће почети. Ако је први порт у опсегу заузет, он се помера на следећи по реду. Ако је слободан, хвата. И постоји параметар који означава максималан број покушаја за ово. Подразумевано је 16. Број је мањи од броја људи у нашој групи у разреду. Сходно томе, након 16 покушаја, Спарк је одустао и рекао да не могу да почнем. Исправили смо овај параметар.

spark.port.maxRetries=50

Затим ћу вам рећи о неким подешавањима која нису баш повезана са специфичностима нашег случаја.

Да бисте брже покренули Спарк, препоручује се да архивирате фасциклу јарс која се налази у матичном директоријуму СПАРК_ХОМЕ и ставите је на ХДФС. Онда неће губити време утоварујући ове јарнике од стране радника.

spark.yarn.archive=hdfs:///tmp/spark-archive.zip

Такође се препоручује да користите крио као серијализатор за бржи рад. Оптимизованији је од подразумеваног.

spark.serializer=org.apache.spark.serializer.KryoSerializer

Такође постоји дугогодишњи проблем са Спарк-ом који се често руши из меморије. Често се то дешава у тренутку када радници све израчунају и пошаљу резултат возачу. Овај параметар смо повећали за себе. Подразумевано је 1ГБ, ми смо направили 3.

spark.driver.maxResultSize=3072

И на крају, као десерт. Како ажурирати Спарк на верзију 2.1 на ХортонВоркс дистрибуцији - ХДП 2.5.3.0. Ова верзија ХДП-а садржи унапред инсталирану верзију 2.0, али смо једном за себе одлучили да се Спарк прилично активно развија, а свака нова верзија исправља неке грешке плус пружа додатне функције, укључујући и за питхон АПИ, па смо одлучили шта треба да бити урађено је ажурирање.

Преузета верзија са званичне веб странице за Хадооп 2.7. Распакујте га и ставите у фасциклу ХДП. По потреби смо инсталирали симболичне везе. Покрећемо га - не почиње. Пише веома чудну грешку.

java.lang.NoClassDefFoundError: com/sun/jersey/api/client/config/ClientConfig

Након гуглања сазнали смо да је Спарк одлучио да не чека да се роди Хадооп и одлучио је да користи нову верзију дреса. Они се сами међусобно расправљају о овој теми у ЈИРА-и. Решење је било преузимање верзија дреса 1.17.1. Поставите ово у фасциклу тегли у СПАРК_ХОМЕ, поново зипујте и отпремите на ХДФС.

Заобишли смо ову грешку, али се појавила нова и прилично поједностављена.

org.apache.spark.SparkException: Yarn application has already ended! It might have been killed or unable to launch application master

У исто време покушавамо да покренемо верзију 2.0 - све је у реду. Покушајте да погодите шта се дешава. Погледали смо у евиденцију ове апликације и видели нешто овако:

/usr/hdp/${hdp.version}/hadoop/lib/hadoop-lzo-0.6.0.${hdp.version}.jar

Генерално, из неког разлога хдп.версион није решен. Након гуглања, пронашли смо решење. Морате да одете до подешавања ИАРН-а у Амбарију и тамо додате параметар на прилагођену локацију за предиво:

hdp.version=2.5.3.0-37

Ова магија је помогла и Варница је полетела. Тестирали смо неколико наших јупитер лаптопова. Све ради. Спремни смо за први час Спарк у суботу (сутра)!

УПД. Током лекције појавио се још један проблем. У неком тренутку, ИАРН је престао да обезбеђује контејнере за Спарк. У ИАРН-у је било потребно исправити параметар, који је подразумевано био 0.2:

yarn.scheduler.capacity.maximum-am-resource-percent=0.8

Односно, само 20% ресурса је учествовало у расподели ресурса. Након промене параметара, поново смо учитали ИАРН. Проблем је решен, а остали учесници су такође могли да покрену контекст.

Извор: ввв.хабр.цом

Додај коментар