001 /* 002 * Licensed to the Apache Software Foundation (ASF) under one or more 003 * contributor license agreements. See the NOTICE file distributed with 004 * this work for additional information regarding copyright ownership. 005 * The ASF licenses this file to You under the Apache License, Version 2.0 006 * (the "License"); you may not use this file except in compliance with 007 * the License. You may obtain a copy of the License at 008 * 009 * http://www.apache.org/licenses/LICENSE-2.0 010 * 011 * Unless required by applicable law or agreed to in writing, software 012 * distributed under the License is distributed on an "AS IS" BASIS, 013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 014 * See the License for the specific language governing permissions and 015 * limitations under the License. 016 */ 017 package javax.script; 018 019 import java.io.*; 020 import java.lang.annotation.AnnotationFormatError; 021 import java.net.URL; 022 import java.util.*; 023 024 public class ScriptEngineManager { 025 026 private final Set engineSpis = new HashSet(); 027 private final Map<String, ScriptEngineFactory> byName = new HashMap<String, ScriptEngineFactory>(); 028 private final Map<String, ScriptEngineFactory> registeredByName = new HashMap(); 029 private final Map<String, ScriptEngineFactory> byExtension = new HashMap<String, ScriptEngineFactory>(); 030 private final Map<String, ScriptEngineFactory> registeredByExtension = new HashMap<String, ScriptEngineFactory>(); 031 private final Map<String, ScriptEngineFactory> byMimeType = new HashMap<String, ScriptEngineFactory>(); 032 private final Map<String, ScriptEngineFactory> registeredByMimeType = new HashMap<String, ScriptEngineFactory>(); 033 private Bindings globalScope; 034 035 public ScriptEngineManager() { 036 this(Thread.currentThread().getContextClassLoader()); 037 } 038 039 public ScriptEngineManager(ClassLoader classLoader) { 040 try 041 { 042 for (Enumeration factoryResources = classLoader.getResources("META-INF/services/javax.script.ScriptEngineFactory"); 043 factoryResources.hasMoreElements();) { 044 URL url = (URL) factoryResources.nextElement(); 045 for (String className : getClassNames(url)) { 046 try { 047 Class factoryClass = classLoader.loadClass(className); 048 Object object = factoryClass.newInstance(); 049 if (object instanceof ScriptEngineFactory) { 050 ScriptEngineFactory factory = (ScriptEngineFactory) object; 051 for (String name : factory.getNames()) { 052 byName.put(name, factory); 053 } 054 for (String extension : factory.getExtensions()) { 055 byExtension.put(extension, factory); 056 } 057 for (String mimeType : factory.getMimeTypes()) { 058 byMimeType.put(mimeType, factory); 059 } 060 engineSpis.add(factory); 061 } 062 } catch(ClassNotFoundException doNothing) { 063 } catch(IllegalAccessException doNothing) { 064 } catch(InstantiationException doNothing) { 065 } catch(LinkageError doNothing) { 066 } catch(AnnotationFormatError doNothing) { 067 } 068 } 069 } 070 } catch(IOException doNothing) { 071 } 072 } 073 074 public Bindings getGlobalScope() { 075 return globalScope; 076 } 077 078 public void setGlobalScope(Bindings globalScope) { 079 this.globalScope = globalScope; 080 } 081 082 public void put(String key, Object value) { 083 if (globalScope != null) { 084 globalScope.put(key, value); 085 } 086 } 087 088 public Object get(String key) { 089 if (globalScope != null) { 090 return globalScope.get(key); 091 } else { 092 return null; 093 } 094 } 095 096 public ScriptEngine getEngineByName(String shortName) { 097 ScriptEngineFactory factory = null; 098 List<Class> factoryClasses = org.apache.servicemix.specs.locator.OsgiLocator.locateAll("javax.script.ScriptEngineFactory"); 099 for (Class factoryClass : factoryClasses) { 100 try { 101 ScriptEngineFactory f = (ScriptEngineFactory) factoryClass.newInstance(); 102 if (f.getNames().contains(shortName)) { 103 factory = f; 104 break; 105 } 106 } catch (Throwable doNothing) { 107 } 108 } 109 if (factory == null) { 110 factory = registeredByName.get(shortName); 111 } 112 if (factory == null) { 113 factory = byName.get(shortName); 114 } 115 if (factory == null) { 116 return null; 117 } else { 118 ScriptEngine engine = factory.getScriptEngine(); 119 engine.setBindings(globalScope, ScriptContext.GLOBAL_SCOPE); 120 return engine; 121 } 122 } 123 124 public ScriptEngine getEngineByExtension(String extension) { 125 ScriptEngineFactory factory = null; 126 List<Class> factoryClasses = org.apache.servicemix.specs.locator.OsgiLocator.locateAll("javax.script.ScriptEngineFactory"); 127 for (Class factoryClass : factoryClasses) { 128 try { 129 ScriptEngineFactory f = (ScriptEngineFactory) factoryClass.newInstance(); 130 if (f.getExtensions().contains(extension)) { 131 factory = f; 132 break; 133 } 134 } catch (Throwable doNothing) { 135 } 136 } 137 if (factory == null) { 138 factory = registeredByExtension.get(extension); 139 } 140 if (factory == null) { 141 factory = byExtension.get(extension); 142 } 143 if (factory == null) { 144 return null; 145 } else { 146 ScriptEngine engine = factory.getScriptEngine(); 147 engine.setBindings(globalScope, ScriptContext.GLOBAL_SCOPE); 148 return engine; 149 } 150 } 151 152 public ScriptEngine getEngineByMimeType(String mimeType) { 153 ScriptEngineFactory factory = null; 154 List<Class> factoryClasses = org.apache.servicemix.specs.locator.OsgiLocator.locateAll("javax.script.ScriptEngineFactory"); 155 for (Class factoryClass : factoryClasses) { 156 try { 157 ScriptEngineFactory f = (ScriptEngineFactory) factoryClass.newInstance(); 158 if (f.getMimeTypes().contains(mimeType)) { 159 factory = f; 160 break; 161 } 162 } catch (Throwable doNothing) { 163 } 164 } 165 if (factory == null) { 166 factory = registeredByMimeType.get(mimeType); 167 } 168 if(factory == null) { 169 factory = byMimeType.get(mimeType); 170 } 171 if (factory == null) { 172 return null; 173 } else { 174 ScriptEngine engine = factory.getScriptEngine(); 175 engine.setBindings(globalScope, ScriptContext.GLOBAL_SCOPE); 176 return engine; 177 } 178 } 179 180 public List<ScriptEngineFactory> getEngineFactories() { 181 List<ScriptEngineFactory> factories = new ArrayList(); 182 List<Class> factoryClasses = org.apache.servicemix.specs.locator.OsgiLocator.locateAll("javax.script.ScriptEngineFactory"); 183 for (Class factoryClass : factoryClasses) { 184 try { 185 factories.add((ScriptEngineFactory) factoryClass.newInstance()); 186 } catch (Throwable doNothing) { 187 } 188 } 189 factories.addAll(engineSpis); 190 return factories; 191 } 192 193 public void registerEngineName(String name, ScriptEngineFactory factory) { 194 registeredByName.put(name, factory); 195 } 196 197 public void registerEngineMimeType(String type, ScriptEngineFactory factory) { 198 registeredByMimeType.put(type, factory); 199 } 200 201 public void registerEngineExtension(String extension, ScriptEngineFactory factory) { 202 registeredByExtension.put(extension, factory); 203 } 204 205 private Iterable<String> getClassNames(URL url) { 206 Stack<String> stack = new Stack<String>(); 207 try { 208 BufferedReader r = new BufferedReader(new InputStreamReader(url.openStream())); 209 String line; 210 while ((line = r.readLine()) != null) { 211 int comment = line.indexOf('#'); 212 if (comment != -1) { 213 line = line.substring(0, comment); 214 } 215 stack.push(line.trim()); 216 } 217 } catch(IOException doNothing) { 218 } 219 return stack; 220 } 221 222 }