import java.util.Vector;\r
\r
import org.apache.log4j.AppenderSkeleton;\r
-import org.apache.log4j.LogManager;\r
+import org.apache.log4j.Level;\r
+import org.apache.log4j.MDC;\r
import org.apache.log4j.spi.LoggingEvent;\r
import org.apache.tools.ant.BuildEvent;\r
+import org.apache.tools.ant.BuildListener;\r
import org.apache.tools.ant.Project;\r
+import org.argeo.slc.core.SlcException;\r
import org.argeo.slc.core.process.SlcExecution;\r
import org.argeo.slc.core.process.SlcExecutionNotifier;\r
import org.argeo.slc.core.process.SlcExecutionStep;\r
-import org.argeo.slc.ws.process.WebServiceSlcExecutionNotifier;\r
-import org.springframework.context.ApplicationContext;\r
-import org.springframework.context.support.AbstractApplicationContext;\r
\r
public class SlcExecutionBuildListener extends AppenderSkeleton implements\r
- ProjectRelatedBuildListener {\r
- private Project project;\r
-\r
- // to avoid stack overflow when logging for log4j\r
- private boolean isLogging = false;\r
-\r
+ BuildListener {\r
private List<SlcExecutionNotifier> notifiers = new Vector<SlcExecutionNotifier>();\r
\r
private boolean currentStepNotified = true;\r
\r
// CUSTOMIZATIONS\r
+ /**\r
+ * Whether to log Ant initialization stuff before the first target has been\r
+ * called.\r
+ */\r
private boolean logBeforeFirstTarget = false;\r
+ /** Whether the first target has been called. */\r
private boolean firstTargetStarted = false;\r
\r
private boolean logTaskStartFinish = true;\r
\r
- public void init(Project project) {\r
- if (this.project != null) {\r
- throw new SlcAntException("Build listener already initialized");\r
- }\r
-\r
- this.project = project;\r
-\r
- if (!LogManager.getRootLogger().isAttached(this)) {\r
- LogManager.getRootLogger().addAppender(this);\r
- }\r
-\r
- SlcExecution slcExecution = (SlcExecution) project\r
- .getReference(SlcAntConstants.REF_SLC_EXECUTION);\r
- if (slcExecution == null)\r
- throw new SlcAntException("No SLC Execution registered.");\r
+ public SlcExecutionBuildListener() {\r
+ // Default log level\r
+ setThreshold(Level.INFO);\r
+ }\r
\r
+ public void buildStarted(BuildEvent event) {\r
+ SlcExecution slcExecution = getSlcExecution(event);\r
for (SlcExecutionNotifier notifier : notifiers) {\r
notifier.newExecution(slcExecution);\r
}\r
-\r
- }\r
-\r
- public void buildStarted(BuildEvent event) {\r
}\r
\r
public void buildFinished(BuildEvent event) {\r
notifier.updateStatus(slcExecution, oldStatus, slcExecution\r
.getStatus());\r
}\r
-\r
-// AbstractApplicationContext context = (AbstractApplicationContext) getProject()\r
-// .getReference(SlcProjectHelper.REF_ROOT_CONTEXT);\r
-// if (context != null)\r
-// context.close();\r
}\r
\r
public void messageLogged(BuildEvent event) {\r
if (slcExecution != null) {\r
if (currentStepNotified) {\r
slcExecution.getSteps().add(\r
- new SlcExecutionStep("LOG", event.getMessage()));\r
+ new SlcExecutionStep(event.getMessage()));\r
notifyStep(slcExecution, slcExecution.currentStep());\r
currentStepNotified = true;\r
} else {\r
if (logTaskStartFinish)\r
msg = "Task " + event.getTask().getTaskName() + " started";\r
\r
- slcExecution.getSteps().add(new SlcExecutionStep("LOG", msg));\r
+ slcExecution.getSteps().add(new SlcExecutionStep(msg));\r
\r
currentStepNotified = false;\r
}\r
}\r
\r
protected SlcExecution getSlcExecution(BuildEvent event) {\r
- Project projectEvt = event.getProject();\r
- if (!projectEvt.equals(project))\r
- throw new SlcAntException("Event project " + projectEvt\r
- + " not consistent with listener project " + project);\r
+ return getSlcExecution(event.getProject());\r
+ }\r
\r
+ protected SlcExecution getSlcExecution(Project project) {\r
SlcExecution slcExecution = (SlcExecution) project\r
- .getReference(SlcAntConstants.REF_SLC_EXECUTION);\r
+ .getReference(AntConstants.REF_SLC_EXECUTION);\r
\r
if (slcExecution == null)\r
- throw new SlcAntException("No SLC Execution registered.");\r
+ throw new SlcException("No SLC Execution registered.");\r
return slcExecution;\r
}\r
\r
protected void addLogStep(BuildEvent event, String msg) {\r
SlcExecution slcExecution = getSlcExecution(event);\r
- slcExecution.getSteps().add(new SlcExecutionStep("LOG", msg));\r
+ slcExecution.getSteps().add(new SlcExecutionStep(msg));\r
\r
notifyStep(slcExecution, slcExecution.currentStep());\r
currentStepNotified = true;\r
\r
@Override\r
protected void append(LoggingEvent event) {\r
- if (isLogging) {\r
- // avoid StackOverflow if notification calls Log4j itself.\r
- return;\r
- }\r
-\r
- // FIXME: make it more generic\r
- if (event.getLoggerName().equals(\r
- WebServiceSlcExecutionNotifier.class.getName())) {\r
- return;\r
- }\r
-\r
- isLogging = true;\r
-\r
- try {\r
- SlcExecution slcExecution = (SlcExecution) project\r
- .getReference(SlcAntConstants.REF_SLC_EXECUTION);\r
- if (slcExecution != null) {\r
- if (currentStepNotified) {\r
- slcExecution.getSteps().add(\r
- new SlcExecutionStep("LOG", event.getMessage()\r
- .toString()));\r
- currentStepNotified = false;\r
- }\r
- slcExecution.currentStep()\r
- .addLog(event.getMessage().toString());\r
- } else {\r
- // TODO: log before initialization?\r
- }\r
- } finally {\r
- isLogging = false;\r
+ Project project = (Project) MDC.get(AntConstants.MDC_ANT_PROJECT);\r
+ if (project == null)\r
+ throw new SlcException("No Ant project registered in Log4j MDC.");\r
+\r
+ SlcExecution slcExecution = getSlcExecution(project);\r
+ if (currentStepNotified) {\r
+ slcExecution.getSteps().add(\r
+ new SlcExecutionStep(event.getMessage().toString()));\r
+ currentStepNotified = false;\r
+ } else {\r
+ slcExecution.currentStep().addLog(event.getMessage().toString());\r
}\r
-\r
}\r
\r
protected boolean shouldLog() {\r
return false;\r
}\r
\r
- public Project getProject() {\r
- return project;\r
+ public void setLogBeforeFirstTarget(boolean logBeforeFirstTarget) {\r
+ this.logBeforeFirstTarget = logBeforeFirstTarget;\r
+ }\r
+\r
+ public void setLogTaskStartFinish(boolean logTaskStartFinish) {\r
+ this.logTaskStartFinish = logTaskStartFinish;\r
+ }\r
+\r
+ public void setLogLevel(String logLevel) {\r
+ setThreshold(Level.toLevel(logLevel));\r
}\r
\r
}\r