Corrected concurrency issues with JRuby
This commit is contained in:
committed by
Mark Fisher
parent
f78d6021a8
commit
a5ac75ea43
@@ -13,95 +13,88 @@
|
||||
package org.springframework.integration.scripting.jsr223;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.Date;
|
||||
import java.util.Map;
|
||||
import java.util.Map.Entry;
|
||||
import javax.script.*;
|
||||
|
||||
import javax.script.ScriptEngine;
|
||||
import javax.script.ScriptEngineManager;
|
||||
import javax.script.ScriptException;
|
||||
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.springframework.integration.scripting.ScriptExecutor;
|
||||
import org.springframework.scripting.ScriptSource;
|
||||
import org.springframework.util.Assert;
|
||||
import org.springframework.util.ClassUtils;
|
||||
|
||||
/**
|
||||
* Executes Jsr223 scripts
|
||||
* Executes JSR223 scripts
|
||||
*
|
||||
* @author David Turanski
|
||||
* @since 2.1
|
||||
*/
|
||||
public class DefaultScriptExecutor implements ScriptExecutor {
|
||||
|
||||
static {
|
||||
if (ClassUtils.isPresent("org.jruby.embed.jsr223.JRubyEngine", System.class.getClassLoader())) {
|
||||
System.setProperty("org.jruby.embed.localvariable.behavior", "transient");
|
||||
System.setProperty("org.jruby.embed.localcontext.scope", "threadsafe");
|
||||
}
|
||||
}
|
||||
|
||||
private static Log log = LogFactory.getLog(DefaultScriptExecutor.class);
|
||||
|
||||
private final ScriptEngine scriptEngine;
|
||||
|
||||
/**
|
||||
* Set the engine name (language)
|
||||
* Set the language name (JSR233 alias)
|
||||
* @param language
|
||||
*/
|
||||
public DefaultScriptExecutor(String language) {
|
||||
ScriptEngineManager manager = new ScriptEngineManager();
|
||||
if (log.isDebugEnabled()){
|
||||
for (ScriptEngineFactory factory: manager.getEngineFactories()) {
|
||||
log.debug(factory.getNames());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
scriptEngine = manager.getEngineByName(language);
|
||||
Assert.notNull(scriptEngine,"JVM cannot create a script engine for name [" + language + "]");
|
||||
|
||||
}
|
||||
|
||||
/*
|
||||
* (non-Javadoc)
|
||||
*
|
||||
* @see
|
||||
* com.dturanski.test.jruby.ScriptExecutor#executeScript(org.springframework
|
||||
* .scripting.ScriptSource)
|
||||
*/
|
||||
public Object executeScript(ScriptSource scriptSource) {
|
||||
return this.executeScript(scriptSource,null);
|
||||
}
|
||||
|
||||
/*
|
||||
* (non-Javadoc)
|
||||
*
|
||||
* @see
|
||||
* com.dturanski.test.jruby.ScriptExecutor#bindVariable(java.lang.String,
|
||||
* java.lang.Object)
|
||||
*/
|
||||
private void bindVariable(String variableName, Object value) {
|
||||
scriptEngine.put(variableName, value);
|
||||
}
|
||||
|
||||
/* (non-Javadoc)
|
||||
* @see org.springframework.integration.jsr233.ScriptExecutor#executeScript(org.springframework.scripting.ScriptSource, java.util.Map)
|
||||
*/
|
||||
public Object executeScript(ScriptSource scriptSource, Map<String, Object> variables) {
|
||||
Assert.notNull(scriptSource, "scriptSource must not be null");
|
||||
synchronized (this) {
|
||||
Object obj = null;
|
||||
try {
|
||||
|
||||
scriptEngine.getBindings(ScriptContext.ENGINE_SCOPE).clear();
|
||||
|
||||
if (variables != null ) {
|
||||
for (Entry<String, Object> entry: variables.entrySet()){
|
||||
bindVariable(entry.getKey(), entry.getValue());
|
||||
}
|
||||
}
|
||||
|
||||
obj = scriptEngine.eval(scriptSource.getScriptAsString());
|
||||
|
||||
}
|
||||
|
||||
catch (ScriptException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
catch (IOException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
|
||||
return obj;
|
||||
if (log.isDebugEnabled()) {
|
||||
log.debug("using script engine : " + scriptEngine.getFactory().getEngineName());
|
||||
}
|
||||
}
|
||||
|
||||
public Object executeScript(ScriptSource scriptSource) {
|
||||
return this.executeScript(scriptSource, null);
|
||||
}
|
||||
|
||||
public synchronized Object executeScript(ScriptSource scriptSource, Map<String, Object> variables) {
|
||||
Object obj = null;
|
||||
try {
|
||||
|
||||
if (variables != null) {
|
||||
for (Entry<String, Object> entry : variables.entrySet()) {
|
||||
scriptEngine.put(entry.getKey(), entry.getValue());
|
||||
}
|
||||
}
|
||||
|
||||
String script = scriptSource.getScriptAsString();
|
||||
|
||||
Date start = new Date();
|
||||
if (log.isDebugEnabled()) {
|
||||
log.debug("executing script: " + script);
|
||||
}
|
||||
|
||||
obj = scriptEngine.eval(script);
|
||||
|
||||
if (log.isDebugEnabled()) {
|
||||
log.debug("script executed in " + (new Date().getTime() - start.getTime()) + " ms");
|
||||
}
|
||||
|
||||
}
|
||||
catch (IOException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
catch (ScriptException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
|
||||
return obj;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -67,7 +67,7 @@ public class Jsr223RefreshTests {
|
||||
private static class CycleResource extends AbstractResource {
|
||||
|
||||
private int count = -1;
|
||||
private String[] scripts = {"\"ruby-#{$payload}-0\"", "\"ruby-#{$payload}-1\""};
|
||||
private String[] scripts = {"\"ruby-#{payload}-0\"", "\"ruby-#{payload}-1\""};
|
||||
|
||||
public String getDescription() {
|
||||
return "CycleResource";
|
||||
|
||||
@@ -33,7 +33,7 @@
|
||||
<service-activator input-channel="inlineScriptInput">
|
||||
<script:script lang="ruby">
|
||||
<![CDATA[
|
||||
"inline-#{$payload}"
|
||||
"inline-#{payload}"
|
||||
]]>
|
||||
</script:script>
|
||||
</service-activator>
|
||||
|
||||
@@ -10,7 +10,7 @@
|
||||
<service-activator input-channel="inlineScriptInput">
|
||||
<script:script lang="ruby">
|
||||
<![CDATA[
|
||||
return "inline-#{$payload}-" + "#{$foo}" + " - " + $bar + " - " + $date
|
||||
return "inline-#{payload}-" + "#{foo}" + " - " + bar + " - " + date
|
||||
]]>
|
||||
<script:variable name="foo" value="foo"/>
|
||||
<script:variable name="bar" value="bar"/>
|
||||
|
||||
@@ -1 +1 @@
|
||||
"ruby-#{$payload}-#{$foo} - #{$bar} - #{$date}"
|
||||
"ruby-#{payload}-#{foo} - #{bar} - #{date}"
|
||||
@@ -2,7 +2,6 @@ class Transformer
|
||||
def transform(payload)
|
||||
"ruby-#{payload}"
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
Transformer.new.transform($payload)
|
||||
Transformer.new.transform(payload)
|
||||
@@ -1,12 +1,12 @@
|
||||
include Java
|
||||
require "java"
|
||||
include_class 'java.util.Date'
|
||||
#payload and headers a global variable
|
||||
if $payload
|
||||
$payload = $payload+" modified #{Date.new}"
|
||||
if payload
|
||||
payload = payload+" modified #{Date.new}"
|
||||
end
|
||||
puts $payload
|
||||
if $headers
|
||||
$headers.each {|key, value| puts "#{key} is #{value}" }
|
||||
puts payload
|
||||
if headers
|
||||
headers.each {|key, value| puts "#{key} is #{value}" }
|
||||
end
|
||||
puts "#{$one} #{$two} #{$three}"
|
||||
$payload
|
||||
payload
|
||||
Reference in New Issue
Block a user