Bases de datos dinámicas con jmoordbcore y MongoDB solo para embebido
Published: 2024-05-09 19:03:22

La nueva versión  de jmoordbcore, soporte especificar el nombre de la base de datos en tiempo de ejecución.

No aplica para entidades que utilizan referencias.


Agregue a su proyecto

```
 
 <properties>
   <version.jmoordbcore>1.1.0</version.jmoordbcore> 
 </properties>

<dependency>
  <groupId>com.github.avbravo</groupId>
  <artifactId>jmoordb-core</artifactId>
  <version>${version.jmoordbcore}</version>
</dependency>

<repositories>
 <repository>
    <id>jitpack.io</id>
    <url>https://jitpack.io</url>
  </repository>
</repositories>
```


Como recordaremos cuando se crea un proyecto que utilice Jmoordbcore se configura en el archivo microprofile-config.properties las propiedades de conexión y bases de datos.



```
mongodb.uri=mongodb://localhost:27017
#-- Database de configuración
mongodb.jmoordb= configurationjmoordbdb

#-- Database History
mongodb.databasehistory=historydb

#-- Database
mongodb.database=accreditation
mongodb.database1=sft
mongodb.database2=practicadb


```

Se define una entidad en el paquete model

```java
@Entity
public class Icono {
@Id(autogeneratedActive = AutogeneratedActive.ON)
private Long idicono;
@Column
private String icono;

// set/get constructores
}

```


Se define un repositorio en el paquete repository

```java
@Repository(entity = Icono.class)
public interface IconoRepository extends CrudRepository<Icono, Long> {

    @Find
    public Optional<Icono> findByIcono(String icono);

    @Lookup
    public List<Icono> lookup(Search search);

    @Count()
    public Long count(Search... search);
    
       @CountLikeBy(caseSensitive = CaseSensitive.NO, likeByType = LikeByType.ANYWHERE)
    public Long countLikeByIcono(String icono);

    @LikeBy(caseSensitive = CaseSensitive.NO, typeOrder = TypeOrder.ASC, likeByType = LikeByType.ANYWHERE)
    public List<Icono> likeByIcono(String icono);

}

```

Creamos un endpoint mediante

