/* * Copyright 2013 Guidewire Software, Inc. */ package gw.plugin.ij.core; import com.intellij.openapi.project.Project; import gw.lang.reflect.gs.IGosuClass; import org.jetbrains.annotations.NotNull; import java.net.URL; import java.net.URLClassLoader; import java.util.Map; import java.util.WeakHashMap; /** */ public class ProjectClassLoader extends URLClassLoader { private static final String[] PREFIXES = { "gw.internal.", "gw.lang.", "gw.plugin." }; private static final Map<Project, ProjectClassLoader> PRJ_TO_CLASSLOADER = new WeakHashMap<>(); public static ProjectClassLoader get( Project project ) { synchronized( PRJ_TO_CLASSLOADER ) { ProjectClassLoader classLoader = PRJ_TO_CLASSLOADER.get( project ); if( classLoader == null ) { PRJ_TO_CLASSLOADER.put( project, classLoader = new ProjectClassLoader() ); } return classLoader; } } private ProjectClassLoader() { super( getUrls(), ProjectClassLoader.class.getClassLoader() ); } @Override protected Class<?> loadClass( @NotNull String name, boolean resolve ) throws ClassNotFoundException { // If _this_ loader has already loaded the class, return it Class cls = findLoadedClass( name ); if( cls != null ) { return cls; } // If the class is a Gosu class or a Plugin class, this loader msut load it for( String prefix : PREFIXES ) { if( name.startsWith( prefix ) ) { return super.loadClass( name, resolve ); } } // Otherwise, let the parent classloader load it cls = getParent().loadClass( name ); if( cls != null && resolve ) { resolveClass( cls ); } return cls; } @NotNull private static URL[] getUrls() { try { URL urlMain = ProjectClassLoader.class.getProtectionDomain().getCodeSource().getLocation(); Class<?> internalClass = Class.forName( "gw.internal.gosu.parser.IGosuClassInternal" ); URL urlCoreGosu = internalClass.getProtectionDomain().getCodeSource().getLocation(); URL urlCoreGosuApi = IGosuClass.class.getProtectionDomain().getCodeSource().getLocation(); if( urlMain.equals( urlCoreGosu ) ) { return new URL[] {urlMain}; } return new URL[] {urlMain, urlCoreGosu, urlCoreGosuApi}; } catch( Exception e ) { throw new RuntimeException( e ); } } }