Comprendre les colonnes, les types de logs, les expressions et les recherches avancées.
Ce document explique comment lire les logs LogsCord, quelles colonnes existent, quels types de logs sont disponibles et comment écrire des expressions de recherche.
LogsCord est un moteur d'audit pour Discord.
Chaque événement enregistré devient une ligne de log. Une ligne contient :
message_delete, member_role_add, voice_join, etc.) ;extra.L'utilisateur peut rechercher avec :
Expression.| Colonne | Type | Description | Exemple |
|---|---|---|---|
id | nombre | Identifiant interne/chronologique du log. | 1780707318980 |
type | texte | Type d'événement Discord. | "member_role_add" |
guildId | texte | ID du serveur Discord. Filtré automatiquement par le serveur sélectionné. | "758391511338844221" |
executor | texte/null | ID de l'utilisateur qui a effectué l'action, quand connu. | "1341946276601663511" |
target | texte/null | ID de l'utilisateur, rôle ou objet ciblé, quand connu. | "1280262760797704245" |
channel | texte/null | ID du salon principal lié au log. | "112233445566778899" |
from | texte/null | Ancienne valeur, souvent ancien salon vocal ou ancienne cible. | "111111111111111111" |
to | texte/null | Nouvelle valeur, souvent nouveau salon vocal ou nouvelle cible. | "222222222222222222" |
role | texte/null | ID de rôle quand le log concerne un rôle unique. | "333333333333333333" |
createdAt | nombre | Date du log en timestamp millisecondes. | 1780707318980 |
extra | JSON | Détails variables selon le type de log. | { "content": "hello" } |
| Cas | Champ utile |
|---|---|
| Chercher un type d'événement | type |
| Chercher ce qu'un modérateur a fait | executor |
| Chercher ce qui est arrivé à un membre | target ou executor selon le type |
| Chercher dans un salon | channel, from, to |
| Chercher par période | sélecteur de période ou createdAt |
| Chercher dans le contenu d'un message | extra.content |
| Chercher par ID de message | extra.messageId |
| Chercher dans un tableau JSON | extra.roles[*].id, extra.attachments[*].url, etc. |
La liste ci-dessous correspond aux types affichables/recherchables par LogsCord côté client. Certains types peuvent dépendre des événements réellement collectés par le bot, de ses permissions Discord et des modules activés.
| Type | Nom affiché | Description |
|---|---|---|
auto_moderation_rule_create | Création de règle de modération automatique | Une règle AutoMod Discord a été créée. |
auto_moderation_rule_update | Mise à jour de règle de modération automatique | Une règle AutoMod Discord a été modifiée. |
auto_moderation_rule_delete | Suppression de règle de modération automatique | Une règle AutoMod Discord a été supprimée. |
auto_moderation_flag_to_channel | Signalement en salon | AutoMod a signalé un message dans un salon. |
auto_moderation_block_message | Message bloqué par modération automatique | AutoMod a bloqué un message. |
automod_action_execution | Action effectuée par la modération automatique | AutoMod a exécuté une action. |
| Type | Nom affiché | Description |
|---|---|---|
message_create | Message envoyé | Un message a été envoyé. |
message_edit | Message modifié | Un message a été modifié. |
message_delete | Message supprimé | Un message a été supprimé. |
message_bulk_delete | Suppression massive de messages | Plusieurs messages ont été supprimés en masse. |
message_reaction_add | Ajout de réaction | Une réaction a été ajoutée à un message. |
message_reaction_remove | Retrait de réaction | Une réaction a été retirée d'un message. |
| Type | Nom affiché | Description |
|---|---|---|
voice_join | Connexion vocale | Un membre a rejoint un salon vocal. |
voice_move | Déplacement vocal | Un membre a changé de salon vocal. |
voice_leave | Déconnexion vocale | Un membre a quitté un salon vocal. |
voice_state_update | Mise à jour de l'état vocal | L'état vocal d'un membre a changé. |
voice_state_video | État vidéo activé/désactivé | La caméra d'un membre a été activée ou désactivée. |
voice_state_stream | État streaming activé/désactivé | Le streaming d'un membre a été activé ou désactivé. |
member_move | Déplacement de membre | Un membre a été déplacé. |
member_disconnect | Déconnexion de membre | Un membre a été déconnecté d'un salon vocal. |
| Type | Nom affiché | Description |
|---|---|---|
member_join | Arrivée d'un membre | Un membre a rejoint le serveur. |
member_leave | Départ d'un membre | Un membre a quitté le serveur. |
member_timeout_create | Timeout créé | Un timeout a été appliqué. |
member_timeout_cancel | Timeout annulé | Un timeout a été annulé. |
member_timeout_update | Timeout mis à jour | Un timeout a été modifié. |
member_ban_add | Bannissement | Un membre a été banni. |
member_ban_remove | Débannissement | Un membre a été débanni. |
member_kick | Expulsion de membre | Un membre a été expulsé. |
member_update_guild_avatar | Changement d'avatar de guilde | L'avatar serveur d'un membre a changé. |
member_update_guild_banner | Changement de bannière de guilde | La bannière serveur d'un membre a changé. |
member_update_nickname | Changement de surnom | Le surnom serveur d'un membre a changé. |
member_role_add | Ajout de rôle | Un ou plusieurs rôles ont été ajoutés à un membre. |
member_role_remove | Suppression de rôle | Un ou plusieurs rôles ont été retirés d'un membre. |
member_mute_activated | Activation du mute | Le mute vocal serveur a été activé. |
member_mute_deactivated | Désactivation du mute | Le mute vocal serveur a été désactivé. |
member_deaf_activated | Activation du deaf | Le deaf vocal serveur a été activé. |
member_deaf_deactivated | Désactivation du deaf | Le deaf vocal serveur a été désactivé. |
| Type | Nom affiché | Description |
|---|---|---|
user_update_username | Changement de nom d'utilisateur | Le username Discord d'un utilisateur a changé. |
user_update_globalname | Changement de nom global | Le nom global Discord a changé. |
user_update_avatar | Changement d'avatar | L'avatar Discord a changé. |
user_update_banner | Changement de bannière | La bannière Discord a changé. |
presence_update | Mise à jour de la présence | Le statut ou les activités d'un membre ont changé. |
| Type | Nom affiché | Description |
|---|---|---|
channel_create | Création de salon | Un salon a été créé. |
channel_update | Mise à jour de salon | Un salon a été modifié. |
channel_delete | Suppression de salon | Un salon a été supprimé. |
channel_position_update | Mise à jour de la position d'un salon | L'ordre des salons a changé. |
channel_overwrite_create | Création d'une autorisation de salon | Une permission spécifique de salon a été créée. |
channel_overwrite_update | Mise à jour d'une autorisation de salon | Une permission spécifique de salon a été modifiée. |
channel_overwrite_delete | Suppression d'une autorisation de salon | Une permission spécifique de salon a été supprimée. |
| Type | Nom affiché | Description |
|---|---|---|
role_create | Création de rôle | Un rôle a été créé. |
role_update | Mise à jour de rôle | Un rôle a été modifié. |
role_delete | Suppression de rôle | Un rôle a été supprimé. |
role_position_update | Mise à jour de la position d'un rôle | L'ordre des rôles a changé. |
| Type | Nom affiché | Description |
|---|---|---|
guild_available | Serveur disponible | Le bot a vu le serveur comme disponible. |
bot_add | Ajout de bot | Un bot a été ajouté au serveur. |
| Type | Nom affiché | Description |
|---|---|---|
emoji_create | Création d'émoji | Un émoji a été créé. |
emoji_update | Mise à jour d'émoji | Un émoji a été modifié. |
emoji_delete | Suppression d'émoji | Un émoji a été supprimé. |
invite_create | Création d'une invitation | Une invitation Discord a été créée. |
invite_update | Mise à jour d'une invitation | Une invitation Discord a été modifiée. |
invite_delete | Suppression d'une invitation | Une invitation Discord a été supprimée. |
Ces types existent dans le rendu client, mais peuvent provenir d'anciens imports, d'intégrations ou de données historiques.
| Type | Nom affiché | Description |
|---|---|---|
sanction_blacklist | Blacklist | Blacklist custom historique. |
sanction_unblacklist | Unblacklist | Retrait de blacklist custom historique. |
sanction_mute | Sanction: Mute | Mute custom historique. |
sanction_unmute | Sanction: Unmute | Retrait de mute custom historique. |
sanction_warn | Sanction: Avertissement | Avertissement custom historique. |
utils_voice_find | =find (Crowbot) | Log vocal utilitaire historique. |
utils_voice_join | =join (Crowbot) | Log vocal utilitaire historique. |
utils_voice_move | =mv (Crowbot) | Log vocal utilitaire historique. |
extra Fréquentesextra contient les détails qui changent selon le type de log.
| Chemin | Types fréquents | Description |
|---|---|---|
extra.content | message_create, message_edit, message_delete | Contenu textuel du message. |
extra.messageId | logs messages | ID Discord du message. |
extra.attachments | logs messages | Liste des pièces jointes. |
extra.attachments[*].url | logs messages | URL d'une pièce jointe. |
extra.embeds | logs messages | Embeds du message. |
extra.mentions.users | logs messages | IDs des utilisateurs mentionnés. |
extra.mentions.roles | logs messages | IDs des rôles mentionnés. |
extra.roles | member_role_add, member_role_remove | Liste des rôles ajoutés/retirés. |
extra.roles[*].id | rôles membre | ID d'un rôle dans la liste. |
extra.roles[*].name | rôles membre | Nom d'un rôle dans la liste. |
extra.reason | modération | Raison fournie par Discord/audit log. |
extra.duration | timeout | Durée d'un timeout. |
extra.oldPresence | presence_update | Ancienne présence. |
extra.newPresence | presence_update | Nouvelle présence. |
Dans l'onglet Filtrer les logs, le mode Expression permet d'écrire une requête avancée.
txtchamp opérateur valeurExemples :
txttype == "message_delete"txtexecutor == "123456789012345678"txttype == "member_role_add" and target == "123456789012345678"| Valeur | Exemple | Notes |
|---|---|---|
| Texte | "message_delete" | Toujours entre guillemets doubles. |
| Nombre | 1780707318980 | Utile pour id ou createdAt. |
| Ensemble | { "a", "b", "c" } | Utilisé avec in ou not in. |
Les ensembles acceptent actuellement des chaînes.
| Champ | Type | Optimisé ClickHouse | Description |
|---|---|---|---|
id | nombre | oui | Identifiant du log. |
type | texte | oui | Type du log. |
guildId | texte | oui | Serveur. Normalement géré par LogsCord. |
executor | texte | oui | Auteur de l'action. |
target | texte | oui | Cible de l'action. |
channel | texte | oui | Salon principal. |
from | texte | oui | Ancienne valeur/salon. |
to | texte | oui | Nouvelle valeur/salon. |
role | texte | oui | Rôle principal. |
createdAt | nombre | oui | Timestamp du log. |
extra.content | texte | oui | Contenu de message. |
extra.messageId | texte | oui | ID du message. |
extra.<array>[*] | texte | oui si comparaison simple | Projection dans un tableau JSON scalaire de extra. |
extra.<array>[*].<field> | texte | oui si comparaison simple | Projection d'un champ dans un tableau d'objets JSON de extra. |
| Opérateur | Description | Exemple |
|---|---|---|
and | Les deux conditions doivent être vraies. | type == "message_delete" and executor == "123" |
or | Au moins une condition doit être vraie. | type == "message_delete" or type == "message_edit" |
not | Inverse une condition. | not is_bot(executor) |
== | Égal à. | type == "member_join" |
!= | Différent de. | type != "presence_update" |
> | Supérieur à. | createdAt > 1780000000000 |
>= | Supérieur ou égal à. | createdAt >= 1780000000000 |
< | Inférieur à. | createdAt < 1781000000000 |
<= | Inférieur ou égal à. | createdAt <= 1781000000000 |
in | La valeur est dans un ensemble. | type in { "message_delete", "message_edit" } |
not in | La valeur n'est pas dans un ensemble. | type not in { "presence_update" } |
Aliases acceptés :
| Alias | Équivalent |
|---|---|
eq | == |
ne | != |
gt | > |
ge | >= |
lt | < |
le | <= |
| Fonction | Arguments | Optimisée ClickHouse | Description | Exemple |
|---|---|---|---|---|
lower(value) | 1 | oui | Convertit une valeur texte en minuscules. | lower(extra.content) == "hello" |
contains(value, needle) | 2 | oui | Vérifie qu'un texte contient une sous-chaîne. | contains(extra.content, "discord.gg") |
match(value, regex) | 2 | oui | Vérifie une expression régulière. | match(extra.content, "discord\\\\.gg") |
exists(value) | 1 | oui | Vérifie qu'une valeur existe/n'est pas vide. | exists(extra.messageId) |
length(value) | 1 | oui | Retourne la taille d'une chaîne ou d'un tableau. | length(extra.embeds) > 0 |
is_bot(userId) | 1 | non | Vérifie si l'ID correspond à un bot du serveur. | not is_bot(executor) |
roles(userId) | 1 | non | Retourne les rôles actuels du membre sous forme { id, name }[]. | roles(executor)[*].id in { "ROLE_ID" } |
Important : is_bot() demande une vérification runtime côté serveur. Une expression qui utilise is_bot() peut être moins optimisable qu'une expression purement SQL.
roles() utilise les rôles actuels du membre sur le serveur, pas forcément les rôles historiques au moment exact du log. Pour les logs member_role_add et member_role_remove, préférer extra.roles[*].id si l'objectif est de filtrer les rôles concernés par l'action.
extraLes projections permettent de chercher dans un tableau JSON stocké dans extra.
Syntaxe :
txtextra.<cheminDuTableau>[*]
extra.<cheminDuTableau>[*].<champ>Exemples :
txtextra.roles[*].id in { "1483959882142060624" }txtextra.mentions.users[*] in { "1464758198291529953" }txtextra.roles[*].name == "Majeur"txtextra.attachments[*].url == "https://example.com/image.png"txtextra.audit.roles[*].meta.id in { "42" }Règles :
| Règle | Détail |
|---|---|
| Racine obligatoire | La projection doit commencer par extra. |
| Une projection maximum | Une seule partie [*] dans le chemin. |
| Champ final optionnel | Utiliser extra.roles[*].id pour un tableau d'objets et extra.mentions.users[*] pour un tableau de valeurs scalaires. |
| Comparaison supportée | ==, !=, in, not in. |
[i]Il est aussi possible de récupérer un élément précis avec un index numérique.
Les index commencent à 0.
txtextra.embeds[0].description == "raid"
contains(extra.embeds[0].description, "raid")
extra.content[0] == "!"Si la valeur est un tableau, [i] récupère l'élément à l'index demandé. Si la valeur est une chaîne, [i] récupère le caractère correspondant.
| Objectif | Expression |
|---|---|
| Messages supprimés | type == "message_delete" |
| Messages modifiés ou supprimés | type in { "message_delete", "message_edit" } |
| Messages contenant une invitation Discord | contains(extra.content, "discord.gg") |
| Messages avec au moins un embed | length(extra.embeds) > 0 |
| Premier embed contenant un texte | contains(extra.embeds[0].description, "raid") |
| Message précis par ID | extra.messageId == "123456789012345678" |
| Message supprimé par un utilisateur précis | type == "message_delete" and executor == "123456789012345678" |
| Objectif | Expression |
|---|---|
| Tous les ajouts de rôles | type == "member_role_add" |
| Tous les retraits de rôles | type == "member_role_remove" |
| Ajout d'un rôle précis | type == "member_role_add" and extra.roles[*].id in { "1483959882142060624" } |
| Retrait d'un rôle précis | type == "member_role_remove" and extra.roles[*].id in { "1483959882142060624" } |
| Rôle par nom | extra.roles[*].name == "Majeur" |
| Objectif | Expression |
|---|---|
| Bans | type == "member_ban_add" |
| Débans | type == "member_ban_remove" |
| Kicks | type == "member_kick" |
| Timeouts créés | type == "member_timeout_create" |
| Sanctions d'un modérateur | type in { "member_ban_add", "member_kick", "member_timeout_create" } and executor == "123456789012345678" |
| Objectif | Expression |
|---|---|
| Connexions vocales | type == "voice_join" |
| Déconnexions vocales | type == "voice_leave" |
| Déplacements vocaux | type == "voice_move" |
| Activité vocale d'un membre | type in { "voice_join", "voice_leave", "voice_move" } and target == "123456789012345678" |
| Mouvements vers un salon précis | type == "voice_move" and to == "123456789012345678" |
| Objectif | Expression dataset |
|---|---|
| Membres arrivés | type == "member_join" |
| Membres partis | type == "member_leave" |
| Messages envoyés | type == "message_create" |
| Rôle spécifique ajouté | type == "member_role_add" and extra.roles[*].id in { "1483959882142060624" } |
| Modération hors bots | type in { "member_ban_add", "member_kick", "member_timeout_create" } and not is_bot(executor) |
| Actions faites par quelqu'un qui a actuellement un rôle | roles(executor)[*].id in { "1483959882142060624" } |
| Actions visant quelqu'un qui a actuellement un rôle | roles(target)[*].id in { "1483959882142060624" } |
L'ordre logique est :
1. parenthèses ; 2. not ; 3. comparaisons ; 4. and ; 5. or.
Utiliser des parenthèses dès qu'il y a un doute :
txt(type == "message_delete" or type == "message_edit") and executor == "123"Sans parenthèses, une expression complexe peut être correcte techniquement mais ambiguë pour un humain.
Certaines expressions sont valides mais ne filtrent rien. LogsCord les nettoie avant de générer la requête SQL.
| Expression | Comportement |
|---|---|
| champ vide | Recherche normale sans filtre expression. |
"" | Recherche normale sans filtre expression. |
"texte" | Recherche normale sans filtre expression. |
123 | Recherche normale sans filtre expression. |
type == "message_create" and "" | Garde seulement type == "message_create". |
type == "message_create" or "" | Devient une recherche normale sans filtre expression. |
Un champ nu est converti en test d'existence :
txtextra.contentéquivaut à :
txtexists(extra.content)| Sujet | Recommandation |
|---|---|
| Performance | Toujours commencer par type == ... ou type in { ... } quand possible. |
| Période | Utiliser le sélecteur de période de l'interface pour réduire le volume. |
| Regex | Garder les regex simples. |
is_bot() | À utiliser si nécessaire, mais moins optimisable. |
extra | Préférer les chemins connus comme extra.content, extra.messageId, extra.roles[*].id. |
| Dashboards | Éviter les expressions runtime non optimisables pour les grands volumes. |
Limites techniques actuelles :
extra ;Une réponse de recherche contient généralement :
| Champ | Description |
|---|---|
result | Liste des logs trouvés. |
members | Membres résolus pour affichage. |
channels | Salons résolus pour affichage. |
explanation | Détails techniques de la recherche. |
explanation.expression.ast | Arbre de l'expression. Utile pour debug. |
explanation.expression.plan.prewhere | Partie optimisée en PREWHERE. |
explanation.expression.plan.where | Partie optimisée en WHERE. |
explanation.expression.plan.residual | Partie évaluée côté Node après ClickHouse. |
explanation.expression.sql | Requête SQL générée avec noms de paramètres. |
Pour un utilisateur final, le plus important est result. Pour diagnostiquer une recherche lente ou incorrecte, regarder plan.residual.
Expressions les plus utiles :
txttype == "message_delete"txttype in { "message_delete", "message_edit" } and executor == "USER_ID"txtcontains(extra.content, "discord.gg")txttype == "member_role_add" and extra.roles[*].id in { "ROLE_ID" }txttype in { "member_ban_add", "member_kick", "member_timeout_create" } and not is_bot(executor)