Search in sources :

Example 1 with CachedScript

use of org.apache.sling.scripting.api.CachedScript in project sling by apache.

the class ScriptCacheImpl method activate.

@Activate
protected void activate(ScriptCacheImplConfiguration configuration, BundleContext bundleCtx) {
    threadPool = threadPoolManager.get("Script Cache Thread Pool");
    bundleContext = bundleCtx;
    additionalExtensions = configuration.org_apache_sling_scripting_cache_additional__extensions();
    int newMaxCacheSize = configuration.org_apache_sling_scripting_cache_size();
    if (newMaxCacheSize != DEFAULT_CACHE_SIZE) {
        // change the map only if there's a configuration change regarding the cache's max size
        CachingMap<CachedScript> newMap = new CachingMap<>(newMaxCacheSize);
        newMap.putAll(internalMap);
        internalMap = newMap;
    }
    ResourceResolver resolver = null;
    try {
        resolver = rrf.getServiceResourceResolver(null);
        searchPaths = resolver.getSearchPath();
    } catch (LoginException e) {
        LOGGER.error("Unable to retrieve a ResourceResolver for determining the search paths.", e);
    } finally {
        if (resolver != null) {
            resolver.close();
        }
    }
    configureCache();
    active = true;
}
Also used : CachingMap(org.apache.sling.scripting.core.impl.helper.CachingMap) CachedScript(org.apache.sling.scripting.api.CachedScript) ResourceResolver(org.apache.sling.api.resource.ResourceResolver) LoginException(org.apache.sling.api.resource.LoginException) Activate(org.osgi.service.component.annotations.Activate)

Example 2 with CachedScript

use of org.apache.sling.scripting.api.CachedScript in project sling by apache.

the class RenderUnitProvider method provide.

@Override
public ProviderOutcome provide(String identifier, RenderContext renderContext, Bindings arguments) {
    if (identifier.endsWith("." + SightlyScriptEngineFactory.EXTENSION)) {
        Bindings globalBindings = renderContext.getBindings();
        SlingScriptHelper sling = BindingsUtils.getHelper(globalBindings);
        SlingHttpServletRequest request = BindingsUtils.getRequest(globalBindings);
        final Resource renderUnitResource = ScriptUtils.resolveScript(scriptingResourceResolverProvider.getRequestScopedResourceResolver(), renderContext, identifier);
        if (renderUnitResource == null) {
            Resource caller = ResourceResolution.getResourceForRequest(request.getResourceResolver(), request);
            if (caller != null) {
                String resourceSuperType = caller.getResourceSuperType();
                StringBuilder errorMessage = new StringBuilder("Cannot find resource ");
                errorMessage.append(identifier).append(" for base path ").append(caller.getPath());
                if (StringUtils.isNotEmpty(resourceSuperType)) {
                    errorMessage.append(" with resource super type ").append(resourceSuperType);
                }
                errorMessage.append(".");
                return ProviderOutcome.failure(new SightlyException(errorMessage.toString()));
            } else {
                return ProviderOutcome.failure(new SightlyException("Cannot resolve template " + identifier + " for script " + sling.getScript().getScriptResource().getPath()));
            }
        }
        RenderUnit renderUnit;
        try {
            CachedScript cachedScript = scriptCache.getScript(renderUnitResource.getPath());
            final SightlyCompiledScript compiledScript;
            if (cachedScript != null) {
                compiledScript = (SightlyCompiledScript) cachedScript.getCompiledScript();
            } else {
                SightlyScriptEngine sightlyScriptEngine = (SightlyScriptEngine) scriptEngineManager.getEngineByName(SightlyScriptEngineFactory.SHORT_NAME);
                String encoding = renderUnitResource.getResourceMetadata().getCharacterEncoding();
                if (StringUtils.isEmpty(encoding)) {
                    encoding = "UTF-8";
                }
                InputStream inputStream = renderUnitResource.adaptTo(InputStream.class);
                if (inputStream == null) {
                    return ProviderOutcome.failure();
                }
                InputStreamReader inputStreamReader = new InputStreamReader(inputStream, encoding);
                ScriptNameAwareReader reader = new ScriptNameAwareReader(inputStreamReader, renderUnitResource.getPath());
                compiledScript = (SightlyCompiledScript) sightlyScriptEngine.compile(reader);
                scriptCache.putScript(new CachedScript() {

                    @Override
                    public String getScriptPath() {
                        return renderUnitResource.getPath();
                    }

                    @Override
                    public CompiledScript getCompiledScript() {
                        return compiledScript;
                    }
                });
            }
            renderUnit = compiledScript.getRenderUnit();
            return ProviderOutcome.success(renderUnit);
        } catch (Exception e) {
            return ProviderOutcome.failure(e);
        }
    }
    return ProviderOutcome.failure();
}
Also used : SightlyCompiledScript(org.apache.sling.scripting.sightly.impl.engine.SightlyCompiledScript) CompiledScript(javax.script.CompiledScript) RenderUnit(org.apache.sling.scripting.sightly.java.compiler.RenderUnit) InputStreamReader(java.io.InputStreamReader) SlingScriptHelper(org.apache.sling.api.scripting.SlingScriptHelper) InputStream(java.io.InputStream) CachedScript(org.apache.sling.scripting.api.CachedScript) Resource(org.apache.sling.api.resource.Resource) SightlyScriptEngine(org.apache.sling.scripting.sightly.impl.engine.SightlyScriptEngine) Bindings(javax.script.Bindings) SlingHttpServletRequest(org.apache.sling.api.SlingHttpServletRequest) SightlyException(org.apache.sling.scripting.sightly.SightlyException) ScriptNameAwareReader(org.apache.sling.scripting.core.ScriptNameAwareReader) SightlyException(org.apache.sling.scripting.sightly.SightlyException) SightlyCompiledScript(org.apache.sling.scripting.sightly.impl.engine.SightlyCompiledScript)

