Ich habe Spark mit Hilfe des AWS EC2-Handbuchs installiert und kann das Programm mit dem bin/pyspark
-Skript starten, um zur Spark-Eingabeaufforderung zu gelangen. Außerdem kann ich die Schnellstart-Quide erfolgreich ausführen.
Ich kann jedoch nicht umsonst herausfinden, wie ich die ausführliche INFO
-Protokollierung nach jedem Befehl beenden kann.
Ich habe fast jedes mögliche Szenario in dem folgenden Code (auskommentieren, auf AUS gesetzt) in meiner log4j.properties
-Datei im conf
-Ordner ausprobiert, in dem ich die Anwendung von und auf jedem Knoten starte und nichts tut. Ich bekomme immer noch die Logging-Anweisungen INFO
, nachdem ich jede Anweisung ausgeführt habe.
Ich bin sehr verwirrt, wie das funktionieren soll.
#Set everything to be logged to the console log4j.rootCategory=INFO, console
log4j.appender.console=org.Apache.log4j.ConsoleAppender
log4j.appender.console.target=System.err
log4j.appender.console.layout=org.Apache.log4j.PatternLayout
log4j.appender.console.layout.ConversionPattern=%d{yy/MM/dd HH:mm:ss} %p %c{1}: %m%n
# Settings to quiet third party logs that are too verbose
log4j.logger.org.Eclipse.jetty=WARN
log4j.logger.org.Apache.spark.repl.SparkIMain$exprTyper=INFO
log4j.logger.org.Apache.spark.repl.SparkILoop$SparkILoopInterpreter=INFO
Hier ist mein vollständiger Klassenpfad, wenn ich SPARK_PRINT_LAUNCH_COMMAND
verwende:
Spark-Befehl: /Library/Java/JavaVirtualMachines/jdk1.8.0_05.jdk/Contents/Home/bin/Java -cp: /root/spark-1.0.1-bin-hadoop2/conf: /root/spark-1.0.1-bin-hadoop2/conf: /root/spark-1.0.1-bin-hadoop2/lib/spark- Assembly-1.0.1-hadoop2.2.0.jar: /root/spark-1.0.1-bin-hadoop2/lib/datanucleus-api-jdo-3.2.1.jar: /root/spark-1.0.1-bin- hadoop2/lib/datanucleus-core-3.2.2.jar: /root/spark-1.0.1-bin-hadoop2/lib/datanucleus-rdbms-3.2.1.jar -XX: MaxPermSize = 128m -Djava.library.path = -Xms512m -Xmx512m org.Apache.spark.deploy.SparkSubmit spark-Shell --class org.Apache.spark.repl.Main
inhalt von spark-env.sh
:
#!/usr/bin/env bash
# This file is sourced when running various Spark programs.
# Copy it as spark-env.sh and edit that to configure Spark for your site.
# Options read when launching programs locally with
# ./bin/run-example or ./bin/spark-submit
# - HADOOP_CONF_DIR, to point Spark towards Hadoop configuration files
# - SPARK_LOCAL_IP, to set the IP address Spark binds to on this node
# - SPARK_PUBLIC_DNS, to set the public dns name of the driver program
# - SPARK_CLASSPATH=/root/spark-1.0.1-bin-hadoop2/conf/
# Options read by executors and drivers running inside the cluster
# - SPARK_LOCAL_IP, to set the IP address Spark binds to on this node
# - SPARK_PUBLIC_DNS, to set the public DNS name of the driver program
# - SPARK_CLASSPATH, default classpath entries to append
# - SPARK_LOCAL_DIRS, storage directories to use on this node for shuffle and RDD data
# - MESOS_NATIVE_LIBRARY, to point to your libmesos.so if you use Mesos
# Options read in YARN client mode
# - HADOOP_CONF_DIR, to point Spark towards Hadoop configuration files
# - SPARK_EXECUTOR_INSTANCES, Number of workers to start (Default: 2)
# - SPARK_EXECUTOR_CORES, Number of cores for the workers (Default: 1).
# - SPARK_EXECUTOR_MEMORY, Memory per Worker (e.g. 1000M, 2G) (Default: 1G)
# - SPARK_DRIVER_MEMORY, Memory for Master (e.g. 1000M, 2G) (Default: 512 Mb)
# - SPARK_YARN_APP_NAME, The name of your application (Default: Spark)
# - SPARK_YARN_QUEUE, The hadoop queue to use for allocation requests (Default: ‘default’)
# - SPARK_YARN_DIST_FILES, Comma separated list of files to be distributed with the job.
# - SPARK_YARN_DIST_ARCHIVES, Comma separated list of archives to be distributed with the job.
# Options for the daemons used in the standalone deploy mode:
# - SPARK_MASTER_IP, to bind the master to a different IP address or hostname
# - SPARK_MASTER_PORT / SPARK_MASTER_WEBUI_PORT, to use non-default ports for the master
# - SPARK_MASTER_OPTS, to set config properties only for the master (e.g. "-Dx=y")
# - SPARK_WORKER_CORES, to set the number of cores to use on this machine
# - SPARK_WORKER_MEMORY, to set how much total memory workers have to give executors (e.g. 1000m, 2g)
# - SPARK_WORKER_PORT / SPARK_WORKER_WEBUI_PORT, to use non-default ports for the worker
# - SPARK_WORKER_INSTANCES, to set the number of worker processes per node
# - SPARK_WORKER_DIR, to set the working directory of worker processes
# - SPARK_WORKER_OPTS, to set config properties only for the worker (e.g. "-Dx=y")
# - SPARK_HISTORY_OPTS, to set config properties only for the history server (e.g. "-Dx=y")
# - SPARK_DAEMON_Java_OPTS, to set config properties for all daemons (e.g. "-Dx=y")
# - SPARK_PUBLIC_DNS, to set the public dns name of the master or workers
export SPARK_SUBMIT_CLASSPATH="$FWDIR/conf"
Führen Sie einfach diesen Befehl im Spark-Verzeichnis aus:
cp conf/log4j.properties.template conf/log4j.properties
Log4j.properties bearbeiten:
# Set everything to be logged to the console
log4j.rootCategory=INFO, console
log4j.appender.console=org.Apache.log4j.ConsoleAppender
log4j.appender.console.target=System.err
log4j.appender.console.layout=org.Apache.log4j.PatternLayout
log4j.appender.console.layout.ConversionPattern=%d{yy/MM/dd HH:mm:ss} %p %c{1}: %m%n
# Settings to quiet third party logs that are too verbose
log4j.logger.org.Eclipse.jetty=WARN
log4j.logger.org.Eclipse.jetty.util.component.AbstractLifeCycle=ERROR
log4j.logger.org.Apache.spark.repl.SparkIMain$exprTyper=INFO
log4j.logger.org.Apache.spark.repl.SparkILoop$SparkILoopInterpreter=INFO
Ersetzen Sie in der ersten Zeile:
log4j.rootCategory=INFO, console
durch:
log4j.rootCategory=WARN, console
Speichern Sie Ihre Shell und starten Sie sie erneut. Es funktioniert für mich für Spark 1.1.0 und Spark 1.5.1 unter OS X.
Inspiriert durch den Pyspark/Tests.Py, den ich gemacht habe
def quiet_logs( sc ):
logger = sc._jvm.org.Apache.log4j
logger.LogManager.getLogger("org"). setLevel( logger.Level.ERROR )
logger.LogManager.getLogger("akka").setLevel( logger.Level.ERROR )
Das Aufrufen dieses Befehls unmittelbar nach dem Erstellen von SparkContext reduzierte die für meinen Test protokollierten stderr-Zeilen von 2647 auf 163. Das Erstellen des SparkContext-Protokolls selbst protokolliert jedoch 163
15/08/25 10:14:16 INFO SparkDeploySchedulerBackend: SchedulerBackend is ready for scheduling beginning after reached minRegisteredResourcesRatio: 0.0
und es ist mir nicht klar, wie man diese programmgesteuert anpasst.
Bearbeiten Sie Ihre Datei conf/log4j.properties und ändern Sie die folgende Zeile:
log4j.rootCategory=INFO, console
zu
log4j.rootCategory=ERROR, console
Ein anderer Ansatz wäre:
Fireup spark-Shell und geben Sie Folgendes ein:
import org.Apache.log4j.Logger
import org.Apache.log4j.Level
Logger.getLogger("org").setLevel(Level.OFF)
Logger.getLogger("akka").setLevel(Level.OFF)
Danach werden keine Protokolle angezeigt.
>>> log4j = sc._jvm.org.Apache.log4j
>>> log4j.LogManager.getRootLogger().setLevel(log4j.Level.ERROR)
Sie können den Protokollierungsgrad in Ihren Skripts auch mit sc.setLogLevel("FATAL")
einstellen. Aus den docs :
Steuere unser LogLevel. Dadurch werden alle benutzerdefinierten Protokolleinstellungen überschrieben. Gültige Protokollebenen sind: ALL, DEBUG, ERROR, FATAL, INFO, OFF, TRACE, WARN
In Spark 2.0 können Sie es auch dynamisch für Ihre Anwendung konfigurieren, indem Sie setLogLevel verwenden:
from pyspark.sql import SparkSession
spark = SparkSession.builder.\
master('local').\
appName('foo').\
getOrCreate()
spark.sparkContext.setLogLevel('WARN')
In der Konsole pyspark ist bereits eine Standardsitzung spark
verfügbar.
Dies kann darauf zurückzuführen sein, wie Spark seinen Klassenpfad berechnet. Meiner Meinung nach ist, dass Hadoops log4j.properties
-Datei auf dem Klassenpfad vor Sparks erscheint und verhindert, dass Ihre Änderungen wirksam werden.
Wenn du läufst
SPARK_PRINT_LAUNCH_COMMAND=1 bin/spark-Shell
dann druckt Spark den vollständigen Klassenpfad, der zum Starten der Shell verwendet wird. In meinem Fall verstehe ich
Spark Command: /usr/lib/jvm/Java/bin/Java -cp :::/root/ephemeral-hdfs/conf:/root/spark/conf:/root/spark/lib/spark-Assembly-1.0.0-hadoop1.0.4.jar:/root/spark/lib/datanucleus-api-jdo-3.2.1.jar:/root/spark/lib/datanucleus-core-3.2.2.jar:/root/spark/lib/datanucleus-rdbms-3.2.1.jar -XX:MaxPermSize=128m -Djava.library.path=:/root/ephemeral-hdfs/lib/native/ -Xms512m -Xmx512m org.Apache.spark.deploy.SparkSubmit spark-Shell --class org.Apache.spark.repl.Main
dabei steht /root/ephemeral-hdfs/conf
an der Spitze des Klassenpfads.
Ich habe ein Problem [SPARK-2913] geöffnet, um dieses Problem in der nächsten Version zu beheben (ich sollte bald einen Patch herausbringen).
In der Zwischenzeit gibt es ein paar Problemumgehungen:
export SPARK_SUBMIT_CLASSPATH="$FWDIR/conf"
zu spark-env.sh
hinzu./root/ephemeral-hdfs/conf/log4j.properties
.Sie können setLogLevel verwenden
val spark = SparkSession
.builder()
.config("spark.master", "local[1]")
.appName("TestLog")
.getOrCreate()
spark.sparkContext.setLogLevel("WARN")
Spark 1.6.2:
log4j = sc._jvm.org.Apache.log4j
log4j.LogManager.getRootLogger().setLevel(log4j.Level.ERROR)
Spark 2.x:
spark.sparkContext.setLogLevel('WARN')
(Funke ist die SparkSession)
Alternativ die alten Methoden,
Benennen Sie conf/log4j.properties.template
in Sparkdir in conf/log4j.properties
um.
Ändern Sie in log4j.properties
log4j.rootCategory=INFO, console
in log4j.rootCategory=WARN, console
.
Verschiedene Protokollebenen verfügbar:
Ich habe dies mit Amazon EC2 mit 1 Master und 2 Slaves und Spark 1.2.1 verwendet.
# Step 1. Change config file on the master node
nano /root/ephemeral-hdfs/conf/log4j.properties
# Before
hadoop.root.logger=INFO,console
# After
hadoop.root.logger=WARN,console
# Step 2. Replicate this change to slaves
~/spark-ec2/copy-dir /root/ephemeral-hdfs/conf/
Ich mache das so:
an der Stelle führe ich das spark-submit
-Skript aus
$ cp /etc/spark/conf/log4j.properties .
$ nano log4j.properties
Ändern Sie INFO
auf die gewünschte Protokollierungsstufe und führen Sie dann Ihren spark-submit
aus.
Das folgende Code-Snippet für Scala-Benutzer:
Option 1:
Unterhalb des Snippets können Sie auf Dateiebene hinzufügen
import org.Apache.log4j.{Level, Logger}
Logger.getLogger("org").setLevel(Level.WARN)
Option 2:
Hinweis: Dies gilt für alle Anwendungen, die eine Funkensitzung verwenden.
import org.Apache.spark.sql.SparkSession
private[this] implicit val spark = SparkSession.builder().master("local[*]").getOrCreate()
spark.sparkContext.setLogLevel("WARN")
Option 3:
Hinweis: Diese Konfiguration sollte zu Ihren log4j.properties hinzugefügt werden (könnte wie /etc/spark/conf/log4j.properties (wo sich die Spark-Installation befindet) oder zu Ihren log4j.properties auf Projektordnerebene lauten), da Sie sich ändern Modulebene. Dies gilt für alle Bewerbungen.
log4j.rootCategory=ERROR, console
IMHO, Option 1 ist sinnvoll, da es auf Dateiebene ausgeschaltet werden kann.
Programmatischer Weg
spark.sparkContext.setLogLevel("WARN")
Verfügbare Optionen
ERROR
WARN
INFO
Fügen Sie dem Befehl spark-submit einfach den folgenden Parameter hinzu
--conf "spark.driver.extraJavaOptions=-Dlog4jspark.root.logger=WARN,console"
Dies überschreibt den Systemwert vorübergehend nur für diesen Job. Überprüfen Sie den genauen Eigenschaftennamen (hier log4jspark.root.logger) in der Datei log4j.properties.
Hoffe das hilft, Prost!
Wenn Sie die Protokollierung (Protokollierungsfunktion für Python) weiterhin verwenden möchten, können Sie versuchen, Konfigurationen für Ihre Anwendung und für Spark aufzuteilen:
LoggerManager()
logger = logging.getLogger(__name__)
loggerSpark = logging.getLogger('py4j')
loggerSpark.setLevel('WARNING')