001 /* 002 * Copyright (C) 2012 eXo Platform SAS. 003 * 004 * This is free software; you can redistribute it and/or modify it 005 * under the terms of the GNU Lesser General Public License as 006 * published by the Free Software Foundation; either version 2.1 of 007 * the License, or (at your option) any later version. 008 * 009 * This software is distributed in the hope that it will be useful, 010 * but WITHOUT ANY WARRANTY; without even the implied warranty of 011 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 012 * Lesser General Public License for more details. 013 * 014 * You should have received a copy of the GNU Lesser General Public 015 * License along with this software; if not, write to the Free 016 * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 017 * 02110-1301 USA, or see the FSF site: http://www.fsf.org. 018 */ 019 package org.crsh.lang.impl.groovy; 020 021 import groovy.lang.GroovyClassLoader; 022 import groovy.lang.GroovyCodeSource; 023 import groovy.lang.Script; 024 import org.codehaus.groovy.control.CompilationFailedException; 025 import org.codehaus.groovy.control.CompilerConfiguration; 026 import org.crsh.shell.ErrorKind; 027 import org.crsh.shell.impl.command.spi.CommandException; 028 import org.crsh.util.ClassFactory; 029 030 /** @author Julien Viet */ 031 class GroovyClassFactory<T> extends ClassFactory<T> { 032 033 /** . */ 034 private final ClassLoader baseLoader; 035 036 /** . */ 037 private final Class<T> baseClass; 038 039 /** . */ 040 final CompilerConfiguration config; 041 042 GroovyClassFactory(ClassLoader baseLoader, Class<T> baseClass, Class<? extends Script> baseScriptClass) { 043 CompilerConfiguration config = new CompilerConfiguration(); 044 config.setRecompileGroovySource(true); 045 config.setScriptBaseClass(baseScriptClass.getName()); 046 047 // 048 this.baseLoader = baseLoader; 049 this.baseClass = baseClass; 050 this.config = config; 051 } 052 053 @Override 054 public Class<? extends T> parse(String name, String source) throws CommandException { 055 Class<?> clazz; 056 try { 057 GroovyCodeSource gcs = new GroovyCodeSource(source, name, "/groovy/shell"); 058 GroovyClassLoader gcl = new GroovyClassLoader(baseLoader, config); 059 clazz = gcl.parseClass(gcs, false); 060 } 061 catch (NoClassDefFoundError e) { 062 throw new CommandException(ErrorKind.INTERNAL, "Could not compile command script " + name, e); 063 } 064 catch (CompilationFailedException e) { 065 throw new CommandException(ErrorKind.INTERNAL, "Could not compile command script " + name, e); 066 } 067 068 if (baseClass.isAssignableFrom(clazz)) { 069 return clazz.asSubclass(baseClass); 070 } else { 071 throw new CommandException(ErrorKind.INTERNAL, "Parsed script " + clazz.getName() + 072 " does not implements " + baseClass.getName()); 073 } 074 } 075 }