Spark + EMR verwendet die Amazon-Einstellung "maximizeResourceAllocation" nicht alle Cores / Vcores

8

Ich führe einen EMR-Cluster (Version emr-4.2.0) für Spark mit dem Amazon-spezifischen maximizeResourceAllocation -Flag wie dokumentiert hier . Diesen Dokumenten zufolge "berechnet diese Option die maximalen Rechen- und Speicherressourcen, die für einen Executor auf einem Knoten in der Kernknotengruppe verfügbar sind, und legt die entsprechenden Spark-Standardeinstellungen mit diesen Informationen fest."

Ich führe den Cluster mit m3.2xlarge-Instanzen für die Arbeiterknoten aus. Ich benutze eine einzige M3.xlarge für den YARN-Master - die kleinste M3-Instanz, auf der ich es ausführen kann, da es nicht viel bringt.

Die Situation ist folgende: Wenn ich einen Spark-Job ausführe, ist die Anzahl der angeforderten Kerne für jeden Executor 8. (Ich habe das erst nach der Konfiguration von "yarn.scheduler.capacity.resource-calculator": "org.apache.hadoop.yarn.util.resource.DominantResourceCalculator" , die nicht wirklich in der Dokumentation ist, aber ich schweife ab). Dies scheint sinnvoll zu sein, denn laut diesen Dokumenten hat ein m3.2xlarge 8 "vCPUs". In den tatsächlichen Instanzen selbst ist jedoch in /etc/hadoop/conf/yarn-site.xml jeder Knoten so konfiguriert, dass yarn.nodemanager.resource.cpu-vcores auf 16 gesetzt ist. Ich würde (zu einer Vermutung) denken, dass das wegen Hyperthreading oder vielleicht etwas anderer Hardware-Fanciness sein muss.

Das Problem ist also so: Wenn ich maximizeResourceAllocation verwende, erhalte ich die Anzahl der "vCPUs", die der Amazon-Instance-Typ hat, was nur die Hälfte der konfigurierten "VCores" zu sein scheint, auf denen YARN läuft der Knoten; Daher verwendet der Executor nur die Hälfte der tatsächlichen Rechenressourcen für die Instanz.

Ist das ein Fehler in Amazon EMR? Haben andere Menschen das gleiche Problem? Gibt es eine andere magische undokumentierte Konfiguration, die ich vermisse?

    
retnuH 30.11.2015, 16:51
quelle

3 Antworten

24

Okay, nach vielen Experimenten konnte ich das Problem aufspüren. Ich werde meine Ergebnisse hier veröffentlichen, um Menschen zu helfen, Frustration in der Zukunft zu vermeiden.

  • Obwohl zwischen den 8 angeforderten Kernen und den 16 VCores, die YARN kennt, eine Diskrepanz besteht, scheint dies keinen Unterschied zu machen. YARN verwendet keine cgroups oder irgendeinen Effekt, um tatsächlich zu begrenzen, wie viele CPUs der Executor tatsächlich benutzen kann.
  • "Cores" auf dem Executor ist eigentlich ein bisschen falsch. Es ist tatsächlich, wie viele gleichzeitige Aufgaben der Executor bereitwillig gleichzeitig ausführen wird; läuft im Wesentlichen darauf hinaus, wie viele Threads auf jedem Executor "arbeiten".
  • Wenn maximizeResourceAllocation festgelegt ist, wird beim Ausführen eines Spark-Programms die Eigenschaft spark.default.parallelism als Anzahl der Instanz-Cores (oder "vCPUs") für alle Nicht-Master-Instanzen im Cluster zur Zeit der Schöpfung. Dies ist wahrscheinlich selbst in normalen Fällen zu klein; Ich habe gehört, dass es empfohlen wird, dies auf das Vierfache der Anzahl der Kerne einzustellen, die Sie für Ihre Jobs benötigen. Dadurch wird sichergestellt, dass in jeder Phase genügend Tasks zur Verfügung stehen, um die CPUs auf allen Executoren beschäftigt zu halten.
  • Wenn Sie Daten haben, die aus verschiedenen Läufen verschiedener Spark-Programme stammen, werden Ihre Daten (in RDD- oder Parquet-Format oder was auch immer) höchstwahrscheinlich mit einer unterschiedlichen Anzahl von Partitionen gespeichert. Stellen Sie beim Ausführen eines Spark-Programms sicher, dass Sie die Daten entweder zur Ladezeit oder vor einer besonders CPU-intensiven Task neu partitionieren. Da Sie zur Laufzeit Zugriff auf die Einstellung spark.default.parallelism haben, kann dies eine bequeme Nummer für die Neupartitionierung sein.

