1 通过包名获取下面所有的类名集合
2 通过类名集合反射获得类对象
-->可以选择拿到标记自定义注解的接口
.filter(clazz -> clazz.getAnnotation(TrpcApi.class) != null)
-->也可以不标记拿到全部接口
3 通过类对象拿到所有的接口
- /**
- * 实现包扫描,通过包名拿到其下面所有的接口
- * @param packageName 包名
- */
- public RpcBootStart scan(String packageName) {
- //1根据包名拿到所有类名
- List
classnames=getClassName(packageName); - //2反射过滤后的接口集合
- //.filter(clazz -> clazz.getAnnotation(TrpcApi.class) != null)
- //用于只获取自己标记的接口,删除可变为标记全部
- List
> classes = classnames.stream() - .map(classname -> {
- try {
- //通过名字反射得到class对象
- return Class.forName(classname);
- } catch (ClassNotFoundException e) {
- throw new RuntimeException(e);
- }
- //过滤所有不含注解的类
- }).filter(clazz -> clazz.getAnnotation(TrpcApi.class) != null)
- .collect(Collectors.toList());
- for (Class> clazz : classes) {
- //获取接口集合
- Class>[] interfaces = clazz.getInterfaces();
- Object instance=null;
- try {
- instance= clazz.getConstructor().newInstance();
- } catch (InstantiationException | IllegalAccessException | InvocationTargetException | NoSuchMethodException e) {
- e.printStackTrace();
- }
- }
1 进行数据清洗,得到一个合适的路径,去除中文乱码,得到一个包的基本路径
2 返回一个类名集合
- /**
- *
- * @param packageName 包名
- * @return 其下面---类名集合
- */
- private List
getClassName(String packageName) { - //1 获取绝对路径 转义拿到
- String basePath=packageName.replaceAll("\\.","/");
- URL url = ClassLoader.getSystemClassLoader().getResource(basePath);
- if (url == null){
- throw new RuntimeException("包扫描路径发生异常");
- }
- //转义包名
- String absolutePath = url.getPath();
- try {
- absolutePath = URLDecoder.decode(absolutePath, "utf-8");
- } catch (UnsupportedEncodingException e) {
- e.printStackTrace();
- }
-
- ArrayList
classNames = new ArrayList<>(); - recursionFile(absolutePath,classNames,basePath);
- return classNames;
- }
1 通过拿到基本路径去递归得到文件
- /**
- * 递归获取包名下所有类名
- * @param absolutePath 转义包名
- * @param classNames 所有类名
- */
- private ArrayList
recursionFile( String absolutePath,ArrayList classNames,String basePath) { - File file = new File(absolutePath);
- //判断是否是文件夹
- if (file.isDirectory()){
- File []childedFile=file.listFiles(new FileFilter() {
- @Override
- public boolean accept(File pathname) {
- return pathname.isDirectory() || pathname.getPath().contains(".class");
- }
- });
- if (childedFile.length==0 || childedFile==null) return classNames;
-
- for (File child : childedFile) {
- if (child.isDirectory()){
- //如果是文件价夹递归调用
- recursionFile(child.getAbsolutePath(),classNames,basePath);
- }else {
- //不是文件夹放在集合中
- String className= getClassNameByAbsolutePath(child.getAbsolutePath(), basePath);
- classNames.add(className);
- }
- }
- }else {
- //不是文件夹放在集合中
- String className= getClassNameByAbsolutePath(absolutePath, basePath);
- classNames.add(className);
- }
- return classNames;
- }
再次进行数据清洗,得到所有.class开头的类的绝对路径加入集合返回
- /**
- *
- * @param absolutePath 当前包名
- * @param basePath 绝对包名路径
- * @return 类名的绝对路径
- */
- private String getClassNameByAbsolutePath(String absolutePath,String basePath) {
- //D:\0_项目管理\TRpc\TRpc_Framework\TRpc_Framework_Core\target\classes\com\trpc\channelHandler\ConsumerChannelInitializer.class
- //转成com\trpc\channelHandler
- String fileName = absolutePath.substring(
- absolutePath.indexOf(
- basePath.replaceAll("/","\\\\")
- )
- );
- //转成com.trpc.channelHandler
- fileName=fileName.replaceAll("\\\\", ".");
- fileName=fileName.substring(0,fileName.indexOf(".class"));
- return fileName;
- }
标记注解:用于添加在接口上,添加是可以在包扫描是获取到该接口
- package com.trpc.annotation;
-
- import com.sun.istack.internal.Interned;
-
- import java.lang.annotation.ElementType;
- import java.lang.annotation.Retention;
- import java.lang.annotation.RetentionPolicy;
- import java.lang.annotation.Target;
-
- /**
- * 自定义注解
- */
- @Target(ElementType.TYPE) //在类上面使用
- @Retention(RetentionPolicy.RUNTIME) //允行时生效
- public @interface TrpcApi {
- }
接口
- package com.trpc.api;
-
- import com.trpc.annotation.TryTimes;
-
- public interface HaloApi {
-
- String halo(String name);
- }
需要添加在具体实现上
- package com.trpc.service.Imp;
-
- import com.trpc.annotation.TrpcApi;
- import com.trpc.api.HaloApi;
-
-
- @TrpcApi
- public class HaloServiceImp implements HaloApi {
- @Override
- public String halo(String name) {
- return "halo"+name;
- }
- }