Ich bin ziemlich neu zu groovy, und Skripte in Java im Allgemeinen, und ich wirklich hoffe, es gibt eine einfache Lösung für mein Problem. In unserer Anwendung können die Benutzer groovy Skripte ausführen, die sie selbst schreiben, und wir müssen steuern, was diese Skripte können und was nicht. Ich lese viele Dinge über Sandboxing groovy, aber entweder ich sehe falsche Orte oder ich übersehe das Offensichtliche. Um es einfach zu machen, habe ich ein kleines Beispiel, das das Problem zeigt. Das ist mein Klassenlader die java.lang.System
entfernt, geladen und verfügbar zu Skripten verhindern sollten:Wie blockiert man den Zugriff auf einige Klassen, wenn man groovige Skripte von Java ausführt?
public class MyClassLoader extends ClassLoader {
@Override
public Class<?> loadClass(String name) throws ClassNotFoundException {
if (name.startsWith("java.lang.System")) {
throw new ClassNotFoundException("Class not found: " + name);
}
return super.loadClass(name);
}
}
Und das ist ein einfaches Programm, das zu nennen versucht System.currentTimeMillis()
:
public static void main(String[] args) {
String code = "java.lang.System.currentTimeMillis();";
ClassLoader classLoader = new MyClassLoader();
Thread.currentThread().setContextClassLoader(classLoader);
GroovyShell shell = new GroovyShell();
Script script = shell.parse(code);
Object result = script.run();
log.debug(result);
}
MyClassLoader
wirft Ausnahmen für java.lang.SystemBeanInfo
und java.lang.SystemCustomizer
, aber der Code wird ausgeführt. Gleiche passiert, wenn ich javax.script
Klassen verwenden:
ScriptEngineManager factory = new ScriptEngineManager();
ScriptEngine engine = factory.getEngineByName("Groovy");
Object o = engine.eval(code);
log.debug(o);
Und wenn ich es mit JavaScript-Engine versuchen, es funktioniert wie erwartet (nur „Groovy“ mit „JavaScript“ in dem obigen Beispiel ersetzen).
Kann mir jemand dabei helfen? BTW, ich benutze groovy-all-1.8.8.jar, mit jdk1.7.0_55.
Dank
Es funktioniert gleich mit groovy v.2.3.6 und Java 1.8.0_05. 'java.lang.System' ist nicht einmal mit diesem Classloader geladen. – Opal
@Opal Dieser Classloader versucht 'java.lang.SystemBeanInfo' und' java.lang.SystemCustomizer' zu laden, was, wie ich annehme, groovy für das Wrapping 'java.lang.System' verwendet. Aber es macht Sinn, dass ein anderer Classloader verwendet wird, unabhängig davon, ob "MyClassLoader" keinen Eltern-Classloader hat, ich weiß einfach nicht, wie es funktioniert und wie man dieses Verhalten anpasst. –