@baruk/core 0.4.2 → 0.6.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.baruk-provenance.json +4 -4
- package/CHANGELOG.md +42 -0
- package/dist/audit/repository.d.ts +33 -1
- package/dist/audit/repository.d.ts.map +1 -1
- package/dist/audit/repository.js +41 -7
- package/dist/audit/repository.js.map +1 -1
- package/dist/auth/service.d.ts +21 -0
- package/dist/auth/service.d.ts.map +1 -1
- package/dist/auth/service.js +46 -1
- package/dist/auth/service.js.map +1 -1
- package/dist/billing/ar-repository.d.ts +41 -1
- package/dist/billing/ar-repository.d.ts.map +1 -1
- package/dist/billing/ar-repository.js +82 -6
- package/dist/billing/ar-repository.js.map +1 -1
- package/dist/billing/provider-account.d.ts +38 -0
- package/dist/billing/provider-account.d.ts.map +1 -1
- package/dist/billing/provider-account.js +58 -2
- package/dist/billing/provider-account.js.map +1 -1
- package/dist/billing/repository.d.ts +44 -0
- package/dist/billing/repository.d.ts.map +1 -1
- package/dist/billing/repository.js +49 -5
- package/dist/billing/repository.js.map +1 -1
- package/dist/cjs/audit/repository.js +41 -7
- package/dist/cjs/audit/repository.js.map +1 -1
- package/dist/cjs/auth/service.js +46 -1
- package/dist/cjs/auth/service.js.map +1 -1
- package/dist/cjs/billing/ar-repository.js +82 -6
- package/dist/cjs/billing/ar-repository.js.map +1 -1
- package/dist/cjs/billing/provider-account.js +60 -1
- package/dist/cjs/billing/provider-account.js.map +1 -1
- package/dist/cjs/billing/repository.js +51 -5
- package/dist/cjs/billing/repository.js.map +1 -1
- package/dist/cjs/clients/ibge.js +117 -0
- package/dist/cjs/clients/ibge.js.map +1 -0
- package/dist/cjs/clients/registry/http.js +157 -0
- package/dist/cjs/clients/registry/http.js.map +1 -0
- package/dist/cjs/clients/registry/ibge-municipios.js +28 -0
- package/dist/cjs/clients/registry/ibge-municipios.js.map +1 -0
- package/dist/cjs/clients/registry/ibge.js +63 -0
- package/dist/cjs/clients/registry/ibge.js.map +1 -0
- package/dist/cjs/clients/registry/lookup.js +191 -0
- package/dist/cjs/clients/registry/lookup.js.map +1 -0
- package/dist/cjs/clients/registry/provider.js +34 -0
- package/dist/cjs/clients/registry/provider.js.map +1 -0
- package/dist/cjs/clients/registry/resolve.js +47 -0
- package/dist/cjs/clients/registry/resolve.js.map +1 -0
- package/dist/cjs/clients/registry/serpro.js +149 -0
- package/dist/cjs/clients/registry/serpro.js.map +1 -0
- package/dist/cjs/clients/registry/service.js +230 -0
- package/dist/cjs/clients/registry/service.js.map +1 -0
- package/dist/cjs/clients/registry/synthetic.js +165 -0
- package/dist/cjs/clients/registry/synthetic.js.map +1 -0
- package/dist/cjs/clients/repository.js +190 -9
- package/dist/cjs/clients/repository.js.map +1 -1
- package/dist/cjs/collection/branding.js +190 -0
- package/dist/cjs/collection/branding.js.map +1 -1
- package/dist/cjs/collection/clearance-store.js +74 -0
- package/dist/cjs/collection/clearance-store.js.map +1 -0
- package/dist/cjs/collection/communication-runtime.js +65 -2
- package/dist/cjs/collection/communication-runtime.js.map +1 -1
- package/dist/cjs/collection/engine.js +20 -0
- package/dist/cjs/collection/engine.js.map +1 -1
- package/dist/cjs/collection/policy.js +29 -1
- package/dist/cjs/collection/policy.js.map +1 -1
- package/dist/cjs/communication/clearance.js +18 -0
- package/dist/cjs/communication/clearance.js.map +1 -0
- package/dist/cjs/communication/dry-run-scenario.js +5 -0
- package/dist/cjs/communication/dry-run-scenario.js.map +1 -1
- package/dist/cjs/communication/engine.js +12 -0
- package/dist/cjs/communication/engine.js.map +1 -1
- package/dist/cjs/communication/policy.js.map +1 -1
- package/dist/cjs/competence/business-days.js +155 -0
- package/dist/cjs/competence/business-days.js.map +1 -0
- package/dist/cjs/competence/catalog-validation.js +174 -0
- package/dist/cjs/competence/catalog-validation.js.map +1 -0
- package/dist/cjs/competence/obligation-preview.js +190 -0
- package/dist/cjs/competence/obligation-preview.js.map +1 -0
- package/dist/cjs/competence/repository.js +330 -17
- package/dist/cjs/competence/repository.js.map +1 -1
- package/dist/cjs/dashboard/pilot-panel.js +90 -0
- package/dist/cjs/dashboard/pilot-panel.js.map +1 -0
- package/dist/cjs/dashboard/repository.js +11 -1
- package/dist/cjs/dashboard/repository.js.map +1 -1
- package/dist/cjs/db/client.js +17 -11
- package/dist/cjs/db/client.js.map +1 -1
- package/dist/cjs/db/provision-e2e-identity.js +116 -0
- package/dist/cjs/db/provision-e2e-identity.js.map +1 -0
- package/dist/cjs/fiscal/applicability.js +164 -0
- package/dist/cjs/fiscal/applicability.js.map +1 -0
- package/dist/cjs/fiscal/collection/authorization.js +186 -0
- package/dist/cjs/fiscal/collection/authorization.js.map +1 -0
- package/dist/cjs/fiscal/collection/competence.js +97 -0
- package/dist/cjs/fiscal/collection/competence.js.map +1 -0
- package/dist/cjs/fiscal/collection/first-contact.js +204 -0
- package/dist/cjs/fiscal/collection/first-contact.js.map +1 -0
- package/dist/cjs/fiscal/collection/plan.js +122 -0
- package/dist/cjs/fiscal/collection/plan.js.map +1 -0
- package/dist/cjs/fiscal/conditions.js +198 -0
- package/dist/cjs/fiscal/conditions.js.map +1 -0
- package/dist/cjs/fiscal/contracts/nfse-adn-contract.js +390 -0
- package/dist/cjs/fiscal/contracts/nfse-adn-contract.js.map +1 -0
- package/dist/cjs/fiscal/contracts/nfse-adn-endpoint.js +108 -0
- package/dist/cjs/fiscal/contracts/nfse-adn-endpoint.js.map +1 -0
- package/dist/cjs/fiscal/contracts/nfse-adn-envelope.js +220 -0
- package/dist/cjs/fiscal/contracts/nfse-adn-envelope.js.map +1 -0
- package/dist/cjs/fiscal/coverage/model.js +137 -0
- package/dist/cjs/fiscal/coverage/model.js.map +1 -0
- package/dist/cjs/fiscal/coverage/requests.js +99 -0
- package/dist/cjs/fiscal/coverage/requests.js.map +1 -0
- package/dist/cjs/fiscal/credentials/inspect.js +182 -0
- package/dist/cjs/fiscal/credentials/inspect.js.map +1 -0
- package/dist/cjs/fiscal/credentials/material.js +168 -0
- package/dist/cjs/fiscal/credentials/material.js.map +1 -0
- package/dist/cjs/fiscal/credentials/onboarding.js +266 -0
- package/dist/cjs/fiscal/credentials/onboarding.js.map +1 -0
- package/dist/cjs/fiscal/credentials/readiness.js +190 -0
- package/dist/cjs/fiscal/credentials/readiness.js.map +1 -0
- package/dist/cjs/fiscal/eligibility.js +199 -0
- package/dist/cjs/fiscal/eligibility.js.map +1 -0
- package/dist/cjs/fiscal/enrollment.js +134 -0
- package/dist/cjs/fiscal/enrollment.js.map +1 -0
- package/dist/cjs/fiscal/ingestion/__fixtures__/nfse.js +128 -0
- package/dist/cjs/fiscal/ingestion/__fixtures__/nfse.js.map +1 -0
- package/dist/cjs/fiscal/ingestion/adn-transport.js +229 -0
- package/dist/cjs/fiscal/ingestion/adn-transport.js.map +1 -0
- package/dist/cjs/fiscal/ingestion/direction.js +36 -0
- package/dist/cjs/fiscal/ingestion/direction.js.map +1 -0
- package/dist/cjs/fiscal/ingestion/nfse-adn.js +228 -0
- package/dist/cjs/fiscal/ingestion/nfse-adn.js.map +1 -0
- package/dist/cjs/fiscal/ingestion/pipeline.js +704 -0
- package/dist/cjs/fiscal/ingestion/pipeline.js.map +1 -0
- package/dist/cjs/fiscal/ingestion/provider.js +51 -0
- package/dist/cjs/fiscal/ingestion/provider.js.map +1 -0
- package/dist/cjs/fiscal/ingestion/repository.js +132 -0
- package/dist/cjs/fiscal/ingestion/repository.js.map +1 -0
- package/dist/cjs/fiscal/ingestion/synthetic-provider.js +103 -0
- package/dist/cjs/fiscal/ingestion/synthetic-provider.js.map +1 -0
- package/dist/cjs/fiscal/ingestion/synthetic-transport-types.js +13 -0
- package/dist/cjs/fiscal/ingestion/synthetic-transport-types.js.map +1 -0
- package/dist/cjs/fiscal/ingestion/synthetic-transport.js +61 -0
- package/dist/cjs/fiscal/ingestion/synthetic-transport.js.map +1 -0
- package/dist/cjs/fiscal/ingestion/xml-reader.js +121 -0
- package/dist/cjs/fiscal/ingestion/xml-reader.js.map +1 -0
- package/dist/cjs/fiscal/repository.js +470 -0
- package/dist/cjs/fiscal/repository.js.map +1 -0
- package/dist/cjs/fiscal/sync/circuit.js +124 -0
- package/dist/cjs/fiscal/sync/circuit.js.map +1 -0
- package/dist/cjs/fiscal/sync/intervention.js +140 -0
- package/dist/cjs/fiscal/sync/intervention.js.map +1 -0
- package/dist/cjs/fiscal/sync/lease.js +146 -0
- package/dist/cjs/fiscal/sync/lease.js.map +1 -0
- package/dist/cjs/fiscal/sync/observability.js +244 -0
- package/dist/cjs/fiscal/sync/observability.js.map +1 -0
- package/dist/cjs/fiscal/sync/orchestrator.js +490 -0
- package/dist/cjs/fiscal/sync/orchestrator.js.map +1 -0
- package/dist/cjs/fiscal/sync/policy.js +143 -0
- package/dist/cjs/fiscal/sync/policy.js.map +1 -0
- package/dist/cjs/fiscal/sync/reprocess.js +241 -0
- package/dist/cjs/fiscal/sync/reprocess.js.map +1 -0
- package/dist/cjs/fiscal/sync/retry.js +183 -0
- package/dist/cjs/fiscal/sync/retry.js.map +1 -0
- package/dist/cjs/fiscal/sync/secret-boundary.js +123 -0
- package/dist/cjs/fiscal/sync/secret-boundary.js.map +1 -0
- package/dist/cjs/fiscal/transport/https.js +309 -0
- package/dist/cjs/fiscal/transport/https.js.map +1 -0
- package/dist/cjs/fiscal/transport/synthetic-tls.js +380 -0
- package/dist/cjs/fiscal/transport/synthetic-tls.js.map +1 -0
- package/dist/cjs/fiscal/transport/types.js +93 -0
- package/dist/cjs/fiscal/transport/types.js.map +1 -0
- package/dist/cjs/import/br-documents.js +85 -0
- package/dist/cjs/import/br-documents.js.map +1 -0
- package/dist/cjs/import/clients-import.js +347 -40
- package/dist/cjs/import/clients-import.js.map +1 -1
- package/dist/cjs/index.js +461 -73
- package/dist/cjs/index.js.map +1 -1
- package/dist/cjs/legal/documents.js +164 -19
- package/dist/cjs/legal/documents.js.map +1 -1
- package/dist/cjs/legal/index.js +3 -1
- package/dist/cjs/legal/index.js.map +1 -1
- package/dist/cjs/legal/types.js.map +1 -1
- package/dist/cjs/onboarding/persistence.js +4 -4
- package/dist/cjs/onboarding/persistence.js.map +1 -1
- package/dist/cjs/pilot/go-live-checklist.js +212 -0
- package/dist/cjs/pilot/go-live-checklist.js.map +1 -0
- package/dist/cjs/pilot/milestone.js +79 -0
- package/dist/cjs/pilot/milestone.js.map +1 -0
- package/dist/cjs/platform/capabilities.js +173 -0
- package/dist/cjs/platform/capabilities.js.map +1 -0
- package/dist/cjs/platform/job-contract.js +411 -0
- package/dist/cjs/platform/job-contract.js.map +1 -0
- package/dist/cjs/rbac/catalog.js +110 -0
- package/dist/cjs/rbac/catalog.js.map +1 -1
- package/dist/cjs/subscription-billing/index.js +9 -1
- package/dist/cjs/subscription-billing/index.js.map +1 -1
- package/dist/cjs/subscription-billing/platform-exemption.js +121 -0
- package/dist/cjs/subscription-billing/platform-exemption.js.map +1 -0
- package/dist/cjs/subscription-billing/service.js +246 -78
- package/dist/cjs/subscription-billing/service.js.map +1 -1
- package/dist/cjs/tenancy/features.js +131 -0
- package/dist/cjs/tenancy/features.js.map +1 -0
- package/dist/cjs/tenancy/settings.js +224 -0
- package/dist/cjs/tenancy/settings.js.map +1 -0
- package/dist/cjs/users/repository.js +24 -1
- package/dist/cjs/users/repository.js.map +1 -1
- package/dist/cjs/vault/repository.js +92 -5
- package/dist/cjs/vault/repository.js.map +1 -1
- package/dist/clients/ibge.d.ts +17 -0
- package/dist/clients/ibge.d.ts.map +1 -0
- package/dist/clients/ibge.js +112 -0
- package/dist/clients/ibge.js.map +1 -0
- package/dist/clients/registry/http.d.ts +61 -0
- package/dist/clients/registry/http.d.ts.map +1 -0
- package/dist/clients/registry/http.js +151 -0
- package/dist/clients/registry/http.js.map +1 -0
- package/dist/clients/registry/ibge-municipios.d.ts +25 -0
- package/dist/clients/registry/ibge-municipios.d.ts.map +1 -0
- package/dist/clients/registry/ibge-municipios.js +25 -0
- package/dist/clients/registry/ibge-municipios.js.map +1 -0
- package/dist/clients/registry/ibge.d.ts +62 -0
- package/dist/clients/registry/ibge.d.ts.map +1 -0
- package/dist/clients/registry/ibge.js +57 -0
- package/dist/clients/registry/ibge.js.map +1 -0
- package/dist/clients/registry/lookup.d.ts +94 -0
- package/dist/clients/registry/lookup.d.ts.map +1 -0
- package/dist/clients/registry/lookup.js +184 -0
- package/dist/clients/registry/lookup.js.map +1 -0
- package/dist/clients/registry/provider.d.ts +124 -0
- package/dist/clients/registry/provider.d.ts.map +1 -0
- package/dist/clients/registry/provider.js +39 -0
- package/dist/clients/registry/provider.js.map +1 -0
- package/dist/clients/registry/resolve.d.ts +36 -0
- package/dist/clients/registry/resolve.d.ts.map +1 -0
- package/dist/clients/registry/resolve.js +44 -0
- package/dist/clients/registry/resolve.js.map +1 -0
- package/dist/clients/registry/serpro.d.ts +57 -0
- package/dist/clients/registry/serpro.d.ts.map +1 -0
- package/dist/clients/registry/serpro.js +143 -0
- package/dist/clients/registry/serpro.js.map +1 -0
- package/dist/clients/registry/service.d.ts +59 -0
- package/dist/clients/registry/service.d.ts.map +1 -0
- package/dist/clients/registry/service.js +225 -0
- package/dist/clients/registry/service.js.map +1 -0
- package/dist/clients/registry/synthetic.d.ts +30 -0
- package/dist/clients/registry/synthetic.d.ts.map +1 -0
- package/dist/clients/registry/synthetic.js +161 -0
- package/dist/clients/registry/synthetic.js.map +1 -0
- package/dist/clients/repository.d.ts +158 -0
- package/dist/clients/repository.d.ts.map +1 -1
- package/dist/clients/repository.js +186 -9
- package/dist/clients/repository.js.map +1 -1
- package/dist/collection/branding.d.ts +65 -0
- package/dist/collection/branding.d.ts.map +1 -1
- package/dist/collection/branding.js +186 -0
- package/dist/collection/branding.js.map +1 -1
- package/dist/collection/clearance-store.d.ts +39 -0
- package/dist/collection/clearance-store.d.ts.map +1 -0
- package/dist/collection/clearance-store.js +69 -0
- package/dist/collection/clearance-store.js.map +1 -0
- package/dist/collection/communication-runtime.d.ts +37 -0
- package/dist/collection/communication-runtime.d.ts.map +1 -1
- package/dist/collection/communication-runtime.js +63 -1
- package/dist/collection/communication-runtime.js.map +1 -1
- package/dist/collection/engine.d.ts +23 -0
- package/dist/collection/engine.d.ts.map +1 -1
- package/dist/collection/engine.js +20 -0
- package/dist/collection/engine.js.map +1 -1
- package/dist/collection/policy.d.ts +25 -0
- package/dist/collection/policy.d.ts.map +1 -1
- package/dist/collection/policy.js +27 -0
- package/dist/collection/policy.js.map +1 -1
- package/dist/communication/clearance.d.ts +53 -0
- package/dist/communication/clearance.d.ts.map +1 -0
- package/dist/communication/clearance.js +15 -0
- package/dist/communication/clearance.js.map +1 -0
- package/dist/communication/dry-run-scenario.d.ts.map +1 -1
- package/dist/communication/dry-run-scenario.js +5 -0
- package/dist/communication/dry-run-scenario.js.map +1 -1
- package/dist/communication/engine.d.ts +10 -0
- package/dist/communication/engine.d.ts.map +1 -1
- package/dist/communication/engine.js +12 -0
- package/dist/communication/engine.js.map +1 -1
- package/dist/communication/policy.d.ts +16 -0
- package/dist/communication/policy.d.ts.map +1 -1
- package/dist/communication/policy.js.map +1 -1
- package/dist/competence/business-days.d.ts +51 -0
- package/dist/competence/business-days.d.ts.map +1 -0
- package/dist/competence/business-days.js +145 -0
- package/dist/competence/business-days.js.map +1 -0
- package/dist/competence/catalog-validation.d.ts +86 -0
- package/dist/competence/catalog-validation.d.ts.map +1 -0
- package/dist/competence/catalog-validation.js +168 -0
- package/dist/competence/catalog-validation.js.map +1 -0
- package/dist/competence/obligation-preview.d.ts +103 -0
- package/dist/competence/obligation-preview.d.ts.map +1 -0
- package/dist/competence/obligation-preview.js +184 -0
- package/dist/competence/obligation-preview.js.map +1 -0
- package/dist/competence/repository.d.ts +139 -1
- package/dist/competence/repository.d.ts.map +1 -1
- package/dist/competence/repository.js +325 -17
- package/dist/competence/repository.js.map +1 -1
- package/dist/dashboard/pilot-panel.d.ts +100 -0
- package/dist/dashboard/pilot-panel.d.ts.map +1 -0
- package/dist/dashboard/pilot-panel.js +87 -0
- package/dist/dashboard/pilot-panel.js.map +1 -0
- package/dist/dashboard/repository.d.ts.map +1 -1
- package/dist/dashboard/repository.js +11 -1
- package/dist/dashboard/repository.js.map +1 -1
- package/dist/db/client.d.ts +45 -0
- package/dist/db/client.d.ts.map +1 -1
- package/dist/db/client.js +16 -11
- package/dist/db/client.js.map +1 -1
- package/dist/db/migrate.d.ts +36 -1
- package/dist/db/migrate.d.ts.map +1 -1
- package/dist/db/migrate.js +199 -32
- package/dist/db/migrate.js.map +1 -1
- package/dist/db/provision-e2e-identity.d.ts +2 -0
- package/dist/db/provision-e2e-identity.d.ts.map +1 -0
- package/dist/db/provision-e2e-identity.js +114 -0
- package/dist/db/provision-e2e-identity.js.map +1 -0
- package/dist/fiscal/applicability.d.ts +73 -0
- package/dist/fiscal/applicability.d.ts.map +1 -0
- package/dist/fiscal/applicability.js +160 -0
- package/dist/fiscal/applicability.js.map +1 -0
- package/dist/fiscal/collection/authorization.d.ts +152 -0
- package/dist/fiscal/collection/authorization.d.ts.map +1 -0
- package/dist/fiscal/collection/authorization.js +178 -0
- package/dist/fiscal/collection/authorization.js.map +1 -0
- package/dist/fiscal/collection/competence.d.ts +66 -0
- package/dist/fiscal/collection/competence.d.ts.map +1 -0
- package/dist/fiscal/collection/competence.js +90 -0
- package/dist/fiscal/collection/competence.js.map +1 -0
- package/dist/fiscal/collection/first-contact.d.ts +103 -0
- package/dist/fiscal/collection/first-contact.d.ts.map +1 -0
- package/dist/fiscal/collection/first-contact.js +201 -0
- package/dist/fiscal/collection/first-contact.js.map +1 -0
- package/dist/fiscal/collection/plan.d.ts +74 -0
- package/dist/fiscal/collection/plan.d.ts.map +1 -0
- package/dist/fiscal/collection/plan.js +119 -0
- package/dist/fiscal/collection/plan.js.map +1 -0
- package/dist/fiscal/conditions.d.ts +99 -0
- package/dist/fiscal/conditions.d.ts.map +1 -0
- package/dist/fiscal/conditions.js +190 -0
- package/dist/fiscal/conditions.js.map +1 -0
- package/dist/fiscal/contracts/nfse-adn-contract.d.ts +315 -0
- package/dist/fiscal/contracts/nfse-adn-contract.d.ts.map +1 -0
- package/dist/fiscal/contracts/nfse-adn-contract.js +386 -0
- package/dist/fiscal/contracts/nfse-adn-contract.js.map +1 -0
- package/dist/fiscal/contracts/nfse-adn-endpoint.d.ts +13 -0
- package/dist/fiscal/contracts/nfse-adn-endpoint.d.ts.map +1 -0
- package/dist/fiscal/contracts/nfse-adn-endpoint.js +103 -0
- package/dist/fiscal/contracts/nfse-adn-endpoint.js.map +1 -0
- package/dist/fiscal/contracts/nfse-adn-envelope.d.ts +77 -0
- package/dist/fiscal/contracts/nfse-adn-envelope.d.ts.map +1 -0
- package/dist/fiscal/contracts/nfse-adn-envelope.js +215 -0
- package/dist/fiscal/contracts/nfse-adn-envelope.js.map +1 -0
- package/dist/fiscal/coverage/model.d.ts +114 -0
- package/dist/fiscal/coverage/model.d.ts.map +1 -0
- package/dist/fiscal/coverage/model.js +130 -0
- package/dist/fiscal/coverage/model.js.map +1 -0
- package/dist/fiscal/coverage/requests.d.ts +70 -0
- package/dist/fiscal/coverage/requests.d.ts.map +1 -0
- package/dist/fiscal/coverage/requests.js +95 -0
- package/dist/fiscal/coverage/requests.js.map +1 -0
- package/dist/fiscal/credentials/inspect.d.ts +114 -0
- package/dist/fiscal/credentials/inspect.d.ts.map +1 -0
- package/dist/fiscal/credentials/inspect.js +178 -0
- package/dist/fiscal/credentials/inspect.js.map +1 -0
- package/dist/fiscal/credentials/material.d.ts +81 -0
- package/dist/fiscal/credentials/material.d.ts.map +1 -0
- package/dist/fiscal/credentials/material.js +164 -0
- package/dist/fiscal/credentials/material.js.map +1 -0
- package/dist/fiscal/credentials/onboarding.d.ts +119 -0
- package/dist/fiscal/credentials/onboarding.d.ts.map +1 -0
- package/dist/fiscal/credentials/onboarding.js +259 -0
- package/dist/fiscal/credentials/onboarding.js.map +1 -0
- package/dist/fiscal/credentials/readiness.d.ts +119 -0
- package/dist/fiscal/credentials/readiness.d.ts.map +1 -0
- package/dist/fiscal/credentials/readiness.js +186 -0
- package/dist/fiscal/credentials/readiness.js.map +1 -0
- package/dist/fiscal/eligibility.d.ts +106 -0
- package/dist/fiscal/eligibility.d.ts.map +1 -0
- package/dist/fiscal/eligibility.js +194 -0
- package/dist/fiscal/eligibility.js.map +1 -0
- package/dist/fiscal/enrollment.d.ts +91 -0
- package/dist/fiscal/enrollment.d.ts.map +1 -0
- package/dist/fiscal/enrollment.js +126 -0
- package/dist/fiscal/enrollment.js.map +1 -0
- package/dist/fiscal/ingestion/__fixtures__/nfse.d.ts +57 -0
- package/dist/fiscal/ingestion/__fixtures__/nfse.d.ts.map +1 -0
- package/dist/fiscal/ingestion/__fixtures__/nfse.js +121 -0
- package/dist/fiscal/ingestion/__fixtures__/nfse.js.map +1 -0
- package/dist/fiscal/ingestion/adn-transport.d.ts +123 -0
- package/dist/fiscal/ingestion/adn-transport.d.ts.map +1 -0
- package/dist/fiscal/ingestion/adn-transport.js +220 -0
- package/dist/fiscal/ingestion/adn-transport.js.map +1 -0
- package/dist/fiscal/ingestion/direction.d.ts +60 -0
- package/dist/fiscal/ingestion/direction.d.ts.map +1 -0
- package/dist/fiscal/ingestion/direction.js +32 -0
- package/dist/fiscal/ingestion/direction.js.map +1 -0
- package/dist/fiscal/ingestion/nfse-adn.d.ts +91 -0
- package/dist/fiscal/ingestion/nfse-adn.d.ts.map +1 -0
- package/dist/fiscal/ingestion/nfse-adn.js +222 -0
- package/dist/fiscal/ingestion/nfse-adn.js.map +1 -0
- package/dist/fiscal/ingestion/pipeline.d.ts +168 -0
- package/dist/fiscal/ingestion/pipeline.d.ts.map +1 -0
- package/dist/fiscal/ingestion/pipeline.js +699 -0
- package/dist/fiscal/ingestion/pipeline.js.map +1 -0
- package/dist/fiscal/ingestion/provider.d.ts +206 -0
- package/dist/fiscal/ingestion/provider.d.ts.map +1 -0
- package/dist/fiscal/ingestion/provider.js +47 -0
- package/dist/fiscal/ingestion/provider.js.map +1 -0
- package/dist/fiscal/ingestion/repository.d.ts +82 -0
- package/dist/fiscal/ingestion/repository.d.ts.map +1 -0
- package/dist/fiscal/ingestion/repository.js +127 -0
- package/dist/fiscal/ingestion/repository.js.map +1 -0
- package/dist/fiscal/ingestion/synthetic-provider.d.ts +92 -0
- package/dist/fiscal/ingestion/synthetic-provider.d.ts.map +1 -0
- package/dist/fiscal/ingestion/synthetic-provider.js +99 -0
- package/dist/fiscal/ingestion/synthetic-provider.js.map +1 -0
- package/dist/fiscal/ingestion/synthetic-transport-types.d.ts +19 -0
- package/dist/fiscal/ingestion/synthetic-transport-types.d.ts.map +1 -0
- package/dist/fiscal/ingestion/synthetic-transport-types.js +9 -0
- package/dist/fiscal/ingestion/synthetic-transport-types.js.map +1 -0
- package/dist/fiscal/ingestion/synthetic-transport.d.ts +55 -0
- package/dist/fiscal/ingestion/synthetic-transport.d.ts.map +1 -0
- package/dist/fiscal/ingestion/synthetic-transport.js +57 -0
- package/dist/fiscal/ingestion/synthetic-transport.js.map +1 -0
- package/dist/fiscal/ingestion/xml-reader.d.ts +55 -0
- package/dist/fiscal/ingestion/xml-reader.d.ts.map +1 -0
- package/dist/fiscal/ingestion/xml-reader.js +112 -0
- package/dist/fiscal/ingestion/xml-reader.js.map +1 -0
- package/dist/fiscal/repository.d.ts +220 -0
- package/dist/fiscal/repository.d.ts.map +1 -0
- package/dist/fiscal/repository.js +449 -0
- package/dist/fiscal/repository.js.map +1 -0
- package/dist/fiscal/sync/circuit.d.ts +86 -0
- package/dist/fiscal/sync/circuit.d.ts.map +1 -0
- package/dist/fiscal/sync/circuit.js +118 -0
- package/dist/fiscal/sync/circuit.js.map +1 -0
- package/dist/fiscal/sync/intervention.d.ts +81 -0
- package/dist/fiscal/sync/intervention.d.ts.map +1 -0
- package/dist/fiscal/sync/intervention.js +135 -0
- package/dist/fiscal/sync/intervention.js.map +1 -0
- package/dist/fiscal/sync/lease.d.ts +118 -0
- package/dist/fiscal/sync/lease.d.ts.map +1 -0
- package/dist/fiscal/sync/lease.js +139 -0
- package/dist/fiscal/sync/lease.js.map +1 -0
- package/dist/fiscal/sync/observability.d.ts +148 -0
- package/dist/fiscal/sync/observability.d.ts.map +1 -0
- package/dist/fiscal/sync/observability.js +239 -0
- package/dist/fiscal/sync/observability.js.map +1 -0
- package/dist/fiscal/sync/orchestrator.d.ts +132 -0
- package/dist/fiscal/sync/orchestrator.d.ts.map +1 -0
- package/dist/fiscal/sync/orchestrator.js +487 -0
- package/dist/fiscal/sync/orchestrator.js.map +1 -0
- package/dist/fiscal/sync/policy.d.ts +87 -0
- package/dist/fiscal/sync/policy.d.ts.map +1 -0
- package/dist/fiscal/sync/policy.js +136 -0
- package/dist/fiscal/sync/policy.js.map +1 -0
- package/dist/fiscal/sync/reprocess.d.ts +76 -0
- package/dist/fiscal/sync/reprocess.d.ts.map +1 -0
- package/dist/fiscal/sync/reprocess.js +237 -0
- package/dist/fiscal/sync/reprocess.js.map +1 -0
- package/dist/fiscal/sync/retry.d.ts +82 -0
- package/dist/fiscal/sync/retry.d.ts.map +1 -0
- package/dist/fiscal/sync/retry.js +176 -0
- package/dist/fiscal/sync/retry.js.map +1 -0
- package/dist/fiscal/sync/secret-boundary.d.ts +169 -0
- package/dist/fiscal/sync/secret-boundary.d.ts.map +1 -0
- package/dist/fiscal/sync/secret-boundary.js +116 -0
- package/dist/fiscal/sync/secret-boundary.js.map +1 -0
- package/dist/fiscal/transport/https.d.ts +86 -0
- package/dist/fiscal/transport/https.d.ts.map +1 -0
- package/dist/fiscal/transport/https.js +303 -0
- package/dist/fiscal/transport/https.js.map +1 -0
- package/dist/fiscal/transport/synthetic-tls.d.ts +99 -0
- package/dist/fiscal/transport/synthetic-tls.d.ts.map +1 -0
- package/dist/fiscal/transport/synthetic-tls.js +374 -0
- package/dist/fiscal/transport/synthetic-tls.js.map +1 -0
- package/dist/fiscal/transport/types.d.ts +134 -0
- package/dist/fiscal/transport/types.d.ts.map +1 -0
- package/dist/fiscal/transport/types.js +88 -0
- package/dist/fiscal/transport/types.js.map +1 -0
- package/dist/import/br-documents.d.ts +26 -0
- package/dist/import/br-documents.d.ts.map +1 -0
- package/dist/import/br-documents.js +78 -0
- package/dist/import/br-documents.js.map +1 -0
- package/dist/import/clients-import.d.ts +122 -4
- package/dist/import/clients-import.d.ts.map +1 -1
- package/dist/import/clients-import.js +341 -41
- package/dist/import/clients-import.js.map +1 -1
- package/dist/index.d.ts +145 -13
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +120 -7
- package/dist/index.js.map +1 -1
- package/dist/legal/documents.d.ts +12 -1
- package/dist/legal/documents.d.ts.map +1 -1
- package/dist/legal/documents.js +162 -18
- package/dist/legal/documents.js.map +1 -1
- package/dist/legal/index.d.ts +2 -2
- package/dist/legal/index.d.ts.map +1 -1
- package/dist/legal/index.js +1 -1
- package/dist/legal/index.js.map +1 -1
- package/dist/legal/types.d.ts +114 -2
- package/dist/legal/types.d.ts.map +1 -1
- package/dist/legal/types.js.map +1 -1
- package/dist/onboarding/persistence.d.ts +10 -1
- package/dist/onboarding/persistence.d.ts.map +1 -1
- package/dist/onboarding/persistence.js +4 -4
- package/dist/onboarding/persistence.js.map +1 -1
- package/dist/pilot/go-live-checklist.d.ts +41 -0
- package/dist/pilot/go-live-checklist.d.ts.map +1 -0
- package/dist/pilot/go-live-checklist.js +209 -0
- package/dist/pilot/go-live-checklist.js.map +1 -0
- package/dist/pilot/milestone.d.ts +56 -0
- package/dist/pilot/milestone.d.ts.map +1 -0
- package/dist/pilot/milestone.js +74 -0
- package/dist/pilot/milestone.js.map +1 -0
- package/dist/platform/capabilities.d.ts +88 -0
- package/dist/platform/capabilities.d.ts.map +1 -0
- package/dist/platform/capabilities.js +169 -0
- package/dist/platform/capabilities.js.map +1 -0
- package/dist/platform/job-contract.d.ts +232 -0
- package/dist/platform/job-contract.d.ts.map +1 -0
- package/dist/platform/job-contract.js +403 -0
- package/dist/platform/job-contract.js.map +1 -0
- package/dist/rbac/catalog.d.ts.map +1 -1
- package/dist/rbac/catalog.js +110 -0
- package/dist/rbac/catalog.js.map +1 -1
- package/dist/subscription-billing/index.d.ts +8 -5
- package/dist/subscription-billing/index.d.ts.map +1 -1
- package/dist/subscription-billing/index.js +4 -3
- package/dist/subscription-billing/index.js.map +1 -1
- package/dist/subscription-billing/platform-exemption.d.ts +89 -0
- package/dist/subscription-billing/platform-exemption.d.ts.map +1 -0
- package/dist/subscription-billing/platform-exemption.js +113 -0
- package/dist/subscription-billing/platform-exemption.js.map +1 -0
- package/dist/subscription-billing/service.d.ts +74 -0
- package/dist/subscription-billing/service.d.ts.map +1 -1
- package/dist/subscription-billing/service.js +182 -16
- package/dist/subscription-billing/service.js.map +1 -1
- package/dist/tenancy/features.d.ts +69 -0
- package/dist/tenancy/features.d.ts.map +1 -0
- package/dist/tenancy/features.js +123 -0
- package/dist/tenancy/features.js.map +1 -0
- package/dist/tenancy/settings.d.ts +63 -0
- package/dist/tenancy/settings.d.ts.map +1 -0
- package/dist/tenancy/settings.js +218 -0
- package/dist/tenancy/settings.js.map +1 -0
- package/dist/users/repository.d.ts +16 -1
- package/dist/users/repository.d.ts.map +1 -1
- package/dist/users/repository.js +24 -1
- package/dist/users/repository.js.map +1 -1
- package/dist/vault/repository.d.ts +69 -1
- package/dist/vault/repository.d.ts.map +1 -1
- package/dist/vault/repository.js +88 -5
- package/dist/vault/repository.js.map +1 -1
- package/package.json +10 -2
- package/src/db/migrations/0045_role_write_scope.sql +122 -0
- package/src/db/migrations/0046_pilot_activation_model.sql +184 -0
- package/src/db/migrations/0047_recipient_clearance.sql +89 -0
- package/src/db/migrations/0048_item_type_note.sql +16 -0
- package/src/db/migrations/0049_national_fiscal_engine.sql +279 -0
- package/src/db/migrations/0050_fiscal_vocabulary_readonly.sql +29 -0
- package/src/db/migrations/0051_seed_rules_from_catalog.sql +72 -0
- package/src/db/migrations/0052_fiscal_rule_delete_scope.sql +57 -0
- package/src/db/migrations/0053_rule_validity_lower_bound.sql +44 -0
- package/src/db/migrations/0054_tenant_profile_and_rule_source.sql +89 -0
- package/src/db/migrations/0055_job_capability_contract.sql +300 -0
- package/src/db/migrations/0056_fiscal_document_ingestion.sql +337 -0
- package/src/db/migrations/0057_fiscal_pending_event_inbox.sql +228 -0
- package/src/db/migrations/0058_fiscal_operational_engine.sql +516 -0
- package/src/db/migrations/0059_fiscal_contract_version.sql +59 -0
- package/src/db/migrations/0060_fiscal_credential_vault_and_run_authorization.sql +321 -0
- package/src/db/migrations/0061_client_official_registry_provenance.sql +193 -0
- package/src/db/migrations/0062_first_contact_and_capability_truth.sql +119 -0
|
@@ -0,0 +1,220 @@
|
|
|
1
|
+
import { URL } from 'node:url';
|
|
2
|
+
import { FiscalTransportError, parseRetryAfter, } from '../transport/types.js';
|
|
3
|
+
import { HttpsFiscalTransport } from '../transport/https.js';
|
|
4
|
+
import { ADN_OFFICIAL_ENVELOPE_PROFILE, ADN_REAL_TRANSPORT_ENABLED, ADN_SYNTHETIC_ENVELOPE_PROFILE, NFSE_ADN_ENVELOPE_SHAPE_VERIFIED, NFSE_ADN_HOSTS, NFSE_ADN_LIMITS, } from '../contracts/nfse-adn-contract.js';
|
|
5
|
+
import { readAdnEnvelope } from '../contracts/nfse-adn-envelope.js';
|
|
6
|
+
import { resolveAdnBaseUrl } from '../contracts/nfse-adn-endpoint.js';
|
|
7
|
+
import { FiscalProviderError, } from './provider.js';
|
|
8
|
+
/**
|
|
9
|
+
* O transporte do ADN — pronto até onde a documentação oficial chega, e parado
|
|
10
|
+
* exatamente onde ela para.
|
|
11
|
+
*
|
|
12
|
+
* ## O que está PROVADO aqui, e o que está apenas PREPARADO
|
|
13
|
+
*
|
|
14
|
+
* **Provado**: a resolução e a AUTORIZAÇÃO do destino (allowlist), a forma da
|
|
15
|
+
* requisição, o encadeamento de NSU, a montagem do TLS mútuo, os tetos de
|
|
16
|
+
* tamanho e de descompressão, e o mapeamento de erro. Tudo isso é exercitado
|
|
17
|
+
* contra o servidor TLS sintético em toda execução da suíte.
|
|
18
|
+
*
|
|
19
|
+
* **Preparado, não provado**: os nomes dos campos do envelope e o status HTTP de
|
|
20
|
+
* cada desfecho. Não por falta de procura: as dezesseis URLs de Swagger que o
|
|
21
|
+
* gov.br publica para o ADN — oito módulos × dois ambientes — não devolvem UM
|
|
22
|
+
* byte de HTTP sem certificado ICP-Brasil de cliente (medido em 2026-09-08). O
|
|
23
|
+
* host que documenta a API é o mesmo que exige a credencial para documentá-la.
|
|
24
|
+
*
|
|
25
|
+
* Por isso o perfil oficial tem `verified: false`, e por isso este transporte
|
|
26
|
+
* recusa `homologation` E `production` — não apenas produção, como na fase
|
|
27
|
+
* anterior. Produção restrita é servidor do governo tanto quanto produção; um
|
|
28
|
+
* parser suposto contra ela devolveria zero documentos com sucesso aparente do
|
|
29
|
+
* mesmo jeito, e o cursor avançaria sobre lotes vazios até a fiscalização.
|
|
30
|
+
*
|
|
31
|
+
* ## Dois portões independentes, e é de propósito
|
|
32
|
+
*
|
|
33
|
+
* 1. `ADN_ENVELOPE_UNVERIFIED` — não sabemos ler a resposta.
|
|
34
|
+
* 2. `ADN_REAL_TRANSPORT_DISABLED` — ninguém autorizou falar.
|
|
35
|
+
*
|
|
36
|
+
* Nenhum implica o outro. No dia em que alguém conferir o envelope, o portão 1
|
|
37
|
+
* abre e o 2 continua fechado — porque ver a resposta uma vez não é o mesmo que
|
|
38
|
+
* autorizar o produto a sincronizar carteira de cliente sozinho.
|
|
39
|
+
*/
|
|
40
|
+
/** @deprecated Use `NFSE_ADN_HOSTS`. Mantido para não quebrar quem já importa. */
|
|
41
|
+
export const ADN_HOSTS = NFSE_ADN_HOSTS;
|
|
42
|
+
/**
|
|
43
|
+
* @deprecated Use `NFSE_ADN_ENVELOPE_SHAPE_VERIFIED` (envelope) ou
|
|
44
|
+
* `NFSE_ADN_PAYLOAD_SHAPE_VERIFIED` (conteúdo).
|
|
45
|
+
*
|
|
46
|
+
* A constante única confundia duas perguntas: sabemos ler o XML da NFS-e (sim,
|
|
47
|
+
* contra o XSD oficial v1.01) e sabemos ler o envelope que o embrulha (não).
|
|
48
|
+
* Um leitor concluía do `false` que também não sabíamos ler o documento.
|
|
49
|
+
*/
|
|
50
|
+
export const ADN_RESPONSE_SHAPE_VERIFIED = NFSE_ADN_ENVELOPE_SHAPE_VERIFIED;
|
|
51
|
+
/**
|
|
52
|
+
* Resolve a URL de um lote.
|
|
53
|
+
*
|
|
54
|
+
* `GET /DFe/{NSU}` — o NSU é a posição de onde continuar. `0` é o começo
|
|
55
|
+
* disponível, e é o que se envia quando não há cursor: não existe "sem
|
|
56
|
+
* parâmetro" nesta API.
|
|
57
|
+
*
|
|
58
|
+
* Cursor ilegível LANÇA, e não volta para `0` em silêncio como fazia antes.
|
|
59
|
+
* Voltar para `0` contra o ambiente nacional refaz a varredura inteira do
|
|
60
|
+
* cliente — que é consumo, e consumo excessivo é o `cStat 656`, cujo bloqueio
|
|
61
|
+
* recai sobre o CNPJ do CLIENTE. Um cursor corrompido é defeito para
|
|
62
|
+
* investigar, não condição para recomeçar.
|
|
63
|
+
*/
|
|
64
|
+
export function adnDfeUrl(baseUrl, fromNsu) {
|
|
65
|
+
if (fromNsu !== null && !/^\d{1,20}$/.test(fromNsu)) {
|
|
66
|
+
throw new FiscalProviderError('invalid', 'cursor NSU ilegível', 'NSU_CURSOR_INVALID');
|
|
67
|
+
}
|
|
68
|
+
return `${baseUrl.replace(/\/+$/, '')}/DFe/${fromNsu ?? '0'}`;
|
|
69
|
+
}
|
|
70
|
+
/** `GET /NFSe/{ChaveAcesso}/Eventos` — os eventos de um documento específico. */
|
|
71
|
+
export function adnEventsUrl(baseUrl, accessKey) {
|
|
72
|
+
if (!/^[A-Za-z0-9]{1,60}$/.test(accessKey)) {
|
|
73
|
+
// Chave com caractere fora do alfabeto seria injeção de caminho. Recusar
|
|
74
|
+
// aqui é mais barato do que confiar em quem monta a chamada.
|
|
75
|
+
throw new FiscalTransportError('protocol', 'ACCESS_KEY_INVALID');
|
|
76
|
+
}
|
|
77
|
+
return `${baseUrl.replace(/\/+$/, '')}/NFSe/${accessKey}/Eventos`;
|
|
78
|
+
}
|
|
79
|
+
/**
|
|
80
|
+
* Status HTTP → erro do provedor, com a espera que o servidor pediu.
|
|
81
|
+
*
|
|
82
|
+
* A tradução mora aqui porque ela é do PROTOCOLO: `429` com `Retry-After` é o
|
|
83
|
+
* servidor dizendo quando voltar, e o motor de retentativa consome essa data em
|
|
84
|
+
* vez de estimar uma.
|
|
85
|
+
*
|
|
86
|
+
* ## O `404` deixou de significar "lote vazio"
|
|
87
|
+
*
|
|
88
|
+
* Ele era mapeado para "não há documento neste NSU" por analogia com o
|
|
89
|
+
* `cStat 137` da NF-e. A analogia não se sustenta: o ADN publica um MECANISMO
|
|
90
|
+
* PRÓPRIO para dizer isso — os códigos `E2215` e `E2230` do ANEXO_IV — e não
|
|
91
|
+
* publica status HTTP nenhum. Traduzir um status suposto em lote vazio é
|
|
92
|
+
* exatamente a fabricação de sucesso que esta fase existe para eliminar.
|
|
93
|
+
*
|
|
94
|
+
* Agora o `404` devolve `null` para que o CORPO seja lido: se ele trouxer o
|
|
95
|
+
* código oficial, o leitor de envelope o reconhece como "sem documentos"; se não
|
|
96
|
+
* trouxer, o leitor recusa. A decisão passa a sair do que o ADN diz, e não do
|
|
97
|
+
* que supomos que o status dele significa.
|
|
98
|
+
*/
|
|
99
|
+
export function mapAdnStatus(status, headers, now = new Date()) {
|
|
100
|
+
if (status >= 200 && status < 300)
|
|
101
|
+
return null;
|
|
102
|
+
const retryAfter = parseRetryAfter(headers['retry-after'], now);
|
|
103
|
+
if (status === 401) {
|
|
104
|
+
return new FiscalProviderError('auth', 'ADN recusou a credencial', 'HTTP_401', retryAfter);
|
|
105
|
+
}
|
|
106
|
+
if (status === 403) {
|
|
107
|
+
return new FiscalProviderError('not_allowed', 'contribuinte sem direito a este documento', 'HTTP_403', retryAfter);
|
|
108
|
+
}
|
|
109
|
+
if (status === 404)
|
|
110
|
+
return null;
|
|
111
|
+
if (status === 429) {
|
|
112
|
+
return new FiscalProviderError('throttled', 'consumo excedido', 'HTTP_429', retryAfter);
|
|
113
|
+
}
|
|
114
|
+
if (status >= 500) {
|
|
115
|
+
return new FiscalProviderError('transient', 'ADN indisponível', `HTTP_${status}`, retryAfter);
|
|
116
|
+
}
|
|
117
|
+
return new FiscalProviderError('invalid', 'resposta recusada', `HTTP_${status}`, retryAfter);
|
|
118
|
+
}
|
|
119
|
+
/** O perfil que um ambiente usa quando o chamador não escolhe. */
|
|
120
|
+
export function defaultAdnProfile(environment) {
|
|
121
|
+
return environment === 'synthetic'
|
|
122
|
+
? ADN_SYNTHETIC_ENVELOPE_PROFILE
|
|
123
|
+
: ADN_OFFICIAL_ENVELOPE_PROFILE;
|
|
124
|
+
}
|
|
125
|
+
/**
|
|
126
|
+
* Os portões do transporte real, em ordem, e o motivo de cada um.
|
|
127
|
+
*
|
|
128
|
+
* Exportada porque a tela precisa dizer POR QUE não sincroniza — e porque um
|
|
129
|
+
* portão que só existe dentro de uma função não é conferível por teste sem
|
|
130
|
+
* construir o transporte inteiro.
|
|
131
|
+
*/
|
|
132
|
+
export function assertAdnTransportAllowed(environment, profile) {
|
|
133
|
+
// 0 · O perfil serve a este ambiente? Impede que o perfil sintético — que é
|
|
134
|
+
// `verified: true` porque descreve o NOSSO servidor de mentira — vire
|
|
135
|
+
// atalho para abrir produção.
|
|
136
|
+
if (!profile.environments.includes(environment)) {
|
|
137
|
+
throw new FiscalProviderError('not_allowed', `perfil ${profile.id} não atende ao ambiente ${environment}`, 'ENVELOPE_PROFILE_ENVIRONMENT_MISMATCH');
|
|
138
|
+
}
|
|
139
|
+
if (environment === 'synthetic')
|
|
140
|
+
return;
|
|
141
|
+
// 1 · Sabemos ler a resposta?
|
|
142
|
+
if (!profile.verified) {
|
|
143
|
+
throw new FiscalProviderError('not_allowed', 'o envelope de resposta do ADN não foi conferido contra o serviço real; ' +
|
|
144
|
+
'os ambientes oficiais permanecem fechados até que seja', 'ADN_ENVELOPE_UNVERIFIED');
|
|
145
|
+
}
|
|
146
|
+
// 2 · Alguém autorizou falar? Independente do anterior, e é o ponto: conferir
|
|
147
|
+
// o envelope não autoriza sincronizar carteira de cliente sozinho.
|
|
148
|
+
if (!ADN_REAL_TRANSPORT_ENABLED) {
|
|
149
|
+
throw new FiscalProviderError('not_allowed', 'transporte real do ADN não habilitado nesta versão', 'ADN_REAL_TRANSPORT_DISABLED');
|
|
150
|
+
}
|
|
151
|
+
}
|
|
152
|
+
/** O transporte do ADN, pronto para receber uma credencial real — e travado. */
|
|
153
|
+
export function createAdnDfeTransport(options) {
|
|
154
|
+
const profile = options.profile ?? defaultAdnProfile(options.environment);
|
|
155
|
+
assertAdnTransportAllowed(options.environment, profile);
|
|
156
|
+
// A allowlist vem DEPOIS dos portões e ANTES de qualquer socket: um destino
|
|
157
|
+
// recusado nunca chega a ter agente de TLS montado com o material do cliente.
|
|
158
|
+
const host = resolveAdnBaseUrl(options.environment, options.baseUrl);
|
|
159
|
+
const timeoutMs = options.timeoutMs ?? NFSE_ADN_LIMITS.requestTimeoutMs.value;
|
|
160
|
+
const transport = options.transport ??
|
|
161
|
+
new HttpsFiscalTransport({
|
|
162
|
+
tls: options.tls,
|
|
163
|
+
maxResponseBytes: NFSE_ADN_LIMITS.maxResponseBytes.value,
|
|
164
|
+
...(options.baseUrl ? {} : { servername: new URL(host).hostname }),
|
|
165
|
+
});
|
|
166
|
+
return {
|
|
167
|
+
contractVersion: profile.contractVersion,
|
|
168
|
+
profileId: profile.id,
|
|
169
|
+
async fetchDfe(input) {
|
|
170
|
+
if (input.environment !== options.environment) {
|
|
171
|
+
// Sem fallback entre ambientes, nos dois sentidos. Um transporte montado
|
|
172
|
+
// para homologação não atende um pedido de produção nem por engano de
|
|
173
|
+
// fiação — e é assim que material de ensaio NÃO entra em carteira real.
|
|
174
|
+
throw new FiscalProviderError('not_allowed', `transporte de "${options.environment}" recusa pedido de "${input.environment}"`, 'ENVIRONMENT_MISMATCH');
|
|
175
|
+
}
|
|
176
|
+
let res;
|
|
177
|
+
try {
|
|
178
|
+
res = await transport.send({
|
|
179
|
+
method: 'GET',
|
|
180
|
+
url: adnDfeUrl(host, input.fromNsu),
|
|
181
|
+
headers: {
|
|
182
|
+
accept: 'application/json',
|
|
183
|
+
// O ADN identifica o contribuinte pelo CERTIFICADO, não por
|
|
184
|
+
// cabeçalho. Este só existe para a trilha do provedor.
|
|
185
|
+
'x-consulta-cnpj': input.actorDocument,
|
|
186
|
+
},
|
|
187
|
+
timeoutMs,
|
|
188
|
+
});
|
|
189
|
+
}
|
|
190
|
+
catch (err) {
|
|
191
|
+
if (err instanceof FiscalTransportError) {
|
|
192
|
+
// Falha de transporte vira falha de provedor com a classe equivalente:
|
|
193
|
+
// quem consome o adapter fala o vocabulário fiscal.
|
|
194
|
+
const cls = err.errorClass === 'certificate'
|
|
195
|
+
? 'auth'
|
|
196
|
+
: err.errorClass === 'tls'
|
|
197
|
+
? 'transient'
|
|
198
|
+
: err.errorClass === 'protocol'
|
|
199
|
+
? 'invalid'
|
|
200
|
+
: 'transient';
|
|
201
|
+
throw new FiscalProviderError(cls, `transporte ${err.errorClass}`, err.code, err.retryAfter);
|
|
202
|
+
}
|
|
203
|
+
throw err;
|
|
204
|
+
}
|
|
205
|
+
const erro = mapAdnStatus(res.status, res.headers);
|
|
206
|
+
if (erro)
|
|
207
|
+
throw erro;
|
|
208
|
+
// Um lote maior que o pedido não é generosidade do servidor: é sinal de
|
|
209
|
+
// que não estamos falando com quem pensamos. O teto efetivo é o menor
|
|
210
|
+
// entre o oficial e o que o motor pediu.
|
|
211
|
+
const teto = Math.min(input.batchLimit, NFSE_ADN_LIMITS.maxDocumentsPerBatch.value);
|
|
212
|
+
return readAdnEnvelope(res.body, {
|
|
213
|
+
profile,
|
|
214
|
+
fromNsu: input.fromNsu,
|
|
215
|
+
maxDocumentsPerBatch: teto,
|
|
216
|
+
});
|
|
217
|
+
},
|
|
218
|
+
};
|
|
219
|
+
}
|
|
220
|
+
//# sourceMappingURL=adn-transport.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"adn-transport.js","sourceRoot":"","sources":["../../../src/fiscal/ingestion/adn-transport.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
import type { FiscalDirection } from './provider.js';
|
|
2
|
+
/**
|
|
3
|
+
* A direção de um documento fiscal — por confronto, nunca por default.
|
|
4
|
+
*
|
|
5
|
+
* ## O que estava errado antes
|
|
6
|
+
*
|
|
7
|
+
* O parser da NFS-e devolvia `direction: 'issued'` fixo, com um comentário
|
|
8
|
+
* dizendo que a ingestão resolveria depois. A ingestão não resolvia. Toda nota
|
|
9
|
+
* capturada nascia "emitida pelo cliente" — inclusive aquelas em que ele é o
|
|
10
|
+
* TOMADOR do serviço.
|
|
11
|
+
*
|
|
12
|
+
* Num escritório contábil isso não é um rótulo impreciso. Emitida é receita;
|
|
13
|
+
* recebida é despesa. O mesmo XML classificado errado troca o sinal do valor no
|
|
14
|
+
* fechamento, e o erro é silencioso porque a tela mostra um rótulo plausível.
|
|
15
|
+
*
|
|
16
|
+
* ## Como se decide
|
|
17
|
+
*
|
|
18
|
+
* O ADN distribui ao contribuinte os documentos em que ele figura como
|
|
19
|
+
* **emitente, tomador ou intermediário** (Manual dos Contribuintes v1.0). São
|
|
20
|
+
* exatamente os três papéis, e o leiaute declara os três participantes. Então a
|
|
21
|
+
* direção é o resultado de comparar o documento do ATOR CONSULTADO com cada um
|
|
22
|
+
* deles — um fato do documento, não uma preferência do produto.
|
|
23
|
+
*
|
|
24
|
+
* ## Por que `unknown` existe
|
|
25
|
+
*
|
|
26
|
+
* Porque a alternativa é mentir. Um documento parcial (`resNFe` da NF-e, por
|
|
27
|
+
* exemplo, que vem antes da manifestação), um leiaute que não traga o
|
|
28
|
+
* participante, ou um ator que não figure em nenhum dos papéis produzem uma
|
|
29
|
+
* pergunta sem resposta. `unknown` diz isso em voz alta, aparece na tela e é
|
|
30
|
+
* filtrável; `issued` por omissão diria uma coisa falsa com cara de verdade.
|
|
31
|
+
*
|
|
32
|
+
* Nada aqui inventa participante: se o campo não veio, ele não é substituído
|
|
33
|
+
* por nenhum outro.
|
|
34
|
+
*/
|
|
35
|
+
export interface DirectionParticipants {
|
|
36
|
+
/** CNPJ/CPF do ator consultado — o cliente em nome de quem se buscou. */
|
|
37
|
+
actorDocument: string | null | undefined;
|
|
38
|
+
issuerDocument?: string | null;
|
|
39
|
+
recipientDocument?: string | null;
|
|
40
|
+
intermediaryDocument?: string | null;
|
|
41
|
+
}
|
|
42
|
+
export interface DirectionVerdict {
|
|
43
|
+
direction: FiscalDirection;
|
|
44
|
+
/**
|
|
45
|
+
* Por que deu nisso. Vai para o normalizado e para a trilha — é o que permite
|
|
46
|
+
* auditar uma classificação sem reabrir o XML.
|
|
47
|
+
*/
|
|
48
|
+
basis: 'actor_is_issuer' | 'actor_is_recipient' | 'actor_is_intermediary' | 'actor_absent' | 'no_participant_matched';
|
|
49
|
+
}
|
|
50
|
+
/** Só os dígitos. `11.222.333/0001-81` e `11222333000181` são o mesmo ator. */
|
|
51
|
+
export declare function normalizeFiscalDocumentNumber(v: string | null | undefined): string | null;
|
|
52
|
+
/**
|
|
53
|
+
* Classifica a direção confrontando o ator com os participantes.
|
|
54
|
+
*
|
|
55
|
+
* A ordem das comparações é a do leiaute, e importa num caso real: uma nota em
|
|
56
|
+
* que o mesmo CNPJ é emitente e tomador (serviço prestado a si) é `issued` —
|
|
57
|
+
* quem emitiu foi ele, e é a emissão que gera a obrigação.
|
|
58
|
+
*/
|
|
59
|
+
export declare function classifyFiscalDirection(p: DirectionParticipants): DirectionVerdict;
|
|
60
|
+
//# sourceMappingURL=direction.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"direction.d.ts","sourceRoot":"","sources":["../../../src/fiscal/ingestion/direction.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,eAAe,CAAC;AAErD;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAgCG;AAEH,MAAM,WAAW,qBAAqB;IACpC,yEAAyE;IACzE,aAAa,EAAE,MAAM,GAAG,IAAI,GAAG,SAAS,CAAC;IACzC,cAAc,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IAC/B,iBAAiB,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IAClC,oBAAoB,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;CACtC;AAED,MAAM,WAAW,gBAAgB;IAC/B,SAAS,EAAE,eAAe,CAAC;IAC3B;;;OAGG;IACH,KAAK,EACD,iBAAiB,GACjB,oBAAoB,GACpB,uBAAuB,GACvB,cAAc,GACd,wBAAwB,CAAC;CAC9B;AAED,+EAA+E;AAC/E,wBAAgB,6BAA6B,CAAC,CAAC,EAAE,MAAM,GAAG,IAAI,GAAG,SAAS,GAAG,MAAM,GAAG,IAAI,CAIzF;AAED;;;;;;GAMG;AACH,wBAAgB,uBAAuB,CAAC,CAAC,EAAE,qBAAqB,GAAG,gBAAgB,CAgBlF"}
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
/** Só os dígitos. `11.222.333/0001-81` e `11222333000181` são o mesmo ator. */
|
|
2
|
+
export function normalizeFiscalDocumentNumber(v) {
|
|
3
|
+
if (!v)
|
|
4
|
+
return null;
|
|
5
|
+
const digits = v.replace(/\D/g, '');
|
|
6
|
+
return digits.length > 0 ? digits : null;
|
|
7
|
+
}
|
|
8
|
+
/**
|
|
9
|
+
* Classifica a direção confrontando o ator com os participantes.
|
|
10
|
+
*
|
|
11
|
+
* A ordem das comparações é a do leiaute, e importa num caso real: uma nota em
|
|
12
|
+
* que o mesmo CNPJ é emitente e tomador (serviço prestado a si) é `issued` —
|
|
13
|
+
* quem emitiu foi ele, e é a emissão que gera a obrigação.
|
|
14
|
+
*/
|
|
15
|
+
export function classifyFiscalDirection(p) {
|
|
16
|
+
const actor = normalizeFiscalDocumentNumber(p.actorDocument);
|
|
17
|
+
// Sem ator não há confronto possível. Devolver `issued` aqui seria repetir o
|
|
18
|
+
// defeito com outro nome.
|
|
19
|
+
if (!actor)
|
|
20
|
+
return { direction: 'unknown', basis: 'actor_absent' };
|
|
21
|
+
if (actor === normalizeFiscalDocumentNumber(p.issuerDocument)) {
|
|
22
|
+
return { direction: 'issued', basis: 'actor_is_issuer' };
|
|
23
|
+
}
|
|
24
|
+
if (actor === normalizeFiscalDocumentNumber(p.recipientDocument)) {
|
|
25
|
+
return { direction: 'received', basis: 'actor_is_recipient' };
|
|
26
|
+
}
|
|
27
|
+
if (actor === normalizeFiscalDocumentNumber(p.intermediaryDocument)) {
|
|
28
|
+
return { direction: 'intermediary', basis: 'actor_is_intermediary' };
|
|
29
|
+
}
|
|
30
|
+
return { direction: 'unknown', basis: 'no_participant_matched' };
|
|
31
|
+
}
|
|
32
|
+
//# sourceMappingURL=direction.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"direction.js","sourceRoot":"","sources":["../../../src/fiscal/ingestion/direction.ts"],"names":[],"mappings":"AA0DA,+EAA+E;AAC/E,MAAM,UAAU,6BAA6B,CAAC,CAA4B;IACxE,IAAI,CAAC,CAAC;QAAE,OAAO,IAAI,CAAC;IACpB,MAAM,MAAM,GAAG,CAAC,CAAC,OAAO,CAAC,KAAK,EAAE,EAAE,CAAC,CAAC;IACpC,OAAO,MAAM,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,IAAI,CAAC;AAC3C,CAAC;AAED;;;;;;GAMG;AACH,MAAM,UAAU,uBAAuB,CAAC,CAAwB;IAC9D,MAAM,KAAK,GAAG,6BAA6B,CAAC,CAAC,CAAC,aAAa,CAAC,CAAC;IAC7D,6EAA6E;IAC7E,0BAA0B;IAC1B,IAAI,CAAC,KAAK;QAAE,OAAO,EAAE,SAAS,EAAE,SAAS,EAAE,KAAK,EAAE,cAAc,EAAE,CAAC;IAEnE,IAAI,KAAK,KAAK,6BAA6B,CAAC,CAAC,CAAC,cAAc,CAAC,EAAE,CAAC;QAC9D,OAAO,EAAE,SAAS,EAAE,QAAQ,EAAE,KAAK,EAAE,iBAAiB,EAAE,CAAC;IAC3D,CAAC;IACD,IAAI,KAAK,KAAK,6BAA6B,CAAC,CAAC,CAAC,iBAAiB,CAAC,EAAE,CAAC;QACjE,OAAO,EAAE,SAAS,EAAE,UAAU,EAAE,KAAK,EAAE,oBAAoB,EAAE,CAAC;IAChE,CAAC;IACD,IAAI,KAAK,KAAK,6BAA6B,CAAC,CAAC,CAAC,oBAAoB,CAAC,EAAE,CAAC;QACpE,OAAO,EAAE,SAAS,EAAE,cAAc,EAAE,KAAK,EAAE,uBAAuB,EAAE,CAAC;IACvE,CAAC;IACD,OAAO,EAAE,SAAS,EAAE,SAAS,EAAE,KAAK,EAAE,wBAAwB,EAAE,CAAC;AACnE,CAAC"}
|
|
@@ -0,0 +1,91 @@
|
|
|
1
|
+
import { FiscalProviderError, type FiscalDocumentAdapter, type FiscalEnvironmentTag, type FiscalFetchResult, type NormalizedFiscalDocument, type RawFiscalDocument } from './provider.js';
|
|
2
|
+
/**
|
|
3
|
+
* Adapter da NFS-e Nacional — Ambiente de Dados Nacional (ADN).
|
|
4
|
+
*
|
|
5
|
+
* ## Fonte
|
|
6
|
+
*
|
|
7
|
+
* "Manual dos Contribuintes — Guia para utilização das API's do ADN", v1.0 de
|
|
8
|
+
* 12/02/2026, publicado em gov.br/nfse. Métodos:
|
|
9
|
+
*
|
|
10
|
+
* GET /DFe/{NSU} documento fiscal por NSU
|
|
11
|
+
* GET /NFSe/{ChaveAcesso}/Eventos eventos vinculados a uma chave
|
|
12
|
+
*
|
|
13
|
+
* O contribuinte consulta documentos em que figura como **emitente, tomador ou
|
|
14
|
+
* intermediário** — diferente da NF-e, onde os documentos emitidos pela própria
|
|
15
|
+
* empresa não são distribuídos.
|
|
16
|
+
*
|
|
17
|
+
* Leiaute: `NFSe_v1.01.xsd` / `tiposComplexos_v1.01.xsd`
|
|
18
|
+
* (`nfse-esquemas_xsd-v1-01-20260209.zip`, publicado em 09/02/2026).
|
|
19
|
+
*
|
|
20
|
+
* ## O que está implementado e o que NÃO está
|
|
21
|
+
*
|
|
22
|
+
* **`parse` é real.** Ele lê a estrutura oficial `NFSe/infNFSe`, com os campos
|
|
23
|
+
* que o XSD declara, e a chave de 53 posições cuja regra de formação o próprio
|
|
24
|
+
* schema documenta: `"NFS" + IBGE(7) + AmbGer(1) + TpInscFed(1) +
|
|
25
|
+
* InscFed(14) + nNFSe(13) + AAMM(4) + cNum(9) + DV(1)`.
|
|
26
|
+
*
|
|
27
|
+
* **`fetchBatch` não fala com o ADN.** O host exige TLS MÚTUO com certificado
|
|
28
|
+
* ICP-Brasil — medido, e não deduzido: o handshake de
|
|
29
|
+
* `adn.producaorestrita.nfse.gov.br` (produção restrita) e o de
|
|
30
|
+
* `adn.nfse.gov.br` (produção) enviam `CertificateRequest`, e nenhuma das
|
|
31
|
+
* dezesseis URLs de Swagger que o gov.br publica para o ADN devolve um byte de
|
|
32
|
+
* HTTP sem certificado de cliente. Não há caminho de teste sem credencial real.
|
|
33
|
+
*
|
|
34
|
+
* A contagem de CAs aceitas é um instantâneo, não uma constante: a Fase 1 mediu
|
|
35
|
+
* 178 em produção restrita e a Fase 3 mediu 170, com produção estável em 5. A
|
|
36
|
+
* lista muda quando o ITI credencia ou descredencia uma AC — o que torna esse
|
|
37
|
+
* número inadequado como asserção de teste, e útil apenas como evidência
|
|
38
|
+
* datada. O fato estável é o `CertificateRequest`, não o seu tamanho.
|
|
39
|
+
*
|
|
40
|
+
* Por isso este adapter recebe um TRANSPORTE injetado. Sem transporte, ele
|
|
41
|
+
* levanta um erro nomeado em vez de inventar resposta: fabricar retorno de
|
|
42
|
+
* servidor oficial produziria uma prova que não prova nada.
|
|
43
|
+
*
|
|
44
|
+
* ## O IBS/CBS já está no leiaute
|
|
45
|
+
*
|
|
46
|
+
* `TCInfNFSe` da v1.01 tem o elemento `IBSCBS` (`TCRTCIBSCBS`). Isto não é
|
|
47
|
+
* previsão: a reforma tributária **já está no schema vigente**. É por isso que
|
|
48
|
+
* o normalizado é `jsonb` e o XML original é preservado — um modelo de colunas
|
|
49
|
+
* fixas descartaria em silêncio campos que já existem.
|
|
50
|
+
*/
|
|
51
|
+
/** O que o adapter precisa para falar com o ADN. Fornecido de fora. */
|
|
52
|
+
export interface AdnTransport {
|
|
53
|
+
/** `GET /DFe/{NSU}` em nome de `actorDocument`, com o certificado do cliente. */
|
|
54
|
+
fetchDfe(input: {
|
|
55
|
+
actorDocument: string;
|
|
56
|
+
fromNsu: string | null;
|
|
57
|
+
batchLimit: number;
|
|
58
|
+
environment: FiscalEnvironmentTag;
|
|
59
|
+
}): Promise<FiscalFetchResult>;
|
|
60
|
+
}
|
|
61
|
+
/**
|
|
62
|
+
* Erro do portão humano.
|
|
63
|
+
*
|
|
64
|
+
* Classe `auth` de propósito: não é falha transitória e retentar não resolve.
|
|
65
|
+
* O que falta é uma pessoa habilitar um certificado — e o produto tem de dizer
|
|
66
|
+
* isso, não "tente de novo mais tarde".
|
|
67
|
+
*/
|
|
68
|
+
export declare class AdnCredentialGateError extends FiscalProviderError {
|
|
69
|
+
constructor();
|
|
70
|
+
}
|
|
71
|
+
export interface NfseAdnAdapterOptions {
|
|
72
|
+
transport?: AdnTransport | null;
|
|
73
|
+
/** Ambientes que ESTA instância opera. */
|
|
74
|
+
environments?: readonly FiscalEnvironmentTag[];
|
|
75
|
+
source?: string;
|
|
76
|
+
/**
|
|
77
|
+
* Versão do contrato. Ausente = a do transporte, quando ele a declara.
|
|
78
|
+
*
|
|
79
|
+
* Herdar do transporte é o comportamento certo: é ele quem escolhe o perfil de
|
|
80
|
+
* envelope, e é o perfil que define o que sabemos ler. Um adapter que
|
|
81
|
+
* declarasse a versão por conta própria poderia dizer `v1` enquanto o
|
|
82
|
+
* transporte lê `v2` — e a trilha registraria a versão errada exatamente no
|
|
83
|
+
* lote que alguém precisaria investigar.
|
|
84
|
+
*/
|
|
85
|
+
contractVersion?: string | null;
|
|
86
|
+
}
|
|
87
|
+
export declare function createNfseAdnAdapter(options?: NfseAdnAdapterOptions): FiscalDocumentAdapter;
|
|
88
|
+
/** Regra de formação da chave, do próprio XSD: 53 posições, prefixo `NFS`. */
|
|
89
|
+
export declare const NFSE_ACCESS_KEY_PATTERN: RegExp;
|
|
90
|
+
export declare function parseNfseDocument(doc: RawFiscalDocument): NormalizedFiscalDocument;
|
|
91
|
+
//# sourceMappingURL=nfse-adn.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"nfse-adn.d.ts","sourceRoot":"","sources":["../../../src/fiscal/ingestion/nfse-adn.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,mBAAmB,EACnB,KAAK,qBAAqB,EAC1B,KAAK,oBAAoB,EAEzB,KAAK,iBAAiB,EACtB,KAAK,wBAAwB,EAC7B,KAAK,iBAAiB,EACvB,MAAM,eAAe,CAAC;AAUvB;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAgDG;AAEH,uEAAuE;AACvE,MAAM,WAAW,YAAY;IAC3B,iFAAiF;IACjF,QAAQ,CAAC,KAAK,EAAE;QACd,aAAa,EAAE,MAAM,CAAC;QACtB,OAAO,EAAE,MAAM,GAAG,IAAI,CAAC;QACvB,UAAU,EAAE,MAAM,CAAC;QACnB,WAAW,EAAE,oBAAoB,CAAC;KACnC,GAAG,OAAO,CAAC,iBAAiB,CAAC,CAAC;CAChC;AAED;;;;;;GAMG;AACH,qBAAa,sBAAuB,SAAQ,mBAAmB;;CAU9D;AAED,MAAM,WAAW,qBAAqB;IACpC,SAAS,CAAC,EAAE,YAAY,GAAG,IAAI,CAAC;IAChC,0CAA0C;IAC1C,YAAY,CAAC,EAAE,SAAS,oBAAoB,EAAE,CAAC;IAC/C,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB;;;;;;;;OAQG;IACH,eAAe,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;CACjC;AAED,wBAAgB,oBAAoB,CAAC,OAAO,GAAE,qBAA0B,GAAG,qBAAqB,CA0C/F;AAED,8EAA8E;AAC9E,eAAO,MAAM,uBAAuB,QAAgB,CAAC;AAErD,wBAAgB,iBAAiB,CAAC,GAAG,EAAE,iBAAiB,GAAG,wBAAwB,CAiFlF"}
|
|
@@ -0,0 +1,222 @@
|
|
|
1
|
+
import { FiscalProviderError, } from './provider.js';
|
|
2
|
+
import { NFSE_ADN_LIMITS } from '../contracts/nfse-adn-contract.js';
|
|
3
|
+
import { decodeFiscalXml, readAttribute, readElement, readText, rootElementName, } from './xml-reader.js';
|
|
4
|
+
/**
|
|
5
|
+
* Erro do portão humano.
|
|
6
|
+
*
|
|
7
|
+
* Classe `auth` de propósito: não é falha transitória e retentar não resolve.
|
|
8
|
+
* O que falta é uma pessoa habilitar um certificado — e o produto tem de dizer
|
|
9
|
+
* isso, não "tente de novo mais tarde".
|
|
10
|
+
*/
|
|
11
|
+
export class AdnCredentialGateError extends FiscalProviderError {
|
|
12
|
+
constructor() {
|
|
13
|
+
super('auth', 'ADN exige TLS mútuo com certificado ICP-Brasil do contribuinte; ' +
|
|
14
|
+
'nenhum transporte credenciado está configurado', 'MTLS_CERTIFICATE_REQUIRED');
|
|
15
|
+
this.name = 'AdnCredentialGateError';
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
export function createNfseAdnAdapter(options = {}) {
|
|
19
|
+
const transport = options.transport ?? null;
|
|
20
|
+
// O transporte do ADN declara `contractVersion`; um transporte sintético de
|
|
21
|
+
// teste não declara. A leitura estrutural cobre os dois sem obrigar todo
|
|
22
|
+
// implementador de `AdnTransport` a inventar um rótulo de contrato externo.
|
|
23
|
+
const declarada = transport?.contractVersion;
|
|
24
|
+
const contractVersion = options.contractVersion ?? (typeof declarada === 'string' ? declarada : null);
|
|
25
|
+
return {
|
|
26
|
+
source: options.source ?? 'nfse_adn',
|
|
27
|
+
contractVersion,
|
|
28
|
+
documentTypes: ['nfse'],
|
|
29
|
+
// Sem transporte, o adapter não declara ambiente algum: um adapter que não
|
|
30
|
+
// sabe falar não deve passar no portão de ambiente do pipeline.
|
|
31
|
+
environments: options.environments ?? (transport ? ['homologation', 'production'] : []),
|
|
32
|
+
// Os dois números são OFICIAIS, e a Fase 3 corrigiu a atribuição deles.
|
|
33
|
+
//
|
|
34
|
+
// A escrita anterior dizia que o manual do ADN "não fixa tamanho de lote" e
|
|
35
|
+
// que a NFS-e "não publica a regra de uma hora que a NF-e publica" — e que
|
|
36
|
+
// adotávamos ambos por simetria com a NT 2014.002. Estava errado nos dois
|
|
37
|
+
// casos. O Manual dos Municípios do ADN §1.4.2.b publica os dois:
|
|
38
|
+
// "Quantidade máxima de documentos no lote: 50" e a espera mínima de uma
|
|
39
|
+
// hora "caso receba a indicação que não existem mais documentos".
|
|
40
|
+
//
|
|
41
|
+
// A diferença não é acadêmica: um valor "adotado por simetria" é o primeiro
|
|
42
|
+
// que alguém afrouxa quando quer sincronizar mais rápido. Um valor de norma
|
|
43
|
+
// não é negociável, e o custo de violá-lo é o CNPJ do CLIENTE bloqueado.
|
|
44
|
+
batchLimit: NFSE_ADN_LIMITS.maxDocumentsPerBatch.value,
|
|
45
|
+
exhaustedBackoffSeconds: NFSE_ADN_LIMITS.exhaustedWaitSeconds.value,
|
|
46
|
+
async fetchBatch(request) {
|
|
47
|
+
if (!transport)
|
|
48
|
+
throw new AdnCredentialGateError();
|
|
49
|
+
return transport.fetchDfe({
|
|
50
|
+
actorDocument: request.actorDocument,
|
|
51
|
+
fromNsu: request.fromNsu,
|
|
52
|
+
batchLimit: request.batchLimit,
|
|
53
|
+
environment: request.environment,
|
|
54
|
+
});
|
|
55
|
+
},
|
|
56
|
+
parse: parseNfseDocument,
|
|
57
|
+
};
|
|
58
|
+
}
|
|
59
|
+
/** Regra de formação da chave, do próprio XSD: 53 posições, prefixo `NFS`. */
|
|
60
|
+
export const NFSE_ACCESS_KEY_PATTERN = /^NFS\d{50}$/;
|
|
61
|
+
export function parseNfseDocument(doc) {
|
|
62
|
+
const xml = decodeFiscalXml(doc.raw);
|
|
63
|
+
const root = rootElementName(xml);
|
|
64
|
+
if (root === 'evento' || root === 'procEventoNFSe')
|
|
65
|
+
return parseNfseEvent(xml, doc);
|
|
66
|
+
if (root !== 'NFSe') {
|
|
67
|
+
throw new FiscalProviderError('invalid', `raiz inesperada: ${root ?? 'ausente'}`);
|
|
68
|
+
}
|
|
69
|
+
const inf = readElement(xml, 'infNFSe');
|
|
70
|
+
if (!inf)
|
|
71
|
+
throw new FiscalProviderError('invalid', 'infNFSe ausente');
|
|
72
|
+
const accessKey = readAttribute(xml, 'infNFSe', 'Id');
|
|
73
|
+
if (!accessKey || !NFSE_ACCESS_KEY_PATTERN.test(accessKey)) {
|
|
74
|
+
// A chave é a identidade do documento. Sem ela não há deduplicação
|
|
75
|
+
// confiável, e deduplicar por hash de XML assinado falharia no primeiro
|
|
76
|
+
// reenvio com assinatura recalculada.
|
|
77
|
+
throw new FiscalProviderError('invalid', 'Id da NFS-e ausente ou fora do formato de 53 posições');
|
|
78
|
+
}
|
|
79
|
+
const emit = readElement(inf, 'emit') ?? '';
|
|
80
|
+
const issuerDocument = readText(emit, 'CNPJ') ?? readText(emit, 'CPF');
|
|
81
|
+
const issuerName = readText(emit, 'xNome');
|
|
82
|
+
// O tomador vive no DPS (Declaração de Prestação de Serviço) embutido.
|
|
83
|
+
const dps = readElement(inf, 'DPS') ?? readElement(inf, 'infDPS') ?? '';
|
|
84
|
+
const toma = readElement(dps, 'toma') ?? '';
|
|
85
|
+
const recipientDocument = readText(toma, 'CNPJ') ?? readText(toma, 'CPF');
|
|
86
|
+
const recipientName = readText(toma, 'xNome');
|
|
87
|
+
// O terceiro papel. O ADN distribui ao contribuinte os documentos em que ele
|
|
88
|
+
// figura como emitente, tomador OU intermediário — e sem ler `interm` a
|
|
89
|
+
// ingestão não teria como distinguir o terceiro caso do "não é nenhum deles".
|
|
90
|
+
const interm = readElement(dps, 'interm') ?? '';
|
|
91
|
+
const intermediaryDocument = readText(interm, 'CNPJ') ?? readText(interm, 'CPF');
|
|
92
|
+
const intermediaryName = readText(interm, 'xNome');
|
|
93
|
+
const dhProc = readText(inf, 'dhProc');
|
|
94
|
+
const issuedAt = dhProc ? safeDate(dhProc) : null;
|
|
95
|
+
const valores = readElement(inf, 'valores') ?? '';
|
|
96
|
+
const grossAmount = readText(valores, 'vServPrest') ?? readText(valores, 'vLiq') ?? null;
|
|
97
|
+
return {
|
|
98
|
+
dedupeKey: `nfse:${accessKey}`,
|
|
99
|
+
documentType: 'nfse',
|
|
100
|
+
// Não há `direction` aqui, e o tipo já não permite: o parser não conhece o
|
|
101
|
+
// ator consultado, então qualquer valor que escrevesse seria chute. Ele
|
|
102
|
+
// devolve os PARTICIPANTES; quem confronta é o motor.
|
|
103
|
+
//
|
|
104
|
+
// O ADN entrega o documento completo, não resumo — não há manifestação do
|
|
105
|
+
// destinatário na NFS-e como há na NF-e.
|
|
106
|
+
contentKind: 'full',
|
|
107
|
+
accessKey,
|
|
108
|
+
documentNumber: readText(inf, 'nNFSe'),
|
|
109
|
+
series: null,
|
|
110
|
+
issuerDocument,
|
|
111
|
+
issuerName,
|
|
112
|
+
recipientDocument,
|
|
113
|
+
recipientName,
|
|
114
|
+
intermediaryDocument,
|
|
115
|
+
intermediaryName,
|
|
116
|
+
issuedAt,
|
|
117
|
+
competenceLabel: issuedAt ? competenceOf(issuedAt) : null,
|
|
118
|
+
grossAmount,
|
|
119
|
+
normalized: {
|
|
120
|
+
layoutVersion: readAttribute(xml, 'NFSe', 'versao'),
|
|
121
|
+
cLocIncid: readText(inf, 'cLocIncid'),
|
|
122
|
+
xLocEmi: readText(inf, 'xLocEmi'),
|
|
123
|
+
xLocPrestacao: readText(inf, 'xLocPrestacao'),
|
|
124
|
+
cStat: readText(inf, 'cStat'),
|
|
125
|
+
ambGer: readText(inf, 'ambGer'),
|
|
126
|
+
// Reforma tributária: o bloco existe no leiaute v1.01. Guardado como veio,
|
|
127
|
+
// sem interpretação — esta fase captura, não apura.
|
|
128
|
+
hasIbsCbs: readElement(inf, 'IBSCBS') !== null,
|
|
129
|
+
},
|
|
130
|
+
event: null,
|
|
131
|
+
};
|
|
132
|
+
}
|
|
133
|
+
function parseNfseEvent(xml, _doc) {
|
|
134
|
+
const inf = readElement(xml, 'infEvento') ?? xml;
|
|
135
|
+
const targetAccessKey = readText(inf, 'chNFSe');
|
|
136
|
+
if (!targetAccessKey) {
|
|
137
|
+
throw new FiscalProviderError('invalid', 'evento sem chave de NFS-e (chNFSe)');
|
|
138
|
+
}
|
|
139
|
+
const code = readText(inf, 'tpEvento');
|
|
140
|
+
const occurredAt = safeDate(readText(inf, 'dhEvento') ?? '');
|
|
141
|
+
const sequence = readText(inf, 'nSeqEvento');
|
|
142
|
+
return {
|
|
143
|
+
// O par (chave, tipo, sequência) identifica o evento. Sem `nSeqEvento` o
|
|
144
|
+
// mesmo tipo só pode ocorrer uma vez, que é o comportamento do leiaute.
|
|
145
|
+
dedupeKey: `nfse-evento:${targetAccessKey}:${code ?? 'sem-tipo'}:${sequence ?? '1'}`,
|
|
146
|
+
documentType: 'nfse',
|
|
147
|
+
// Evento não tem direção própria: ele HERDA a do documento que altera. Um
|
|
148
|
+
// cancelamento sobre uma nota recebida é um evento de nota recebida, e
|
|
149
|
+
// classificá-lo como `issued` — que era o que o campo fixo fazia — inverte
|
|
150
|
+
// o sinal do fato no fechamento.
|
|
151
|
+
contentKind: 'full',
|
|
152
|
+
accessKey: targetAccessKey,
|
|
153
|
+
normalized: { tpEvento: code, nSeqEvento: sequence },
|
|
154
|
+
event: {
|
|
155
|
+
type: eventTypeOf(code),
|
|
156
|
+
code,
|
|
157
|
+
occurredAt,
|
|
158
|
+
sequence,
|
|
159
|
+
targetAccessKey,
|
|
160
|
+
},
|
|
161
|
+
};
|
|
162
|
+
}
|
|
163
|
+
/**
|
|
164
|
+
* Códigos de evento da NFS-e Nacional, do XSD oficial.
|
|
165
|
+
*
|
|
166
|
+
* Extraídos de `tiposEventos_v1.01.xsd` (`nfse-esquemas_xsd-v1-01-20260209.zip`),
|
|
167
|
+
* onde cada evento é um elemento `e<codigo>` com a descrição na enumeração do
|
|
168
|
+
* seu tipo. São dezesseis, e a lista é fechada pelo leiaute.
|
|
169
|
+
*
|
|
170
|
+
* A primeira versão disto adivinhava por prefixo (`1010*` = cancelamento) e
|
|
171
|
+
* ESTAVA ERRADA: `101101` é cancelamento e não casa com `1010`, enquanto
|
|
172
|
+
* `105102` — que é cancelamento por substituição — casaria com um prefixo
|
|
173
|
+
* `1051` inventado. Adivinhar a semântica de um código fiscal por prefixo é
|
|
174
|
+
* exatamente como uma nota cancelada passaria despercebida, ou uma nota viva
|
|
175
|
+
* seria marcada como cancelada. O mapa é explícito porque a fonte é explícita.
|
|
176
|
+
*/
|
|
177
|
+
const NFSE_EVENT_CODES = {
|
|
178
|
+
'101101': 'cancellation', // Cancelamento de NFS-e
|
|
179
|
+
'105102': 'replacement', // Cancelamento de NFS-e por Substituição
|
|
180
|
+
'101103': 'correction', // Solicitação de Análise Fiscal para Cancelamento
|
|
181
|
+
'105104': 'cancellation', // Cancelamento Deferido por Análise Fiscal
|
|
182
|
+
'105105': 'correction', // Cancelamento INDEFERIDO — a nota segue válida
|
|
183
|
+
'305101': 'cancellation', // Cancelamento por Ofício
|
|
184
|
+
'305102': 'correction', // Bloqueio por Ofício
|
|
185
|
+
'305103': 'correction', // Desbloqueio por Ofício
|
|
186
|
+
'202201': 'manifestation',
|
|
187
|
+
'203202': 'manifestation',
|
|
188
|
+
'204203': 'manifestation',
|
|
189
|
+
'205204': 'manifestation',
|
|
190
|
+
'202205': 'manifestation',
|
|
191
|
+
'203206': 'manifestation',
|
|
192
|
+
'204207': 'manifestation',
|
|
193
|
+
'205208': 'manifestation',
|
|
194
|
+
};
|
|
195
|
+
/**
|
|
196
|
+
* Tipo de evento a partir do código oficial.
|
|
197
|
+
*
|
|
198
|
+
* Desconhecido vira `other`, e NUNCA cancelamento. Errar para `other` preserva
|
|
199
|
+
* a nota; errar para `cancellation` a marca como cancelada — um cancelamento
|
|
200
|
+
* inventado é pior que um evento não classificado, porque o primeiro some do
|
|
201
|
+
* fechamento e o segundo só fica sem rótulo.
|
|
202
|
+
*
|
|
203
|
+
* `105105` é o caso que mostra por que o mapa não pode ser por prefixo: é o
|
|
204
|
+
* cancelamento **indeferido**, isto é, a nota CONTINUA válida. Um prefixo
|
|
205
|
+
* `1051` a cancelaria.
|
|
206
|
+
*/
|
|
207
|
+
function eventTypeOf(code) {
|
|
208
|
+
if (!code)
|
|
209
|
+
return 'other';
|
|
210
|
+
return NFSE_EVENT_CODES[code] ?? 'other';
|
|
211
|
+
}
|
|
212
|
+
function safeDate(v) {
|
|
213
|
+
if (!v)
|
|
214
|
+
return null;
|
|
215
|
+
const d = new Date(v);
|
|
216
|
+
return Number.isNaN(d.getTime()) ? null : d;
|
|
217
|
+
}
|
|
218
|
+
/** `YYYY-MM` em UTC. A competência CONTÁBIL pode ser outra, e é decidida depois. */
|
|
219
|
+
function competenceOf(d) {
|
|
220
|
+
return `${d.getUTCFullYear()}-${String(d.getUTCMonth() + 1).padStart(2, '0')}`;
|
|
221
|
+
}
|
|
222
|
+
//# sourceMappingURL=nfse-adn.js.map
|