<?php

namespace CfdiUtils\Validate\Cfdi33\RecepcionPagos\Helpers;

class FormaPagoCatalog
{
    public function obtain(string $key): FormaPagoEntry
    {
        $map = [
            [
                'key' => '01',
                'description' => 'Efectivo',
                'useSenderRfc' => false,
                'useSenderAccount' => false,
                'useSenderAccountRegExp' => '',
                'useReceiverRfc' => false,
                'useReceiverAccount' => false,
                'useReceiverAccountRegExp' => '',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '02',
                'description' => 'Cheque nominativo',
                'useSenderRfc' => true,
                'useSenderAccount' => true,
                'useSenderAccountRegExp' => '/^([0-9]{11}|[0-9]{18})$/',
                'useReceiverRfc' => true,
                'useReceiverAccount' => true,
                'useReceiverAccountRegExp' => '/^([0-9]{10,11}|[0-9]{15,16}|[0-9]{18}|[A-Z0-9_]{10,50})$/',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '03',
                'description' => 'Transferencia electrónica de fondos',
                'useSenderRfc' => true,
                'useSenderAccount' => true,
                'useSenderAccountRegExp' => '/^([0-9]{10}|[0-9]{16}|[0-9]{18})$/',
                'useReceiverRfc' => true,
                'useReceiverAccount' => true,
                'useReceiverAccountRegExp' => '/^([0-9]{10}|[0-9]{18})$/',
                'allowPaymentSignature' => true,
            ],
            [
                'key' => '04',
                'description' => 'Tarjeta de crédito',
                'useSenderRfc' => true,
                'useSenderAccount' => true,
                'useSenderAccountRegExp' => '/^([0-9]{16})$/',
                'useReceiverRfc' => true,
                'useReceiverAccount' => true,
                'useReceiverAccountRegExp' => '/^([0-9]{10,11}|[0-9]{15,16}|[0-9]{18}|[A-Z0-9_]{10,50})$/',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '05',
                'description' => 'Monedero electrónico',
                'useSenderRfc' => true,
                'useSenderAccount' => true,
                'useSenderAccountRegExp' => '/^([0-9]{10,11}|[0-9]{15,16}|[0-9]{18}|[A-Z0-9_]{10,50})$/',
                'useReceiverRfc' => true,
                'useReceiverAccount' => true,
                'useReceiverAccountRegExp' => '/^([0-9]{10,11}|[0-9]{15,16}|[0-9]{18}|[A-Z0-9_]{10,50})$/',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '06',
                'description' => 'Dinero electrónico',
                'useSenderRfc' => true,
                'useSenderAccount' => true,
                'useSenderAccountRegExp' => '/^([0-9]{10})$/',
                'useReceiverRfc' => false,
                'useReceiverAccount' => false,
                'useReceiverAccountRegExp' => '',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '08',
                'description' => 'Vales de despensa',
                'useSenderRfc' => false,
                'useSenderAccount' => false,
                'useSenderAccountRegExp' => '',
                'useReceiverRfc' => false,
                'useReceiverAccount' => false,
                'useReceiverAccountRegExp' => '',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '12',
                'description' => 'Dación en pago',
                'useSenderRfc' => false,
                'useSenderAccount' => false,
                'useSenderAccountRegExp' => '',
                'useReceiverRfc' => false,
                'useReceiverAccount' => false,
                'useReceiverAccountRegExp' => '',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '13',
                'description' => 'Pago por subrogación',
                'useSenderRfc' => false,
                'useSenderAccount' => false,
                'useSenderAccountRegExp' => '',
                'useReceiverRfc' => false,
                'useReceiverAccount' => false,
                'useReceiverAccountRegExp' => '',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '14',
                'description' => 'Pago por consignación',
                'useSenderRfc' => false,
                'useSenderAccount' => false,
                'useSenderAccountRegExp' => '',
                'useReceiverRfc' => false,
                'useReceiverAccount' => false,
                'useReceiverAccountRegExp' => '',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '15',
                'description' => 'Condonación',
                'useSenderRfc' => false,
                'useSenderAccount' => false,
                'useSenderAccountRegExp' => '',
                'useReceiverRfc' => false,
                'useReceiverAccount' => false,
                'useReceiverAccountRegExp' => '',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '17',
                'description' => 'Compensación',
                'useSenderRfc' => false,
                'useSenderAccount' => false,
                'useSenderAccountRegExp' => '',
                'useReceiverRfc' => false,
                'useReceiverAccount' => false,
                'useReceiverAccountRegExp' => '',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '23',
                'description' => 'Novación',
                'useSenderRfc' => false,
                'useSenderAccount' => false,
                'useSenderAccountRegExp' => '',
                'useReceiverRfc' => false,
                'useReceiverAccount' => false,
                'useReceiverAccountRegExp' => '',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '24',
                'description' => 'Confusión',
                'useSenderRfc' => false,
                'useSenderAccount' => false,
                'useSenderAccountRegExp' => '',
                'useReceiverRfc' => false,
                'useReceiverAccount' => false,
                'useReceiverAccountRegExp' => '',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '25',
                'description' => 'Remisión de deuda',
                'useSenderRfc' => false,
                'useSenderAccount' => false,
                'useSenderAccountRegExp' => '',
                'useReceiverRfc' => false,
                'useReceiverAccount' => false,
                'useReceiverAccountRegExp' => '',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '26',
                'description' => 'Prescripción o caducidad',
                'useSenderRfc' => false,
                'useSenderAccount' => false,
                'useSenderAccountRegExp' => '',
                'useReceiverRfc' => false,
                'useReceiverAccount' => false,
                'useReceiverAccountRegExp' => '',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '27',
                'description' => 'A satisfacción del acreedor',
                'useSenderRfc' => false,
                'useSenderAccount' => false,
                'useSenderAccountRegExp' => '',
                'useReceiverRfc' => false,
                'useReceiverAccount' => false,
                'useReceiverAccountRegExp' => '',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '28',
                'description' => 'Tarjeta de débito',
                'useSenderRfc' => true,
                'useSenderAccount' => true,
                'useSenderAccountRegExp' => '/^([0-9]{16})$/',
                'useReceiverRfc' => true,
                'useReceiverAccount' => true,
                'useReceiverAccountRegExp' => '/^([0-9]{10,11}|[0-9]{15,16}|[0-9]{18}|[A-Z0-9_]{10,50})$/',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '29',
                'description' => 'Tarjeta de servicios',
                'useSenderRfc' => true,
                'useSenderAccount' => true,
                'useSenderAccountRegExp' => '/^([0-9]{15,16})$/',
                'useReceiverRfc' => true,
                'useReceiverAccount' => true,
                'useReceiverAccountRegExp' => '/^([0-9]{10,11}|[0-9]{15,16}|[0-9]{18}|[A-Z0-9_]{10,50})$/',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '30',
                'description' => 'Aplicación de anticipos',
                'useSenderRfc' => false,
                'useSenderAccount' => false,
                'useSenderAccountRegExp' => '',
                'useReceiverRfc' => false,
                'useReceiverAccount' => false,
                'useReceiverAccountRegExp' => '',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '31',
                'description' => 'Intermediario pagos',
                'useSenderRfc' => false,
                'useSenderAccount' => false,
                'useSenderAccountRegExp' => '',
                'useReceiverRfc' => false,
                'useReceiverAccount' => false,
                'useReceiverAccountRegExp' => '',
                'allowPaymentSignature' => false,
            ],
            [
                'key' => '99',
                'description' => 'Por definir',
                'useSenderRfc' => true,
                'useSenderAccount' => true,
                'useSenderAccountRegExp' => '/^\S*$/',
                'useReceiverRfc' => true,
                'useReceiverAccount' => true,
                'useReceiverAccountRegExp' => '/^\S*$/',
                'allowPaymentSignature' => true,
            ],
        ];

        $keys = array_column($map, 'key');
        $index = array_search($key, $keys, true);
        if (false === $index) {
            throw new \OutOfBoundsException("Key '$key' was not found in the catalog");
        }
        return new FormaPagoEntry(...array_values($map[$index]));
    }
}