```java
@Path("icono")
@Tag(name = "Información del icono", description = "End-point para entidad Icono")
@RolesAllowed({"admin"})
public class IconoController {

    
    // <editor-fold defaultstate="collapsed" desc="Inject">
    @Inject
    IconoRepository iconoRepository;
    
      @Inject
HistoryRepository historyRepository;


// </editor-fold>


    // <editor-fold defaultstate="collapsed" desc="findAll">
    @GET
    @RolesAllowed({"admin"})
    @Produces({MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON})
  
    public List<Icono> findAll() {
       
        return iconoRepository.findAll();
    }
// </editor-fold>

    // <editor-fold defaultstate="collapsed" desc="Icono findByIdicono">
    @GET
    @RolesAllowed({"admin"})
    @Path("{idicono}")
    public Icono findByIdicono(
            @Parameter(description = "El idicono", required = true, example = "1", schema = @Schema(type = SchemaType.NUMBER)) @PathParam("idicono") Long idicono) {



        return iconoRepository.findByPk(idicono).orElseThrow(
                () -> new WebApplicationException("No hay icono con idicono " + idicono, Response.Status.NOT_FOUND));

    }
// </editor-fold>
    // <editor-fold defaultstate="collapsed" desc="Icono findByIcononame">
    @GET
    @RolesAllowed({"admin"})
    @Path("icononame")
   
   
    public Icono findByIcono(@Parameter(description = "El icononame", required = true, example = "1", schema = @Schema(type = SchemaType.STRING)) @QueryParam("icono") final String icono) {



        return iconoRepository.findByIcono(icono).orElseThrow(
                () -> new WebApplicationException("No hay icono con icono " + icono, Response.Status.NOT_FOUND));

    }
//// </editor-fold>
// <editor-fold defaultstate="collapsed" desc="List<Icono> lookup(@QueryParam("filter") String filter, @QueryParam("sort") String sort, @QueryParam("page") Integer page, @QueryParam("size") Integer size)">

    @GET
    @Path("lookup")
    @RolesAllowed({"admin"})
   
    @Produces({MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON})

    public List<Icono> lookup(@QueryParam("filter") String filter, @QueryParam("sort") String sort, @QueryParam("page") Integer page, @QueryParam("size") Integer size) {
        List<Icono> suggestions = new ArrayList<>();
        try {

        Search search = DocumentUtil.convertForLookup(filter, sort, page, size);
        suggestions = iconoRepository.lookup(search);

        } catch (Exception e) {
       
          MessagesUtil.error(MessagesUtil.nameOfClassAndMethod() + "error: " + e.getLocalizedMessage());
        }

        return suggestions;
    }

    // </editor-fold>

    // <editor-fold defaultstate="collapsed" desc="Response save">
    @POST
    @RolesAllowed({"admin"})
    public Response save(
            @RequestBody(description = "Crea un nuevo icono.", content = @Content(mediaType = "application/json", schema = @Schema(implementation = Icono.class))) Icono icono) {
iconoRepository.setDynamicDatabase("database1");
  Optional<Icono> iconoOptional=iconoRepository.save(icono);
        if(iconoOptional.isPresent()){
            saveHistory(icono);
               return Response.status(201).entity(iconoOptional.get()).build();
        }else{
              return Response.status(400).entity("Error " + iconoRepository.getJmoordbException().getLocalizedMessage()).build();
        }
    }
// </editor-fold>
    // <editor-fold defaultstate="collapsed" desc="Response update">

    @PUT
    @RolesAllowed({"admin"})
    public Response update(
            @RequestBody(description = "Crea un nuevo icono.", content = @Content(mediaType = "application/json", schema = @Schema(implementation = Icono.class))) Icono icono) {


         if(iconoRepository.update(icono)){
             saveHistory(icono);
               return Response.status(201).entity(icono).build();
        }else{
              return Response.status(400).entity("Error " + iconoRepository.getJmoordbException().getLocalizedMessage()).build();
        }
    }
// </editor-fold>

    // <editor-fold defaultstate="collapsed" desc="Response delete">
    @DELETE
    @RolesAllowed({"admin"})
    @Path("{idicono}")
    public Response delete(
            @Parameter(description = "El elemento idicono", required = true, example = "1", schema = @Schema(type = SchemaType.NUMBER)) @PathParam("idicono") Long idicono) {
        if(iconoRepository.deleteByPk(idicono) ==0L){
              return Response.status(201).entity(Boolean.TRUE).build();
        }else{
            return Response.status(400).entity("Error " + iconoRepository.getJmoordbException().getLocalizedMessage()).build();
        }
    }
    // </editor-fold>
    
     // <editor-fold defaultstate="collapsed" desc="Long count(@QueryParam("filter") String filter, @QueryParam("sort") String sort, @QueryParam("page") Integer page, @QueryParam("size") Integer size)">

    @GET
    @Path("count")
    @RolesAllowed({"admin"})
   

    @Produces({MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON})

    public Long count(@QueryParam("filter") String filter, @QueryParam("sort") String sort, @QueryParam("page") Integer page, @QueryParam("size") Integer size) {
       Long result = 0L;
        try {

        Search search = DocumentUtil.convertForLookup(filter, sort, page, size);
        result = iconoRepository.count(search);

        } catch (Exception e) {
       
          MessagesUtil.error(MessagesUtil.nameOfClassAndMethod() + "error: " + e.getLocalizedMessage());
        }

        return result;
    }

    // </editor-fold>
     // <editor-fold defaultstate="collapsed" desc="private void saveHistory(Icono icono)">
    
    private void saveHistory(Icono icono){
        try {
                History history = new History.Builder()                 
               .collection("icono")
                    .idcollection(icono.getIdicono().toString())
                                .database("accreditation")
                    .data(icono.toString())
                    .actionHistory(icono.getActionHistory().get(icono.getActionHistory().size()-1)                  )
                     .build();
            historyRepository.save(history);
        } catch (Exception e) {
           ConsoleUtil.error("saveHistory() "+e.getLocalizedMessage());
        }
    }
     
    
// </editor-fold>
    
    
    
         // <editor-fold defaultstate="collapsed" desc="Long countLikeByRole(@QueryParam("role") String role)">
    @GET
    @Path("countlikebyicono")
    @Produces({MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON})

    public Long countLikeByIcono(@QueryParam("icono") String icono) {
        Long result = 0L;
        try {

            
            result = iconoRepository.countLikeByIcono(icono);

        } catch (Exception e) {

            MessagesUtil.error(MessagesUtil.nameOfClassAndMethod() + "error: " + e.getLocalizedMessage());
        }

        return result;
    }

    // </editor-fold>
      // <editor-fold defaultstate="collapsed" desc="List<Role> likeByRole(@QueryParam("role") String role)">

    @GET
    @Path("likebyicono")
    @RolesAllowed({"admin"})
     @Produces({MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON})

    public List<Icono> likeByIcono(@QueryParam("icono") String icono) {
        List<Icono> suggestions = new ArrayList<>();
        try {

       
        suggestions = iconoRepository.likeByIcono(icono);

        } catch (Exception e) {
       
          MessagesUtil.error(MessagesUtil.nameOfClassAndMethod() + "error: " + e.getLocalizedMessage());
        }

        return suggestions;
    }

    // </editor-fold>
}



```


Cuando se compila la aplicación se genera el código necesario para interactuar desde nuestra aplicación Java con MongoDB.


Cuando deseamos que el nombre de la base de datos no se tome del archivo microprofile-config.properties, podemos definirlo mediante el método .setDynamicDatabase("database"); del repositorio, que asignara el nombre de la base de datos que se pasa como parámetros y tendrá precedencia sobre el archivo de configuración. Tenga presente que se debe asignar a cada método para que sea funcional.

```java
    @POST
    @RolesAllowed({"admin"})
    public Response save(
            @RequestBody(description = "Crea un nuevo icono.", content = @Content(mediaType = "application/json", schema = @Schema(implementation = Icono.class))) Icono icono) {
        iconoRepository.setDynamicDatabase("database1");
        Optional<Icono> iconoOptional = iconoRepository.save(icono);
        if (iconoOptional.isPresent()) {
            saveHistory(icono);
            return Response.status(201).entity(iconoOptional.get()).build();
        } else {
            return Response.status(400).entity("Error " + iconoRepository.getJmoordbException().getLocalizedMessage()).build();
        }
    }
```

Método para buscar todos los documentos se asigna la base de datos.

```java
@GET
@RolesAllowed({"admin"})
@Produces({MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON})
    
    public List<Icono> findAll() {
         iconoRepository.setDynamicDatabase("database1");
        return iconoRepository.findAll();
    }

```

Por el contrario si no se coloca se tomara la base de datos del archivo de configuración.


```java
@GET
@RolesAllowed({"admin"})
@Produces({MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON})
    
    public List<Icono> findAll() {
       //  iconoRepository.setDynamicDatabase("database1");
        return iconoRepository.findAll();
    }

```