stackoverflow中有很多关于这个问题的答案?但是,大多数将ClassLoader.getSystemClassLoader()
强制转换为URLClassLoader,并且此方法不再有效。
这些类必须由systemclassloader找到。
还有其他解决方案吗?-无需重启jar-不创建自己的类加载器(在这种情况下,我必须用自己的类替换systemclassloader)
丢失的类/ jar必须仅在启动时添加,而我不想在清单中使用“ Classpath”添加。我找到了带有premain-Method的Java代理。这也可以很好地工作,但是在这种情况下,我想启动premain方法而不调用“ java -javaagent:... -jar ...”
目前,我从缺少类路径的开头开始重新启动程序:
public class LibLoader { protected static List<File> files = new LinkedList<>(); public static void add(File file) { files.add(file); } public static boolean containsLibraries() { RuntimeMXBean runtimeMxBean = ManagementFactory.getRuntimeMXBean(); String[] classpaths = runtimeMxBean.getClassPath().split(System.getProperty("path.separator")); List<File> classpathfiles = new LinkedList<>(); for(String string : classpaths) classpathfiles.add(new File(string)); for(File file : files) { if(!classpathfiles.contains(file)) return false; } return true; } public static String getNewClassPaths() { StringBuilder builder = new StringBuilder(); RuntimeMXBean runtimeMxBean = ManagementFactory.getRuntimeMXBean(); builder.append(runtimeMxBean.getClassPath()); for(File file : files) { if(builder.length() > 0) builder.append(System.getProperty("path.separator")); builder.append(file.getAbsolutePath()); } return builder.toString(); } public static boolean restartWithLibrary(Class<?> main, String[] args) throws IOException { if(containsLibraries()) return false; List<String> runc = new LinkedList<>(); runc.add(System.getProperty("java.home") + "\\bin\\javaw.exe"); RuntimeMXBean runtimeMxBean = ManagementFactory.getRuntimeMXBean(); List<String> arguments = runtimeMxBean.getInputArguments(); runc.addAll(arguments); File me = new File(LibLoader.class.getProtectionDomain().getCodeSource().getLocation().getPath()); String classpaths = getNewClassPaths(); if(!classpaths.isEmpty()) { runc.add("-cp"); runc.add(classpaths); } if(me.isFile()) { runc.add("-jar"); runc.add(me.getAbsolutePath().replace("%20", " ")); } else { runc.add(main.getName()); } for(String arg : args) runc.add(arg); ProcessBuilder processBuilder = new ProcessBuilder(runc); processBuilder.directory(new File(".")); processBuilder.redirectOutput(Redirect.INHERIT); processBuilder.redirectError(Redirect.INHERIT); processBuilder.redirectInput(Redirect.INHERIT); Process process = processBuilder.start(); try { process.waitFor(); } catch (InterruptedException e) { e.printStackTrace(); } return true; } }
希望有人有更好的解决方案。
stackoverflow中有很多关于这个问题的答案?但是大多数将ClassLoader.getSystemClassLoader()强制转换为URLClassLoader,并且这种方法现在可以正常工作了。这些类必须通过...
问题是,必须在系统
ClassLoader
中找到这些类,而不是通过新的ClassLoader
找到这些类。