Example 3 with CachedScript

use of org.apache.sling.scripting.api.CachedScript in project sling by apache.

the class DefaultSlingScript method call.

/**
     * @see org.apache.sling.api.scripting.SlingScript#call(org.apache.sling.api.scripting.SlingBindings, java.lang.String, java.lang.Object[])
     * @throws ScriptEvaluationException
     */
public Object call(SlingBindings props, String method, Object... args) {
    Bindings bindings = null;
    Reader reader = null;
    boolean disposeScriptHelper = !props.containsKey(SLING);
    ResourceResolver oldResolver = null;
    try {
        bindings = verifySlingBindings(props);
        // use final variable for inner class!
        final Bindings b = bindings;
        // create script context
        final ScriptContext ctx = new ScriptContext() {

            private Bindings globalScope;

            private Bindings engineScope = b;

            private Writer writer = (Writer) b.get(OUT);

            private Writer errorWriter = new LogWriter((Logger) b.get(LOG));

            private Reader reader = (Reader) b.get(READER);

            private Bindings slingScope = new SimpleBindings();

            /**
                 * @see javax.script.ScriptContext#setBindings(javax.script.Bindings, int)
                 */
            public void setBindings(final Bindings bindings, final int scope) {
                switch(scope) {
                    case SlingScriptConstants.SLING_SCOPE:
                        this.slingScope = bindings;
                        break;
                    case 100:
                        if (bindings == null)
                            throw new NullPointerException("Bindings for ENGINE scope is null");
                        this.engineScope = bindings;
                        break;
                    case 200:
                        this.globalScope = bindings;
                        break;
                    default:
                        throw new IllegalArgumentException("Invalid scope");
                }
            }

            /**
                 * @see javax.script.ScriptContext#getBindings(int)
                 */
            public Bindings getBindings(final int scope) {
                switch(scope) {
                    case SlingScriptConstants.SLING_SCOPE:
                        return slingScope;
                    case 100:
                        return this.engineScope;
                    case 200:
                        return this.globalScope;
                }
                throw new IllegalArgumentException("Invalid scope");
            }

            /**
                 * @see javax.script.ScriptContext#setAttribute(java.lang.String, java.lang.Object, int)
                 */
            public void setAttribute(final String name, final Object value, final int scope) {
                if (name == null)
                    throw new IllegalArgumentException("Name is null");
                final Bindings bindings = getBindings(scope);
                if (bindings != null) {
                    bindings.put(name, value);
                }
            }

            /**
                 * @see javax.script.ScriptContext#getAttribute(java.lang.String, int)
                 */
            public Object getAttribute(final String name, final int scope) {
                if (name == null)
                    throw new IllegalArgumentException("Name is null");
                final Bindings bindings = getBindings(scope);
                if (bindings != null) {
                    return bindings.get(name);
                }
                return null;
            }

            /**
                 * @see javax.script.ScriptContext#removeAttribute(java.lang.String, int)
                 */
            public Object removeAttribute(final String name, final int scope) {
                if (name == null)
                    throw new IllegalArgumentException("Name is null");
                final Bindings bindings = getBindings(scope);
                if (bindings != null) {
                    return bindings.remove(name);
                }
                return null;
            }

            /**
                 * @see javax.script.ScriptContext#getAttribute(java.lang.String)
                 */
            public Object getAttribute(String name) {
                if (name == null)
                    throw new IllegalArgumentException("Name is null");
                for (final int scope : SCOPES) {
                    final Bindings bindings = getBindings(scope);
                    if (bindings != null) {
                        final Object o = bindings.get(name);
                        if (o != null) {
                            return o;
                        }
                    }
                }
                return null;
            }

            /**
                 * @see javax.script.ScriptContext#getAttributesScope(java.lang.String)
                 */
            public int getAttributesScope(String name) {
                if (name == null)
                    throw new IllegalArgumentException("Name is null");
                for (final int scope : SCOPES) {
                    if ((getBindings(scope) != null) && (getBindings(scope).containsKey(name))) {
                        return scope;
                    }
                }
                return -1;
            }

            /**
                 * @see javax.script.ScriptContext#getScopes()
                 */
            public List<Integer> getScopes() {
                return Arrays.asList(SCOPES);
            }

            /**
                 * @see javax.script.ScriptContext#getWriter()
                 */
            public Writer getWriter() {
                return this.writer;
            }

            /**
                 * @see javax.script.ScriptContext#getErrorWriter()
                 */
            public Writer getErrorWriter() {
                return this.errorWriter;
            }

            /**
                 * @see javax.script.ScriptContext#setWriter(java.io.Writer)
                 */
            public void setWriter(Writer writer) {
                this.writer = writer;
            }

            /**
                 * @see javax.script.ScriptContext#setErrorWriter(java.io.Writer)
                 */
            public void setErrorWriter(Writer writer) {
                this.errorWriter = writer;
            }

            /**
                 * @see javax.script.ScriptContext#getReader()
                 */
            public Reader getReader() {
                return this.reader;
            }

            /**
                 * @see javax.script.ScriptContext#setReader(java.io.Reader)
                 */
            public void setReader(Reader reader) {
                this.reader = reader;
            }
        };
        // set the current resource resolver if a request is available from the bindings
        if (props.getRequest() != null) {
            oldResolver = requestResourceResolver.get();
            requestResourceResolver.set(props.getRequest().getResourceResolver());
        }
        // set the script resource resolver as an attribute
        ctx.setAttribute(SlingScriptConstants.ATTR_SCRIPT_RESOURCE_RESOLVER, this.scriptResource.getResourceResolver(), SlingScriptConstants.SLING_SCOPE);
        reader = getScriptReader();
        if (method != null && !(this.scriptEngine instanceof Invocable)) {
            reader = getWrapperReader(reader, method, args);
        }
        // evaluate the script
        final Object result;
        if (method == null && this.scriptEngine instanceof Compilable) {
            CachedScript cachedScript = scriptCache.getScript(scriptName);
            if (cachedScript == null) {
                ScriptNameAwareReader snReader = new ScriptNameAwareReader(reader, scriptName);
                CompiledScript compiledScript = ((Compilable) scriptEngine).compile(snReader);
                cachedScript = new CachedScriptImpl(scriptName, compiledScript);
                scriptCache.putScript(cachedScript);
                LOGGER.debug("Adding {} to the script cache.", scriptName);
            } else {
                LOGGER.debug("Script {} was already cached.", scriptName);
            }
            result = cachedScript.getCompiledScript().eval(ctx);
        } else {
            result = scriptEngine.eval(reader, ctx);
        }
        // call method - if supplied and script engine supports direct invocation
        if (method != null && (this.scriptEngine instanceof Invocable)) {
            try {
                ((Invocable) scriptEngine).invokeFunction(method, Arrays.asList(args).toArray());
            } catch (NoSuchMethodException e) {
                throw new ScriptEvaluationException(this.scriptName, "Method " + method + " not found in script.", e);
            }
        }
        // optionall flush the output channel
        Object flushObject = bindings.get(FLUSH);
        if (flushObject instanceof Boolean && (Boolean) flushObject) {
            ctx.getWriter().flush();
        }
        // allways flush the error channel
        ctx.getErrorWriter().flush();
        return result;
    } catch (IOException ioe) {
        throw new ScriptEvaluationException(this.scriptName, ioe.getMessage(), ioe);
    } catch (ScriptException se) {
        Throwable cause = (se.getCause() == null) ? se : se.getCause();
        throw new ScriptEvaluationException(this.scriptName, se.getMessage(), cause);
    } finally {
        if (props.getRequest() != null) {
            requestResourceResolver.set(oldResolver);
        }
        // close the script reader (SLING-380)
        if (reader != null) {
            try {
                reader.close();
            } catch (IOException ignore) {
            // don't care
            }
        }
        // dispose of the SlingScriptHelper
        if (bindings != null && disposeScriptHelper) {
            final InternalScriptHelper helper = (InternalScriptHelper) bindings.get(SLING);
            if (helper != null) {
                helper.cleanup();
            }
        }
    }
}
Also used : CompiledScript(javax.script.CompiledScript) ScriptEvaluationException(org.apache.sling.api.scripting.ScriptEvaluationException) CachedScript(org.apache.sling.scripting.api.CachedScript) Reader(java.io.Reader) InputStreamReader(java.io.InputStreamReader) ScriptNameAwareReader(org.apache.sling.scripting.core.ScriptNameAwareReader) StringReader(java.io.StringReader) BufferedReader(java.io.BufferedReader) ScriptContext(javax.script.ScriptContext) Logger(org.slf4j.Logger) SlingBindings(org.apache.sling.api.scripting.SlingBindings) SimpleBindings(javax.script.SimpleBindings) Bindings(javax.script.Bindings) ProtectedBindings(org.apache.sling.scripting.core.impl.helper.ProtectedBindings) Invocable(javax.script.Invocable) ScriptException(javax.script.ScriptException) Compilable(javax.script.Compilable) IOException(java.io.IOException) ScriptNameAwareReader(org.apache.sling.scripting.core.ScriptNameAwareReader) SimpleBindings(javax.script.SimpleBindings) CachedScriptImpl(org.apache.sling.scripting.core.impl.helper.CachedScriptImpl) ResourceResolver(org.apache.sling.api.resource.ResourceResolver) PrintWriter(java.io.PrintWriter) Writer(java.io.Writer)

