Fonctions cloud
Les fonctions cloud exécutent votre propre code dans Fundamentum, lors d'un appel HTTP ou à chaque message d'un topic, sans serveur à gérer. Cette page vous montre comment écrire une fonction, la déployer avec la CLI fun, la déclencher et consulter son historique d'exécution.
Ce que vous pouvez en faire
- Décoder des charges utiles propriétaires : transformez la trame binaire d'un appareil en JSON compréhensible par vos systèmes.
- Enrichir : ajoutez du contexte à un message avant qu'il n'atteigne un connecteur ou Insight.
- Acheminer : lisez un topic et écrivez le résultat dans un autre.
- Traduire des actions : réutilisez une fonction comme encodeur qui convertit les actions de la plateforme dans le protocole de votre appareil (voir Actions and custom encoders).
Vous écrivez les fonctions en Go, Rust, JavaScript ou Python. Chaque exécution s'effectue dans un bac à sable isolé, et chaque exécution est enregistrée avec ses journaux et ses erreurs.
Fonctionnement d'une fonction
Une fonction est un programme qui lit un document JSON sur l'entrée standard et écrit son résultat sur la sortie standard :
{
"input": "<base64 of the request body or topic message>",
"context": {"function_id": "<function-id>", "project_id": 1234},
"metadata": {"<key>": "<base64 value>"}
}
inputest la charge utile brute, encodée en base64.metadatacontient les valeurs des en-têtes HTTPX-Function-<key>, ou des en-têtes de messagefunction-<key>, également encodées en base64.- Tout ce qui est écrit sur la sortie d'erreur standard est conservé comme journal d'exécution.
- Les variables de fonction que vous définissez sont disponibles sous forme de variables d'environnement.
| Déclencheur | Entrée | Destination de la sortie |
|---|---|---|
| HTTP : un appel à la Public API | Le corps de la requête, tel quel | La réponse de l'API |
| Topic : un message sur un topic d'entrée | La valeur du message | Le topic de sortie, si vous en définissez un |
Une fonction déclenchée par un topic peut s'exécuter plusieurs fois pour le même message ; rendez-la idempotente. Par défaut, une fonction traite une seule exécution à la fois et met les autres en file d'attente ; définissez scaling.pool_size (supérieur à 1) pour en exécuter plusieurs en parallèle.
Le moteur d'exécution, les cibles de compilation et le SDK sont décrits dans Runtime and SDK.
Avant de commencer
- La CLI
funinstallée et connectée (voir Authentication). - L'ID de votre projet et, pour les déclencheurs par topic, les ID des topics d'entrée et de sortie.
- La chaîne d'outils de votre langage, comme indiqué sur la page Runtime and SDK.
- Les permissions
functiondont vous avez besoin (store,upload,invoke,monitor… ; voir Roles and permissions).
1. Écrire la fonction
Cette fonction Go décode une trame de température de deux octets et renvoie du JSON. Elle utilise uniquement la bibliothèque standard :
package main
import (
"encoding/binary"
"encoding/json"
"fmt"
"os"
)
type request struct {
Input []byte `json:"input"` // base64 in the JSON, decoded by encoding/json
Metadata map[string][]byte `json:"metadata"`
}
func main() {
var req request
if err := json.NewDecoder(os.Stdin).Decode(&req); err != nil || len(req.Input) < 2 {
fmt.Fprintln(os.Stderr, "invalid input")
os.Exit(1)
}
tenths := int16(binary.BigEndian.Uint16(req.Input[:2]))
json.NewEncoder(os.Stdout).Encode(map[string]float64{"temperature": float64(tenths) / 10})
}
Compilez-la pour le moteur d'exécution des fonctions avec la commande indiquée sur la page Runtime and SDK.
2. Créer la fonction
fun functions new temp-decoder --project <project-id> --language go \
--description "Decode temperature frames" \
--connector <input-topic-id>:<output-topic-id> \
--variable UNIT=celsius
temp-decoder est un nom local que la CLI conserve pour vous, afin que les commandes suivantes n'aient pas besoin des ID. Omettez --connector pour une fonction déclenchée uniquement par HTTP. Utilisez --ask pour être invité à saisir les valeurs manquantes. Les connecteurs qui formeraient un cycle entre des topics sont rejetés.
3. Téléverser le code
fun functions upload temp-decoder <path-to-compiled-function>
Chaque téléversement remplace le code précédent. Les fichiers peuvent atteindre 1 GiB.
4. Invoquer la fonction via HTTP
printf '\000\347' > frame.bin
fun functions invoke -n temp-decoder -i frame.bin
La requête brute, avec des en-têtes de métadonnées facultatifs :
POST https://api.fundamentum-iot.com/v2/projects/<project-id>/functions/<function-id>:invoke
Authorization: Bearer $TOKEN
X-Function-Device: <serial-number>
<request body>
La réponse indique l'heure de début, la durée en secondes et la sortie. format vaut json lorsque la sortie est du JSON valide, unicode pour tout autre texte, et base64 pour une sortie binaire :
{
"status": "success",
"data": {
"started_at": "Thu, 22 Oct 2026 14:30:00 UTC",
"execution_time": 0.004,
"output": {"format": "json", "value": {"temperature": 23.1}}
}
}
| Statut | Signification |
|---|---|
404 |
La fonction n'existe pas dans ce projet |
408 |
L'exécution a atteint son délai d'expiration |
424 |
Aucun code n'a encore été téléversé |
5. Consulter l'historique d'exécution
fun functions executions list -n temp-decoder
Chaque exécution affiche sa source (http ou pubsub), started_at, execution_time, log et error. Les exécutions sont conservées pendant 7 jours.
Gérer les fonctions
| Tâche | Commande |
|---|---|
| Lister les fonctions d'un projet | fun functions list --project <project-id> |
| Modifier la configuration (délais d'expiration, variables, connecteurs, mise à l'échelle) | fun functions edit temp-decoder |
| Donner un nom local à une fonction existante | fun functions names add temp-decoder --project <project-id> --function <function-id> |
| Appeler directement l'API | fun api v2 functions <operation> --project-id <project-id> |
Étapes suivantes
- Référence de l'API dans Swagger UI : Functions
- Actions and custom encoders : utilisez une fonction comme encodeur pour vos appareils.
- Runtime and SDK : contrat du moteur d'exécution, cibles de compilation, SDK.
- Connectors : transmettez le topic de sortie de la fonction à vos systèmes.