Actualizar las fechas en rango de dos fechas y validar los disponibles excluyendo el entity actual
Last updated
Was this helpful?
Last updated
Was this helpful?
Cuando implementamos los filtros en rangos de dos fechas, a veces necesitamos editar las fechas/hora de inicio o fin, y necesitamos evaluar que estén disponibles para asignar un vehículo, pero nos encontramos en la situación que debemos excluir el Entity actual de la búsqueda debió a que nos indicaría que el ya existe, y deseamos es modificar la fecha u hora.
Para ello agregamos al filtro ne("viajes.idviaje",viaje.getIdviaje());, de esta manera realiza la búsqueda entre los demás registros e ignora el mismo para permitir su edición.
Bson filter= Filters.and(eq("vehiculo.idvehiculo",viaje.getVehiculo().getIdvehiculo()),eq("activo","si"),ne("idviaje",viaje.getIdviaje()));
return repository.isAvailableBetweenDateHour(filter,
"fechahorainicioreserva", viaje.getFechahorainicioreserva(), "fechahorafinreserva", viaje.getFechahorafinreserva());
Se crean dos objetos de tipo fecha para almacenar el valor de la fecha/hora de inicio y de fin.
Controller
Declara los atributos y definir los métodos set/get
Boolean iseditable = false;
Date fechaHoraInicioReservaanterior= new Date();
Date fechaHoraFinReservaAnterior= new Date();
Vehiculo vehiculoSelected;
Conductor conductorSelected;
Agregar la validación para viewfecha
Obtener los valores de la fecha/hora de inicio y fin actuales
@PostConstruct
public void init() {
try {
vehiculoScheduleModel = new DefaultScheduleModel();
conductorScheduleModel = new DefaultScheduleModel();
solicitudScheduleModel = new DefaultScheduleModel();
viajeScheduleModel = new DefaultScheduleModel();
iseditable = false;
vehiculoSelected = new Vehiculo();
conductorSelected = new Conductor();
String action = loginController.get("viaje");
String id = loginController.get("idviaje");
String pageSession = loginController.get("pageviaje");
//Search
if (loginController.get("searchviaje") == null || loginController.get("searchviaje").equals("")) {
loginController.put("searchviaje", "_init");
}
writable = false;
viajeList = new ArrayList<>();
viajeFiltered = new ArrayList<>();
viaje = new Viaje();
viajeDataModel = new ViajeDataModel(viajeList);
if (pageSession != null) {
page = Integer.parseInt(pageSession);
}
Integer c = viajeRepository.sizeOfPage(rowPage);
page = page > c ? c : page;
if (action != null) {
switch (action) {
case "gonew":
viaje = new Viaje();
viaje.setFechahorainicioreserva(DateUtil.getFechaHoraActual());
viaje.setFechahorafinreserva(DateUtil.getFechaHoraActual());
viaje.setActivo("si");
viaje.setLugarpartida("UTP-AZUERO");
viajeSelected = viaje;
writable = false;
break;
case "view":
if (id != null) {
Optional<Viaje> optional = viajeRepository.find("idviaje", Integer.parseInt(id));
if (optional.isPresent()) {
viaje = optional.get();
viajeSelected = viaje;
vehiculoSelected = viaje.getVehiculo();
conductorSelected = viaje.getConductor();
fechaHoraInicioReservaanterior = viaje.getFechahorainicioreserva();
fechaHoraFinReservaAnterior = viaje.getFechahorafinreserva();
iseditable = true;
writable = true;
}
}
break;
case "golist":
move();
break;
}
} else {
move();
}
} catch (Exception e) {
errorServices.errorMessage(nameOfClass(), nameOfMethod(), e.getLocalizedMessage());
}
}// </editor-fold>
@Override
public String edit() {
try {
if (!viajeServices.isValid(viaje)) {
return "";
}
if (noHayCambioFechaHoras()) {
//si cambia el vehiculo
if (!viaje.getVehiculo().getIdvehiculo().equals(vehiculoSelected.getIdvehiculo())) {
if (!viajeServices.vehiculoDisponible(viaje)) {
JsfUtil.warningMessage(rf.getMessage("warning.vehiculoenviajefechas"));
return null;
}
}
// si cambio el conductor
if (!viaje.getConductor().getIdconductor().equals(conductorSelected.getIdconductor())) {
if (viaje.getConductor().getEscontrol().equals("no")) {
if (!viajeServices.conductorDisponible(viaje)) {
JsfUtil.warningMessage(rf.getMessage("warning.conductoresenviajefechas"));
return null;
}
}
}
} else {
//si cambia el vehiculo
if (!viajeServices.vehiculoDisponibleExcluyendoMismoViaje(viaje)) {
JsfUtil.warningMessage(rf.getMessage("warning.vehiculoenviajefechas"));
return null;
}
// si cambio el conductor
if (viaje.getConductor().getEscontrol().equals("no")) {
if (!viajeServices.conductorDisponibleExcluyendoMismoViaje(viaje)) {
JsfUtil.warningMessage(rf.getMessage("warning.conductoresenviajefechas"));
return null;
}
}
}
viaje.getUserInfo().add(userInfoServices.generateUserinfo(loginController.getUsername(), "update"));
//guarda el contenido actualizado
revisionHistoryTransporteejbRepository.save(revisionHistoryServices.getRevisionHistory(viaje.getIdviaje().toString(), loginController.getUsername(),
"update", "viaje", viajeRepository.toDocument(viaje).toString()));
viajeRepository.update(viaje);
JsfUtil.successMessage(rf.getAppMessage("info.update"));
} catch (Exception e) {
errorServices.errorMessage(nameOfClass(), nameOfMethod(), e.getLocalizedMessage());
}
return "";
}
Maneja eventos del calendar y valida las fechas/horas
public void handleSelect(SelectEvent event) {
try {
viajeServices.isValidDate(viaje);
} catch (Exception e) {
errorServices.errorMessage(nameOfClass(), nameOfMethod(), e.getLocalizedMessage());
}
}// </editor-fold>
Se utiliza para generar el List<Vehiculo> que sera mostrado en el autocomplete en base la disponibilidad o no en el rango de fechas.
public List<Vehiculo> completeVehiculo(String query) {
List<Vehiculo> suggestions = new ArrayList<>();
List<Vehiculo> temp = new ArrayList<>();
try {
Boolean found = false;
query = query.trim();
if (iseditable && noHayCambioFechaHoras()) {
suggestions.add(vehiculoSelected);
}
String field = (String) UIComponent.getCurrentComponent(FacesContext.getCurrentInstance()).getAttributes().get("field");
temp = vehiculoRepository.findRegex(field, query, true, new Document(field, 1));
if (!temp.isEmpty()) {
List<Vehiculo> validos = new ArrayList<>();
if (noHayCambioFechaHoras()) {
validos = temp.stream()
.filter(x -> isVehiculoActivoDisponible(x)).collect(Collectors.toList());
} else {
validos = temp.stream()
.filter(x -> isVehiculoActivoDisponibleExcluyendoMismoViaje(x)).collect(Collectors.toList());
//si cambia el vehiculo
}
if (validos.isEmpty()) {
return suggestions;
}
if (vehiculoList == null || vehiculoList.isEmpty()) {
validos.forEach((v) -> {
suggestions.add(v);
}); // validos.add(vehiculoSelected);
// return validos;
} else {
// REMOVERLOS SI YA ESTAN EN EL LISTADO
validos.forEach((v) -> {
Optional<Vehiculo> optional = vehiculoList.stream()
.filter(v2 -> v2.getIdvehiculo() == v.getIdvehiculo())
.findAny();
if (!optional.isPresent()) {
suggestions.add(v);
}
});
}
}
} catch (Exception e) {
errorServices.errorMessage(nameOfClass(), nameOfMethod(), e.getLocalizedMessage());
}
return suggestions;
}
Verifica si el vehículo esta disponible
public Boolean isVehiculoActivoDisponible(Vehiculo vehiculo) {
Boolean valid = false;
try {
if (vehiculo.getActivo().equals("no") && vehiculo.getEnreparacion().equals("si")) {
} else {
if (viajeServices.vehiculoDisponible(vehiculo, viaje.getFechahorainicioreserva(), viaje.getFechahorafinreserva())) {
valid = true;
}
}
} catch (Exception e) {
errorServices.errorDialog(nameOfClass(), nameOfMethod(), nameOfMethod(), e.getLocalizedMessage());
}
return valid;
}
Verifica si esta disponible excluyendo el mismo viaje , se usa cuando se va a editar un viaje y debe mostrar el vehiculo que estaba asignado.
public Boolean isVehiculoActivoDisponibleExcluyendoMismoViaje(Vehiculo vehiculo) {
Boolean valid = false;
try {
if (vehiculo.getActivo().equals("no") && vehiculo.getEnreparacion().equals("si")) {
} else {
if (viajeServices.vehiculoDisponibleExcluyendoMismoViaje(vehiculo, viaje.getFechahorainicioreserva(), viaje.getFechahorafinreserva(), viaje.getIdviaje())) {
valid = true;
}
}
} catch (Exception e) {
errorServices.errorDialog(nameOfClass(), nameOfMethod(), "isVehiculoValid()", e.getLocalizedMessage());
}
return valid;
}
En el método agregamos el filtro por idvehiculo, activo y que no sea el viaje actual, para que lo excluya de la búsqueda.
public Boolean vehiculoDisponible(Vehiculo vehiculo, Date fechahorainicioreserva, Date fechahorafinreserva) {
try {
Bson filter= Filters.and(eq("vehiculo.idvehiculo",vehiculo.getIdvehiculo()),eq("activo","si"));
//
return repository.isAvailableBetweenDateHour(filter,
"fechahorainicioreserva", fechahorainicioreserva, "fechahorafinreserva", fechahorafinreserva);
} catch (Exception e) {
JsfUtil.errorDialog("vehiculoDisponible() ", e.getLocalizedMessage().toString());
}
return false;
}
Filtra los registros de viajes excluyendo el mismo viaje, util para ediciòn
try {
Bson filter= Filters.and(eq("vehiculo.idvehiculo",vehiculo.getIdvehiculo()),eq("activo","si"),ne("idviaje",idviaje));
return repository.isAvailableBetweenDateHour(filter,
"fechahorainicioreserva", fechahorainicioreserva, "fechahorafinreserva", fechahorafinreserva);
} catch (Exception e) {
JsfUtil.errorDialog("vehiculoDisponible() ", e.getLocalizedMessage().toString());
}
return false;
}
Devuelva la lista de Viajes con que choca ese vehiculo
public List<Viaje> viajesVehiculoChoques(Vehiculo vehiculo, Date fechahorainicioreserva, Date fechahorafinreserva) {
List<Viaje> list = new ArrayList<>();
try {
Bson filter= Filters.and(eq("vehiculo.idvehiculo",vehiculo.getIdvehiculo()),eq("activo","si"));
return repository.notAvailableBetweenDateHour(filter,
"fechahorainicioreserva", fechahorainicioreserva, "fechahorafinreserva", fechahorafinreserva);
} catch (Exception e) {
JsfUtil.errorDialog("viajesVehiculoChoques() ", e.getLocalizedMessage().toString());
}
return list;
}
Valida que los rangos de fechas sean correctos
public Boolean isValidDate(Viaje viajes) {
try {
if (DateUtil.fechaMenor(viaje.getFechahorafinreserva(), viaje.getFechahorainicioreserva())) {
JsfUtil.warningDialog("Advertencia", "Fecha de regreso menor que la fecha de partida");
return false;
}
if (DateUtil.fechaMenor(viaje.getFechahorafinreserva(), viaje.getFechahorainicioreserva())) {
JsfUtil.warningDialog("Advertencia", "Fecha de regreso menor que la fecha de partida");
return false;
}
if (DateUtil.fechaIgual(viaje.getFechahorafinreserva(), viaje.getFechahorainicioreserva())) {
JsfUtil.warningDialog("Advertencia", "Fecha de regreso es igual a la fecha de partida");
return false;
}
if (DateUtil.getHoraDeUnaFecha(viaje.getFechahorainicioreserva()) == 0
&& DateUtil.getMinutosDeUnaFecha(viaje.getFechahorainicioreserva()) == 0) {
JsfUtil.warningDialog("Advertencia", "La hora de partida no debe ser cero");
return false;
}
if (DateUtil.getHoraDeUnaFecha(viaje.getFechahorafinreserva()) == 0
&& DateUtil.getMinutosDeUnaFecha(viaje.getFechahorafinreserva()) == 0) {
JsfUtil.warningDialog("Advertencia", "La hora de llegada no debe ser cero");
return false;
}
return true;
} catch (Exception e) {
JsfUtil.errorDialog("isValid() ", e.getLocalizedMessage().toString());
}
return false;
}
<?xml version='1.0' encoding='UTF-8' ?>
<!DOCTYPE html>
<ui:composition template="/layout/template.xhtml"
xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:b="http://bootsfaces.net/ui"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:p="http://primefaces.org/ui"
xmlns:a="http://xmlns.jcp.org/jsf/composite/avbravo"
xmlns:extensionviaje="http://xmlns.jcp.org/jsf/composite/extensionviaje">
<ui:define name="content">
<!--<h:outputStylesheet library="bsf" name="css/thumbnails.css"/>-->
<style>
.thumbnail { max-width: 100%; }
img.thumbnail:hover, img.thumbnail:focus {
border: 1px solid;
border-color: #428BCA;
}
</style>
<b:form id="form" prependId="false" rendered="#{loginController.loggedIn and applicationMenu.viaje.query}" onkeypress="if (event.keyCode == 13) {
return false;
}">
<h:panelGroup id="content" layout="block">
<a:messages id="msg"/>
<b:panel title="#{msg['titleview.viaje']}" look="primary">
<b:panelGrid id="panel" colSpans="2,10" size="xs" rendered="#{viajeController.writable}">
<p:outputLabel value="#{msg['field.idviaje']}" />
<p:outputLabel value="#{viajeController.viaje.idviaje}" id="idviaje" />
<p:outputLabel value="#{msg['field.fechahorainicioreserva']}"/>
<p:fieldset>
<extensionviaje:calendar disabled="false"
pattern="dd/MM/yyyy HH:mm a" value="#{viajeController.viaje.fechahorainicioreserva}"
label="#{msg['field.fechahorainicioreserva']}" />
<p:spacer width="25"/>
<extensionviaje:calendar disabled="true"
pattern="dd/MM/yyyy HH:mm a" value="#{viajeController.fechaHoraInicioReservaanterior}"
label="#{msg['field.fechahorainicioreserva']}" />
<p:spacer width="25"/>
<b:commandButton look="success"
title="#{msg['label.solicitudpendiente']}"
immediate="true"
iconAwesome="fa-calendar"
update="solicitudDetails"
action="#{viajeController.prepareScheduleSolicitud()}"
oncomplete="PF('solicitudDialog').show();" />
</p:fieldset>
<p:outputLabel value="#{msg['field.fechahorafinreserva']}" />
<p:fieldset>
<extensionviaje:calendar disabled="false"
pattern="dd/MM/yyyy HH:mm a" value="#{viajeController.viaje.fechahorafinreserva}" label="#{msg['field.fechahorafinreserva']}" />
<p:spacer width="25"/>
<extensionviaje:calendar disabled="true"
pattern="dd/MM/yyyy HH:mm a" value="#{viajeController.fechaHoraFinReservaAnterior}" label="#{msg['field.fechahorafinreserva']}" />
</p:fieldset>
<p:outputLabel value="#{msg['field.lugarpartida']}" />
<a:inputText value="#{viajeController.viaje.lugarpartida}" />
<p:outputLabel value="#{msg['field.lugardestino']}" />
<a:inputText value="#{viajeController.viaje.lugardestino}" />
<p:outputLabel value="#{msg['field.vehiculo']}"
id="vehiculolabel" />
<p:fieldset>
<extensionviaje:autocompletevehiculos id="vehiculo"/>
<p:spacer width="25"/>
<p:outputLabel value="#{viajeController.vehiculoSelected.marca}- #{viajeController.vehiculoSelected.modelo }-#{viajeController.vehiculoSelected.placa }" />
<p:spacer width="25"/>
<b:commandButton look="primary"
immediate="true"
title="#{msg['label.viajevehiculo']}"
iconAwesome="fa-calendar"
update="vehiculoDetails"
action="#{viajeController.prepareScheduleVehiculo()}"
oncomplete="PF('vehiculoDialog').show();" />
</p:fieldset>
<p:outputLabel value="#{msg['field.conductor']}" />
<p:fieldset>
<extensionviaje:autocompleteconductor id="conductor"/>
<p:spacer width="25"/>
<p:outputLabel value="#{viajeController.conductorSelected.nombre}- #{viajeController.conductorSelected.cedula }" />
<p:spacer width="25"/>
<b:commandButton look="primary"
immediate="true"
title="#{msg['label.viajeconductor']}"
iconAwesome="fa-calendar"
update="conductorDetails"
action="#{viajeController.prepareScheduleConductor()}"
oncomplete="PF('conductorDialog').show();" />
</p:fieldset>
<p:outputLabel value="#{msg['field.comentarios']}"/>
<b:inputTextarea requiredMessage="#{msg['field.comentarios']}"
required="true"
rows="2" value="#{viajeController.viaje.comentarios}" />
<p:outputLabel value="#{msg['field.kmestimados']}" />
<a:inputText span="5" value="#{viajeController.viaje.kmestimados}" />
<p:outputLabel value="#{msg['field.costocombustible']}" />
<a:inputText label="#{msg['field.costocombustible']}"
span="5" value="#{viajeController.viaje.costocombustible}" />
<p:outputLabel value="#{msg['field.realizado']}" />
<a:noyes value="#{viajeController.viaje.realizado}" id="realizado" required="true"/>
<p:outputLabel value="#{msg['field.activo']}" />
<a:yesno value="#{viajeController.viaje.activo}" id="activo" required="true"/>
</b:panelGrid>
<a:view
renderedDelete="#{applicationMenu.viaje.delete and viajeController.writable and viajeController.viaje.realizado eq 'no'}"
renderedEdit="#{applicationMenu.viaje.edit and viajeController.writable and viajeController.viaje.realizado eq 'no'}"
renderedList="#{applicationMenu.viaje.list and viajeController.writable}"
edit="#{viajeController.edit()}"
delete="#{viajeController.delete(viajeController.viaje,true)}"
print="#{viajeController.print()}"
url="#{viajeController.prepare('golist',viajeController.viaje)}"
/>
</b:panel>
</h:panelGroup>
<p:dialog widgetVar="vehiculoDialog" header="#{msg['dialogo.viajevehiculos']}"
width="850" height="450"
styleClass="customDialog"
responsive="true"
showEffect="clip" hideEffect="clip">
<b:panelGrid id="vehiculoDetails" colSpans="12" size="xs" >
<p:schedule id="vehiculoSchedule"
rightHeaderTemplate="month,agendaWeek,agendaDay,basicDay"
value="#{viajeController.vehiculoScheduleModel}" widgetVar="vehiculoSchedule" timeZone="GMT-5" locale="es">
</p:schedule>
<b:commandButton value="#{app['button.close']}"
iconAwesome="fa-close"
oncomplete="PF('vehiculoDialog').hide();"/>
</b:panelGrid>
</p:dialog>
<p:dialog widgetVar="conductorDialog" header="#{msg['dialogo.viajeconductor']}"
width="850" height="450"
styleClass="customDialog"
responsive="true"
showEffect="clip" hideEffect="clip">
<b:panelGrid id="conductorDetails" colSpans="12" size="xs" >
<p:schedule id="conductorSchedule"
rightHeaderTemplate="month,agendaWeek,agendaDay,basicDay"
value="#{viajeController.conductorScheduleModel}" widgetVar="conductorSchedule" timeZone="GMT-5" locale="es">
</p:schedule>
<b:commandButton value="#{app['button.close']}"
iconAwesome="fa-close"
oncomplete="PF('conductorDialog').hide();"/>
</b:panelGrid>
</p:dialog>
<p:dialog widgetVar="solicitudDialog" header="#{msg['dialogo.viajesolicitud']}"
width="850" height="450"
styleClass="customDialog"
responsive="true"
showEffect="clip" hideEffect="clip">
<b:panelGrid id="solicitudDetails" colSpans="12" size="xs" >
<p:schedule id="solicitudSchedule"
rightHeaderTemplate="month,agendaWeek,agendaDay,basicDay"
value="#{viajeController.solicitudScheduleModel}" widgetVar="solicitudSchedule" timeZone="GMT-5" locale="es">
</p:schedule>
<b:commandButton value="#{app['button.close']}"
iconAwesome="fa-close"
oncomplete="PF('solicitudDialog').hide();"/>
</b:panelGrid>
</p:dialog>
</b:form>
<a:denegado renderedcondition="#{!loginController.loggedIn or !applicationMenu.viaje.query}" />
<br/><br/><br/>
</ui:define>
</ui:composition>