Backgrounds avec authentification
Ce guide montre comment ajouter différents types de fonds de plan avec authentification en utilisant IdentityManager.
Types d'identité disponibles
L'IdentityManager supporte plusieurs types d'identité :
- TOKEN : Token en clair
- IDENTITY : Information d'identité en clair (objet ou string)
- LOCALSTORAGE : Identité stockée dans le localStorage
- URL : Identité demandée à un service tiers
- FUNCTION : Identité récupérée via une fonction
Méthodes d'application (apply)
- query : Ajoute l'identité en paramètre d'URL
- header : Ajoute un header personnalisé
- headers : Ajoute plusieurs headers (identité = objet)
- bearer : Ajoute un header
Authorization: Bearer <token> - basic : Ajoute un header
Authorization: Basic <base64> - cookie : Ajoute un cookie
1. WMTS avec Bearer Token
Utilisation d'un token Bearer pour accéder à un service WMTS protégé.
// Source d'identité partagée avec Bearer
await kmapvInstance.addIdentitySource({
id: 'wmts-service',
type: 'TOKEN',
token: 'votre-token-jwt',
apply: {
type: 'bearer'
},
refreshInterval: 3600000 // Rafraîchir toutes les heures
});
// Ajout du fond WMTS
await kmapvInstance.backgroundLayer.addBackgroundLayer(
'fond-wmts-protege',
'wmts',
{
title: 'WMTS Protégé (Bearer)',
url: 'https://example.com/wmts/getcapabilities',
identity: {
id: 'wmts-service'
},
params: {
layer: 'NomDuLayer',
tileMatrixSet: 'EPSG:3857'
}
}
);
2. Layer XYZ avec Query Parameter
Token ajouté en paramètre d'URL pour un service de tuiles XYZ.
// Identité directement sur le layer
kmapvInstance.backgroundLayer.addBackgroundLayer(
'xyz-avec-token',
'layerXYZ',
{
title: 'XYZ avec token URL',
url: 'https://tiles.example.com/{z}/{x}/{y}.png',
identity: {
type: 'TOKEN',
token: 'abc123xyz',
apply: {
type: 'query',
name: 'apikey' // Résultat : ?apikey=abc123xyz
}
}
}
);
3. WMS Tuilé avec Basic Auth
Authentification Basic pour un WMS tuilé.
// Option 1 : Username/Password en clair (déconseillé en production)
kmapvInstance.backgroundLayer.addBackgroundLayer(
'wms-tiled-basic',
'wmstiled',
{
title: 'WMS Tuilé (Basic Auth)',
url: 'https://wms.example.com/service',
projection: 'EPSG:3857',
identity: {
type: 'IDENTITY',
identity: {
username: 'user',
password: 'pass'
},
apply: {
type: 'basic'
}
},
params: {
LAYERS: 'layer1,layer2'
}
}
);
// Option 2 : Via service d'authentification
kmapvInstance.backgroundLayer.addBackgroundLayer(
'wms-tiled-basic-url',
'wmstiled',
{
title: 'WMS Tuilé (Basic via URL)',
url: 'https://wms.example.com/service',
identity: {
type: 'url',
url: 'https://auth.example.com/api/getCredentials',
method: 'GET',
apply: {
type: 'basic'
},
refreshInterval: 1800000 // 30 minutes
},
params: {
LAYERS: 'cadastre'
}
}
);
4. WMS Non-tuilé avec Headers multiples
Plusieurs headers d'authentification pour un WMS non-tuilé.
// Source partagée avec headers multiples
await kmapvInstance.addIdentitySource({
id: 'multi-headers-auth',
type: 'IDENTITY',
identity: {
'Authorization': 'Bearer xyz789',
'X-Api-Key': 'ma-cle-api',
'X-Client-Id': 'mon-client-id'
},
apply: {
type: 'headers'
}
});
kmapvInstance.backgroundLayer.addBackgroundLayer(
'wms-untiled-headers',
'wmsuntiled',
{
title: 'WMS Non-tuilé (Multi-headers)',
url: 'https://wms-secure.example.com/service',
identity: {
id: 'multi-headers-auth'
},
params: {
LAYERS: 'reseau-hydraulique',
STYLES: 'style-default'
}
}
);
5. Vector (WFS) avec Basic Auth
Source vectorielle WFS avec authentification.
// Option 1 : Basic auth avec username/password
kmapvInstance.dataLayer.addDataLayer({
title: 'WFS Protégé (Basic)',
layerId: 'wfs-basic',
style: monStyle,
wfs: {
url: 'https://wfs.example.com/service',
projection: 'EPSG:3946',
geometryName: 'geometry',
identity: {
type: 'IDENTITY',
identity: {
username: 'user',
password: 'pass'
},
apply: {
type: 'basic'
}
},
params: {
typename: 'namespace:layer'
}
}
});
// Option 2 : Via fonction personnalisée
kmapvInstance.dataLayer.addDataLayer({
title: 'WFS Protégé (Function)',
layerId: 'wfs-function',
style: monStyle,
wfs: {
url: 'https://wfs.example.com/service',
identity: {
type: 'FUNCTION',
getIdentity: async () => {
// Logique personnalisée pour obtenir les credentials
const response = await fetch('/api/get-wfs-credentials');
const data = await response.json();
return {
username: data.user,
password: data.pass
};
},
apply: {
type: 'basic'
},
refreshInterval: 600000 // 10 minutes
},
params: {
typename: 'mon:calque'
}
}
});
6. Vector Tile avec JWT Token
Tuiles vectorielles avec authentification JWT.
// Source partagée pour plusieurs vector tiles
await kmapvInstance.addIdentitySource({
id: 'geoservice',
type: 'url',
method: 'POST',
url: 'https://services.example.com/api/auth/login',
auth: {
username: 'monuser',
password: 'monpass'
},
responseIdentityName: 'token', // Nom de la propriété dans la réponse JSON
apply: {
type: 'query',
name: 'jwt' // Ajouté comme ?jwt=<token>
},
refreshInterval: 3600000 // 1 heure
});
// Vector Tile OSM Basic
await kmapvInstance.backgroundLayer.addBackgroundLayer(
'vector-osm-basic',
'vectorTile',
{
title: 'OSM Basic (Vector Tile)',
styleUrl: 'https://services.example.com/styles/osm-basic/style.json',
identity: {
id: 'geoservice'
}
}
);
// Vector Tile Cadastre
await kmapvInstance.backgroundLayer.addBackgroundLayer(
'vector-cadastre',
'vectorTile',
{
title: 'Cadastre (Vector Tile)',
styleUrl: 'https://services.example.com/styles/cadastre/style.json',
identity: {
id: 'geoservice'
}
}
);
7. LocalStorage avec Header personnalisé
Récupération du token depuis le localStorage.
// Stocker le token dans localStorage (à faire au préalable)
localStorage.setItem('MY_MAP_TOKEN', JSON.stringify({
accessToken: 'mon-token-xyz',
expiresAt: Date.now() + 3600000
}));
// Utilisation du token depuis localStorage
kmapvInstance.backgroundLayer.addBackgroundLayer(
'fond-localstorage',
'layerXYZ',
{
title: 'XYZ avec LocalStorage',
url: 'https://secure-tiles.example.com/{z}/{x}/{y}.png',
identity: {
type: 'LOCALSTORAGE',
path: 'MY_MAP_TOKEN',
responseIdentityName: 'accessToken',
apply: {
type: 'header',
name: 'X-Access-Token',
scheme: 'Token' // Résultat : X-Access-Token: Token <value>
}
}
}
);
8. ArcGIS avec Token en Query
Service ArcGIS REST avec token.
// Token statique
kmapvInstance.backgroundLayer.addBackgroundLayer(
'arcgis-token',
'arcgis',
{
title: 'ArcGIS (Token)',
url: 'https://services.arcgis.com/xyz/arcgis/rest/services/MyMap/MapServer',
identity: {
type: 'TOKEN',
token: 'mon-token-arcgis',
apply: {
type: 'query',
name: 'token'
}
}
}
);
// Token dynamique via URL
kmapvInstance.backgroundLayer.addBackgroundLayer(
'arcgis-dynamic-token',
'arcgis',
{
title: 'ArcGIS (Token dynamique)',
url: 'https://services.arcgis.com/xyz/arcgis/rest/services/MyMap/MapServer',
identity: {
type: 'url',
url: 'https://arcgis.example.com/tokens/generate',
method: 'POST',
data: {
username: 'user',
password: 'pass',
client: 'referer',
referer: window.location.origin,
expiration: 60,
f: 'json'
},
responseIdentityName: 'token',
apply: {
type: 'query',
name: 'token'
},
refreshInterval: 3000000 // 50 minutes
}
}
);
9. Exemple complet avec gestion d'erreur
Exemple robuste avec gestion d'erreur et rafraîchissement.
// Fonction pour gérer l'authentification avec retry
async function setupSecureBackground() {
try {
// Créer une source d'identité avec gestion d'erreur
await kmapvInstance.addIdentitySource({
id: 'secure-service',
type: 'url',
url: 'https://auth.example.com/api/token',
method: 'POST',
data: {
grant_type: 'client_credentials',
client_id: 'my-client-id',
client_secret: 'my-secret'
},
responseIdentityName: 'access_token',
apply: {
type: 'bearer'
},
refreshInterval: 2700000 // 45 minutes (token valide 1h)
});
// Ajouter le fond de plan
await kmapvInstance.backgroundLayer.addBackgroundLayer(
'secure-background',
'wmts',
{
title: 'Fond sécurisé',
url: 'https://secure-wmts.example.com/service',
identity: {
id: 'secure-service'
},
params: {
layer: 'secure-layer'
}
}
);
console.log('Fond de plan sécurisé ajouté avec succès');
} catch (error) {
console.error('Erreur lors de l\'ajout du fond sécurisé:', error);
// Gérer l'erreur (afficher un message à l'utilisateur, etc.)
}
}
setupSecureBackground();
10. Cookie Authentication
Utilisation de cookies pour l'authentification (rare mais possible).
kmapvInstance.backgroundLayer.addBackgroundLayer(
'wms-cookie-auth',
'wmstiled',
{
title: 'WMS avec Cookie',
url: 'https://wms.example.com/service',
identity: {
type: 'TOKEN',
token: 'session-id-xyz789',
apply: {
type: 'cookie',
name: 'SESSIONID' // Cookie: SESSIONID=session-id-xyz789
}
},
params: {
LAYERS: 'data-layer'
}
}
);
Bonnes pratiques
Sécurité
- Ne jamais hardcoder les credentials en production
- Utiliser HTTPS pour toutes les requêtes d'authentification
- Implémenter le rafraîchissement automatique avec
refreshInterval - Gérer les erreurs d'authentification proprement
- Utiliser des tokens temporaires plutôt que des mots de passe
Performance
- Partager les sources d'identité entre plusieurs calques via
addIdentitySource() - Configurer
refreshIntervallégèrement avant l'expiration réelle du token - Mettre en cache les tokens dans localStorage quand approprié
Code
// ✅ BON : Source partagée
await kmapvInstance.addIdentitySource({
id: 'shared-auth',
type: 'url',
url: 'https://auth.example.com/token',
// ...
});
// Réutiliser pour plusieurs layers
layer1.identity = { id: 'shared-auth' };
layer2.identity = { id: 'shared-auth' };
layer3.identity = { id: 'shared-auth' };
// ❌ MAUVAIS : Duplication
layer1.identity = { type: 'url', url: '...', /* config complète */ };
layer2.identity = { type: 'url', url: '...', /* config complète */ };
layer3.identity = { type: 'url', url: '...', /* config complète */ };
Débogage
Pour déboguer les problèmes d'authentification :
// Activer les logs de l'identity manager
kmapvInstance.on('identity:error', (event) => {
console.error('Erreur d\'identité:', event);
});
// Vérifier l'état d'une source
const identityManager = kmapvInstance.getIdentityManager('my-source-id');
console.log('Token actuel:', identityManager.identity);
// L'identité est automatiquement rafraîchie lors des appels getRequest()
// si refreshInterval est configuré et que le délai est dépassé
Rafraîchissement automatique
L'IdentityManager récupère l'identité à la demande lors du premier appel à getRequest(), puis la rafraîchit automatiquement si refreshInterval est configuré et que le délai d'expiration est dépassé. Plus besoin d'appeler init() ou restart() manuellement !
