@infosel-sdk/core
Version:
Core SDK for Infosel financial services platform. Provides essential infrastructure for authentication, HTTP/GraphQL communication, storage management, and error handling.
447 lines (345 loc) • 12.1 kB
Markdown
# @infosel-sdk/core
[](https://badge.fury.io/js/@infosel-sdk%2Fcore)
[](https://opensource.org/licenses/MIT)
[](https://www.typescriptlang.org/)
SDK Core para la plataforma de servicios financieros Infosel. Proporciona infraestructura esencial para autenticación, comunicación HTTP/GraphQL, gestión de almacenamiento y manejo de errores.
## 🚀 Características
- **✨ Configuration Builder Pattern**: Nueva API fluida para configuración sin duplicaciones
- **🔐 Gestión de Autenticación**: Proveedores de autenticación KeyCloak y basados en tokens
- **🌐 Cliente HTTP**: Cliente HTTP configurable con interceptores de autenticación
- **📡 Cliente GraphQL**: Cliente GraphQL basado en Apollo con utilidades de consulta
- **💾 Gestión de Almacenamiento**: Soporte para almacenamiento local, en memoria y encriptado
- **🚨 Manejo de Errores**: Sistema completo de tipos de error y gestión centralizada
- **⚙️ Gestor del SDK**: Configuración y gestión centralizada del SDK
- **🔧 Configuración de Realm**: Configuración dinámica de realm para múltiples ambientes
## 📦 Instalación
```bash
npm install @infosel-sdk/core
```
### Compatibilidad de Versiones
- **React**: >=18.0.0
- **React Native**: >=0.70.0 (opcional)
- **Node.js**: >=16.0.0
- **TypeScript**: >=4.5.0
### Dependencias Opcionales
- `react-native-encrypted-storage`: Solo necesario para aplicaciones React Native que requieran almacenamiento encriptado
## 🔧 Configuración
### ✨ Nueva Configuración con Builder Pattern (Recomendado)
La nueva API elimina la duplicación de configuración y proporciona validaciones centralizadas:
#### Autenticación KeyCloak
```typescript
import { InfoselSdkManager, AuthConfigurationBuilder } from '@infosel-sdk/core';
const authConfig = AuthConfigurationBuilder
.keyCloak()
.withRealm('my-realm')
.withEnvironment('qa')
.withCredentials({
grant_type: 'client_credentials',
client_id: 'my-app-client',
client_secret: 'my-app-secret',
})
.build();
const sdk = InfoselSdkManager.initWithConfiguration({
authConfiguration: authConfig,
});
console.log(sdk.getRealm()); // 'my-realm'
```
#### Autenticación con Token Existente
```typescript
import { InfoselSdkManager, AuthConfigurationBuilder, Token } from '@infosel-sdk/core';
const token: Token = {
accessToken: 'your-access-token',
refreshToken: 'your-refresh-token',
};
const authConfig = AuthConfigurationBuilder
.existingToken()
.withRealm('production-realm')
.withEnvironment('prod')
.withClientId('production-client')
.withToken(token)
.build();
const sdk = InfoselSdkManager.initWithConfiguration({
authConfiguration: authConfig,
});
```
#### Configuración con Valores por Defecto
```typescript
import { InfoselSdkManager, AuthConfigurationBuilder } from '@infosel-sdk/core';
// Usa 'hub' como realm por defecto y 'prod' como environment
const authConfig = AuthConfigurationBuilder
.keyCloak()
.withCredentials({
grant_type: 'client_credentials',
client_id: 'my-client',
client_secret: 'my-secret',
})
.build();
const sdk = InfoselSdkManager.initWithConfiguration({
authConfiguration: authConfig,
});
```
### Configuración Legacy (Compatibilidad)
```typescript
import { InfoselSdkManager } from '@infosel-sdk/core';
const sdk = InfoselSdkManager.init({
mode: 'qa',
realm: 'my-realm',
authProviderConfig: {
type: 'key-cloak',
credentials: {
grant_type: 'client_credentials',
client_id: 'my-client',
client_secret: 'my-secret',
},
},
});
```
## 🔍 Validación de Configuración
El nuevo sistema incluye validaciones robustas:
```typescript
import { AuthConfigurationBuilder } from '@infosel-sdk/core';
const builder = AuthConfigurationBuilder
.keyCloak()
.withRealm('invalid@realm') // Caracteres inválidos
.withCredentials({
grant_type: 'client_credentials',
client_id: '', // Client ID vacío
client_secret: 'secret',
});
// Validar antes de construir
const validation = builder.validate();
if (!validation.isValid) {
console.log('Errores:', validation.errors);
// ['Realm contains invalid characters...', 'Client ID is required...']
}
// O validar automáticamente al construir
try {
const config = builder.build();
} catch (error) {
console.error(error.message); // Lista todos los errores de validación
}
```
## 🌍 Configuración por Ambiente
```typescript
import { AuthConfigurationBuilder, Environment } from '@infosel-sdk/core';
function createSdkForEnvironment(env: Environment) {
const baseBuilder = AuthConfigurationBuilder
.keyCloak()
.withEnvironment(env);
if (env === 'qa') {
return baseBuilder
.withRealm('qa-realm')
.withCredentials({
grant_type: 'client_credentials',
client_id: 'qa-client',
client_secret: 'qa-secret',
})
.build();
} else {
return baseBuilder
.withRealm('prod-realm')
.withCredentials({
grant_type: 'client_credentials',
client_id: 'prod-client',
client_secret: 'prod-secret',
})
.build();
}
}
const qaSdk = InfoselSdkManager.initWithConfiguration({
authConfiguration: createSdkForEnvironment('qa'),
});
```
## 💾 Almacenamiento
El SDK proporciona un sistema de almacenamiento que se adapta automáticamente según la plataforma:
### **Convención de Archivos**
- **`app_local_storage.ts`**: Implementación para Web (localStorage)
- **`app_local_storage.native.ts`**: Implementación para React Native (EncryptedStorage)
### **Uso del Almacenamiento**
```typescript
import { AppLocalStorage } from '@infosel-sdk/core';
const storage = new AppLocalStorage();
// Guardar datos
await storage.saveObject('user-data', { name: 'John', id: 123 });
// Obtener datos
const userData = await storage.getObject('user-data');
// Eliminar datos
await storage.removeObject('user-data');
```
## 🔐 Proveedores de Autenticación
### Token Auth Provider
```typescript
import { TokenAuthProvider } from '@infosel-sdk/core';
// Uso directo (para casos avanzados)
const authProvider = new TokenAuthProvider(
'qa', // environment
token, // Token object
'custom-realm', // realm
'custom-client' // clientId
);
```
### KeyCloak Auth Provider
```typescript
import { KeyCloakAuthProvider } from '@infosel-sdk/core';
// Uso directo (para casos avanzados)
const authProvider = new KeyCloakAuthProvider('qa', {
type: 'key-cloak',
credentials: {
grant_type: 'client_credentials',
client_id: 'client',
client_secret: 'secret',
},
realm: 'custom-realm',
});
```
## 🌐 Cliente HTTP
```typescript
import { InfoselHttpClient } from '@infosel-sdk/core';
const httpClient = new InfoselHttpClient({
baseURL: 'https://api.infosel.com',
timeout: 30000,
});
// GET request
const data = await httpClient.get('/users');
// POST request
const response = await httpClient.post('/users', { name: 'John' });
```
## 🔍 Cliente GraphQL
```typescript
import { InfoselGraphQlClient, queryfy } from '@infosel-sdk/core';
const graphqlClient = new InfoselGraphQlClient({
url: 'https://api.infosel.com/graphql',
});
// Query simple
const query = queryfy`
query GetUser($id: ID!) {
user(id: $id) {
id
name
email
}
}
`;
const result = await graphqlClient.query(query, { id: '123' });
```
## 🚨 Manejo de Errores
```typescript
import { SdkError, SdkErrorType } from '@infosel-sdk/core';
try {
const data = await httpClient.get('/users');
} catch (error) {
if (error instanceof SdkError) {
switch (error.type) {
case SdkErrorType.AXIOS_RESPONSE_ERROR:
console.error('Error de respuesta HTTP:', error.message);
break;
case SdkErrorType.LOCAL_STORAGE_KEY_NOT_FOUND:
console.error('Clave de almacenamiento no encontrada:', error.message);
break;
case SdkErrorType.INVALID_AUTH_PROVIDER_CONFIG:
console.error('Configuración de autenticación inválida:', error.message);
break;
default:
console.error('Error del SDK:', error.message);
}
}
}
```
## 📚 API Reference
### Clases Principales
- `InfoselSdkManager`: Gestor principal del SDK
- `AuthConfigurationBuilder`: Builder para configuraciones de autenticación
- `ConfigurationValidator`: Validador centralizado de configuraciones
- `AppLocalStorage`: Almacenamiento local adaptativo
- `InfoselHttpClient`: Cliente HTTP con interceptores
- `InfoselGraphQlClient`: Cliente GraphQL
- `TokenAuthProvider`: Proveedor de autenticación por token
- `KeyCloakAuthProvider`: Proveedor de autenticación KeyCloak
### Interfaces y Tipos
- `AuthConfiguration`: Configuración de autenticación centralizada
- `ValidationResult`: Resultado de validación con errores detallados
- `SdkConfig`: Configuración legacy del SDK (compatibilidad)
- `ModernSdkConfig`: Nueva configuración del SDK
- `Environment`: Tipo para ambientes ('qa' | 'prod')
- `AuthType`: Tipo de autenticación ('key-cloak' | 'existing-token')
### Tipos de Error
- `SdkErrorType.SDK_MANAGER_NOT_INITIALIZED`: SDK no inicializado
- `SdkErrorType.AXIOS_RESPONSE_ERROR`: Error de respuesta HTTP
- `SdkErrorType.LOCAL_STORAGE_KEY_NOT_FOUND`: Clave de almacenamiento no encontrada
- `SdkErrorType.LOCAL_STORAGE_NOT_AVAILABLE`: Almacenamiento no disponible
- `SdkErrorType.GRAPH_QL_ERROR`: Error de GraphQL
- `SdkErrorType.INVALID_AUTH_PROVIDER_CONFIG`: Configuración de autenticación inválida
## 🆕 Novedades en v0.0.4
### ✨ Configuration Builder Pattern
- **Nueva API fluida** para configuración sin duplicaciones
- **Validaciones centralizadas** con mensajes de error descriptivos
- **Single source of truth** para configuración de realm
- **Compatibilidad hacia atrás** mantenida
### 🔧 Mejoras en Configuración
- **Configuración dinámica de realm** para múltiples ambientes
- **Validación de formatos** de realm, client_id y credenciales
- **Valores por defecto inteligentes** basados en el tipo de autenticación
- **Type safety mejorado** con TypeScript
### 📖 Documentación
- **Ejemplos completos** de uso del Configuration Builder
- **Guías de migración** desde configuración legacy
- **Casos de uso avanzados** para diferentes ambientes
## 🔄 Migración desde v0.0.3
### Antes
```typescript
// ❌ Configuración duplicada
const sdk = InfoselSdkManager.init({
mode: 'qa',
realm: 'my-realm', // Primera definición
authProviderConfig: {
type: 'key-cloak',
realm: 'my-realm', // Segunda definición (duplicada)
credentials: { /* ... */ },
},
});
```
### Después
```typescript
// ✅ Single source of truth
const authConfig = AuthConfigurationBuilder
.keyCloak()
.withRealm('my-realm') // Una sola definición
.withEnvironment('qa')
.withCredentials({ /* ... */ })
.build();
const sdk = InfoselSdkManager.initWithConfiguration({
authConfiguration: authConfig,
});
```
## 🧪 Testing
```bash
# Ejecutar tests
npm test
# Ejecutar tests con cobertura
npm run test:coverage
# Ejecutar tests específicos
npm test -- --testPathPattern="auth_configuration_builder"
```
## 🔨 Development
```bash
# Instalar dependencias
npm install
# Compilar TypeScript
npm run build
# Crear distribución
npm run build:dist
```
## 🤝 Contribución
1. Fork el proyecto
2. Crea una rama para tu feature (`git checkout -b feature/AmazingFeature`)
3. Commit tus cambios (`git commit -m 'Add some AmazingFeature'`)
4. Push a la rama (`git push origin feature/AmazingFeature`)
5. Abre un Pull Request
## 📄 Licencia
Este proyecto está bajo la Licencia MIT. Ver el archivo `LICENSE` para más detalles.
## 📞 Soporte
- **Documentación**: [Ejemplos de Configuration Builder](./CONFIGURATION_BUILDER_EXAMPLES.md)
- **Issues**: [GitHub Issues](https://github.com/infosel/am-sdks/issues)
- **Equipo**: Infosel Team
---
**Hecho con ❤️ por el equipo de Infosel**