Le parsing s'exécute sans aucune erreur. par contre, je n’arrive pas à accéder à des champs à l'intérieur des brackets [ ], par exemple le champservices.id. J'ai tenté un formatage manuellement de mon JSON, sur un petit exemple, pour enlever les [ ] et ça marche. La solution manuelle est très lourde et trop risquée, c'est même une solution pas propre du tout, car j'ai des données non structurées et très compliquées à appréhender.
Je pense qu'il doit exister une solution triviale à ce problème, étant donné que les [ ] font parties du format JSON. Mais en cherchant sur internet, je ne trouve rien à ce sujet.
En sortie (stdout, élasticsearch, ...), est ce que le tableau json est bien la et bien structuré comme attendu?
Peux tu donner la configuration des filtres derrière que tu utilises pour travailler sur le tableau json ?
Remarque : quand je cherche à gauche le champ en question pour afficher sa valeur, pour chaque ligne, il ne le trouve pas ( car il me propose que les champs non vides), d'ailleurs quand je force pour qu'il m'affiche même les champs non vides, le champ en question est mappé, mais sa valeur est non affichée, comme tu peux le voir sr cette capture.
le comble c'est que si on exploite ce mapping dans un dashboard, il le trouve et affiche ses valeurs. mais quand on veut l'exploiter sur discover ou logstash ça ne marche pas.
Je me demande si il faudrait une syntaxe plus adaptée pour ce problème en particulier ?
OK.
Bon, globalement, saches que la suite Elastic n'est pas très copain avec les tableaux d'objets.
Pour ta conf Logstash, si ton but est d'anonymiser le champ "balance" de ton tableau d'objets, voici comment tu peux faire :
ruby {
code => "
accounts = event.get('[RequestHeader][ResponseBody][accounts]')
accounts.each do |account|
account['balance'] = '*****'
end
event.set('[RequestHeader][ResponseBody][accounts]', accounts)
"
}
Ensuite, pour que ton tableau d'objets soit correctement interprété, il faut définir le mapping suivant dans Elasticsearch :
{
"type": "nested"
}
Enfin, il faut utiliser minimum Kibana 7.6 pour avoir les tableaux d'objet "nested" supportés, au moins dans la barre de recherche avec la syntaxe KQL.
et dans chaque branche il y a un problème de mapping. Est ce qu'il faut du coup les faire en cascade, c'est à dire, dans l'exemple que je t'ai donné, traité [cardShipment] en premier puis traiter ses fils ainsi de suite jusqu'à ce qu'on arrive à la feuille ?
car en réalité le parsing de json commence après la RepsonseBody.
Pour appliquer le mapping "nested" dans Elasticsearch, il faut le postitionner dans le mapping de l'index template poussé par Logstash, dans la sortie "elasticsearch".
Tu as un champ "template", qui te permet de personnaliser le mapping Elasticsearch de l'index créé.
Tu peux notamment définir dans un index template, des dynamic templates, permettant de customiser le mapping d'un champ basé sur son nom ou son type.
Côté Logstash, je t'ai montré une boucle d'exemple sur "accounts" qui anonymise le champ "balance", mais tu peux faire autant de boucles que nécessaire.
Après, pour tous les champs "à plat" (qui ne sont pas dans un tableau d'objets), tu peux simplement utiliser le filtre "mutate".
De manière générale, je ne te conseille pas vraiment d'avoir beaucoup de tableaux d'objets dans Elasticsearch et encore moins des tableaux dans des tableaux.
Si tu as bcp de tableaux d'objets, tu peux éventuellement utiliser le filtre "split" pour spliter ton document en autant de documents que d'entrées de tableau.
Car j'ai essayé cette dernière écriture sur tous mes champs à anonymiser et ça marche sauf que j'ai un ralentissement important. Pour info, pour ce flux seulement, j'ai 220 champs à anonymiser.
Ps: je n'ai pas encore testé d'ajouter le mapping " nested" à ce que j'ai fait.
Le script ruby est là pour parcourir les entrées du tableau d'objets, et mettre à jour une (ou plusieurs) propriété(s) de chaque entrée du tableau.
Si tu n'avais pas de tableau d'objets, un simple "mutate" aurait suffi.
Ainsi, "balance" n'est pas un champ de "accounts", mais un champ de chaque entrée du tableau "accounts".
Je t’avoue que je n’arrive pas à faire la différence là : « balance" n'est pas un champ de "accounts", mais un champ de chaque entrée du tableau "accounts". »
Ce que j’avais compris à la base c’est que le script Ruby récupère le sous arbre « le fils » de accounts, et « account » c’est le mapping jusqu’à « accounts », c’est à dire [requestheader]...[accounts]. Du coup, pour moi, opter pour cette écriture ou celle que j’ai proposée est la même chose. Et ce qui m’intriguait c’est le « nested », que je ne comprends pas jusqu’à maintenant.
Aussi quand j’ai testé avec Ruby sur plus de 200 champs, que j’ai anonymisé, la taille de mon index a augmenté de presque 20% et dans discover, dans kibana, les requêtes sont tres tres lentes...
Apache, Apache Lucene, Apache Hadoop, Hadoop, HDFS and the yellow elephant
logo are trademarks of the
Apache Software Foundation
in the United States and/or other countries.