importjava.io.File;importjava.io.FileInputStream;importjava.io.FileOutputStream;importjava.io.IOException;importjava.io.InputStream;importjava.io.OutputStream;importjava.lang.reflect.Array;importjava.lang.reflect.InvocationTargetException;importjava.lang.reflect.Method;importjava.net.URL;importjava.net.URLClassLoader;importjava.util.ArrayList;importjava.util.Arrays;importjava.util.Enumeration;importjava.util.jar.JarEntry;importjava.util.jar.JarFile;importjava.util.jar.JarOutputStream;importjava.util.jar.Manifest;public classEJob {private static ArrayList classPath = new ArrayList();/**Unpack a jar file into a directory.*/
public static void unJar(File jarFile, File toDir) throwsIOException {
JarFile jar= newJarFile(jarFile);try{
Enumeration entries=jar.entries();while(entries.hasMoreElements()) {
JarEntry entry=(JarEntry) entries.nextElement();if (!entry.isDirectory()) {
InputStream in=jar.getInputStream(entry);try{
File file= newFile(toDir, entry.getName());if (!file.getParentFile().mkdirs()) {if (!file.getParentFile().isDirectory()) {throw new IOException("Mkdirs failed to create " +file.getParentFile().toString());
}
}
OutputStream out= newFileOutputStream(file);try{byte[] buffer = new byte[8192];inti;while ((i = in.read(buffer)) != -1) {
out.write(buffer,0, i);
}
}finally{
out.close();
}
}finally{
in.close();
}
}
}
}finally{
jar.close();
}
}/*** Run a Hadoop job jar. If the main class is not in the jar's manifest,
* then it must be provided on the command line.*/
public static void runJar(String[] args) throwsThrowable {
String usage= "jarFile [mainClass] args...";if (args.length < 1) {
System.err.println(usage);
System.exit(-1);
}int firstArg = 0;
String fileName= args[firstArg++];
File file= newFile(fileName);
String mainClassName= null;
JarFile jarFile;try{
jarFile= newJarFile(fileName);
}catch(IOException io) {throw new IOException("Error opening job jar: " +fileName).initCause(io);
}
Manifest manifest=jarFile.getManifest();if (manifest != null) {
mainClassName= manifest.getMainAttributes().getValue("Main-Class");
}
jarFile.close();if (mainClassName == null) {if (args.length < 2) {
System.err.println(usage);
System.exit(-1);
}
mainClassName= args[firstArg++];
}
mainClassName= mainClassName.replaceAll("/", ".");
File tmpDir= new File(System.getProperty("java.io.tmpdir"));
tmpDir.mkdirs();if (!tmpDir.isDirectory()) {
System.err.println("Mkdirs failed to create " +tmpDir);
System.exit(-1);
}final File workDir = File.createTempFile("hadoop-unjar", "", tmpDir);
workDir.delete();
workDir.mkdirs();if (!workDir.isDirectory()) {
System.err.println("Mkdirs failed to create " +workDir);
System.exit(-1);
}
Runtime.getRuntime().addShutdownHook(newThread() {public voidrun() {try{
fullyDelete(workDir);
}catch(IOException e) {
}
}
});
unJar(file, workDir);
classPath.add(new File(workDir + "/").toURL());
classPath.add(file.toURL());
classPath.add(new File(workDir, "classes/").toURL());
File[] libs= new File(workDir, "lib").listFiles();if (libs != null) {for (int i = 0; i < libs.length; i++) {
classPath.add(libs[i].toURL());
}
}
ClassLoader loader= new URLClassLoader(classPath.toArray(new URL[0]));
Thread.currentThread().setContextClassLoader(loader);
Class> mainClass = Class.forName(mainClassName, true, loader);
Method main= mainClass.getMethod("main", new Class[] { Array.newInstance(String.class, 0).getClass() });
String[] newArgs= Arrays.asList(args).subList(firstArg, args.length).toArray(new String[0]);try{
main.invoke(null, newObject[] { newArgs });
}catch(InvocationTargetException e) {throwe.getTargetException();
}
}/*** Delete a directory and all its contents. If we return false, the
* directory may be partially-deleted.*/
public static boolean fullyDelete(File dir) throwsIOException {
File contents[]=dir.listFiles();if (contents != null) {for (int i = 0; i < contents.length; i++) {if(contents[i].isFile()) {if (!contents[i].delete()) {return false;
}
}else{//try deleting the directory//this might be a symlink
boolean b = false;
b=contents[i].delete();if(b) {//this was indeed a symlink or an empty directory
continue;
}//if not an empty directory or symlink let//fullydelete handle it.
if (!fullyDelete(contents[i])) {return false;
}
}
}
}returndir.delete();
}/*** Add a directory or file to classpath.
*
*@paramcomponent*/
public static voidaddClasspath(String component) {if ((component != null) && (component.length() > 0)) {try{
File f= newFile(component);if(f.exists()) {
URL key=f.getCanonicalFile().toURL();if (!classPath.contains(key)) {
classPath.add(key);
}
}
}catch(IOException e) {
}
}
}/*** Add default classpath listed in bin/hadoop bash.
*
*@paramhadoopHome*/
public static voidaddDefaultClasspath(String hadoopHome) {//Classpath initially contains conf dir.
addClasspath(hadoopHome + "/conf");//For developers, add Hadoop classes to classpath.
addClasspath(hadoopHome + "/build/classes");if (new File(hadoopHome + "/build/webapps").exists()) {
addClasspath(hadoopHome+ "/build");
}
addClasspath(hadoopHome+ "/build/test/classes");
addClasspath(hadoopHome+ "/build/tools");//For releases, add core hadoop jar & webapps to classpath.
if (new File(hadoopHome + "/webapps").exists()) {
addClasspath(hadoopHome);
}
addJarsInDir(hadoopHome);
addJarsInDir(hadoopHome+ "/build");//Add libs to classpath.
addJarsInDir(hadoopHome + "/lib");
addJarsInDir(hadoopHome+ "/lib/jsp-2.1");
addJarsInDir(hadoopHome+ "/build/ivy/lib/Hadoop/common");
}/*** Add all jars in directory to classpath, sub-directory is excluded.
*
*@paramdirPath*/
public static voidaddJarsInDir(String dirPath) {
File dir= newFile(dirPath);if (!dir.exists()) {return;
}
File[] files=dir.listFiles();if (files == null) {return;
}for (int i = 0; i < files.length; i++) {if(files[i].isDirectory()) {continue;
}else{
addClasspath(files[i].getAbsolutePath());
}
}
}/*** Create a temp jar file in "java.io.tmpdir".
*
*@paramroot
*@return*@throwsIOException*/
public static File createTempJar(String root) throwsIOException {if (!newFile(root).exists()) {return null;
}
Manifest manifest= newManifest();
manifest.getMainAttributes().putValue("Manifest-Version", "1.0");final File jarFile = File.createTempFile("EJob-", ".jar", new File(System.getProperty("java.io.tmpdir")));
Runtime.getRuntime().addShutdownHook(newThread() {public voidrun() {
jarFile.delete();
}
});
JarOutputStream out= new JarOutputStream(newFileOutputStream(jarFile), manifest);
createTempJarInner(out,new File(root), "");
out.flush();
out.close();returnjarFile;
}private static void createTempJarInner(JarOutputStream out, File f, String base) throwsIOException {if(f.isDirectory()) {
File[] fl=f.listFiles();if (base.length() > 0) {
base= base + "/";
}for (int i = 0; i < fl.length; i++) {
createTempJarInner(out, fl[i], base+fl[i].getName());
}
}else{
out.putNextEntry(newJarEntry(base));
FileInputStream in= newFileInputStream(f);byte[] buffer = new byte[1024];int n =in.read(buffer);while (n != -1) {
out.write(buffer,0, n);
n=in.read(buffer);
}
in.close();
}
}/*** Return a classloader based on user-specified classpath and parent
* classloader.
*
*@return
*/
public staticClassLoader getClassLoader() {
ClassLoader parent=Thread.currentThread().getContextClassLoader();if (parent == null) {
parent= EJob.class.getClassLoader();
}if (parent == null) {
parent=ClassLoader.getSystemClassLoader();
}return new URLClassLoader(classPath.toArray(new URL[0]), parent);
}
}