TL; DR

  1. maximizeResourceAllocation wird fast alles für Sie richtig machen außer ...
  2. Sie möchten wahrscheinlich spark.default.parallelism auf 4x Anzahl von Instanzkernen setzen, auf denen der Job ausgeführt werden soll, auf einer "Schritt" (in EMR-Sprache) / "Anwendung" (in YARN-Sprache) Basis, dh setze es jedes Mal und ...
  3. Stellen Sie sicher, dass in Ihrem Programm so ist, dass Ihre Daten entsprechend partitioniert sind (d. h. viele Partitionen haben), damit Spark es korrekt parallelisieren kann
retnuH 02.12.2015 11:05
quelle
2

Mit dieser Einstellung sollten Sie 1 Executor für jede Instanz (außer dem Master) mit jeweils 8 Kernen und etwa 30 GB RAM erhalten.

Ist die Spark-Benutzerschnittstelle bei http: //: 8088 / diese Zuordnung nicht angezeigt?

Ich bin mir nicht sicher, ob die Einstellung im Vergleich zu der anderen Seite, die auf der Seite "Dynamische Zuweisung von Executoren aktivieren" erwähnt wird, wirklich viel Wert ist. Dadurch kann Spark die eigene Anzahl von Instanzen für einen Job verwalten. Wenn Sie eine Task mit 2 CPU-Kernen und 3G RAM pro Executor starten, erhalten Sie ein recht gutes Verhältnis von CPU zu Speicher für die EMR-Instanzgrößen. p>     

Ewan Leith 30.11.2015 17:12
quelle
0

In der EMR-Version 3.x wurde diese maximizeResourceAllocation mit einer Referenztabelle implementiert: Ссылка

Es wird von einem Shell-Skript verwendet: maximize-spark-default-config , im selben Repo können Sie sehen, wie sie das implementiert haben.

vielleicht in der neuen EMR-Version 4, diese Referenztabelle war irgendwie falsch ... ich glaube, dass Sie alle diese AWS-Skript in Ihrer EC2-Instanz von EMR finden können, sollte sich in / usr / lib / Funken oder / opt / aws oder so ähnlich.

zumindest, Sie können Ihre eigenen bootstrap action -Skripte dafür in EMR 4 schreiben, mit einer korrekten Referenztabelle, ähnlich der Implementierung in EMR 3.x

Da wir die STUPS Infrastruktur verwenden werden, sollten Sie auch die STUPS Appliance für Spark ansehen: Ссылка

Sie können die Anzahl der Kerne explizit angeben, indem Sie den Senza-Parameter DefaultCores bei der Bereitstellung Ihres Funke-Clusters festlegen

Einige der Highlights dieser Appliance im Vergleich zu EMR sind:

kann es sogar mit dem Instanztyp t2 verwenden, automatisch skalierbar basierend auf Rollen wie andere STUPS-Appliances usw.

und Sie können Ihren Cluster einfach im HA-Modus mit zoekeeper bereitstellen, sodass kein SPOF auf dem Hauptknoten, HA-Modus in EMR derzeit noch nicht möglich ist, und ich glaube, dass EMR hauptsächlich für "groß" ausgelegt ist Cluster vorübergehend für Ad-hoc-Analyse-Jobs ", nicht für" dedizierte Cluster, die dauerhaft eingeschaltet ist ", so HA-Modus wird nicht in naher Zukunft mit EMR möglich sein.

    
chutium 02.12.2015 13:00
quelle