2026-10-05 17:53:41 -05:00
|
|
|
using Microsoft.Extensions.Configuration;
|
|
|
|
|
using Net.Business.Entities;
|
|
|
|
|
using Net.Business.Entities.ServicesLayer.InventoryTransferRequest;
|
|
|
|
|
using Net.Business.Entities.WMS.SolicitudTransferencia;
|
|
|
|
|
using Net.Connection.ServiceLayer;
|
|
|
|
|
using Net.CrossCotting;
|
|
|
|
|
using System;
|
|
|
|
|
using System.Collections.Generic;
|
|
|
|
|
using System.Linq;
|
|
|
|
|
using System.Net.Http;
|
|
|
|
|
using System.Threading.Tasks;
|
|
|
|
|
|
|
|
|
|
namespace Net.Data.WMS.SolicitudTransferencia
|
|
|
|
|
{
|
|
|
|
|
// Modulo 100% nuevo (sin equivalente en el .NET original) - porte 1:1 de
|
|
|
|
|
// itca_api_sap_wms_python/app/services/solicitud_transferencia_service.py.
|
|
|
|
|
// Actualiza y cierra documentos InventoryTransferRequests (Solicitud de
|
|
|
|
|
// Traslado) en SAP Business One via Service Layer. Ver
|
|
|
|
|
// docs/SOLICITUD_TRANSFERENCIA.md para el detalle completo del contrato.
|
|
|
|
|
public class SolicitudTransferenciaRepository : ISolicitudTransferenciaRepository
|
|
|
|
|
{
|
|
|
|
|
private readonly string _aplicacionName;
|
|
|
|
|
private readonly IConfiguration _configuration;
|
|
|
|
|
private readonly IHttpClientFactory _clientFactory;
|
|
|
|
|
|
|
|
|
|
public SolicitudTransferenciaRepository(IHttpClientFactory clientFactory, IConfiguration configuration)
|
|
|
|
|
{
|
|
|
|
|
_aplicacionName = GetType().Name;
|
|
|
|
|
_configuration = configuration;
|
|
|
|
|
_clientFactory = clientFactory;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Devuelve null en exito (el caller arma un BE_ResultadoTransaccion 200 con
|
|
|
|
|
// body - ver el controller; no responde 204 porque muchos clientes HTTP,
|
|
|
|
|
// incluido HttpClient de .NET, no leen el body de un 204 - ver
|
|
|
|
|
// docs/SOLICITUD_TRANSFERENCIA.md).
|
|
|
|
|
//
|
|
|
|
|
// El PATCH SOLO actualiza cantidades de linea existentes en SAP - no toca
|
|
|
|
|
// fechas, almacenes ni ningun otro campo del documento - y ELIMINA una
|
|
|
|
|
// linea cuando Cantidad = 0. Confirmado contra el Service Layer real de QA:
|
|
|
|
|
// alcanza con mandar LineNum + Quantity por linea junto con el header
|
|
|
|
|
// B1S-ReplaceCollectionsOnPatch: true, que le indica a Service Layer que
|
|
|
|
|
// trate StockTransferLines como reemplazo COMPLETO del array, no un merge
|
|
|
|
|
// parcial. SAP ademas RECHAZA una linea mandada explicita con Quantity: 0,
|
|
|
|
|
// por eso se omite del array en vez de mandarla en cero.
|
|
|
|
|
//
|
2026-10-12 08:51:50 -05:00
|
|
|
// Al ser un reemplazo completo, SAP TAMBIEN exige el campo Rate en cada
|
|
|
|
|
// linea. Se manda Rate: 0.0 fijo (request validado contra SAP); esto pisa
|
|
|
|
|
// el Rate que tuviera la linea en el documento. No se valida que la linea
|
|
|
|
|
// exista: si no existe, el error lo devuelve SAP.
|
2026-10-05 17:53:41 -05:00
|
|
|
public async Task<BE_ResultadoTransaccion<object>> Update(int docEntry, BE_SolicitudTransferenciaPatchRequest entidad)
|
|
|
|
|
{
|
|
|
|
|
ResultadoTransaccion<object> resultadoTransaccion = new ResultadoTransaccion<object>("Update", _aplicacionName);
|
|
|
|
|
|
|
|
|
|
try
|
|
|
|
|
{
|
|
|
|
|
var connectServiceLayer = new ConnectionServiceLayer(_configuration, _clientFactory);
|
|
|
|
|
|
|
|
|
|
var lines = new List<object>();
|
|
|
|
|
foreach (var detalle in entidad.Detalle ?? new List<BE_SolicitudTransferenciaPatchDetalle>())
|
|
|
|
|
{
|
|
|
|
|
if (detalle.Cantidad == 0) continue;
|
|
|
|
|
|
2026-10-12 08:51:50 -05:00
|
|
|
lines.Add(new { LineNum = detalle.Linea, Quantity = detalle.Cantidad, Rate = 0.0 });
|
2026-10-05 17:53:41 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
await connectServiceLayer.PatchNoContentAsync(
|
|
|
|
|
$"InventoryTransferRequests({docEntry})",
|
|
|
|
|
new { StockTransferLines = lines },
|
|
|
|
|
new Dictionary<string, string> { ["B1S-ReplaceCollectionsOnPatch"] = "true" });
|
|
|
|
|
|
|
|
|
|
return null;
|
|
|
|
|
}
|
|
|
|
|
catch (Exception ex)
|
|
|
|
|
{
|
|
|
|
|
return resultadoTransaccion.GetInformacionResultado(ex.Message.ToString(), (object)entidad);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// Cierra el documento completo. Funcionalidad nueva (no existe en el .NET
|
|
|
|
|
// original) - SAP Service Layer cierra documentos via POST a la sub-ruta
|
|
|
|
|
// /Close, mismo patron que Picking/HojaRuta/Cerrar. Devuelve null en exito
|
|
|
|
|
// (el caller arma el BE_ResultadoTransaccion 200 con body).
|
|
|
|
|
public async Task<BE_ResultadoTransaccion<object>> Cerrar(int docEntry)
|
|
|
|
|
{
|
|
|
|
|
ResultadoTransaccion<object> resultadoTransaccion = new ResultadoTransaccion<object>("Cerrar", _aplicacionName);
|
|
|
|
|
|
|
|
|
|
try
|
|
|
|
|
{
|
|
|
|
|
var connectServiceLayer = new ConnectionServiceLayer(_configuration, _clientFactory);
|
|
|
|
|
await connectServiceLayer.PostActionAsync($"InventoryTransferRequests({docEntry})/Close");
|
|
|
|
|
return null;
|
|
|
|
|
}
|
|
|
|
|
catch (Exception ex)
|
|
|
|
|
{
|
|
|
|
|
return resultadoTransaccion.GetInformacionResultado(ex.Message.ToString(), (object)null);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|