Cargue todas las clases de un paquete con una anotación @Path

He intentado buscar respuestas, pero no he encontrado nada. Quiero aprovechar un JAR existente que tiene varias clases en varias partes de un paquete. Estas clases tienen anotaciones JAX-RS, por lo que esperaba usar CXF para cargarlas todas y conectarlas como puntos finales de CXF.

¿Es posible con CXF apuntarlo a un paquete y hacer que conecte todas las clases a los puntos finales?

preguntado el 10 de septiembre de 12 a las 22:09

1 Respuestas

Por lo que sé CXF no cargará algunas clases de algunos jar anotado con alguna anotación. Tienes que hacer esto manualmente. Por ejemplo, para obtener las clases anotadas con una anotación específica, puede usar esto:

public class AnnotationHandler {

    private static final Logger LOGGER = LoggerFactory.getLogger(AnnotationHandler.class);

    /**
     * Scans all classes accessible from the context class loader which belong to the given package and sub packages.
     *
     * @param packageName the base package
     * @return The classes
     * @throws ClassNotFoundException if class not found exception occurs
     * @throws IOException            if IO error occurs
     */
    public Iterable<Class> getClasses(String packageName)
            throws ClassNotFoundException, IOException {
        ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
        String path = packageName.replace('.', '/');
        Enumeration<URL> resources = classLoader.getResources(path);
        LinkedList<File> dirs = new LinkedList<File>();
        while (resources.hasMoreElements()) {
            URL resource = resources.nextElement();
            dirs.add(new File(resource.getFile()));
        }
        LinkedList<Class> classes = new LinkedList<Class>();
        for (File directory : dirs) {
            classes.addAll(findClasses(directory, packageName));
        }
        return classes;
    }

    /**
     * Recursive method used to find all classes in a given directory and sub directories.
     *
     * @param directory   the base directory
     * @param packageName the package name for classes found inside the base directory
     * @return the classes
     * @throws ClassNotFoundException if class not found exception occurrs
     */
    private LinkedList<Class> findClasses(File directory, String packageName)
            throws ClassNotFoundException {
        LinkedList<Class> classes = new LinkedList<Class>();
        if (!directory.exists()) {
            return classes;
        }
        File[] files = directory.listFiles();
        if (files != null) {
            for (File file : files) {
                if (file.isDirectory()) {
                    classes.addAll(findClasses(file, packageName + "." + file.getName()));
                } else if (file.getName().endsWith(".class")) {
                    classes.add(Class.forName(
                            packageName + '.'
                                    + file.getName().substring(0, file.getName().length() - 6)));
                }
            }
        }
        return classes;
    }

    /**
     * Finds all classes annotated with passed annotation in provided package. Unchecked system exception might be
     * thrown if the class is not found or IO exception occurs.
     *
     * @param annotationClass annotation class
     * @param packageName     package name to search for annotated classes
     * @return list of annotated class with specified annotation
     */
    public LinkedList<Class> findAnnotatedClasses(Class annotationClass, String packageName) {
        LinkedList<Class> classes = new LinkedList<Class>();
        try {
            for (Class clazz : getClasses(packageName)) {
                if (clazz.isAnnotationPresent(annotationClass)) {
                    classes.add(clazz);
                }
            }
        } catch (ClassNotFoundException ex) {
            LOGGER.error("Class not found exception occurred.", ex);
            throw new SystemException("Class not found exception occurred.", ex);
        } catch (IOException ex) {
            LOGGER.error("IO exception occurred.", ex);
            throw new SystemException("IO exception occurred.", ex);
        }
        return classes;
    }

}

Llame al findAnnotatedClasses al proporcionar la clase de anotación y el nombre del paquete para buscar y tendrá una lista de clases anotadas con la anotación especificada.

Entonces puedes hacer lo que quieras con esas clases.

Respondido el 11 de Septiembre de 12 a las 17:09

guau. Gracias por todo eso, funcionó perfectamente. Supongo que esperaba una opción CXF, pero en ausencia esto era lo que tenía en mente. - Nicholas

No es la respuesta que estás buscando? Examinar otras preguntas etiquetadas or haz tu propia pregunta.