1 ΠΈ 2 ΠΏΡΠ½ΠΊΡ Π½Π΅ ΠΏΡΠΈΠ½ΠΈΠΌΠ°Π΅Ρ. Π£ΡΡΠ°Π» Π±ΠΈΡΡΡΡ Ρ Π²Π°Π»ΠΈΠ΄Π°ΡΠΎΡΠΎΠΌ. Π£ΠΆΠ΅ Π²ΡΡΡΠ΅ΡΠΊΠΈ ΠΊΠΎΠ΄ ΠΏΠ΅ΡΠ΅ΠΏΠΈΡΡΠ²Π°Π». ΠΠΎΠΌΠΎΠ³ΠΈΡΠ΅, ΠΊΡΠΎ ΠΌΠΎΠΆΠ΅Ρ!
package com.javarush.task.task36.task3606;
import com.sun.org.apache.bcel.internal.util.ClassLoader;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;
/*
ΠΡΠ²Π°ΠΈΠ²Π°Π΅ΠΌ ClassLoader ΠΈ Reflection
*/
public class Solution {
private List<Class> hiddenClasses = new ArrayList<>();
private String packageName;
public Solution(String packageName) {
this.packageName = packageName;
}
public static void main(String[] args) throws ClassNotFoundException {
Solution solution = new Solution(Solution.class.getProtectionDomain().getCodeSource().getLocation().getPath() + "com/javarush/task/task36/task3606/data/second");
solution.scanFileSystem();
System.out.println(solution.getHiddenClassObjectByKey("secondhiddenclassimpl"));
System.out.println(solution.getHiddenClassObjectByKey("firsthiddenclassimpl"));
System.out.println(solution.getHiddenClassObjectByKey("packa"));
}
public void scanFileSystem() throws ClassNotFoundException {
String sep = System.getProperty("file.separator");
String pathName = packageName;
if(!(packageName.endsWith(sep))){
pathName = pathName.concat(sep);
}
//List<Path> allFiles = new ArrayList<>();
//allFiles = Files.walk(Paths.get(pathName)).filter(Files::isRegularFile).collect(Collectors.toList());
File[] allFiles = new File(pathName).listFiles();
for (File f: allFiles) {
System.out.println("All files: " + f.toString());
if(f.toString().endsWith(".class")){
NewClassLoader nc = new NewClassLoader();
Class clazz = nc.findClass(pathName.toString() + f.getName());
hiddenClasses.add(clazz);
/*
Class[] interfaces = clazz.getInterfaces();
for(Class i : interfaces) {
System.out.println(i.getSimpleName());
if(i.getSimpleName().equals("HiddenClass")) {
hiddenClasses.add(clazz);
System.out.println("Added class" + clazz.toString());
break;
}
} */
}
}
}
public HiddenClass getHiddenClassObjectByKey(String key) {
Constructor constructor;
Constructor[] constructors;
Class[] parameterTypes = {};
Class[] interfaces;
for(Class clazz : hiddenClasses) {
if(clazz.getSimpleName().toLowerCase().startsWith(key.toLowerCase())) {
interfaces = clazz.getInterfaces();
for(Class i : interfaces) {
System.out.println("ΠΠ°ΠΉΠ΄Π΅Π½ ΠΈΠ½ΡΠ΅ΡΡΠ΅ΠΉΡ: " + i.getSimpleName() + " Ρ ΠΊΠ»Π°ΡΡΠ°: " + clazz.getSimpleName());
if(i.getSimpleName().equals("HiddenClass")) {
try {
constructor = clazz.getDeclaredConstructor(parameterTypes);
constructor.setAccessible(true);
try {
System.out.println("Π‘ΠΎΠ·Π΄Π°Π½ΠΈΠ΅ ΠΎΠ±ΡΠ΅ΠΊΡΠ°");
return (HiddenClass) constructor.newInstance();
} catch (InstantiationException | IllegalAccessException | IllegalArgumentException
| InvocationTargetException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
} catch (NoSuchMethodException | SecurityException e) {
// TODO Auto-generated catch block
System.out.println("ΠΠ΅Ρ ΡΠ°ΠΊΠΎΠ³ΠΎ ΠΊΠΎΠ½ΡΡΡΡΠΊΡΠΎΡΠ°");
//e.printStackTrace();
constructor = null;
break;
}
//if((constructor = clazz.getDeclaredConstructor()) != null) {
}
}
}
}
return null;
}
public static class NewClassLoader extends ClassLoader{
private String className;
/*
public NewClassLoader(ClassLoader classLoader, String ClassName) {
super(classLoader);
this.packageName = packageName;
}
*/
@Override
public Class<?> findClass(String className) throws ClassNotFoundException {
try {
/**
* ΠΠΎΠ»ΡΡΠ΅ΠΌ Π±Π°ΠΉΡ-ΠΊΠΎΠ΄ ΠΈΠ· ΡΠ°ΠΉΠ»Π° ΠΈ Π·Π°Π³ΡΡΠΆΠ°Π΅ΠΌ ΠΊΠ»Π°ΡΡ Π² ΡΠ°Π½ΡΠ°ΠΉΠΌ
*/
Path path = Paths.get(className);
//System.out.println(path);
byte[] b = Files.readAllBytes(path);
className = path.getFileName().toString();
//System.out.println(className);
return defineClass(null, b, 0, b.length);
}
catch (FileNotFoundException e) {
System.out.println(className + " not found!");
} catch (IOException e) {
System.out.println(className + " i\\o error!");
return super.findClass(className);
}
return null;
}
}
}