From 679b4011018ea2df11ba08ee8fe2a77620e77d18 Mon Sep 17 00:00:00 2001 From: Juan Pablo Vial Date: Thu, 8 May 2025 17:17:49 -0400 Subject: [PATCH] Servicio Toku para enviar datos --- app/src/Service/MediosPago/Toku.php | 119 +++++++++ .../unit/src/Service/MediosPago/TokuTest.php | 244 ++++++++++++++++++ 2 files changed, 363 insertions(+) create mode 100644 app/src/Service/MediosPago/Toku.php create mode 100644 app/tests/unit/src/Service/MediosPago/TokuTest.php diff --git a/app/src/Service/MediosPago/Toku.php b/app/src/Service/MediosPago/Toku.php new file mode 100644 index 0000000..4def84a --- /dev/null +++ b/app/src/Service/MediosPago/Toku.php @@ -0,0 +1,119 @@ +{strtolower($type)} = $endPoint; + return $this; + } + + /** + * @param Model\Persona $persona + * @return array + * @throws EmptyResponse + */ + public function sendPersona(Model\Persona|Model\Venta\Propietario $persona): array + { + $rut = implode('', [$persona->rut, strtoupper($persona->dv)]); + try { + return $this->customer->getById($rut); + } catch (EmptyResponse $exception) { + $datos = $persona->datos; + $customerData = [ + 'rut' => $rut, + 'nombreCompleto' => $persona->nombreCompleto(), + 'email' => $datos?->email ?? '', + 'telefono' => $datos?->telefono ?? '' + ]; + if (!$this->customer->add($customerData)) { + throw new EmptyResponse("Could not save Customer for Persona {$rut}", $exception); + } + return $this->customer->getById($rut); + } + } + /** + * @param Model\Venta $venta + * @return bool + * @throws EmptyResponse + */ + public function sendVenta(Model\Venta $venta): array + { + $customer = $this->sendPersona($venta->propietario()); + try { + return $this->subscription->getById($venta->id); + } catch (EmptyResponse $exception) { + $subscriptionData = [ + 'customer' => $customer['toku_id'], + 'product_id' => $venta->id, + 'venta' => $venta + ]; + if (!$this->subscription->add($subscriptionData)) { + throw new EmptyResponse("Could not save Subscription for Venta {$venta->id}", $exception); + } + return $this->subscription->getById($venta->id); + } + } + + /** + * @param Model\Venta $venta + * @return array + * @throws EmptyResponse + */ + public function sendCuotas(Model\Venta $venta): array + { + $customer = $this->sendPersona($venta->propietario()); + $subscription = $this->sendVenta($venta); + + $invoices = []; + $errors = []; + foreach ($venta->formaPago()->pie->cuotas() as $cuota) { + try { + $invoices []= $this->invoice->getById($cuota->id); + } catch (EmptyResponse $exception) { + try { + $invoiceData = [ + 'customer' => $customer['toku_id'], + 'product_id' => $venta->id, + 'subscription' => $subscription['toku_id'], + 'cuota' => $cuota + ]; + if (!$this->invoice->add($invoiceData)) { + throw new EmptyResponse("Could not add Invoice for Cuota {$cuota->id}", $exception); + } + $invoices []= $this->invoice->getById($cuota->id); + } catch (EmptyResponse $exception) { + $this->logger->warning($exception); + $errors []= $exception; + } + } + } + if (count($errors) > 0) { + $this->logger->warning("Revisar el envĂ­o de cuotas de la Venta {$venta->id}"); + } + return $invoices; + } +} diff --git a/app/tests/unit/src/Service/MediosPago/TokuTest.php b/app/tests/unit/src/Service/MediosPago/TokuTest.php new file mode 100644 index 0000000..1d42b18 --- /dev/null +++ b/app/tests/unit/src/Service/MediosPago/TokuTest.php @@ -0,0 +1,244 @@ +logger = $this->getMockBuilder(LoggerInterface::class) + ->disableOriginalConstructor()->getMock(); + + $datos = $this->getMockBuilder(Model\Persona\Datos::class) + ->disableOriginalConstructor()->getMock(); + $datos->email = $faker->email(); + $datos->telefono = $faker->randomNumber(9); + $this->persona = $this->getMockBuilder(Model\Persona::class) + ->disableOriginalConstructor()->getMock(); + $this->persona->rut = $faker->randomNumber(); + $this->persona->digito = 'K'; + $this->persona->nombres = $faker->firstName(); + $this->persona->apellidoPaterno = $faker->lastName(); + $this->persona->apellidoMaterno = $faker->lastName(); + $this->persona->method('datos')->willReturn($datos); + $this->persona->method('__get')->with('dv')->willReturn($this->persona->digito); + $this->customer = $this->getMockBuilder(Model\MediosPago\Toku\Customer::class) + ->disableOriginalConstructor()->getMock(); + $this->customer->id = $faker->randomNumber(); + $this->customer->persona = $this->persona; + $this->customer->toku_id = $faker->ean13(); + $this->customer->method('rut')->willReturn(implode('', [ + $this->persona->rut, + strtoupper($this->persona->digito) + ])); + + $pie = $this->getMockBuilder(Model\Venta\Pie::class) + ->disableOriginalConstructor()->getMock(); + $pie->valor = $faker->randomFloat(); + $formaPago = $this->getMockBuilder(Model\Venta\FormaPago::class) + ->disableOriginalConstructor()->getMock(); + $formaPago->pie = $pie; + $proyecto = $this->getMockBuilder(Model\Proyecto::class) + ->disableOriginalConstructor()->getMock(); + $proyecto->descripcion = $faker->sentence(); + $summary = implode(' - ', [ + $faker->randomNumber(4), + 'E' . $faker->randomNumber(3), + 'B' . $faker->randomNumber(3), + ]); + $propiedad = $this->getMockBuilder(Model\Venta\Propiedad::class) + ->disableOriginalConstructor()->getMock(); + $propiedad->method('summary')->willReturn($summary); + $datos2 = $this->getMockBuilder(Model\Venta\Datos::class) + ->disableOriginalConstructor()->getMock(); + $datos2->email = $datos->email; + $datos2->telefono = $datos->telefono; + $propietario = $this->getMockBuilder(Model\Venta\Propietario::class) + ->disableOriginalConstructor()->getMock(); + $propietario->rut = $this->persona->rut; + $propietario->dv = $this->persona->dv; + $propietario->nombres = $this->persona->nombres; + $propietario->apellidos = ['paterno' => $this->persona->apellidoPaterno, 'materno' => $this->persona->apellidoMaterno]; + $propietario->datos = $datos2; + $this->venta = $this->getMockBuilder(Model\Venta::class) + ->disableOriginalConstructor()->getMock(); + $this->venta->id = $faker->randomNumber(); + $this->venta->method('formaPago')->willReturn($formaPago); + $this->venta->method('proyecto')->willReturn($proyecto); + $this->venta->method('propiedad')->willReturn($propiedad); + $this->venta->method('propietario')->willReturn($propietario); + $this->subscription = $this->getMockBuilder(Model\MediosPago\Toku\Subscription::class) + ->disableOriginalConstructor()->getMock(); + $this->subscription->id = $faker->randomNumber(); + $this->subscription->venta = $this->venta; + $this->subscription->toku_id = $faker->ean13(); + + $pago = $this->getMockBuilder(Model\Venta\Pago::class) + ->disableOriginalConstructor()->getMock(); + $pago->fecha = $faker->dateTime(); + $pago->valor = $faker->randomNumber(6); + $pago->method('valor')->willReturn($faker->randomFloat(3, 10, 500)); + $this->cuota = $this->getMockBuilder(Model\Venta\Cuota::class) + ->disableOriginalConstructor()->getMock(); + $this->cuota->id = $faker->randomNumber(); + $this->cuota->numero = $faker->randomNumber(2); + $this->cuota->pago = $pago; + $pie->method('cuotas')->willReturn([$this->cuota]); + $this->invoice = $this->getMockBuilder(Model\MediosPago\Toku\Invoice::class) + ->disableOriginalConstructor()->getMock(); + $this->invoice->id = $faker->randomNumber(); + $this->invoice->cuota = $this->cuota; + $this->invoice->toku_id = $faker->ean13(); + + $this->customerService = $this->getMockBuilder(Service\MediosPago\Toku\Customer::class) + ->disableOriginalConstructor()->getMock(); + $this->customerService->method('getById')->willReturn([ + 'id' => $this->customer->id, + 'rut' => $this->customer->rut(), + 'toku_id' => $this->customer->toku_id + ]); + $this->customerService->method('get')->willReturn([ + 'id' => $this->customer->toku_id, + 'goverment_id' => $this->customer->rut(), + 'external_id' => $this->customer->rut(), + 'name' => implode(' ', [$this->persona->nombres, $this->persona->apellidoPaterno, $this->persona->apellidoMaterno]), + 'mail' => $this->persona->datos()->email, + 'phone_number' => $this->persona->datos()->telefono, + 'silenced_until' => null, + 'default_agent' => 'contacto@incoviba.cl', + 'agent_phone_number' => null, + 'pac_mandate_id' => null, + 'send_mail' => false, + 'default_receipt_type' => null, + 'rfc' => null, + 'tax_zip_code' => null, + 'fiscal_regime' => null, + 'secondary_emails' => [], + 'metadata' => [] + ]); + $this->customerService->method('add')->willReturn(true); + $this->customerService->method('edit')->willReturn(true); + $this->customerService->method('delete'); + + $this->subscriptionService = $this->getMockBuilder(Service\MediosPago\Toku\Subscription::class) + ->disableOriginalConstructor()->getMock(); + $this->subscriptionService->method('getById')->willReturn([ + 'id' => $this->subscription->id, + 'venta_id' => $this->venta->id, + 'toku_id' => $this->subscription->toku_id, + ]); + $this->subscriptionService->method('get')->willReturn([ + 'id' => $this->subscription->toku_id, + 'customer' => $this->customer->toku_id, + 'product_id' => $this->venta->id, + 'pac_mandate_id' => null, + 'is_recurring' => false, + 'amount' => $pie->valor, + 'due_day' => null, + 'receipt_product_code' => null, + 'metadata' => [ + 'proyecto' => $proyecto->descripcion, + 'propiedad' => $propiedad->summary(), + ] + ]); + $this->subscriptionService->method('add')->willReturn(true); + $this->subscriptionService->method('edit')->willReturn(true); + $this->subscriptionService->method('delete'); + + $this->invoiceService = $this->getMockBuilder(Service\MediosPago\Toku\Invoice::class) + ->disableOriginalConstructor()->getMock(); + $this->invoiceService->method('getById')->willReturn([ + 'id' => $this->invoice->id, + 'cuota_id' => $this->cuota->id, + 'toku_id' => $this->invoice->toku_id, + ]); + $this->invoiceService->method('get')->willReturn([ + 'id' => $this->invoice->toku_id, + 'customer' => $this->customer->toku_id, + 'product_id' => $this->venta->id, + 'subscription' => $this->subscription->toku_id, + 'is_paid' => false, + 'due_date' => $pago->fecha->format('Y-m-d'), + 'is_void' => false, + 'amount' => $pago->valor(), + 'link_payment' => '', + 'metadata' => [ + 'numero' => $this->cuota->numero, + 'valor' => $this->cuota->pago->valor, + 'UF' => $this->cuota->pago->valor(), + ], + 'receipt_type' => null, + 'id_receipt' => null, + 'source' => null, + 'disable_automatic_payment' => false, + 'currency_code' => 'CLF', + 'invoice_external_id' => $this->cuota->id, + ]); + $this->invoiceService->method('add')->willReturn(true); + $this->invoiceService->method('edit')->willReturn(true); + $this->invoiceService->method('delete'); + } + + public function testSendCustomer(): void + { + $service = new Service\MediosPago\Toku($this->logger); + $service->register(Service\MediosPago\Toku::CUSTOMER, $this->customerService); + + $expected = [ + 'id' => $this->customer->id, + 'rut' => $this->customer->rut(), + 'toku_id' => $this->customer->toku_id + ]; + + $this->assertEquals($expected, $service->sendPersona($this->persona)); + } + public function testSendSubscription(): void + { + $service = new Service\MediosPago\Toku($this->logger); + $service->register(Service\MediosPago\Toku::CUSTOMER, $this->customerService); + $service->register(Service\MediosPago\Toku::SUBSCRIPTION, $this->subscriptionService); + + $expected = [ + 'id' => $this->subscription->id, + 'venta_id' => $this->venta->id, + 'toku_id' => $this->subscription->toku_id, + ]; + + $this->assertEquals($expected, $service->sendVenta($this->venta)); + } + public function testSendInvoice(): void + { + $service = new Service\MediosPago\Toku($this->logger); + $service->register(Service\MediosPago\Toku::CUSTOMER, $this->customerService); + $service->register(Service\MediosPago\Toku::SUBSCRIPTION, $this->subscriptionService); + $service->register(Service\MediosPago\Toku::INVOICE, $this->invoiceService); + + $expected = [ + [ + 'id' => $this->invoice->id, + 'cuota_id' => $this->cuota->id, + 'toku_id' => $this->invoice->toku_id, + ] + ]; + + $this->assertEquals($expected, $service->sendCuotas($this->venta)); + } +}