Skip to content

Instantly share code, notes, and snippets.

@DoneSpeak
Last active April 11, 2020 05:39
Show Gist options
  • Save DoneSpeak/1fa0f5c55b2c9819464bd97949e462c5 to your computer and use it in GitHub Desktop.
Save DoneSpeak/1fa0f5c55b2c9819464bd97949e462c5 to your computer and use it in GitHub Desktop.
[ClassUtil.java] to get the location of a class. #JavaGuide
import java.net.MalformedURLException;
import java.net.URL;
import lombok.extern.slf4j.Slf4j;
/**
* 参考: https://github.com/scijava/scijava-common/blob/scijava-common-2.62.1/src/main/java/org/scijava/util/ClassUtils.java#L296-L355
* @author Yang Guanrong
* @date 2020/04/10 12:30
*/
@Slf4j
public class ClassUtil {
/**
* 获取类所在的jar的classes路径
*
* <p>
* 如果类是在文件系统(如 /path/to/package/TheClass.class)则返回基本目录(如 file:/path/to), 如果类是在JAR文件中(如
* /path/to/the-jar.jar!/the/package/TheClass),则返回jar中路径(如 jar:file:/path/to/the-jar.jar!/BOOT-INF/classes!/),
* 如果发生错误,则返回null
* </p>
*/
public static URL getLocation(Class<?> clazz) {
if (clazz == null) {
// could not load the class
return null;
}
try {
URL codeSourceLocation = clazz.getProtectionDomain().getCodeSource().getLocation();
if (codeSourceLocation != null) {
return codeSourceLocation;
}
} catch (Exception e) {
// SecurityException: Cannot access protection domain.
// NullPointerException: Protection domain or code source is null.
}
final URL classResource = clazz.getResource(clazz.getSimpleName() + ".class");
if (classResource == null) {
// cannot find class resource
return null;
}
String url = classResource.toString();
// java.io.File -> java/io/File.class
String suffix = clazz.getCanonicalName().replace('.', '/') + ".class";
if (!url.endsWith(suffix)) {
if (isDebugEnable()) {
log.debug("Weired URL: {} should end with {}", url, suffix);
}
// weired URL
return null;
}
String classesUrl = url.substring(0, url.length() - suffix.length());
try {
return new URL(classesUrl);
} catch (MalformedURLException e) {
if (isDebugEnable()) {
log.debug(e.getMessage(), e);
}
return null;
}
}
public static URL getFileLocation(Class<?> clazz) {
URL url = getLocation(clazz);
if(url == null) {
return url;
}
String path = url.toString();
if(path.startsWith("jar:")) {
// 移除 "jar:" prefix 和 "!/" 后缀
path = path.substring(4, path.length() - 2);
}
try {
return new URL(path);
} catch (MalformedURLException e) {
if (isDebugEnable()) {
log.debug(e.getMessage(), e);
}
return null;
}
}
private static boolean isDebugEnable() {
return log.isDebugEnabled();
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment