From c0afb3db7cb7fcca6f326a66195bb49b7014b3eb Mon Sep 17 00:00:00 2001 From: Florian Hotze Date: Sun, 30 Jun 2024 21:51:19 +0200 Subject: [PATCH 1/5] Add ScriptEngineManager::isPreCompilationSupported Signed-off-by: Florian Hotze --- .../automation/module/script/ScriptEngineFactory.java | 9 +++++++++ .../automation/module/script/ScriptEngineManager.java | 8 ++++++++ .../module/script/internal/ScriptEngineManagerImpl.java | 9 +++++++++ 3 files changed, 26 insertions(+) diff --git a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/ScriptEngineFactory.java b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/ScriptEngineFactory.java index 857ab343c66..91fe7eaa239 100644 --- a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/ScriptEngineFactory.java +++ b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/ScriptEngineFactory.java @@ -58,6 +58,15 @@ public interface ScriptEngineFactory { */ List getScriptTypes(); + /** + * This method returns whether the ScriptEngine supports pre-compilation of scripts. + * + * @return true if pre-compilation is supported, else false + */ + default boolean supportsPreCompilation() { + return false; + } + /** * This method "scopes" new values into the given ScriptEngine. * diff --git a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/ScriptEngineManager.java b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/ScriptEngineManager.java index b0ebcf8d72d..a511bbf83ef 100644 --- a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/ScriptEngineManager.java +++ b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/ScriptEngineManager.java @@ -61,6 +61,14 @@ public interface ScriptEngineManager { */ boolean isSupported(String scriptType); + /** + * Checks if the supplied file extension or MimeType supports pre-compilation. + * + * @param scriptType a file extension (script) or MimeType (ScriptAction or ScriptCondition) + * @return true, if pre-compilation supported, else false + */ + boolean isPreCompilationSupported(String scriptType); + /** * Add a listener that is notified when a ScriptEngineFactory is added or removed * diff --git a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/ScriptEngineManagerImpl.java b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/ScriptEngineManagerImpl.java index 6267666dc7d..b2e4e8d5a49 100644 --- a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/ScriptEngineManagerImpl.java +++ b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/ScriptEngineManagerImpl.java @@ -251,6 +251,15 @@ public boolean isSupported(String scriptType) { return findEngineFactory(scriptType) != null; } + @Override + public boolean isPreCompilationSupported(String scriptType) { + ScriptEngineFactory engineFactory = findEngineFactory(scriptType); + if (engineFactory != null) { + return engineFactory.supportsPreCompilation(); + } + return false; + } + private void addAttributeToScriptContext(ScriptEngine engine, String name, Object value) { ScriptContext scriptContext = engine.getContext(); From d1b1d0bb07a4abfb86b812b757169b061ee9813c Mon Sep 17 00:00:00 2001 From: Florian Hotze Date: Sun, 30 Jun 2024 22:29:01 +0200 Subject: [PATCH 2/5] ScriptConditionHandler/ScriptActionHandler: Add support for pre-compilation of scripts Signed-off-by: Florian Hotze --- .../handler/AbstractScriptModuleHandler.java | 53 +++++++++++++++++++ .../internal/handler/ScriptActionHandler.java | 15 +++--- .../handler/ScriptConditionHandler.java | 24 +++++---- .../automation/handler/ActionHandler.java | 8 +++ .../automation/handler/ConditionHandler.java | 8 +++ 5 files changed, 90 insertions(+), 18 deletions(-) diff --git a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/AbstractScriptModuleHandler.java b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/AbstractScriptModuleHandler.java index de3661021eb..8993d98e165 100644 --- a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/AbstractScriptModuleHandler.java +++ b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/AbstractScriptModuleHandler.java @@ -18,10 +18,14 @@ import java.util.Optional; import java.util.UUID; +import javax.script.Compilable; +import javax.script.CompiledScript; import javax.script.ScriptContext; import javax.script.ScriptEngine; +import javax.script.ScriptException; import org.eclipse.jdt.annotation.NonNullByDefault; +import org.eclipse.jdt.annotation.Nullable; import org.openhab.core.automation.Module; import org.openhab.core.automation.handler.BaseModuleHandler; import org.openhab.core.automation.module.script.ScriptEngineContainer; @@ -35,6 +39,7 @@ * * @author Kai Kreuzer - Initial contribution * @author Simon Merschjohann - Initial contribution + * @author Florian Hotze - Add support for script pre-compilation * * @param the type of module the concrete handler can handle */ @@ -54,6 +59,7 @@ public abstract class AbstractScriptModuleHandler extends Base private final String engineIdentifier; private Optional scriptEngine = Optional.empty(); + private Optional compiledScript = Optional.empty(); private final String type; protected final String script; @@ -80,6 +86,31 @@ private static String getValidConfigParameter(String parameter, Configuration co } } + /** + * Compiles the script if the script engine supports pre-compilation. + */ + protected void compileScriptIfSupported() throws ScriptException { + if (!scriptEngineManager.isPreCompilationSupported(type)) { + return; + } + + if (compiledScript.isPresent()) { + return; + } + Optional engine = getScriptEngine(); + if (engine.isPresent()) { + ScriptEngine scriptEngine = engine.get(); + if (scriptEngine instanceof Compilable) { + logger.debug("Pre-compiling script of rule with UID '{}'", ruleUID); + compiledScript = Optional.ofNullable(((Compilable) scriptEngine).compile(script)); + } else { + logger.error( + "Script engine of rule with UID '{}' does not implement Compilable but claims to support pre-compilation", + module.getId()); + } + } + } + @Override public void dispose() { scriptEngineManager.removeEngine(engineIdentifier); @@ -169,4 +200,26 @@ protected void resetExecutionContext(ScriptEngine engine, Map context executionContext.removeAttribute(key, ScriptContext.ENGINE_SCOPE); } } + + /** + * Evaluates the passed script with the ScriptEngine. + * + * @param engine the script engine that is used + * @param script the script to evaluate + * @return the value returned from the execution of the script + */ + protected @Nullable Object eval(ScriptEngine engine, String script) { + try { + if (compiledScript.isPresent()) { + logger.debug("Executing pre-compiled script of rule with UID '{}'", ruleUID); + return compiledScript.get().eval(engine.getContext()); + } + logger.debug("Executing script of rule with UID '{}'", ruleUID); + return engine.eval(script); + } catch (ScriptException e) { + logger.error("Script execution of rule with UID '{}' failed: {}", ruleUID, e.getMessage(), + logger.isDebugEnabled() ? e : null); + return null; + } + } } diff --git a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/ScriptActionHandler.java b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/ScriptActionHandler.java index 772a0ced3f2..7026f596f50 100644 --- a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/ScriptActionHandler.java +++ b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/ScriptActionHandler.java @@ -31,6 +31,7 @@ * * @author Kai Kreuzer - Initial contribution * @author Simon Merschjohann - Initial contribution + * @author Florian Hotze - Add support for script pre-compilation */ @NonNullByDefault public class ScriptActionHandler extends AbstractScriptModuleHandler implements ActionHandler { @@ -61,6 +62,11 @@ public void dispose() { super.dispose(); } + @Override + public void compile() throws ScriptException { + super.compileScriptIfSupported(); + } + @Override public @Nullable Map execute(final Map context) { Map resultMap = new HashMap<>(); @@ -71,13 +77,8 @@ public void dispose() { getScriptEngine().ifPresent(scriptEngine -> { setExecutionContext(scriptEngine, context); - try { - Object result = scriptEngine.eval(script); - resultMap.put("result", result); - } catch (ScriptException e) { - logger.error("Script execution of rule with UID '{}' failed: {}", ruleUID, e.getMessage(), - logger.isDebugEnabled() ? e : null); - } + Object result = eval(scriptEngine, script); + resultMap.put("result", result); resetExecutionContext(scriptEngine, context); }); diff --git a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/ScriptConditionHandler.java b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/ScriptConditionHandler.java index d25ff4e1077..e5cb4e5411d 100644 --- a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/ScriptConditionHandler.java +++ b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/ScriptConditionHandler.java @@ -30,6 +30,7 @@ * * @author Kai Kreuzer - Initial contribution * @author Simon Merschjohann - Initial contribution + * @author Florian Hotze - Add support for script pre-compilation */ @NonNullByDefault public class ScriptConditionHandler extends AbstractScriptModuleHandler implements ConditionHandler { @@ -42,6 +43,11 @@ public ScriptConditionHandler(Condition module, String ruleUID, ScriptEngineMana super(module, ruleUID, scriptEngineManager); } + @Override + public void compile() throws ScriptException { + super.compileScriptIfSupported(); + } + @Override public boolean isSatisfied(final Map context) { boolean result = false; @@ -55,18 +61,14 @@ public boolean isSatisfied(final Map context) { if (engine.isPresent()) { ScriptEngine scriptEngine = engine.get(); setExecutionContext(scriptEngine, context); - try { - Object returnVal = scriptEngine.eval(script); - if (returnVal instanceof Boolean boolean1) { - result = boolean1; - } else { - logger.error("Script of rule with UID '{}' did not return a boolean value, but '{}'", ruleUID, - returnVal); - } - } catch (ScriptException e) { - logger.error("Script execution of rule with UID '{}' failed: {}", ruleUID, e.getMessage(), - logger.isDebugEnabled() ? e : null); + Object returnVal = eval(scriptEngine, script); + if (returnVal instanceof Boolean boolean1) { + result = boolean1; + } else { + logger.error("Script of rule with UID '{}' did not return a boolean value, but '{}'", ruleUID, + returnVal); } + resetExecutionContext(scriptEngine, context); } return result; diff --git a/bundles/org.openhab.core.automation/src/main/java/org/openhab/core/automation/handler/ActionHandler.java b/bundles/org.openhab.core.automation/src/main/java/org/openhab/core/automation/handler/ActionHandler.java index 355dba470c6..bc3599ee9eb 100644 --- a/bundles/org.openhab.core.automation/src/main/java/org/openhab/core/automation/handler/ActionHandler.java +++ b/bundles/org.openhab.core.automation/src/main/java/org/openhab/core/automation/handler/ActionHandler.java @@ -31,6 +31,14 @@ */ @NonNullByDefault public interface ActionHandler extends ModuleHandler { + /** + * Called to compile an {@link Action} of the {@link Rule} when the rule is initialized. + * + * @throws Exception if the compilation fails + */ + default void compile() throws Exception { + // Do nothing by default + } /** * Called to execute an {@link Action} of the {@link Rule} when it is needed. diff --git a/bundles/org.openhab.core.automation/src/main/java/org/openhab/core/automation/handler/ConditionHandler.java b/bundles/org.openhab.core.automation/src/main/java/org/openhab/core/automation/handler/ConditionHandler.java index 7adc0b6ce2d..5bb5cf4bb00 100644 --- a/bundles/org.openhab.core.automation/src/main/java/org/openhab/core/automation/handler/ConditionHandler.java +++ b/bundles/org.openhab.core.automation/src/main/java/org/openhab/core/automation/handler/ConditionHandler.java @@ -29,6 +29,14 @@ */ @NonNullByDefault public interface ConditionHandler extends ModuleHandler { + /** + * Called to compile the {@link Condition} when the {@link Rule} is initialized. + * + * @throws Exception if the compilation fails + */ + default void compile() throws Exception { + // Do nothing by default + } /** * Checks if the Condition is satisfied in the given {@code context}. From 4688e50302f2cbb9d9e16f10402fcc3f132d8769 Mon Sep 17 00:00:00 2001 From: Florian Hotze Date: Sun, 30 Jun 2024 23:58:15 +0200 Subject: [PATCH 3/5] RuleEngineImpl: Implement compilation of rules on start-up and when activating a rule Signed-off-by: Florian Hotze --- .../automation/internal/RuleEngineImpl.java | 127 +++++++++++++++++- 1 file changed, 126 insertions(+), 1 deletion(-) diff --git a/bundles/org.openhab.core.automation/src/main/java/org/openhab/core/automation/internal/RuleEngineImpl.java b/bundles/org.openhab.core.automation/src/main/java/org/openhab/core/automation/internal/RuleEngineImpl.java index 07b803cca73..69fb534fadc 100644 --- a/bundles/org.openhab.core.automation/src/main/java/org/openhab/core/automation/internal/RuleEngineImpl.java +++ b/bundles/org.openhab.core.automation/src/main/java/org/openhab/core/automation/internal/RuleEngineImpl.java @@ -110,6 +110,7 @@ * @author Benedikt Niehues - change behavior for unregistering ModuleHandler * @author Markus Rathgeb - use a managed rule * @author Ana Dimova - new reference syntax: list[index], map["key"], bean.field + * @author Florian Hotze - add support for script condition/action compilation */ @Component(immediate = true, service = { RuleManager.class }) @NonNullByDefault @@ -819,6 +820,8 @@ public synchronized void setEnabled(String uid, boolean enable) { *
    *
  • Set the module handlers. If there are errors, set the rule status (handler error) and return with error * indication. + *
  • Compile the conditions and actions. If there are errors, set the rule status (handler error) and return with + * indication. *
  • Register the rule. Set the rule status and return with success indication. *
* @@ -845,6 +848,11 @@ private boolean activateRule(final WrappedRule rule) { return false; } + // Compile the conditions and actions and so check if they are valid. + if (!compileRule(rule)) { + return false; + } + // Register the rule and set idle status. register(rule); setStatus(ruleUID, new RuleStatusInfo(RuleStatus.IDLE)); @@ -862,6 +870,58 @@ private boolean activateRule(final WrappedRule rule) { return true; } + /** + * Compile the conditions and actions of the given rule. + * If there are errors, set the rule status (handler error) and return with indication. + * + * @param rule the rule whose conditions and actions should be compiled + * @return true if compilation succeeded, otherwise false + */ + private boolean compileRule(final WrappedRule rule) { + try { + compileConditions(rule); + compileActions(rule); + return true; + } catch (Throwable t) { + setStatus(rule.getUID(), new RuleStatusInfo(RuleStatus.UNINITIALIZED, + RuleStatusDetail.HANDLER_INITIALIZING_ERROR, t.getMessage())); + unregister(rule); + return false; + } + } + + /** + * Compile the conditions and actions of the given rule. + * If there are errors, set the rule status (handler error). + * + * @param ruleUID the UID of the rule whose conditions and actions should be compiled + */ + private void compileRule(String ruleUID) { + final WrappedRule rule = getManagedRule(ruleUID); + if (rule == null) { + logger.warn("Failed to compile rule '{}': Invalid Rule UID", ruleUID); + return; + } + synchronized (this) { + final RuleStatus ruleStatus = getRuleStatus(ruleUID); + if (ruleStatus != null && ruleStatus != RuleStatus.IDLE) { + logger.error("Failed to compile rule ‘{}' with status '{}'", ruleUID, ruleStatus.name()); + return; + } + // change state to INITIALIZING + setStatus(ruleUID, new RuleStatusInfo(RuleStatus.INITIALIZING)); + } + if (!compileRule(rule)) { + return; + } + // change state to IDLE only if the rule has not been DISABLED. + synchronized (this) { + if (getRuleStatus(ruleUID) == RuleStatus.INITIALIZING) { + setStatus(ruleUID, new RuleStatusInfo(RuleStatus.IDLE)); + } + } + } + @Override public @Nullable RuleStatusInfo getStatusInfo(String ruleUID) { final WrappedRule rule = managedRules.get(ruleUID); @@ -1134,6 +1194,32 @@ private Map getContext(String ruleUID, @Nullable Set return context; } + /** + * This method compiles conditions of the {@link Rule} when they exist. + * It is called when the rule is initialized. + * + * @param rule compiled rule. + */ + private void compileConditions(WrappedRule rule) { + final Collection conditions = rule.getConditions(); + if (conditions.isEmpty()) { + return; + } + for (WrappedCondition wrappedCondition : conditions) { + final Condition condition = wrappedCondition.unwrap(); + ConditionHandler cHandler = wrappedCondition.getModuleHandler(); + if (cHandler != null) { + try { + cHandler.compile(); + } catch (Throwable t) { + String errMessage = "Failed to pre-compile condition: " + condition.getId() + "(" + t.getMessage() + + ")"; + throw new RuntimeException(errMessage, t); + } + } + } + } + /** * This method checks if all rule's condition are satisfied or not. * @@ -1163,6 +1249,31 @@ private boolean calculateConditions(WrappedRule rule) { return true; } + /** + * This method compiles actions of the {@link Rule} when they exist. + * It is called when the rule is initialized. + * + * @param rule compiled rule. + */ + private void compileActions(WrappedRule rule) { + final Collection actions = rule.getActions(); + if (actions.isEmpty()) { + return; + } + for (WrappedAction wrappedAction : actions) { + final Action action = wrappedAction.unwrap(); + ActionHandler aHandler = wrappedAction.getModuleHandler(); + if (aHandler != null) { + try { + aHandler.compile(); + } catch (Throwable t) { + String errMessage = "Failed to pre-compile action: " + action.getId() + "(" + t.getMessage() + ")"; + throw new RuntimeException(errMessage, t); + } + } + } + } + /** * This method evaluates actions of the {@link Rule} and set their {@link Output}s when they exist. * @@ -1435,7 +1546,7 @@ public String getOutputName() { @Override public void onReadyMarkerAdded(ReadyMarker readyMarker) { - executeRulesWithStartLevel(); + compileRules(); } @Override @@ -1443,6 +1554,20 @@ public void onReadyMarkerRemoved(ReadyMarker readyMarker) { started = false; } + /** + * This method compiles the conditions and actions of all rules. It is called when the rule engine is started. + * By compiling when the rule engine is started, we make sure all conditions and actions are compiled, even if their + * handlers weren't available when the rule was added to the rule engine. + */ + private void compileRules() { + getScheduledExecutor().submit(() -> { + ruleRegistry.getAll().forEach(r -> { + compileRule(r.getUID()); + }); + executeRulesWithStartLevel(); + }); + } + private void executeRulesWithStartLevel() { getScheduledExecutor().submit(() -> { ruleRegistry.getAll().stream() // From 41bcd8d8581ab59f47ef84b3dad45ebbfed3eb35 Mon Sep 17 00:00:00 2001 From: Florian Hotze Date: Sat, 6 Jul 2024 13:51:14 +0200 Subject: [PATCH 4/5] Address review Signed-off-by: Florian Hotze --- .../automation/module/script/ScriptEngineFactory.java | 9 --------- .../automation/module/script/ScriptEngineManager.java | 8 -------- .../module/script/internal/ScriptEngineManagerImpl.java | 9 --------- .../internal/handler/AbstractScriptModuleHandler.java | 8 ++------ .../script/internal/handler/ScriptActionHandler.java | 2 +- .../script/internal/handler/ScriptConditionHandler.java | 2 +- 6 files changed, 4 insertions(+), 34 deletions(-) diff --git a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/ScriptEngineFactory.java b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/ScriptEngineFactory.java index 91fe7eaa239..857ab343c66 100644 --- a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/ScriptEngineFactory.java +++ b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/ScriptEngineFactory.java @@ -58,15 +58,6 @@ public interface ScriptEngineFactory { */ List getScriptTypes(); - /** - * This method returns whether the ScriptEngine supports pre-compilation of scripts. - * - * @return true if pre-compilation is supported, else false - */ - default boolean supportsPreCompilation() { - return false; - } - /** * This method "scopes" new values into the given ScriptEngine. * diff --git a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/ScriptEngineManager.java b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/ScriptEngineManager.java index a511bbf83ef..b0ebcf8d72d 100644 --- a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/ScriptEngineManager.java +++ b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/ScriptEngineManager.java @@ -61,14 +61,6 @@ public interface ScriptEngineManager { */ boolean isSupported(String scriptType); - /** - * Checks if the supplied file extension or MimeType supports pre-compilation. - * - * @param scriptType a file extension (script) or MimeType (ScriptAction or ScriptCondition) - * @return true, if pre-compilation supported, else false - */ - boolean isPreCompilationSupported(String scriptType); - /** * Add a listener that is notified when a ScriptEngineFactory is added or removed * diff --git a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/ScriptEngineManagerImpl.java b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/ScriptEngineManagerImpl.java index b2e4e8d5a49..6267666dc7d 100644 --- a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/ScriptEngineManagerImpl.java +++ b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/ScriptEngineManagerImpl.java @@ -251,15 +251,6 @@ public boolean isSupported(String scriptType) { return findEngineFactory(scriptType) != null; } - @Override - public boolean isPreCompilationSupported(String scriptType) { - ScriptEngineFactory engineFactory = findEngineFactory(scriptType); - if (engineFactory != null) { - return engineFactory.supportsPreCompilation(); - } - return false; - } - private void addAttributeToScriptContext(ScriptEngine engine, String name, Object value) { ScriptContext scriptContext = engine.getContext(); diff --git a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/AbstractScriptModuleHandler.java b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/AbstractScriptModuleHandler.java index 8993d98e165..285e238bd74 100644 --- a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/AbstractScriptModuleHandler.java +++ b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/AbstractScriptModuleHandler.java @@ -87,13 +87,9 @@ private static String getValidConfigParameter(String parameter, Configuration co } /** - * Compiles the script if the script engine supports pre-compilation. + * Creates the {@link ScriptEngine} and compiles the script if the {@link ScriptEngine} implements {@link Compilable}. */ - protected void compileScriptIfSupported() throws ScriptException { - if (!scriptEngineManager.isPreCompilationSupported(type)) { - return; - } - + protected void compileScript() throws ScriptException { if (compiledScript.isPresent()) { return; } diff --git a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/ScriptActionHandler.java b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/ScriptActionHandler.java index 7026f596f50..a170683b881 100644 --- a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/ScriptActionHandler.java +++ b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/ScriptActionHandler.java @@ -64,7 +64,7 @@ public void dispose() { @Override public void compile() throws ScriptException { - super.compileScriptIfSupported(); + super.compileScript(); } @Override diff --git a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/ScriptConditionHandler.java b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/ScriptConditionHandler.java index e5cb4e5411d..a51ad384195 100644 --- a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/ScriptConditionHandler.java +++ b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/ScriptConditionHandler.java @@ -45,7 +45,7 @@ public ScriptConditionHandler(Condition module, String ruleUID, ScriptEngineMana @Override public void compile() throws ScriptException { - super.compileScriptIfSupported(); + super.compileScript(); } @Override From c33942fa81de7e354a2009f33a806767c3356933 Mon Sep 17 00:00:00 2001 From: Florian Hotze Date: Sat, 6 Jul 2024 14:20:08 +0200 Subject: [PATCH 5/5] Skip script compilation if no ScriptEngine found for language Signed-off-by: Florian Hotze --- .../internal/handler/AbstractScriptModuleHandler.java | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/AbstractScriptModuleHandler.java b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/AbstractScriptModuleHandler.java index 285e238bd74..325d742be58 100644 --- a/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/AbstractScriptModuleHandler.java +++ b/bundles/org.openhab.core.automation.module.script/src/main/java/org/openhab/core/automation/module/script/internal/handler/AbstractScriptModuleHandler.java @@ -87,12 +87,19 @@ private static String getValidConfigParameter(String parameter, Configuration co } /** - * Creates the {@link ScriptEngine} and compiles the script if the {@link ScriptEngine} implements {@link Compilable}. + * Creates the {@link ScriptEngine} and compiles the script if the {@link ScriptEngine} implements + * {@link Compilable}. */ protected void compileScript() throws ScriptException { if (compiledScript.isPresent()) { return; } + if (!scriptEngineManager.isSupported(this.type)) { + logger.debug( + "ScriptEngine for language '{}' could not be found, skipping compilation of script for identifier: {}", + type, engineIdentifier); + return; + } Optional engine = getScriptEngine(); if (engine.isPresent()) { ScriptEngine scriptEngine = engine.get();