Vérification de la validité des fichiers au chargement

Modifié par Aurelie Bertrand le 2024/11/04 10:55

Il est possible de réaliser une vérification sur les fichiers (sanity check) ajoutés via les tableaux de bord (contenu additionnel Bouton ou Documents) ou le Studio pour s’assurer qu’ils répondent bien à certains critères : nom, extension, contenu, etc.

Pour cela, on va configurer dans les paramètres serveurs, un script (Python, Shell ou autre) qui sera exécuté à chaque ajout de fichier. Si aucun script n’est configuré, le comportement par défaut s'applique : aucune vérification n’est réalisée sur les fichiers ajoutés.

❗ Si la fonctionnalité est activée, tous les fichiers ajoutés (que ce soit via les tableaux de bord ou le Studio) sont vérifiés.
L’idée est alors dans le script de vérifier uniquement les fichiers ajoutés dans certains serveurs de documents spécifiques. Si cela n’est pas fait, les ajouts d’autres fichiers comme des cartes JSON, des modèles HTML (pour les fabriques et/ou rapports HTML), d’images peuvent être bloqués.

Fonctionnement

❗ Ne fonctionne que pour l’ajout de fichiers vers des serveurs de documents de type file system.

Il faut tout d'abord configurer :

  • Le script dans les paramètres serveurs
  • Un contenu additionnel (Bouton ou Documents) dans les tableaux de bord pour autoriser les utilisateurs à ajouter des fichiers dans un certain dossier cible (serveur de documents).

Pour plus de détails, consultez le paragraphe Configuration ci-dessous.

Une fois ces configurations effectuées, à chaque ajout de fichier – via les éléments de contenus additionnels configurés – DigDash fera appel au script.

  1. Avant exécution du script : le fichier est placé dans le répertoire “temp” de l’utilisateur.
  2. À l'exécution du script :
    • Si le fichier est supprimé ou déplacé du dossier “temp” de l’utilisateur avant la fin de l'exécution, l’ajout ne se fait pas dans le dossier cible.
      ➡ le fichier ne correspond pas aux critères attendus vérifiés dans le script.
    • Si le fichier n’est pas supprimé ou déplacé du dossier “temp” de l’utilisateur à la fin de l’exécution, le fichier est ajouté au dossier cible.

Un message s'affiche pour indiquer le statut du fichier.

Configuration

Configuration dans DigDash

Paramètres serveur

  1. Allez dans Configuration -> Paramètres serveur.
  2. Allez dans le menu Exports et API -> Hook pour l'envoi de fichiers.
    Hook
  3. Dans le champ Chemin de l'exécutable, entrez le chemin vers le script à exécuter.
    Sous Windows, on ne peut pas directement faire appel au script Python, il faut passer par un fichier .bat.

Tableaux de bord

Dans les tableaux de bord, ajoutez un contenu additionnel Bouton ou Documents pour autoriser les utilisateurs à ajouter des fichiers dans un certain dossier cible.
Consultez le paragraphe Ajouter des éléments additionnels pour plus de détails.

Configuration du Script Python

À chaque appel du script, celui-ci est exécuté avec 6 paramètres. L'ordre est important pour les utiliser dans l'exécutable.

  • sys.argv[0] : le chemin d'accès à l'exécutable
  • sys.argv[1] : le nom d'utilisateur connecté qui envoie le fichier
  • sys.argv[2] : le chemin du dossier cible (exemple un serveur de documents) 
  • sys.argv[3] : le nom du fichier envoyé
  • sys.argv[4] : le chemin du fichier temporaire qui sera envoyé au dossier cible à la fin de l'exécutable s’il n’y a pas d'erreur
  • sys.argv[5] : l'identifiant du CMS

Pour indiquer le statut du fichier, les codes de sortie suivants sont utilisés :

  • sys.exit(0) : Le fichier a été correctement intégré ➡ Affichage du message standard indiquant que le fichier a été correctement intégré
  • sys.exit(n différent de 0) : Le fichier a été rejeté ➡ Affichage du message personnalisé du script (via un print())
    Par exemple, sys.exit(1).

Exemple de script :

import pandas as pd #Need to install xlrd library
import shutil
import sys
import os
from datetime import datetime, date

filename = sys.argv[3]
filepath = sys.argv[4]
user = sys.argv[1]
destination_error_path = "C:/Users/lovaraza/Desktop/atelier/dev/hookup/rejected/"

#Delete file on error
def delete_file(filepath):
    os.remove(filepath)

#Move file on error 
def move_file(filepath, destination_error_path, filename):
    shutil.move(filepath,destination_error_path+filename.replace(os.path.splitext(filename)[1],datetime.now().strftime("_%Y%m%d%H%M%S_by_user_" + user + os.path.splitext(filename)[1])))
   #shutil.move(filepath,destination_error_path+filename.replace(".xls",date.today().strftime("_%Y%m%d_%H%M%S.xls")))

#Format : KPI_YYYY.xls 
#Content : "Date", "Category", "Nb"
def check_file(filename, destination_error_path, filepath):
    error_message = ''

   #Check file extension
   if os.path.splitext(filename)[1] != ".xls":
        error_message += "*** Error in the file type. Xls file expected. "
   else:
        filename_split = filename.replace(".xls","").split("_")

       #Check filename format
       if len(filename_split) != 2:
            error_message += '*** The file does not have the 2 parameters expected. '
       else:
           #Check 1st parameter 
           if filename_split[0] != "KPI" :
                error_message += "*** Error in the filename. First parameter should be equal to KPI. "

           #Check 2nd parameter 
           try:
               if int(filename_split[1]) < 2000 or int(filename_split[1]) > 2023:
                    error_message += "*** Error in the filename. Second parameter should be an integer representing the year in yyyy format and between 2000 and 2023 included (ex: 2022). "
           except:
                error_message += "*** Error in the filename. Second parameter should be an integer representing the year in yyyy format and between 2000 and 2023 included (ex: 2022). "

            df = pd.read_excel(filepath)
            column_order = ["Date", "Category", "Nb"]

           #Check column order
            index = 0
           for i in df.columns:
               if column_order[index] != i:
                    index_column = index + 1
                    error_message += "*** Error in the name of column " + str(index_column) + " : " + column_order[index] + " is expected instead of " + i + " . "
                index += 1

   if error_message != '':
       #delete_file(filepath)
        error_message += " *** File renamed " + filename.replace(os.path.splitext(filename)[1],datetime.now().strftime("_%Y%m%d%H%M%S_attempt_by_" + user + os.path.splitext(filename)[1])) + " and moved to " + destination_error_path + "."
        move_file(filepath, destination_error_path, filename)
       print(error_message)
        sys.exit(1)
   else:
        sys.exit(0)

check_file(filename, destination_error_path, filepath)