Cartes
Découvrez les types de cartes, créez une instance et mettez à jour ses données en direct. Une liste de lecture place l’identifiant de carte retourné.
screenrig cards list --category ops
screenrig cards show gauge
screenrig card create --type gauge --file gauge-params.json
screenrig card list
screenrig card show crd_01EXAMPLEGAUGE000000000
screenrig card params crd_01EXAMPLEGAUGE000000000 --file gauge-params.json
screenrig card data get crd_01EXAMPLEGAUGE000000000
screenrig card data put crd_01EXAMPLEGAUGE000000000 --file gauge-data.json --ttl 30m --expect-rev 1
screenrig card preview crd_01EXAMPLEGAUGE000000000 --output gauge.png
screenrig card delete crd_01EXAMPLEGAUGE000000000| Paramètre | Type | Requis | Par défaut | Notes |
|---|---|---|---|---|
cards list --tag TAG | string | non | aucun | Correspond à une étiquette du catalogue. |
cards list --category CATEGORY | string | non | aucun | Correspond à une catégorie du catalogue. Avec --tag, une carte doit correspondre aux deux. |
cards show <id> | string | oui | aucun | L’identifiant de carte du catalogue issu de cards list, comme gauge. |
card create --type ID | string | oui | aucun | L’identifiant de carte du catalogue issu de cards list. |
card create --major N | integer | non | version majeure actuelle | Épingle une version majeure du catalogue. |
card create --file FILE | chemin | oui | aucun | Les paramètres statiques sous forme d’objet JSON d’au plus 1 Mio, ou - pour stdin. |
<id> | string | oui | aucun | L’identifiant de carte crd_ que prennent card show, card params, card delete et card data. |
card params --file FILE | chemin | oui | aucun | Les nouveaux paramètres statiques, lus comme pour card create. Ils remplacent immédiatement les anciens. |
card data put --file FILE | chemin | oui | aucun | Le document de données sous forme d’objet JSON, ou - pour stdin. Il remplace tout le document. |
card data put --ttl DURATION | string | non | aucun | Vide les données après cette durée, écrans hors ligne compris : 30m, 12h ou 1d, de 1s à 365d. Incompatible avec --expires-at. |
card data put --expires-at INSTANT | string | non | aucun | Vide les données à cet horodatage ISO 8601, qui porte un fuseau horaire. Une écriture sans aucune des deux options efface l’ancienne expiration. |
card data put --expect-rev REVISION | string | non | aucun | Écrit seulement si les données sont toujours à cette révision, celle que montre card data get. Une valeur périmée donne revision_conflict (sortie 6). |
card preview <type|id> | string | oui | aucun | Un identifiant de carte du catalogue, ou un identifiant de carte crd_ pour dessiner cette instance avec ses propres paramètres et données. |
card preview --output FILE | chemin | oui | aucun | Écrit le PNG ici. Les dossiers parents sont créés. |
card preview --params FILE | chemin | non | aucun | Propriétés statiques sous forme d’objet JSON. |
card preview --data FILE | chemin | non | aucun | Le document dynamique sous forme d’objet JSON. |
card preview --feed FILE | chemin | non | aucun | Le document de flux hôte sous forme d’objet JSON. Un flux dont la carte a besoin et que vous omettez est signalé. |
card preview --width PX / --height PX | integer | non | 1920 / 1080 | Taille de l’image, de 1 à 8192. |
card preview --layout LAYOUT | string | non | full | full, free, center, wide, header, footer, corner, chip ou strip : la mise en page à dessiner. |
card preview --anchor ANCHOR | string | non | aucun | Le coin d’une mise en page corner ou chip, ou le bord d’un strip. |
card preview --now ISO | string | non | l’heure actuelle | Fige l’horloge à cet instant ISO 8601. |
card preview --timezone ZONE | string | non | celui de cette machine | Dessine dans ce fuseau horaire IANA, comme America/Vancouver. |
cards show affiche le params_schema et le data_schema de la carte, ses propriétés statiques et dynamiques, son niveau, ses mises en page et son flux, ainsi qu’un exemple à copier dans une page de liste de lecture. card create renvoie l’identifiant crd_ de l’instance, et une relance identique après une réponse perdue réutilise la clé d’idempotence enregistrée.
card data put remplace le document immédiatement, sans republier la liste de lecture. La validation propre à la carte refuse un document qu’elle ne peut pas afficher (card_data_invalid), et une expiration vide les données sur chaque écran quand rien ne les renouvelle. card delete supprime l’instance et ses données, et répond resource_conflict (sortie 5) tant qu’une liste de lecture la place.
card preview dessine la carte dans un Chromium ou Chrome local et écrit un PNG ; il ne publie rien. Définissez SCREENRIG_BROWSER sur le chemin du navigateur si aucun des navigateurs habituels n’est installé. data.file est le chemin écrit et data.unrendered liste ce que l’aperçu n’a pas pu dessiner, par exemple un flux hôte que vous n’avez pas fourni. Ouvrez l’image avant de publier. Cartes intégrées décrit les mises en page, les propriétés et les flux de chaque carte.
Webhooks de carte
Un webhook de carte est une URL qui écrit le document de données d'une carte, de sorte qu'un système externe comme un CMS, un point de vente ou un script envoie des données à une carte avec un seul POST HTTP. kv webhook create, list, rotate-secret et delete acceptent --card CARD_ID à la place de --app-id, jamais les deux ; update et deliveries ci-dessous ne fonctionnent que sur les cartes. Une carte peut avoir au maximum 20 webhooks.
kv webhook create --card CARD_ID [--description TEXT] [--map FILE|-] [--key-template TEMPLATE] [--signing]
[--verify VENDOR [--verify-secret-file FILE|-] [--verify-header NAME] [--verify-encoding hex|base64]
[--verify-timestamp-header NAME] [--verify-tolerance SECONDS]] [--handshake VENDOR]
kv webhook list --card CARD_ID
kv webhook rotate-secret <webhook_id> --card CARD_ID [--signing]
kv webhook delete <webhook_id> --card CARD_IDLa création d’un webhook de carte ne prend aucune clé. --map FILE (ou - pour stdin) est le mappage, --key-template écrit des documents par clé, --signing active la signature, et --verify et --handshake acceptent les envois propres à un fournisseur (Signatures et poignées de main des fournisseurs). La réponse contient data.secret et, si le webhook signe, data.signing_secret, chacun affiché une seule fois.
L'expéditeur s'authentifie comme pour un webhook d'application : Authorization: Bearer <secret> avec le secret srkw_…, ou HTTP Basic avec l'identifiant du webhook comme nom d'utilisateur, de sorte que https://kvw_ID:srkw_…@api.screenrig.ai/… convient à un expéditeur qui n'accepte qu'une URL. Le corps, d'au plus 1 Mio, est du JSON ou application/x-www-form-urlencoded ; un nom de formulaire répété devient un tableau. Sans mappage, l'objet envoyé est le document de données de la carte.
Un mappage est un modèle JSON qui construit le document à partir du corps. Une chaîne contenant des espaces réservés comme {{body.alert.title}} ou {{body.items[0].name}} est du texte, et une chaîne qui est exactement un espace réservé conserve le type de la valeur. Un chemin commence par body ou query (les paramètres de requête de l'URL), et un chemin qui ne contient rien est vide dans le texte et omet une valeur isolée. $each mappe un tableau avec item et index dans la portée, $group avec $by regroupe dans l'ordre de première apparition, $number lit 1,234.50, $3.50, 3,50 € ou 12% (ajoutez "$decimal": "," pour une virgule décimale), $bool lit true, yes, y, 1 et x, et $text avec $max tronque le texte. Le modèle est vérifié à l'enregistrement : invalid_request nomme l'endroit en cause.
{
"title": "{{body.alert.title}}",
"body": "{{body.alert.message}}",
"items": { "$each": "{{body.items}}", "$limit": 20, "$template": { "text": "{{item.name}}" } }
}curl https://api.screenrig.ai/api/cards/crd_01EXAMPLEBOARD0000000000/kv-webhooks/kvw_01EXAMPLEWEBHOOK00000/write \
-H "Authorization: Bearer $CARD_WEBHOOK_SECRET" \
-H "Content-Type: application/json" \
--data '{"alert":{"title":"Fire drill","message":"Leave by the east door"},"items":[{"name":"Floor 2"}]}'--key-template TEMPLATE écrit des documents par clé à la place du document propre à la carte. Le modèle est une clé de données de carte avec des jetons {screen.field.NAME}, comme room-{screen.field.room}, et l’objet mappé (ou le corps posté, sans mappage) ne contient qu’un tableau documents d’objets {fields, document} : chaque objet fields remplit le modèle et chaque document est écrit sous la clé qu’il produit. Un élément de page qui donne le même modèle comme data montre à chaque écran le document de ses propres champs. Chaque document est vérifié avant qu’aucun ne soit écrit, et une clé répétée est refusée. Un échec de stockage peut laisser une partie du lot écrite : renvoyez le même corps avec le même Idempotency-Key. Les clés qu’un envoi omet gardent leurs données, et un webhook ne fixe aucune expiration. Documents par clé montre un mappage.
Chaque envoi est vérifié comme les données de la carte elle-même : card_data_invalid nomme le chemin et rien n’est écrit. Un document identique à celui en cours de la carte reçoit la réponse unchanged et n’écrit rien, de sorte qu’aucun écran n’est réveillé. Un envoi accepté ne compte pas dans le plafond de requêtes d’agent, un webhook accepte au plus 120 envois par minute, et un en-tête Idempotency-Key déduplique les nouvelles tentatives d’un expéditeur pendant 24 heures.
Une mauvaise adresse, un secret erroné ou absent, un webhook désactivé, une signature absente ou erronée et chaque GET reçoivent la même réponse 404, de sorte qu'un aperçu de lien ou une supposition n'apprend rien. kv webhook deliveries en donne la raison.
Avec --signing, chaque envoi doit aussi porter ScreenRig-Signature: t=<unix seconds>,v1=<hex>, où v1 est le HMAC-SHA256 de t, d'un point et du corps brut sous le secret de signature whsec_…, et t doit être à moins de cinq minutes de l'horloge du serveur. C'est le format des signatures de webhook de screenRIG.
Signatures et poignées de main des fournisseurs
Les fournisseurs signent leurs envois à leur façon, et certains ne peuvent pas envoyer votre secret du tout. Un webhook de carte peut vérifier la signature du fournisseur à la place du secret et répondre à la poignée de main de configuration du fournisseur : GitHub, Stripe, Shopify, Slack, Linear, Vercel, Asana, Microsoft Graph, monday.com, Trello et Azure Event Grid y envoient donc directement, sans relais. Tout autre expéditeur qui signe avec HMAC fonctionne aussi. Définissez-les avec --verify et --handshake sur kv webhook create, et modifiez-les avec kv webhook update.
--verify VENDORaccepte la signature propre à un fournisseur, avec--verify-secret-file FILE(ou-pour stdin, jamais en argument) qui contient le secret que le fournisseur affiche. Pourgeneric_hmac,--verify-header NAMEnomme l’en-tête qui porte la signature,--verify-encodingvauthex(par défaut) oubase64,--verify-timestamp-header NAMEnomme un en-tête qui porte l’heure Unix, et--verify-tolerance SECONDSindique de combien elle peut s’écarter de l’horloge du serveur (300 par défaut). Un envoi qui porte la signature valide du fournisseur est accepté sans le secretsrkw_propre au webhook, qui continue de fonctionner à côté. Le secret du fournisseur est stocké chiffré et affiché seulement sous la formesetet d’unhintde ses quatre derniers caractères. Aveckv webhook update,--verifysans--verify-secret-fileconserve le secret stocké tant que le fournisseur reste le même, et--clear-verifysupprime la vérification et son secret.--verifyet--signings’excluent mutuellement.--handshake VENDORestmicrosoft_graph,monday,trelloouazure_event_grid, et--clear-handshakele supprime. Slack et Asana répondent à leurs propres poignées de main par--verify.
--verify | En-tête | Ce qui est signé | Horodatage |
|---|---|---|---|
github | X-Hub-Signature-256 | HMAC-SHA256 du corps | Aucun |
stripe | Stripe-Signature | HMAC-SHA256 de l’horodatage, d’un point et du corps ; n’importe quel v1 peut correspondre | 5 minutes |
shopify | X-Shopify-Hmac-Sha256 | HMAC-SHA256 du corps, en base64 | Aucun |
slack | X-Slack-Signature | HMAC-SHA256 de v0:, de l’horodatage, de deux-points et du corps | X-Slack-Request-Timestamp, 5 minutes |
linear | Linear-Signature | HMAC-SHA256 du corps | webhookTimestamp dans le corps, 1 minute |
vercel | x-vercel-signature | HMAC-SHA1 du corps | Aucun |
asana | X-Hook-Signature | HMAC-SHA256 du corps, avec pour clé le X-Hook-Secret de la poignée de main | Aucun |
generic_hmac | Le --verify-header que vous nommez | HMAC-SHA256 du corps ou, avec un --verify-timestamp-header, de l’horodatage, d’un point et du corps | --verify-tolerance |
La clé de chaque HMAC est le texte du secret tel que le fournisseur l’affiche (celui de Stripe comprend whsec_). Une signature est vérifiée sur le corps exactement tel qu’il est arrivé, en temps constant, avant que l’envoi ne consomme du budget d’écriture, et elle est jugée avant son horodatage : timestamp_stale signifie toujours que le secret était le bon. Un corps peut être du JSON, un formulaire ou multipart/form-data, où un champ de texte est body.FIELD et où les fichiers sont comptés, non lus.
| Fournisseur | screenRIG répond | Envois suivants |
|---|---|---|
Slack (--verify slack) | Le url_verification signé avec son challenge ; une personne qui teste avec curl peut envoyer le secret du webhook à la place | Signés avec le secret de signature |
Asana (--verify asana) | Le X-Hook-Secret de la poignée de main, qu’il garde chiffré comme clé de chaque X-Hook-Signature. Le même secret de nouveau est une relance ; un secret différent est refusé avec handshake_invalid | X-Hook-Signature |
Microsoft Graph (--handshake microsoft_graph) | Le ?validationToken= décodé comme text/plain | Portent le secret du webhook |
monday.com (--handshake monday) | Le challenge qu’il envoie, renvoyé en JSON | Portent le secret du webhook |
Trello (--handshake trello) | Une vérification HEAD répond 200 sans corps, pour ce webhook seulement | Portent le secret du webhook |
Azure Event Grid (--handshake azure_event_grid) | {"validationResponse": "CODE"} | Portent le secret du webhook |
Une poignée de main n’est traitée que pour un webhook configuré pour ce fournisseur, avant qu’aucun identifiant ne soit demandé, pour une requête qui est cette poignée de main, et jamais par un webhook désactivé. Elle n’écrit rien, n’est jamais facturée et ne consomme aucun budget de débit. Microsoft Graph, monday.com, Trello et Azure Event Grid n’envoient aucun en-tête que screenRIG vérifie : leurs envois ne sont donc acceptés qu’avec le secret du webhook. Azure Event Grid le transmet comme un en-tête de livraison statique, Authorization: Bearer srkw_…, marqué secret, et ses événements arrivent sous forme de tableau : un mappage lit donc body[0].
| Fournisseur | Dans les paramètres du fournisseur |
|---|---|
| GitHub | Settings, Webhooks, Add webhook : l’URL de charge utile est le url du webhook, le type de contenu est application/json, et le même secret. Le ping de GitHub est signé et accepté |
| Stripe | Workbench, Webhooks : ajoutez le url et affichez son secret de signature. Pendant que Stripe fait pivoter un secret, il envoie un v1 pour chacun et l’un ou l’autre est accepté ; remplacez ensuite le secret stocké avec kv webhook update --verify stripe --verify-secret-file FILE |
| Shopify | Abonnez-vous avec le url au format JSON. Le secret est le secret client de l’application |
| Slack | L’URL de requête de l’API Events est le url, et le secret est le secret de signature de l’application. Une commande à barre oblique envoie un formulaire : {{body.text}}, {{body.user_name}} |
| Linear | Dans les paramètres de l’API, créez un webhook avec le url et copiez son secret de signature. Le webhookTimestamp du corps doit se situer à une minute de l’horloge du serveur |
| Vercel | Team settings, Webhooks : créez-en un avec le url. Vercel affiche le secret une seule fois |
| Asana | Créez le webhook avec --verify asana : il n’a pas encore de secret et refuse les événements avec secret_pending. Créez ensuite le webhook Asana avec target réglé sur le url, et la poignée de main définit le secret. Pour prendre un nouveau secret, exécutez kv webhook update avec --clear-verify, puis de nouveau avec --verify asana |
| Microsoft Graph | Créez l’abonnement avec notificationUrl réglé sur le url |
| monday.com | Exécutez create_webhook avec le url |
| Trello | POST /1/webhooks avec callbackURL réglé sur le url |
| Azure Event Grid | Créez l’abonnement aux événements avec le url comme point de terminaison du webhook, et ajoutez l’en-tête de livraison ci-dessus |
echo '{"title":"{{body.repository.full_name}}","body":"{{body.head_commit.message}}"}' |
screenrig kv webhook create --card crd_01EXAMPLEBOARD0000000000 --description "Pushes" \
--verify github --verify-secret-file github.secret --map -
Un expéditeur qui signe avec son propre HMAC nomme l’en-tête, l’encodage et, s’il signe un horodatage, l’en-tête d’horodatage :
echo '{"title":"{{body.sensor}}","body":"{{body.state}}"}' |
screenrig kv webhook create --card crd_01EXAMPLEBOARD0000000000 --verify generic_hmac --verify-secret-file acme.secret \
--verify-header X-Acme-Signature --verify-encoding base64 --verify-timestamp-header X-Acme-Time --verify-tolerance 120 \
--map -
ts=$(date +%s); body='{"sensor":"door","state":"open"}'
sig=$(printf '%s.%s' "$ts" "$body" | openssl dgst -sha256 -hmac "$SECRET" -binary | openssl base64 -A)
curl "$URL" -H "Content-Type: application/json" -H "X-Acme-Time: $ts" -H "X-Acme-Signature: $sig" -d "$body"
Chaque échec donne le même 404 que tout autre refus. kv webhook deliveries montre la raison, et une poignée de main apparaît avec le résultat handshake :
| Raison | Sens |
|---|---|
signature_missing | Une vérification du fournisseur est définie et l’envoi ne portait ni le secret ni l’en-tête du fournisseur |
signature_invalid | L’en-tête est mal formé ou ne correspond pas au corps |
timestamp_missing | La signature exige un horodatage que l’envoi ne portait pas |
timestamp_stale | La signature est valide et son horodatage est hors de la fenêtre |
secret_pending | Une vérification Asana attend encore sa poignée de main |
handshake_invalid | La requête est la poignée de main d’un fournisseur et ne peut pas recevoir de réponse |
kv webhook update#
Modifier un webhook de carte : sa description, son mappage, ses documents par clé, son état activé, sa signature, la vérification du fournisseur ou la poignée de main.
kv webhook update <webhook_id> --card CARD_ID [--description TEXT] [--map FILE|-] [--clear-map]
[--key-template TEMPLATE] [--clear-key-template] [--enable|--disable] [--signing|--no-signing]
[--verify VENDOR [--verify-secret-file FILE|-] [--verify-header NAME] [--verify-encoding hex|base64]
[--verify-timestamp-header NAME] [--verify-tolerance SECONDS]] [--clear-verify]
[--handshake VENDOR] [--clear-handshake]| Paramètre | Type | Requis | Par défaut | Notes |
|---|---|---|---|---|
<webhook_id> | string | oui | aucun | L’identifiant de webhook kvw_. |
--card CARD_ID | string | oui | aucun | L'identifiant de carte crd_. |
--description TEXT | string | non | aucun | Ce qui y envoie, au maximum 200 octets. Il ne doit pas contenir de justificatif. |
--map FILE | chemin | non | aucun | Remplacer le mappage par un objet JSON lu depuis un fichier, ou - pour stdin. Incompatible avec --clear-map. |
--clear-map | boolean | non | désactivé | Supprimer le mappage : l'objet envoyé devient le document. |
--key-template TEMPLATE | string | non | aucun | Définit le modèle de clé qui indexe les documents, comme room-{screen.field.room}. Incompatible avec --clear-key-template. |
--clear-key-template | boolean | non | désactivé | Revient à écrire le document propre à la carte. |
--enable / --disable | boolean | non | désactivé | --disable répond à chaque envoi comme à un mauvais secret jusqu'à --enable. |
--signing / --no-signing | boolean | non | désactivé | --signing exige l’en-tête de signature et affiche le secret de signature une fois ; un webhook qui signe déjà garde son secret, que kv webhook rotate-secret --signing remplace. --no-signing cesse de l’exiger. Incompatible avec --verify. |
--verify VENDOR | string | non | aucun | Remplace la vérification du fournisseur : github, stripe, shopify, slack, linear, vercel, asana ou generic_hmac. Sans --verify-secret-file, le secret stocké est conservé si le fournisseur est le même, de sorte qu’un en-tête ou une fenêtre peut changer seul ; un autre fournisseur a besoin du sien. Incompatible avec --clear-verify. |
--verify-secret-file FILE | chemin | non | le secret stocké | Lit le secret du fournisseur depuis un fichier, ou - pour stdin (jamais en argument). asana n’en prend aucun. Une seule option lit stdin. |
--verify-header NAME | string | avec generic_hmac | aucun | L’en-tête qui porte la signature, de 1 à 100 lettres, chiffres, - ou _. |
--verify-encoding ENCODING | string | non | hex | Avec generic_hmac : hex ou base64 ; elle peut commencer par sha256=. |
--verify-timestamp-header NAME | string | non | aucun | Avec generic_hmac : un en-tête qui porte l’heure Unix en secondes, ou en millisecondes sur 13 chiffres. |
--verify-tolerance SECONDS | integer | non | 300 | Avec --verify-timestamp-header : de combien l’horodatage peut s’écarter de l’horloge du serveur, de 1 à 86400. |
--clear-verify | boolean | non | désactivé | Cesse d’accepter la signature du fournisseur et oublie son secret. Une vérification Asana n’accepte une nouvelle poignée de main qu’après --clear-verify puis de nouveau --verify asana. |
--handshake VENDOR | string | non | aucun | Définit la poignée de main à laquelle l’URL répond : microsoft_graph, monday, trello ou azure_event_grid. Incompatible avec --clear-handshake. |
--clear-handshake | boolean | non | désactivé | Cesse de répondre à la poignée de main du fournisseur. |
Au moins un changement est requis.
screenrig kv webhook update kvw_01EXAMPLEWEBHOOK00000 --card crd_01EXAMPLEBOARD0000000000 --map alert-map.json
screenrig kv webhook update kvw_01EXAMPLEWEBHOOK00000 --card crd_01EXAMPLEBOARD0000000000 --verify stripe --verify-secret-file stripe.secret
screenrig kv webhook update kvw_01EXAMPLEWEBHOOK00000 --card crd_01EXAMPLEBOARD0000000000 --clear-verifyL’enveloppe est le webhook. data.signing_secret n’apparaît qu’une fois, dans la réponse qui a activé la signature. Après une mise à jour interrompue ou ambiguë, relancez la même commande : elle réutilise la clé d’idempotence enregistrée.
kv webhook deliveries#
Lire le journal de livraison d'un webhook de carte, du plus récent au plus ancien, pour les sept derniers jours.
kv webhook deliveries <webhook_id> --card CARD_ID [--limit N]| Paramètre | Type | Requis | Par défaut | Notes |
|---|---|---|---|---|
<webhook_id> | string | oui | aucun | L’identifiant de webhook kvw_. |
--card CARD_ID | string | oui | aucun | L'identifiant de carte crd_. |
--limit N | number | non | 100 | Nombre de livraisons à retourner, de 1 à 100. |
screenrig kv webhook deliveries kvw_01EXAMPLEWEBHOOK00000 --card crd_01EXAMPLEBOARD0000000000Chaque élément a at, outcome (written, unchanged, refused, invalid ou handshake), reason (credentials, signature pour un ScreenRig-Signature échoué, disabled, body, mapping, card_data_invalid, rate_limited, internal, ou une raison propre au fournisseur du tableau ci-dessus), detail, status, bytes, files (les parties fichier d’un envoi multipart, qui sont ignorées), revision et request_id. Aucun corps, en-tête ni identifiant n’est stocké, et un envoi à une mauvaise adresse ne laisse aucune ligne.