Cómo obtener la ruta del directorio de recursos mediante programación


86

Tengo el siguiente diseño de directorio:

  • src
    • principal
      • Java
      • recursos
        • sql (scripts para base de datos)
        • primavera (configuración)
      • Aplicación Web

Dentro de una clase ServletContextListener, quiero acceder a los archivos del directorio SQL y enumerarlos. Básicamente, mi problema es con la ruta, porque sé que enumerar archivos en un directorio en pocas palabras es:

File folder = new File(path);
File[] listOfFiles = folder.listFiles();

Quizás podría usar el ServletContextEventObjeto para intentar construir una ruta haciaresources/sql

public void contextInitialized(ServletContextEvent event) {
    event.getServletContext(); //(getRealPath etc.)
}

¿Existe algo para establecer ese camino de una manera relativa, no codificada? Algo como new File("classpath:sql")(preferiblemente primavera si es posible) o ¿qué debo hacer con el servletContext al que apuntar resources/sql?


Hay tres variantes de solución, según la situación: stackoverflow.com/a/56327069/715269
Gangnus

Respuestas:


69

Supongo que el contenido de src/main/resources/se copia WEB-INF/classes/dentro de su .war en el momento de la compilación. Si ese es el caso, puede hacerlo (sustituyendo los valores reales por el nombre de la clase y la ruta que se está cargando).

URL sqlScriptUrl = MyServletContextListener.class
                       .getClassLoader().getResource("sql/script.sql");

¡¡Gracias!! esto funcionó para mí, con esa URL, luego construyo la ruta para el nuevo archivo y finalmente obtengo los archivos en ese directorio.
yamilmedina

2
No necesita el archivo. Ya tienes una URL. Ni siquiera puede asumir que hay un archivo o un directorio en absoluto. Es posible que el WAR no se haya desempacado.
Marqués de Lorne

¿Qué significa MyServletContextListener aquí?
Tejesh Raut

@TejeshRaut Es un marcador de posición para una clase que implementa javax.servlet.ServletContextListener. Lo usé como ejemplo porque la pregunta tenía un fragmento del contextInitialized cual es un método definido por la ServletContextListenerinterfaz.
Dev

60

Finalmente, esto es lo que hice:

private File getFileFromURL() {
    URL url = this.getClass().getClassLoader().getResource("/sql");
    File file = null;
    try {
        file = new File(url.toURI());
    } catch (URISyntaxException e) {
        file = new File(url.getPath());
    } finally {
        return file;
    }
}

...

File folder = getFileFromURL();
File[] listOfFiles = folder.listFiles();

11
¿Está seguro de utilizarlo "/sql"como parámetro? Tengo problemas con una barra inicial, pero "sql"funciona.
Abdull

2
Tenga en cuenta que puede obtener una URL diferente con this.getClass (). GetResource ("/ sql"));
ShadowGames

Esto no funcionará en todos los contenedores. Tomcat, por ejemplo.
Marqués de Lorne

16
import org.springframework.core.io.ClassPathResource;

...

File folder = new ClassPathResource("sql").getFile();
File[] listOfFiles = folder.listFiles();

Vale la pena señalar que esto limitará sus opciones de implementación, ClassPathResource.getFile()solo funciona si el contenedor ha explotado (descomprimido) su archivo war.


6

Simplemente use la clase com.google.common.io.Resources . Ejemplo:

 URL url = Resources.getResource("file name")

Después de eso, tiene métodos como: .getContent (), .getFile (), .getPath (), etc.


1
¿También admiten la obtención de recursos mientras se ejecuta el código desde un archivo jar?
Displee
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.