diff --git a/engine/src/main/java/org/apache/hop/workflow/engine/WorkflowEngineFactory.java b/engine/src/main/java/org/apache/hop/workflow/engine/WorkflowEngineFactory.java index fdac2b6bc2a..03f7ac8a631 100644 --- a/engine/src/main/java/org/apache/hop/workflow/engine/WorkflowEngineFactory.java +++ b/engine/src/main/java/org/apache/hop/workflow/engine/WorkflowEngineFactory.java @@ -28,6 +28,7 @@ import org.apache.hop.workflow.config.IWorkflowEngineRunConfiguration; import org.apache.hop.workflow.config.WorkflowRunConfiguration; import org.apache.hop.workflow.engines.local.LocalWorkflowEngine; +import org.apache.hop.workflow.engines.remote.RemoteWorkflowEngine; public class WorkflowEngineFactory { @@ -106,6 +107,8 @@ private static final IWorkflowEngine createWorkflowE if (workflowEngine instanceof LocalWorkflowEngine localWorkflowEngine) { localWorkflowEngine.setParentLoggingObject(parentLogging); + } else if (workflowEngine instanceof RemoteWorkflowEngine remoteWorkflowEngine) { + remoteWorkflowEngine.setParentLoggingObject(parentLogging); } workflowEngine.setWorkflowMeta(workflowMeta); diff --git a/engine/src/main/java/org/apache/hop/www/BaseWorkflowServlet.java b/engine/src/main/java/org/apache/hop/www/BaseWorkflowServlet.java index e6752aeb776..603d1a022e5 100644 --- a/engine/src/main/java/org/apache/hop/www/BaseWorkflowServlet.java +++ b/engine/src/main/java/org/apache/hop/www/BaseWorkflowServlet.java @@ -125,6 +125,7 @@ protected IPipelineEngine createPipeline( variables, variables.resolve(runConfigurationName), metadataProvider, pipelineMeta); pipeline.setParent(servletLoggingObject); pipeline.setMetadataProvider(metadataProvider); + pipeline.setLogLevel(pipelineExecutionConfiguration.getLogLevel()); // Also copy the parameters over... copyParameters(pipeline, pipelineExecutionConfiguration.getParametersMap()); diff --git a/engine/src/test/java/org/apache/hop/workflow/engine/WorkflowEngineFactoryTest.java b/engine/src/test/java/org/apache/hop/workflow/engine/WorkflowEngineFactoryTest.java new file mode 100644 index 00000000000..fbc52080afc --- /dev/null +++ b/engine/src/test/java/org/apache/hop/workflow/engine/WorkflowEngineFactoryTest.java @@ -0,0 +1,106 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package org.apache.hop.workflow.engine; + +import static org.junit.jupiter.api.Assertions.assertEquals; +import static org.junit.jupiter.api.Assertions.assertInstanceOf; +import static org.junit.jupiter.api.Assertions.assertSame; + +import org.apache.hop.core.HopEnvironment; +import org.apache.hop.core.exception.HopException; +import org.apache.hop.core.logging.LogLevel; +import org.apache.hop.core.logging.LoggingObjectType; +import org.apache.hop.core.logging.SimpleLoggingObject; +import org.apache.hop.core.variables.Variables; +import org.apache.hop.metadata.serializer.memory.MemoryMetadataProvider; +import org.apache.hop.workflow.WorkflowMeta; +import org.apache.hop.workflow.config.IWorkflowEngineRunConfiguration; +import org.apache.hop.workflow.config.WorkflowRunConfiguration; +import org.apache.hop.workflow.engines.local.LocalWorkflowEngine; +import org.apache.hop.workflow.engines.local.LocalWorkflowRunConfiguration; +import org.apache.hop.workflow.engines.remote.RemoteWorkflowEngine; +import org.apache.hop.workflow.engines.remote.RemoteWorkflowRunConfiguration; +import org.junit.jupiter.api.BeforeAll; +import org.junit.jupiter.api.Test; + +class WorkflowEngineFactoryTest { + + @BeforeAll + static void setUpBeforeClass() throws HopException { + HopEnvironment.init(); + } + + /** + * The parent logging object is how the log level is pushed down into the engine. A workflow that + * runs on a server needs it as much as one that runs locally, or the server ends up logging at + * Basic whatever level was asked for. See issue #3173. + */ + @Test + void remoteEngineKeepsTheParentLoggingObject() throws Exception { + SimpleLoggingObject parent = createParent(); + + RemoteWorkflowEngine engine = + assertInstanceOf( + RemoteWorkflowEngine.class, + createEngine("Remote", new RemoteWorkflowRunConfiguration(), parent)); + + assertSame(parent, engine.getParent()); + assertEquals(LogLevel.DEBUG, engine.getParent().getLogLevel()); + } + + /** The local engine has always been given the parent, this makes sure it keeps it. */ + @Test + void localEngineKeepsTheParentLoggingObject() throws Exception { + SimpleLoggingObject parent = createParent(); + + LocalWorkflowEngine engine = + assertInstanceOf( + LocalWorkflowEngine.class, + createEngine("Local", new LocalWorkflowRunConfiguration(), parent)); + + assertSame(parent, engine.getParent()); + } + + private SimpleLoggingObject createParent() { + SimpleLoggingObject parent = + new SimpleLoggingObject("a-parent", LoggingObjectType.HOP_GUI, null); + parent.setLogLevel(LogLevel.DEBUG); + return parent; + } + + /** + * @param enginePluginId the id of the workflow engine plugin to run with, normally filled in when + * the run configuration is read from its metadata + */ + private IWorkflowEngine createEngine( + String enginePluginId, + IWorkflowEngineRunConfiguration engineRunConfiguration, + SimpleLoggingObject parent) + throws HopException { + engineRunConfiguration.setEnginePluginId(enginePluginId); + + String name = "a-" + enginePluginId + "-run-configuration"; + MemoryMetadataProvider metadataProvider = new MemoryMetadataProvider(); + metadataProvider + .getSerializer(WorkflowRunConfiguration.class) + .save(new WorkflowRunConfiguration(name, "", null, engineRunConfiguration, false)); + + return WorkflowEngineFactory.createWorkflowEngine( + new Variables(), name, metadataProvider, new WorkflowMeta(), parent); + } +} diff --git a/integration-tests/hop_server/0011-loglevel.hpl b/integration-tests/hop_server/0011-loglevel.hpl new file mode 100644 index 00000000000..669771c4c27 --- /dev/null +++ b/integration-tests/hop_server/0011-loglevel.hpl @@ -0,0 +1,101 @@ + + + + + 0011-loglevel + Y + Writes a message to the log at the Debug level. When this pipeline is executed on a + server with a Debug log level, the message shows up in the log of that server. When the log + level is not carried over to the server, the server runs at Basic and swallows the message. + See issue #3173. + + + Normal + + + N + 1000 + 100 + - + 2024/01/01 00:00:00.000 + - + 2024/01/01 00:00:00.000 + + + + + + Generate a row + Write debug message + Y + + + + Generate a row + RowGenerator + + Y + + 1 + + none + + + + + 5000 + + N + 1 + + + + 48 + 80 + + + + Write debug message + WriteToLog + + Y + + 1 + + none + + + N + + + N + 0 + Debug + LOGLEVEL-MARKER-3173 + + + 224 + 80 + + + + + + diff --git a/integration-tests/hop_server/0012-loglevel-workflow.hwf b/integration-tests/hop_server/0012-loglevel-workflow.hwf new file mode 100644 index 00000000000..9cbb17326f2 --- /dev/null +++ b/integration-tests/hop_server/0012-loglevel-workflow.hwf @@ -0,0 +1,80 @@ + + + + 0012-loglevel-workflow + Y + Writes a message to the log at the Debug level. When this workflow is executed on a + server with a Debug log level, the message shows up in the log of that server. When the log + level is not carried over to the server, the server runs at Basic and swallows the message. + See issue #3173. + + + - + 2024/01/01 00:00:00.000 + - + 2024/01/01 00:00:00.000 + + + + + Start + + SPECIAL + + 1 + 12 + 60 + 0 + 0 + N + 0 + 1 + N + 50 + 50 + + + + Write debug message + + WRITE_TO_LOG + + Debug + LOGLEVEL-MARKER-3173-WORKFLOW + + N + 250 + 50 + + + + + + Start + Write debug message + Y + Y + Y + + + + + + diff --git a/integration-tests/hop_server/main-0011-test-remote-loglevel.hwf b/integration-tests/hop_server/main-0011-test-remote-loglevel.hwf new file mode 100644 index 00000000000..60aeffae0f7 --- /dev/null +++ b/integration-tests/hop_server/main-0011-test-remote-loglevel.hwf @@ -0,0 +1,94 @@ + + + + main-0011-test-remote-loglevel + Y + Runs a pipeline on a server with a Debug log level. The pipeline writes a message to + the log at that level, so the message only shows up when the log level reaches the server. + See issue #3173. + + + - + 2024/01/01 00:00:00.000 + - + 2024/01/01 00:00:00.000 + + + + + Start + + SPECIAL + + 1 + 12 + 60 + 0 + 0 + N + 0 + 1 + N + 50 + 50 + + + + Run loglevel pipeline on server + + PIPELINE + + ${PROJECT_HOME}/0011-loglevel.hpl + N + N + N + N + N + + + N + N + Debug + N + Y + N + remote + + Y + + N + 250 + 50 + + + + + + Start + Run loglevel pipeline on server + Y + Y + Y + + + + + + diff --git a/integration-tests/hop_server/main-0012-test-remote-loglevel-workflow.hwf b/integration-tests/hop_server/main-0012-test-remote-loglevel-workflow.hwf new file mode 100644 index 00000000000..8dff1ad7b0a --- /dev/null +++ b/integration-tests/hop_server/main-0012-test-remote-loglevel-workflow.hwf @@ -0,0 +1,94 @@ + + + + main-0012-test-remote-loglevel-workflow + Y + Runs a workflow on a server with a Debug log level. The workflow writes a message to + the log at that level, so the message only shows up when the log level reaches the server. + See issue #3173. + + + - + 2024/01/01 00:00:00.000 + - + 2024/01/01 00:00:00.000 + + + + + Start + + SPECIAL + + 1 + 12 + 60 + 0 + 0 + N + 0 + 1 + N + 50 + 50 + + + + Run loglevel workflow on server + + WORKFLOW + + ${PROJECT_HOME}/0012-loglevel-workflow.hwf + N + N + N + N + N + + + N + N + Debug + N + Y + N + remote + + Y + + N + 250 + 50 + + + + + + Start + Run loglevel workflow on server + Y + Y + Y + + + + + + diff --git a/integration-tests/hop_server/metadata/pipeline-run-configuration/remote.json b/integration-tests/hop_server/metadata/pipeline-run-configuration/remote.json index f9d2a760a3f..9ca2e6dd2bc 100644 --- a/integration-tests/hop_server/metadata/pipeline-run-configuration/remote.json +++ b/integration-tests/hop_server/metadata/pipeline-run-configuration/remote.json @@ -4,13 +4,16 @@ "export_resources": true, "resources_target_folder": "", "resources_source_folder": "", + "run_config": "local", "server_poll_interval": "", - "run_config": "", "hop_server": "testserver", "server_poll_delay": "" } }, + "defaultSelection": false, "configurationVariables": [], "name": "remote", - "description": "" + "description": "", + "dataProfile": "", + "executionInfoLocationName": "" } \ No newline at end of file