Ce document décrit l’API des tags v2 de Fess, avec laquelle les utilisateurs connectés gèrent leurs propres tags et les posent sur des documents. Pour l’enveloppe de réponse commune, le modèle d’erreur et les jetons CSRF, voir Vue d’ensemble de l’API.
L’URL de base est http://<Server Name>/api/v2/ (exemple en environnement local : http://localhost:8080/api/v2).
Note
Les tags sont désactivés par défaut. Pour les utiliser, définissez user.tag.enabled=true dans fess_config.properties. features.user_tag de /api/v2/ui/config indique l’état. Tant que les tags sont désactivés, les endpoints des tags répondent invalid_request (400) à une requête qui passe les contrôles CSRF et Origin et utilise une méthode prise en charge.
Fonctionnement des tags
Les tags sont gérés par utilisateur. L’utilisateur qui crée un tag en est le propriétaire, et le propriétaire est l’identifiant de connexion. Deux utilisateurs peuvent employer le même nom et avoir malgré tout deux tags distincts.
Seuls les utilisateurs connectés peuvent utiliser les tags. Chaque endpoint agit en tant qu’utilisateur de la session de connexion ; un jeton d’accès ne remplace pas une connexion. Un appelant non connecté reçoit
auth_required(401).Un nouveau tag est privé : seul son propriétaire le voit. Quand le propriétaire partage le tag, tout utilisateur connecté peut le voir et filtrer avec. Un utilisateur non connecté ne voit aucun tag, partagé ou non.
Seul le propriétaire peut modifier ou supprimer un tag, ou le poser sur des documents et l’en retirer. Un tag partagé d’un autre utilisateur sert uniquement à l’affichage et au filtrage. Les administrateurs gèrent tous les tags dans l’écran d’administration (voir Tag).
Un tag est posé sur l’URL d’un document : tous les documents indexés ayant cette URL le reçoivent. L’exception est un tag qui a un hôte virtuel : il n’est posé que sur les documents des paramètres d’exploration qui ont cet hôte virtuel, de sorte que la même URL explorée pour deux hôtes virtuels donne deux documents. Un tag sans hôte virtuel et un document sans hôte virtuel se comportent comme avant (voir Hôtes virtuels ci-dessous).
Chaque tag a deux identifiants.
valueLa valeur du tag,
base64url(nom):base64url(propriétaire)(UTF-8, sans remplissage), stockée dans le champtagde l’index. Traitez-la comme une valeur opaque servant à filtrer les résultats de recherche.idL’identifiant du tag, le SHA-256 de
valueen hexadécimal minuscule (64 caractères). Il s’indique dans des chemins comme/api/v2/tags/{tagId}. Renommer un tag change à la foisvalueetid.
Le nom d’un tag est normalisé en NFKC, les suites d’espaces sont réduites à une seule et les extrémités sont rognées. Le résultat doit compter de 1 à user.tag.name.max.length (par défaut : 50) caractères, et les noms contenant un caractère de contrôle ou de format (comme un caractère de largeur nulle ou un forçage bidirectionnel) sont refusés.
Hôtes virtuels
Lorsque des hôtes virtuels sont configurés, les tags suivent l’hôte virtuel de la requête, comme la facette des tags.
Un tag enregistre l’hôte virtuel de la requête qui l’a créé.
Pour une requête qui correspond à un hôte virtuel,
GET /api/v2/tagset le champaddabledes points d’accès de tags de document ne listent que les tags de l’appelant de cet hôte virtuel. Un tag d’un autre hôte virtuel, ou un tag sans hôte virtuel, n’est pas listé. Le renommer, le supprimer ou le poser sur un document paridrenvoienot_found(404). Le poser sur un document parnamerenvoieconflict(409), car un appelant n’a qu’un tag par nom pour l’ensemble des hôtes virtuels. Une requête qui ne correspond à aucun hôte virtuel voit tous les tags.Un tag d’un hôte virtuel n’est posé sur un document que si les paramètres d’exploration du document ont cet hôte virtuel. Cela s’applique lorsque le document est indexé à nouveau, lorsque la tâche
tag_updaters’exécute et lorsque le tag est posé sur le document. Un tag sans hôte virtuel et un document sans hôte virtuel ne sont pas limités.Un administrateur peut modifier l’hôte virtuel d’un tag, ou supprimer le tag, sur l’écran Type de tag (voir Tag).
Les tags dans la recherche
Tant que user.tag.enabled vaut true, l’API de recherche (/api/v2/search) traite les tags comme suit.
Chaque résultat porte dans
tagsles tags que l’appelant peut voir. Chaque entrée avalue,name,owner,mine(truelorsque l’appelant est le propriétaire) etshared(truepour un tag partagé).tagsest absent s’il n’y en a aucun. Le champ d’indextaglui-même n’est jamais renvoyé.facet.field=tagrenvoie dansfacet_fieldune facette des tags que l’appelant peut voir. Outrevalueetcount, chaque compartiment alabel(le nom du tag),owner,mineetshared.fields.tag=<valeur>restreint les résultats aux documents portant un tag. Passez tel quel levaluedestagsd’un résultat ou d’un compartiment de la facette.
Une condition sur les tags (fields.tag, tag:, ex_q, facet.query) ne correspond qu’à la valeur exacte d’un tag que l’appelant peut voir. La valeur d’un tag qu’il ne peut pas voir, ainsi que les conditions avec joker, par préfixe, approximatives et par plage, ne correspondent à rien. Un appelant non connecté ne reçoit ni tags ni facette de tags, et une condition sur les tags ne correspond à rien.
La valeur d’un tag contient :, il faut donc la placer entre guillemets dans une requête : q=tag:"<value>" fonctionne. Sans les guillemets, q=tag:<value> ne correspond à rien et ex_q=tag:<value> est refusé avec HTTP 400.
Un utilisateur voit au plus user.tag.visible.max.size (par défaut : 1000) tags, les siens en premier. Au-delà, les tags n’apparaissent ni dans tags des résultats ni dans la facette, mais peuvent toujours servir au filtrage.
Quand les documents reflètent les modifications
La création, la modification et la suppression des tags, ainsi que leur pose et leur retrait sur les documents, apparaissent immédiatement dans les endpoints des tags. Le champ tag des documents indexés, en revanche, est mis à jour via une file d’attente en mémoire que la tâche « Log Aggregator » (log_aggregator) applique en bloc chaque minute. Les résultats, la facette et les filtres reflètent donc une modification au bout d’une minute environ au plus. Après un renommage, les documents gardent l’ancienne valeur jusqu’au prochain traitement de la file, et le tag n’y est pas affiché entre-temps.
Pour la file d’attente et les tâches, voir Tag.
Lister les tags
Requête
| Méthode HTTP | GET |
| Point de terminaison | /api/v2/tags |
Renvoie les tags de l’appelant, par ordre de tri et par nom. Les tags partagés des autres utilisateurs ne sont pas inclus.
Réponse
En cas de succès (200), les champs suivants sont renvoyés directement sous response de l’enveloppe commune.
{
"response": {
"status": 0,
"tags": [
{
"id": "54788d242d35bdc53a2573eb7485b1d79c6c82a024c716ef6e27fc22064fb084",
"value": "YS1yZWxpcmU:Y2xhaXJl",
"name": "a-relire",
"shared": false,
"sort_order": 0,
"path_count": 3
}
]
}
}
tags | Les tags de l’appelant. Chacun a |
Tableau : Champs de réponse
Créer un tag
Requête
| Méthode HTTP | POST |
| Point de terminaison | /api/v2/tags |
Crée un tag de l’appelant. Comme requête qui modifie l’état, elle exige l’en-tête X-Fess-CSRF-Token (voir Vue d’ensemble de l’API).
Un utilisateur peut avoir au plus
user.tag.max.tags(par défaut :1000) tags. Au-delà, l’endpoint répondinvalid_request(400).Si l’appelant a déjà un tag de ce nom, l’endpoint répond
conflict(409). Qu’un autre utilisateur ait un tag de même nom n’a pas d’importance.
Envoyez Content-Type: application/json ; le corps fait au plus 1 Kio (1024 octets).
{
"name": "a-relire",
"shared": false
}
name | Nom du tag (str, obligatoire). |
shared | true rend le tag visible par tout utilisateur connecté (bool, par défaut : false). |
Tableau : Corps de la requête
Réponse
En cas de succès (200), tag directement sous response contient le nouveau tag, sous la forme d’une entrée de GET /api/v2/tags avec un path_count de 0.
Modifier un tag
Requête
| Méthode HTTP | PUT |
| Point de terminaison | /api/v2/tags/{tagId} |
Renomme un tag de l’appelant ou change son partage. L’en-tête X-Fess-CSRF-Token est requis.
Le corps contient
name,sharedou les deux.Un nouveau
namerenomme le tag, ce qui lui donne un nouvelidet une nouvellevalue. Les documents portant l’ancienne valeur reçoivent la nouvelle au prochain traitement de la file. Renommer vers un nom que l’appelant utilise déjà répondconflict(409) et laisse le tag inchangé.sharedchange seulement qui voit le tag ; aucun document n’est mis à jour. Passersharedàfalseconserve les rôles et groupes qu’un administrateur a ajoutés aux permissions.Un tag partagé d’un autre utilisateur répond
forbidden(403), et un tag que l’appelant ne peut pas voirnot_found(404).Une écriture qui perd plusieurs fois face à une autre mise à jour répond aussi
conflict(409).
{
"name": "relu",
"shared": true
}
En cas de succès (200), response contient tag (le tag modifié) et renamed (true si le tag a été renommé, auquel cas tag.id et tag.value sont nouveaux).
Supprimer un tag
Requête
| Méthode HTTP | DELETE |
| Point de terminaison | /api/v2/tags/{tagId} |
Supprime un tag de l’appelant. Les documents perdent sa valeur au prochain traitement de la file. L’en-tête X-Fess-CSRF-Token est requis. Un tag partagé d’un autre utilisateur répond forbidden (403), et un tag que l’appelant ne peut pas voir not_found (404).
En cas de succès (200), response contient id (l’identifiant du tag supprimé) et deleted (toujours true).
Obtenir les tags d’un document
Requête
| Méthode HTTP | GET |
| Point de terminaison | /api/v2/documents/{docId}/tags |
Renvoie les tags posés sur l’URL du document que l’appelant peut voir, ainsi que les tags de l’appelant qui n’y sont pas encore posés. Le document est recherché avec les rôles de l’appelant : un document qu’il ne peut pas rechercher répond not_found (404).
Réponse
En cas de succès (200), les champs suivants sont renvoyés directement sous response de l’enveloppe commune.
{
"response": {
"status": 0,
"doc_id": "a1b2c3d4e5f6",
"tags": [
{
"id": "54788d242d35bdc53a2573eb7485b1d79c6c82a024c716ef6e27fc22064fb084",
"value": "YS1yZWxpcmU:Y2xhaXJl",
"name": "a-relire",
"owner": "claire",
"mine": true,
"shared": false
},
{
"id": "41e429a7d0081e25390c3840268d736dca00250167bab94250389aee9e08e2ed",
"value": "c3BlY3M:Ym9i",
"name": "specs",
"owner": "bob",
"mine": false,
"shared": true
}
],
"addable": []
}
}
Tableau : Champs de réponse
Poser un tag sur un document
Requête
| Méthode HTTP | POST |
| Point de terminaison | /api/v2/documents/{docId}/tags |
Ajoute l’URL du document à un tag de l’appelant. L’en-tête X-Fess-CSRF-Token est requis.
Le corps (Content-Type: application/json, 1 Kio au plus) indique soit id, un tag existant, soit name, un nom de tag. Si les deux sont indiqués, id l’emporte.
{
"name": "a-relire"
}
Avec
name, si l’appelant n’a aucun tag de ce nom, un tag privé est créé et posé. Le nouveau tag compte dansuser.tag.max.tags.Un tag peut être posé sur au plus
user.tag.max.paths(par défaut :10000) URL. Au-delà, l’endpoint répondinvalid_request(400).L”
idd’un tag d’un autre utilisateur répondforbidden(403) si l’appelant peut voir le tag, etnot_found(404) sinon.En cas de succès, la réponse contient les champs de « Obtenir les tags d’un document » plus
addedettag. Les endpoints des tags montrent le tag immédiatement ; les résultats de recherche des documents ayant cette URL le reflètent au prochain traitement de la file (environ une minute plus tard).
Retirer un tag d’un document
Requête
| Méthode HTTP | DELETE |
| Point de terminaison | /api/v2/documents/{docId}/tags/{tagId} |
Retire l’URL du document du tag de l’appelant indiqué par tagId. L’en-tête X-Fess-CSRF-Token est requis. Un tag d’un autre utilisateur répond forbidden (403) si l’appelant peut le voir, et not_found (404) sinon. En cas de succès, la réponse contient les champs de « Obtenir les tags d’un document » plus removed.
Réponses d’erreur
Pour le détail du modèle d’erreur, voir Vue d’ensemble de l’API. Les endpoints des tags renvoient les statuts HTTP suivants.
Tableau : Réponses d’erreur
Paramètres
Les paramètres suivants de fess_config.properties règlent les tags.
| Propriété | Description | Par défaut |
|---|---|---|
user.tag.enabled | Indique si les utilisateurs connectés peuvent utiliser les tags. | false |
user.tag.name.max.length | Longueur maximale d’un nom de tag, en points de code. | 50 |
user.tag.max.tags | Nombre maximal de tags qu’un utilisateur peut posséder. | 1000 |
user.tag.max.paths | Nombre maximal d’URL sur lesquelles un tag peut être posé. | 10000 |
user.tag.queue.max.size | Nombre maximal de modifications gardées en mémoire jusqu’à ce qu’elles atteignent les documents. Une modification au-delà est abandonnée avec un journal WARN. | 10000 |
user.tag.process.batch.size | Nombre d’URL mises à jour par requête en bloc lors de l’application des modifications aux documents. | 100 |
user.tag.visible.max.size | Nombre maximal de tags visibles par un utilisateur dans une recherche. | 1000 |