Skip to content

Commit ab0e19f

Browse files
authored
Merge pull request #1 from FiscalAPI/feat/xml-downloader
Feat/xml downloader
2 parents e745eaa + 8600a98 commit ab0e19f

14 files changed

Lines changed: 1136 additions & 82 deletions

README.md

Lines changed: 48 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -5,20 +5,56 @@
55

66
**SDK oficial de FiscalAPI para Node.js**, la API de facturación CFDI y otros servicios fiscales en México. Simplifica la integración con los servicios de facturación electrónica, eliminando las complejidades del SAT y facilitando la generación de facturas, notas de crédito, complementos de pago, nómina, carta porte, y más. ¡Factura sin dolor!
77

8-
## 🚀 Características
9-
10-
- Soporte completo para **CFDI 4.0**
11-
- Compatible con múltiples versiones de Node.js (desde **Node.js 12.0.0**)
12-
- Soporte para ESM y CommonJS
13-
- Operaciones asíncronas con Promises
14-
- Dos modos de operación: **Por valores** o **Por referencias**
15-
- Manejo simplificado de errores
16-
- Búsqueda en catálogos del SAT
17-
- Tipos TypeScript completos
18-
- Documentación completa y ejemplos prácticos
8+
9+
## 📋 Facturación CFDI 4.0
10+
- **Soporte completo para CFDI 4.0** con todas las especificaciones oficiales
11+
- **Timbrado de facturas de ingreso** con validación automática
12+
- **Timbrado de notas de crédito** (facturas de egreso)
13+
- **Timbrado de complementos de pago** en MXN, USD y EUR.
14+
- **Consulta del estatus de facturas** en el SAT en tiempo real
15+
- **Cancelación de facturas**
16+
- **Generación de archivos PDF** de las facturas con formato profesional
17+
- **Personalización de logos y colores** en los PDF generados
18+
- **Envío de facturas por correo electrónico** automatizado
19+
- **Descarga de archivos XML** con estructura completa
20+
- **Almacenamiento y recuperación** de facturas por 5 años.
21+
- Dos [modos de operación](https://docs.fiscalapi.com/modes-of-operation): **Por valores** o **Por referencias**
22+
23+
## 📥 Descarga Masiva
24+
- **Acceso a catálogos de descarga masiva** del SAT
25+
- **Descarga de CFDI y Metadatos** en lotes grandes
26+
- **Descarga masiva XML** con filtros personalizados
27+
- **Reglas de descarga automática por RFC**
28+
- **Solicitudes de descarga** via API y Dashboard.
29+
- **Automatización de solicitudes de descarga**
30+
31+
## 👥 Gestión de Personas
32+
- **Administración de personas** (emisores, receptores, clientes, usuarios, etc.)
33+
- **Gestión de certificados CSD y FIEL** (subir archivos .cer y .key a FiscalAPI)
34+
- **Configuración de datos fiscales** (RFC, domicilio fiscal, régimen fiscal)
35+
36+
## 🛍️ Gestión de Productos/Servicios
37+
- **Gestión de productos y servicios** con catálogo personalizable
38+
- **Administración de impuestos aplicables** (IVA, ISR, IEPS)
39+
40+
## 📚 Consulta de Catálogos SAT
41+
- **Consulta en catálogos oficiales del SAT** actualizados
42+
- **Consulta en catálogos oficiales de Descarga masiva del SAT** actualizados
43+
- **Búsqueda de información** en catálogos del SAT con filtros avanzados
44+
- **Acceso y búsqueda** en catálogos completos
45+
46+
## 📖 Recursos Adicionales
47+
- **Cientos de ejemplos de código** disponibles en múltiples lenguajes de programación
48+
- Documentación completa con guías paso a paso
49+
- Ejemplos prácticos para casos de uso comunes
50+
- Soporte técnico especializado
51+
- Actualizaciones regulares conforme a cambios del SAT
52+
1953

2054
## 📦 Instalación
2155

56+
Compatible con múltiples versiones de Node.js ( **Node.js 12.0.0** o superior)
57+
2258
**npm**:
2359

2460
```bash
@@ -44,7 +80,7 @@ Puedes usar el SDK tanto en aplicaciones Node.js tradicionales como en framework
4480

4581
// o ESM
4682
import { FiscalapiClient } from 'fiscalapi';
47-
83+
4884
const settings = {
4985
apiUrl: "https://test.fiscalapi.com", // https://live.fiscalapi.com (producción)
5086
apiKey: "<tu_api_key>",

examples/all-samples.ts

Lines changed: 131 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
1+
import { DownloadCatalogService } from './../src/services/download-catalog.service';
12
import { DateTime } from 'luxon';
2-
import { CancelInvoiceRequest, CreatePdfRequest, GlobalInformation,FiscalapiClient, FiscalapiSettings, Invoice, InvoiceStatusRequest, Person, Product, SendInvoiceRequest, TaxFile } from '../src';
3+
import { CancelInvoiceRequest, CreatePdfRequest, GlobalInformation,FiscalapiClient, FiscalapiSettings, Invoice, InvoiceStatusRequest, Person, Product, SendInvoiceRequest, TaxFile, DownloadRule, DownloadRequest } from '../src';
34
import { inspect } from 'util';
45
inspect.defaultOptions.depth = null; // Deshabilitar la profundidad de inspección para objetos anidados la salida de la consola
56
inspect.defaultOptions.colors = true; // Habilitar colores para la salida de la consola
@@ -17,7 +18,9 @@ async function main() : Promise<void> {
1718
debug:true // true, imprime raw request y response en consola, util durante el desarrollo de la integración.
1819
};
1920

20-
21+
settings.apiUrl="http://localhost:5001";
22+
settings.apiKey="sk_development_3e94867a_959a_4140_a2e7_420f435aa8fc";
23+
settings.tenant="102e5f13-e114-41dd-bea7-507fce177281";
2124

2225

2326
// Sellos SAT de prueba (KARLA FUENTE NOLASCO FUNK671228PH6)
@@ -540,10 +543,6 @@ async function main() : Promise<void> {
540543

541544

542545

543-
544-
545-
546-
547546
// Crear factura de ingreso por referencias (solo IDs)
548547
// const invoiceByReferences: Invoice = {
549548
// versionCode: "4.0",
@@ -557,18 +556,18 @@ async function main() : Promise<void> {
557556
// exchangeRate: 1,
558557
// exportCode: "01",
559558
// issuer: {
560-
// id: "3f3478b4-60fd-459e-8bfc-f8239fc96257"
559+
// id: "78d380fd-1b69-4e3c-8bc0-4f57737f7d5f"
561560
// // No es necesario incluir otros datos del emisor al usar el ID
562561
// },
563562
// recipient: {
564-
// id: "96b46762-d246-4a67-a562-510a25dbafa9"
563+
// id: "2b5dadc5-7e55-41b2-888b-dd844ae5058e"
565564
// // No es necesario incluir otros datos del receptor al usar el ID
566565
// },
567566
// items: [
568567
// {
569-
// id: "114a4be5-fb65-40b2-a762-ff0c55c6ebfa", // ID del producto/servicio
568+
// id: "27808326-1824-4f3c-87fb-03ace1066f16", // ID del producto/servicio
570569
// quantity: 2, // Solo es necesario especificar la cantidad
571-
// discount: 255.85 // Y opcionalmente el descuento
570+
// //discount: 255.85 // Y opcionalmente el descuento
572571
// }
573572
// ]
574573
// };
@@ -1315,6 +1314,128 @@ async function main() : Promise<void> {
13151314
// console.log('apiResponse:', apiResponse);
13161315

13171316

1317+
/*******DESCARGA MASIVA**********/
1318+
1319+
1320+
//Obtener todos los catálogos de descarga masiva disponibles
1321+
//const apiResponse = await client.downloadCatalogs.getList();
1322+
//console.log('apiResponse:', apiResponse);
1323+
1324+
// Listar los registros del catálogo 'SatInvoiceStatuses' de descarga masiva.
1325+
// const apiResponse = await client.downloadCatalogs.listCatalog("SatInvoiceStatuses");
1326+
// console.log('apiResponse:', apiResponse);
1327+
1328+
/**********REGLA DE DESCARGA MASIVA**********/
1329+
1330+
// Obtener lista paginada de reglas de descarga masiva
1331+
// const apiResponse = await client.downloadRules.getList(1,2);
1332+
// console.log('apiResponse:', apiResponse);
1333+
1334+
// Obtener regla de descarga masiva por ID
1335+
// const apiResponse = await client.downloadRules.getById("80314e76-fb8b-42c3-89e2-82195a3dfd36");
1336+
// console.log('apiResponse:', apiResponse);
1337+
1338+
// Crear una regla de descarga masiva
1339+
// var request: DownloadRule =
1340+
// {
1341+
// personId: "b0c1cf6c-153a-464e-99df-5741f45d6695", //Persona que recibió los CFDI
1342+
// description: "Regla descarga demo ...",
1343+
// satQueryTypeId: "CFDI",
1344+
// downloadTypeId: "Recibidos",
1345+
// satInvoiceStatusId : "Vigente",
1346+
// };
1347+
// const apiResponse = await client.downloadRules.create(request);
1348+
// console.log('apiResponse:', apiResponse);
1349+
1350+
// Crear una regla de descarga masiva de prueba
1351+
// const apiResponse = await client.downloadRules.createTestRule();
1352+
// console.log('apiResponse:', apiResponse);
1353+
1354+
1355+
1356+
// Actualizar una regla de descarga masiva (descripción)
1357+
// var request: DownloadRule =
1358+
// {
1359+
// id: "465873fb-d2b6-4cb9-8c4d-1e6eb4b2ff28",
1360+
// description: "Regla descarga actualizada",
1361+
// };
1362+
// const apiResponse = await client.downloadRules.update(request);
1363+
// console.log('apiResponse:', apiResponse);
1364+
1365+
1366+
// Eliminar una regla de descarga masiva
1367+
// const apiResponse = await client.downloadRules.delete("465873fb-d2b6-4cb9-8c4d-1e6eb4b2ff28");
1368+
// console.log('apiResponse:', apiResponse);
1369+
1370+
1371+
1372+
/* **********SOLICITUD DE DESCARGA MASIVA**********/
1373+
1374+
// LISTAR SOLICITUDES DE DESCARGA MASIVA
1375+
// Obtener lista paginada de solicitudes de descarga masiva
1376+
// const apiResponse = await client.downloadRequests.getList(1, 2);
1377+
// console.log('apiResponse:', apiResponse);
1378+
1379+
1380+
// OBTENER SOLICITUD POR ID
1381+
// const apiResponse = await client.downloadRequests.getById("bddef7bf-ae7a-488f-9dba-5435d24f51d6");
1382+
// console.log('apiResponse:', apiResponse);
1383+
1384+
1385+
// LISTAR XMLS POR SOLICITUD ID
1386+
// Obtener lista paginada de xmls descargados asociados a una solicitud de descarga.
1387+
// const apiResponse = await client.downloadRequests.getXmlsAsync("bddef7bf-ae7a-488f-9dba-5435d24f51d6");
1388+
// console.log('apiResponse:', apiResponse);
1389+
1390+
1391+
// LISTAR META-ITEMS POR SOLICITUD ID
1392+
// Obtener lista paginada de metadatos descargados asociados a una solicitud de descarga.
1393+
// const apiResponse = await client.downloadRequests.getMetadataItemsAsync("bddef7bf-ae7a-488f-9dba-5435d24f51d6");
1394+
// console.log('apiResponse:', apiResponse);
1395+
1396+
1397+
// DESCARGAR PAQUETE POR SOLICITUD ID
1398+
// Descargar paquete (.zip file) de una solicitud de descarga masiva.
1399+
// const apiResponse = await client.downloadRequests.downloadPackageAsync("bddef7bf-ae7a-488f-9dba-5435d24f51d6");
1400+
// console.log('apiResponse:', apiResponse);
1401+
1402+
1403+
// OBTENER SAT REQUEST POR SOLICITUD ID
1404+
// Descargar SAT request (.xml file) de una solicitud de descarga masiva. (debug/testing)
1405+
// const apiResponse = await client.downloadRequests.downloadSatRequestAsync("bddef7bf-ae7a-488f-9dba-5435d24f51d6");
1406+
// console.log('apiResponse:', apiResponse);
1407+
1408+
1409+
// OBTENER SAT RESPONSE POR SOLICITUD ID
1410+
// Descargar SAT response (.xml file) de una solicitud de descarga masiva. (debug/testing)
1411+
// const apiResponse = await client.downloadRequests.downloadSatResponseAsync("bddef7bf-ae7a-488f-9dba-5435d24f51d6");
1412+
// console.log('apiResponse:', apiResponse);
1413+
1414+
1415+
// CREAR SOLICITUD DE DESCARGA MASIVA
1416+
// Crear solicitud para descargar facturas de los últimos 5 días.
1417+
// const request: DownloadRequest = {
1418+
// downloadRuleId: "14eb6460-a90a-46a8-afaa-d673cc3e38cd",
1419+
// downloadRequestTypeId: "Manual",
1420+
// startDate: DateTime.now().minus({ days: 5 }), // 5 días atrás
1421+
// endDate: DateTime.now()
1422+
// };
1423+
// const apiResponse = await client.downloadRequests.create(request);
1424+
// console.log('apiResponse:', apiResponse);
1425+
1426+
1427+
// ELIMINAR SOLICITUD DE DESCARGA MASIVA
1428+
// const apiResponse = await client.downloadRequests.delete("5e677807-3959-4d64-9c56-89451e9b81d4");
1429+
// console.log('apiResponse:', apiResponse);
1430+
1431+
1432+
// BUSCAR SOLICITUD POR FECHA DE CREACIÓN
1433+
// const apiResponse = await client.downloadRequests.searchAsync(new Date());
1434+
// console.log('apiResponse:', apiResponse);
1435+
1436+
1437+
1438+
13181439
console.log('End Fiscalapi node...');
13191440
} catch (error: unknown) {
13201441
console.error('Error inesperado:', error);

package.json

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,13 @@
11
{
22
"name": "fiscalapi",
3-
"version": "4.0.142",
4-
"description": "SDK de Node.js para FiscalAPI",
3+
"version": "4.0.270",
4+
"description": "SDK de Node.js para Fiscalapi",
55
"main": "dist/cjs/index.js",
66
"module": "dist/esm/index.js",
77
"types": "dist/types/index.d.ts",
88
"files": [
99
"dist/",
10+
"README.md",
1011
"fiscalapi.ico",
1112
"fiscalapi.png",
1213
"LICENSE.txt"
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
import { ApiResponse } from "../common/api-response";
2+
import { CatalogDto } from "../common/catalog-dto";
3+
4+
/**
5+
* Interfaz del servicio de catálogos de descarga masiva
6+
*/
7+
export interface IDownloadCatalogService {
8+
/**
9+
* GET /api/v4/download-catalogs
10+
* Recupera todos los nombres de los catálogos de descarga masiva disponibles para listarlos individualmente por nombre.
11+
*
12+
* @returns Lista de nombres de catálogos disponibles
13+
*/
14+
getList(): Promise<ApiResponse<string[]>>;
15+
16+
/**
17+
* GET /api/v4/download-catalogs/{catalogName}
18+
* Lista todos los registros de un catálogo pasando el nombre del catálogo
19+
*
20+
* @param catalogName - Nombre del catálogo
21+
* @returns Lista de registros del catálogo
22+
*/
23+
listCatalog(catalogName: string): Promise<ApiResponse<CatalogDto[]>>;
24+
}
Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
import { IFiscalapiService } from './fiscalapi-service.interface';
2+
import { DownloadRequest, Xml, MetadataItem } from '../models/download';
3+
import { ApiResponse } from '../common/api-response';
4+
import { PagedList } from '../common/paged-list';
5+
import { FileResponse } from '../common/file-response';
6+
7+
/**
8+
* Interfaz del servicio de solicitudes de descarga masiva
9+
*/
10+
export interface IDownloadRequestService extends IFiscalapiService<DownloadRequest> {
11+
/**
12+
* Lista los xmls descargados para un requestId.
13+
*
14+
* @param requestId - ID de la solicitud
15+
* @returns Lista paginada de objetos Xml
16+
*/
17+
getXmlsAsync(requestId: string): Promise<ApiResponse<PagedList<Xml>>>;
18+
19+
/**
20+
* Lista los meta-items descargados para un requestId.
21+
*
22+
* @param requestId - ID de la solicitud
23+
* @returns Lista paginada de objetos MetadataItem
24+
*/
25+
getMetadataItemsAsync(requestId: string): Promise<ApiResponse<PagedList<MetadataItem>>>;
26+
27+
/**
28+
* Downloads la lista de paquetes (archivos .zip) de un requestId.
29+
*
30+
* @param requestId - ID de la solicitud
31+
* @returns Lista de FileResponses
32+
*/
33+
downloadPackageAsync(requestId: string): Promise<ApiResponse<FileResponse[]>>;
34+
35+
/**
36+
* Descarga el archivo crudo de solicitud SAT para un requestId.
37+
*
38+
* @param requestId - ID de la solicitud
39+
* @returns Objeto de respuesta de archivo
40+
*/
41+
downloadSatRequestAsync(requestId: string): Promise<ApiResponse<FileResponse>>;
42+
43+
/**
44+
* Descarga la respuesta SAT para un requestId.
45+
*
46+
* @param requestId - ID de la solicitud
47+
* @returns Objeto de respuesta de archivo
48+
*/
49+
downloadSatResponseAsync(requestId: string): Promise<ApiResponse<FileResponse>>;
50+
51+
/**
52+
* Busca solicitudes de descarga creadas en una fecha específica.
53+
*
54+
* @param createdAt - Fecha de creación
55+
* @returns Lista de solicitudes de descarga
56+
*/
57+
searchAsync(createdAt: Date): Promise<ApiResponse<DownloadRequest[]>>;
58+
}
Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
import { IFiscalapiService } from './fiscalapi-service.interface';
2+
import { DownloadRequest, DownloadRule } from '../models/download';
3+
import { ApiResponse } from '../common/api-response';
4+
5+
/**
6+
* Interfaz del servicio de reglas de descarga masiva
7+
*/
8+
export interface IDownloadRuleService extends IFiscalapiService<DownloadRule> {
9+
/**
10+
* GET /api/v4/download-rules/test
11+
* Crea una regla de descarga masiva de prueba
12+
*
13+
* @returns Regla de descarga masiva de prueba
14+
*/
15+
createTestRule(): Promise<ApiResponse<DownloadRequest>>;
16+
}
17+

0 commit comments

Comments
 (0)