Erreurs, limites et gestion des versions
Erreurs
Une commande qui échoue est rejetée avec une EmbedError. Son code est stable et conçu pour servir de critère de branchement ; message est rédigé pour un développeur qui lit la console.
const { EmbedError } = IconMapEmbed;
try {
await map.applyBookmark({ bookmarkId });
} catch (e) {
if (!(e instanceof EmbedError)) throw e;
switch (e.code) {
case "unknown_id": return forgetBookmark(bookmarkId);
case "denied_capability": return hideBookmarkMenu();
default: report(e.code, e.message, e.requestId);
}
}
| Propriété | |
|---|---|
code |
L'un des codes d'erreur |
message |
Ce qui s'est mal passé, en une phrase |
detailedMessage |
La cause sous-jacente, s'il y en a une |
requestId |
Présent lorsque l'échec a impliqué nos serveurs : indiquez-le dans votre demande au support |
detail |
Compléments structurés, par exemple { undeclared: [...] } sur undeclared_filter |
Quel code signifie quoi
Les codes se répartissent en quatre familles, et la bonne réaction diffère pour chacune.
Votre page n'est pas autorisée : denied_origin, denied_capability. C'est l'auteur qui en décide. denied_origin rejette ready lui-même : aucune session n'est ouverte, et rien ne fonctionnera tant que votre site n'aura pas été ajouté aux origines autorisées de la carte. denied_capability signifie qu'un groupe est désactivé (ou, pour exportImage et print, qu'une étiquette de confidentialité refuse l'exportation). Masquez la fonctionnalité ; réessayer ne servira à rien.
La carte ne la propose pas : unsupported_command, unknown_id, undeclared_filter. Vérifiez capabilities.commands avant de proposer une fonctionnalité, et construisez vos sélecteurs à partir de ce que la carte indique (getLayers, getBookmarks, getFilterSchema) plutôt qu'à partir d'id inscrits dans votre code.
L'appel était incorrect : invalid_args, too_large. Il s'agit d'un bogue dans le code appelant ; le message nomme l'argument.
Réessayez plus tard : rate_limited, busy, budget_exceeded, data_error, timeout, not_ready. Espacez les tentatives plutôt que de boucler.
Deux codes proviennent du SDK et non de la carte : timeout (aucune réponse en 15 secondes ; modifiable avec l'option commandTimeoutMs) et destroyed (vous avez détruit ou rechargé la carte pendant qu'une commande était en cours).
Échecs au démarrage
Si la carte ne peut pas démarrer du tout (publication révoquée, jeton refusé), ready est rejetée et l'option onError est appelée. La carte affiche son propre message au lecteur, sauf si vous passez hideErrors: true et affichez le vôtre.
Limites
Elles sont fixes. Votre page ne peut pas les relever et un auteur ne peut pas les abaisser ; elles sont aussi exportées sous le nom EMBED_LIMITS.
| Limite | Valeur | En cas de dépassement |
|---|---|---|
| Commandes | 60 par seconde | rate_limited |
| Un message de commande | 64 KB | too_large, et la commande n'est jamais lue |
| Une charge utile d'événement | 32 KB | l'événement est abandonné |
Clés dans highlight / selectByKey |
500 | invalid_args |
| Opérations d'analyse | 60 par minute, 1 en cours + 4 en attente par couche | budget_exceeded, busy |
| Résultats d'analyse | 1 000 id ou 200 lignes par liste | tronqués, avec truncated: true |
featureHover |
un toutes les 100 ms | regroupés : la dernière valeur arrive toujours |
Des capacités, pas des versions
await map.ready se résout avec un descripteur de ce à quoi cette carte répondra :
{
protocol: 2,
commands: ["getView", "setView", ...],
events: ["viewChanged", "featureClick", ...],
policy: { enabled: true, read: true, camera: true, layers: true, ... },
map: { publishId, surface: "published", dataMode: "snapshot", bookmarks: true, locales: ["en-US", "de-DE", ...] }
}
commands est déjà l'intersection de trois éléments : ce que cette version de la carte implémente, ce que ce type d'incorporation prend en charge et ce que l'auteur a activé. La seule vérification dont vous aurez jamais besoin est donc :
if (capabilities.commands.includes("exportImage")) showExportButton();
Les nouvelles commandes apparaissent en étant ajoutées à cette liste. Une page écrite aujourd'hui continue de fonctionner ; une page qui veut une commande plus récente la demande et fonctionne en mode dégradé lorsqu'elle est absente.
Compatibilité entre anciennes et nouvelles versions
La carte et le SDK sont publiés séparément : chacun s'accommode de ce que l'autre soit plus ancien.
| Votre page utilise | La carte est | Résultat |
|---|---|---|
| Le SDK actuel | Actuelle | Tout ce que décrit cette documentation |
| Le SDK actuel | Une carte plus ancienne sans API de contrôle | La carte s'affiche. ready se résout avec une liste commands vide au lieu de rester bloquée ; les commandes sont rejetées avec unsupported_command |
SDK 0.x (affichage et setFilters uniquement) |
Actuelle | Fonctionne sans modification |
La version convenue se trouve dans map.protocol. Vous ne devriez pas en avoir besoin.
Cycle de vie
map.reload(); // reload the frame; subscriptions are restored when it is back
map.destroy(); // remove the frame; anything in flight rejects with `destroyed`
getEmbed(element) renvoie le handle déjà monté dans un élément, et reset(element) le détruit : utile dans les frameworks où le code qui monte la carte n'est pas celui qui fait le nettoyage.
Modèle de sécurité
Pour une revue de sécurité, voici les propriétés qui comptent :
- Isolation. La carte s'exécute dans un iframe d'origine différente. Elle ne peut pas lire votre page, et votre page ne peut pas la lire ; le seul canal est
postMessage. - Qui peut parler. La carte n'accepte de messages que de la fenêtre qui l'a encadrée, et seulement si l'origine de cette fenêtre figure parmi les origines autorisées par l'auteur. Un cadre tiers sur votre page ne peut pas piloter la carte, même depuis une origine autorisée. Le SDK, de son côté, n'accepte de messages que du cadre qu'il a créé, sur l'origine attendue, et n'envoie les jetons nulle part ailleurs.
- Ce qui peut être dit. Une liste fermée de commandes aux arguments validés. Aucune n'accepte d'URL, de requête, de style, de HTML ou de script.
- Ce qui revient. Uniquement ce qu'un lecteur voit déjà : les champs d'info-bulle, jamais de lignes complètes ; jamais la configuration de la carte, ses sources de données ou ses requêtes.
- Qui décide. Les origines autorisées et les réglages des groupes de commandes font partie de la publication signée, appliquée à l'intérieur de la carte et, lorsqu'une commande atteint nos serveurs (
refreshData), appliquée là aussi. - L'accès aux données est inchangé. L'API n'ajoute aucun nouveau chemin vers les données. Une carte publiée lit ce que la publication a figé ou ce que la sécurité au niveau des lignes de son jeton autorise ; une incorporation organisationnelle lit les données au nom du lecteur connecté.
- Étiquettes de confidentialité. L'export d'image et l'impression obéissent aux mêmes règles d'étiquettes de confidentialité que toute autre exportation depuis Icon Map.
- Télémétrie. Nous comptons les sessions de contrôle et les groupes de commandes utilisés. Les valeurs des arguments (valeurs de filtre, sélections, titres de vos menus) ne sont jamais collectées.
La même liste d'origines autorisées définit aussi la stratégie frame-ancestors : elle détermine donc quels sites peuvent encadrer la carte.