Example 4 with CachedScript

use of org.apache.sling.scripting.api.CachedScript in project sling by apache.

the class RhinoJavaScriptEngine method compile.

public CompiledScript compile(Reader scriptReader) throws ScriptException {
    final String scriptName = getScriptName(scriptReader);
    CachedScript cachedScript = scriptCache.getScript(scriptName);
    if (cachedScript != null) {
        LOGGER.debug("Detected cached script for {}.", scriptName);
        return cachedScript.getCompiledScript();
    } else {
        scriptReader = wrapReaderIfEspScript(scriptReader, scriptName);
        try {
            final Context rhinoContext = Context.enter();
            rhinoContext.setOptimizationLevel(optimizationLevel());
            if (!ScriptRuntime.hasTopCall(rhinoContext)) {
                // setup the context for use
                WrapFactory wrapFactory = ((RhinoJavaScriptEngineFactory) getFactory()).getWrapFactory();
                rhinoContext.setWrapFactory(wrapFactory);
            }
            final int lineNumber = 1;
            final Object securityDomain = null;
            final Script script = rhinoContext.compileReader(scriptReader, scriptName, lineNumber, securityDomain);
            final SlingCompiledScript slingCompiledScript = new SlingCompiledScript(script, this);
            cachedScript = new CachedScript() {

                @Override
                public String getScriptPath() {
                    return scriptName;
                }

                @Override
                public CompiledScript getCompiledScript() {
                    return slingCompiledScript;
                }
            };
            // SLING-4935 avoid caching scripts for which we cannot determine a name
            if (!scriptName.equals(NO_SCRIPT_NAME)) {
                scriptCache.putScript(cachedScript);
            }
            LOGGER.debug("Added {} script to Script Cache.", scriptName);
            return slingCompiledScript;
        } catch (IOException e) {
            final ScriptException se = new ScriptException("Failure running script " + scriptName + ": " + e.getMessage());
            se.initCause(e);
            throw se;
        } finally {
            Context.exit();
        }
    }
}
Also used : Context(org.mozilla.javascript.Context) ScriptContext(javax.script.ScriptContext) CompiledScript(javax.script.CompiledScript) CachedScript(org.apache.sling.scripting.api.CachedScript) Script(org.mozilla.javascript.Script) CompiledScript(javax.script.CompiledScript) WrapFactory(org.mozilla.javascript.WrapFactory) CachedScript(org.apache.sling.scripting.api.CachedScript) IOException(java.io.IOException) ScriptException(javax.script.ScriptException) JavaScriptException(org.mozilla.javascript.JavaScriptException) ScriptableObject(org.mozilla.javascript.ScriptableObject)

Aggregations

CachedScript (org.apache.sling.scripting.api.CachedScript)4 CompiledScript (javax.script.CompiledScript)3 IOException (java.io.IOException)2 InputStreamReader (java.io.InputStreamReader)2 Bindings (javax.script.Bindings)2 ScriptContext (javax.script.ScriptContext)2 ScriptException (javax.script.ScriptException)2 ResourceResolver (org.apache.sling.api.resource.ResourceResolver)2 ScriptNameAwareReader (org.apache.sling.scripting.core.ScriptNameAwareReader)2 BufferedReader (java.io.BufferedReader)1 InputStream (java.io.InputStream)1 PrintWriter (java.io.PrintWriter)1 Reader (java.io.Reader)1 StringReader (java.io.StringReader)1 Writer (java.io.Writer)1 Compilable (javax.script.Compilable)1 Invocable (javax.script.Invocable)1 SimpleBindings (javax.script.SimpleBindings)1 SlingHttpServletRequest (org.apache.sling.api.SlingHttpServletRequest)1 LoginException (org.apache.sling.api.resource.LoginException)1