se agrega funcion para soft delete de una receta

This commit is contained in:
FrancoPandolfo 2025-06-05 21:37:02 +00:00
parent bf1784f61c
commit 1ff27ec0b6
4 changed files with 140 additions and 13 deletions

View file

@ -1,2 +1,3 @@
wallet
!wallet/.gitkeep
bin/

View file

@ -51,6 +51,16 @@ type Vacuna struct {
PractitionerDocumentNumber string `json:"practitionerDocumentNumber"`
}
type Estado string
const (
EstadoDraft Estado = "draft"
EstadoActive Estado = "active"
EstadoOnHold Estado = "on_hold"
EstadoCancelled Estado = "cancelled"
EstadoCompleted Estado = "completed"
EstadoStoped Estado = "stoped"
)
func (s *SmartContract) InitLedger(ctx contractapi.TransactionContextInterface) error {
recetas := []Receta{
{
@ -150,11 +160,11 @@ func (s *SmartContract) FirmarReceta(ctx contractapi.TransactionContextInterface
if err := json.Unmarshal(recetaJSON, &receta); err != nil {
return fmt.Errorf("error al parsear la receta: %v", err)
}
if receta.Status != "draft" {
if receta.Status != Estado.Draft {
return fmt.Errorf("la receta %s no puede ser firmada porque no está en estado 'draft'", recetaID)
}
receta.Signature = firma
receta.Status = "active"
receta.Status = Estado.Active
receta.StatusChange = "FIRMADA"
updatedRecetaJSON, err := json.Marshal(receta)
if err != nil {
@ -187,12 +197,12 @@ func (s *SmartContract) EntregarReceta(ctx contractapi.TransactionContextInterfa
return fmt.Errorf("error al parsear la receta actual: %v", err)
}
if recetaActual.Status != "active" {
if recetaActual.Status != Estado.Active {
return fmt.Errorf("solo se puede entregar la receta si está en estado 'active'")
}
// Cambiar el estado a ENTREGADO
recetaActual.Status = "completed"
recetaActual.Status = Estado.Completed
// Guardar la receta modificada
updatedRecetaJSON, err := json.Marshal(recetaActual)
@ -230,7 +240,33 @@ func (s *SmartContract) DeleteReceta(ctx contractapi.TransactionContextInterface
return fmt.Errorf("la receta %s no existe", id)
}
return ctx.GetStub().DelState(id)
// Obtener receta
recetaJSON, err := ctx.GetStub().GetState(id)
if err != nil {
return fmt.Errorf("error al obtener la receta: %v", err)
}
var receta Receta
err = json.Unmarshal(recetaJSON, &receta)
if err != nil {
return fmt.Errorf("error al deserializar la receta: %v", err)
}
// Cambiar el estado a "cancelled"
receta.Status = Estado.Cancelled
// Volver a guardar la receta modificada
recetaActualizadaJSON, err := json.Marshal(receta)
if err != nil {
return fmt.Errorf("error al serializar la receta actualizada: %v", err)
}
err = ctx.GetStub().PutState(id, recetaActualizadaJSON)
if err != nil {
return fmt.Errorf("error al guardar la receta actualizada: %v", err)
}
return nil
}
func (s *SmartContract) RecetaExists(ctx contractapi.TransactionContextInterface, id string) (bool, error) {
@ -277,11 +313,20 @@ func (s *SmartContract) GetAllRecetas(ctx contractapi.TransactionContextInterfac
return nil, err
}
if len(queryResponse.Value) == 0 {
continue // Ignorar valores vacíos
}
var receta Receta
err = json.Unmarshal(queryResponse.Value, &receta)
if err != nil {
return nil, err
continue // O podrías loggear el error si es útil
}
if receta.Status == status.Cancelled {
continue // Ignorar recetas canceladas
}
recetas = append(recetas, &receta)
}

View file

@ -178,6 +178,39 @@ public class RecetaController {
}
}
@PostMapping("/borrar")
public ResponseEntity<RecetaDto> delete(@RequestBody Map<String, String> requestBody) {
logger.info("Received request to obtain receta with ID: {}", requestBody.get("id")); // Log de entrada
try {
String id = requestBody.get("id");
logger.debug("Searching for receta with ID: {}", id); // Log de búsqueda
recetaService.borrarReceta(id);
logger.debug("Receta deleted: {}", id); // Log cuando se encuentra la receta
return new ResponseEntity<>(HttpStatus.OK);
} catch (IOException e) {
logger.error("IOException occurred while deleting receta with ID: {}", requestBody.get("id"), e); // Log de
// excepción
// específica
return new ResponseEntity<>(HttpStatus.NOT_ACCEPTABLE);
} catch (GatewayException e) {
logger.error("GatewayException occurred while deleting receta with ID: {}", requestBody.get("id"), e); // Log
// de
// excepción
// Gateway
return new ResponseEntity<>(HttpStatus.NOT_ACCEPTABLE);
} catch (Exception e) {
logger.error("Unexpected error occurred while deleting receta with ID: {}", requestBody.get("id"), e); // Log
// de
// error
// inesperado
return new ResponseEntity<>(HttpStatus.INTERNAL_SERVER_ERROR);
}
}
private RecetaDto mapToDto(Receta receta) {
RecetaDto dto = new RecetaDto();
dto.setIdentifier(receta.getIdentifier());

View file

@ -11,9 +11,6 @@ import lombok.SneakyThrows;
import org.hyperledger.fabric.client.*;
import org.hyperledger.fabric.client.identity.*;
import org.springframework.stereotype.Service;
import org.hyperledger.fabric.client.identity.Identity;
import org.hyperledger.fabric.client.identity.Signer;
import javax.annotation.PostConstruct;
import java.io.IOException;
@ -118,9 +115,31 @@ public class RecetaService {
}
public Receta obtenerReceta(String recetaId) throws GatewayException, IOException {
var evaluateResult = contract.evaluateTransaction("ReadReceta", recetaId);
ObjectMapper objectMapper = new ObjectMapper();
return objectMapper.readValue(evaluateResult, Receta.class);
System.out.println("[INFO] Iniciando obtención de receta con ID: " + recetaId);
try {
System.out.println("[DEBUG] Ejecutando transacción 'ReadReceta' con ID: " + recetaId);
var evaluateResult = contract.evaluateTransaction("ReadReceta", recetaId);
System.out.println("[DEBUG] Resultado de transacción recibido: " + new String(evaluateResult));
ObjectMapper objectMapper = new ObjectMapper();
Receta receta = objectMapper.readValue(evaluateResult, Receta.class);
System.out.println("[INFO] Receta parseada exitosamente para ID: " + recetaId);
return receta;
} catch (GatewayException e) {
System.err.println("[ERROR] GatewayException al obtener receta con ID: " + recetaId);
e.printStackTrace(System.err);
throw e;
} catch (IOException e) {
System.err.println("[ERROR] IOException al parsear receta con ID: " + recetaId);
e.printStackTrace(System.err);
throw e;
} catch (Exception e) {
System.err.println("[ERROR] Error inesperado al obtener receta con ID: " + recetaId);
e.printStackTrace(System.err);
throw new RuntimeException("Error inesperado al obtener la receta", e);
}
}
public List<Receta> obtenerTodasLasRecetas() throws GatewayException, IOException {
@ -151,7 +170,36 @@ public class RecetaService {
public void firmarReceta(String recetaId, String signature)
throws CommitStatusException, EndorseException, CommitException, SubmitException {
contract.submitTransaction("FirmarReceta", recetaId, signature);
System.out.println("[INFO] Iniciando firma de receta con ID: " + recetaId);
try {
var evaluateResult = contract.submitTransaction("FirmarReceta", recetaId, signature);
System.out.println("[DEBUG] Resultado de transacción recibido: " + new String(evaluateResult));
System.out.println("[INFO] Receta firmada exitosamente para ID: " + recetaId);
} catch (Exception e) {
System.err.println("[ERROR] Error al firmar receta: " + e.getMessage());
e.printStackTrace();
}
}
public void borrarReceta(String recetaId) throws GatewayException, IOException {
System.out.println("[INFO] Iniciando borrado de receta con ID: " + recetaId);
try {
System.out.println("[DEBUG] Ejecutando transacción 'DeleteReceta' con ID: " + recetaId);
var evaluateResult = contract.evaluateTransaction("DeleteReceta", recetaId);
System.out.println("[DEBUG] Resultado de transacción recibido: " + new String(evaluateResult));
System.out.println("[INFO] Receta borrada exitosamente para ID: " + recetaId);
} catch (GatewayException e) {
System.err.println("[ERROR] GatewayException al borrar receta con ID: " + recetaId);
e.printStackTrace(System.err);
throw e;
} catch (Exception e) {
System.err.println("[ERROR] Error inesperado al borrar receta con ID: " + recetaId);
e.printStackTrace(System.err);
throw new RuntimeException("Error inesperado al borrar la receta", e);
}
}
public List<Receta> obtenerRecetasPorDniYEstado(String dni, String estado) throws GatewayException, IOException {