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.java; 020 021 import org.crsh.cli.descriptor.Format; 022 import org.crsh.cli.impl.descriptor.IntrospectionException; 023 import org.crsh.shell.ErrorKind; 024 import org.crsh.shell.impl.command.spi.CommandException; 025 import org.crsh.shell.impl.command.ShellSession; 026 import org.crsh.shell.impl.command.spi.Command; 027 import org.crsh.lang.spi.CommandResolution; 028 029 import java.io.IOException; 030 import java.util.Collections; 031 import java.util.List; 032 import java.util.Set; 033 034 /** @author Julien Viet */ 035 public class JavaCompiler implements org.crsh.lang.spi.Compiler { 036 037 /** . */ 038 private static final Set<String> EXT = Collections.singleton("java"); 039 040 /** . */ 041 private final org.crsh.lang.impl.java.Compiler compiler; 042 043 /** . */ 044 private final ClassLoader loader; 045 046 JavaCompiler(ClassLoader loader) { 047 this.compiler = new org.crsh.lang.impl.java.Compiler(loader); 048 this.loader = loader; 049 } 050 051 public Set<String> getExtensions() { 052 return EXT; 053 } 054 055 public CommandResolution compileCommand(String name, byte[] source) throws CommandException, NullPointerException { 056 String script = new String(source); 057 List<JavaClassFileObject> classFiles; 058 try { 059 classFiles = compiler.compile(name, script); 060 } 061 catch (IOException e) { 062 throw new CommandException(ErrorKind.INTERNAL, "Could not access command", e); 063 } 064 catch (CompilationFailureException e) { 065 throw new CommandException(ErrorKind.INTERNAL, "Could not compile command", e); 066 } 067 for (JavaClassFileObject classFile : classFiles) { 068 String className = classFile.getClassName(); 069 String simpleName = className.substring(className.lastIndexOf('.') + 1); 070 if (simpleName.equals(name)) { 071 LoadingClassLoader loader = new LoadingClassLoader(this.loader, classFiles); 072 try { 073 Class<?> clazz = loader.loadClass(classFile.getClassName()); 074 final ClassShellCommand command; 075 try { 076 command = new ClassShellCommand(clazz); 077 } 078 catch (IntrospectionException e) { 079 throw new CommandException(ErrorKind.INTERNAL, "Invalid cli annotations", e); 080 } 081 final String description = command.describe(name, Format.DESCRIBE); 082 return new CommandResolution() { 083 @Override 084 public String getDescription() { 085 return description; 086 } 087 @Override 088 public Command<Object> getCommand() throws CommandException { 089 return command; 090 } 091 }; 092 } 093 catch (ClassNotFoundException e) { 094 throw new CommandException(ErrorKind.INTERNAL, "Command cannot be loaded", e); 095 } 096 } 097 } 098 throw new CommandException(ErrorKind.INTERNAL, "Command class not found"); 099 } 100 101 public void init(ShellSession session) { 102 // 103 } 104 105 public void destroy(ShellSession session) { 106 // 107 } 108 109 public String doCallBack(ShellSession session, String name, String defaultValue) { 110 throw new UnsupportedOperationException("not yet implemented"); 111 } 112 }