Rechercher dans le blog

Automatiser les tâches d'administration de votre portail SIG avec Python

Bonjour à tous ! Aujourd'hui, je voulais revenir sur la démonstration d'automatisation des tâches d'administration d'un portail avec l'ArcGIS API for Python que j'ai réalisée à l'occasion de la conférence SIG 2022 lors de l'atelier "Vision et stratégie du système ArcGIS".

Vous pouvez regarder la vidéo sur Youtube ici. N'hésitez bien sûr pas à regarder l'atelier en entier si vous avez le temps car il permet d'obtenir une vision complète de l'écosystème que représente ArcGIS à l'heure actuelle. 

Revenons-en à nos pythons. Le notebook que je vais vous présenter est disponible comme d'habitude disponible sur mon Github.

 

Contexte et but du script 

Pourquoi utiliser l'API Python?

Les tâches d'administration d'un portail ArcGIS (Online ou Enterprise) peuvent parfois être répétitives et chronophages. Le but ici est de réduire le temps accordé à ces tâches en les automatisant avec l'API Python. Il est particulièrement intéressant de mettre en place ce type de script pour des actions qui reviennent régulièrement dans vos flux de travail.

Le  but du script sera ici d'automatiser la création de vues sur une couche, de groupes, l'inscription d'utilisateurs dans les groupes et la création de tableaux de bord pour une enseigne de magasin nommée Jardi,

Les besoins de Jardi

Cette enseigne possède des magasins dans toute la France, que vous pouvez voir sur la carte ci-dessous. Chacun de ces magasins sont répartis dans un des cinq secteurs commerciaux : Sud-Est, Nord-Est, Grand-Ouest, Centre-Sud-Ouest et Ile-de-France. Le script va parcourir la table attributaire de la couche pour récupérer les noms de ces différents secteurs, puis créer un groupe par secteur et y ajouter les responsables commerciaux. Il créera ensuite une vue par secteur commercial (qui permet de ne voir que les données de la couche qui correspondent au secteur) qu'il ajoutera également dans les groupes correspondant. Enfin, il créera un tableau de bord pour rendre plus simple la supervision des magasins du secteur par le responsable.

 

Nous utiliserons les données des magasins collectées sur les années 2021 et 2020. Des parties de ce script pourront être réutilisées chaque année pour mettre à jour les données. Il garantira également  l'homogénéité des tableaux de bord créés. Enfin, nous travaillons ici sur un nombre réduit de secteurs commerciaux, mais un script de ce type révèle aussi toutes ses capacités sur un plus grand nombre des données : imaginez par exemple le temps nécessaire pour créer une vue, un groupe et un tableau de bord par département !

L'environnement utilisé

Dans cette démonstration, j'ai utilisé l'environnement ArcGIS Notebook,  que vous pouvez retrouver aussi bien en tant que rôle serveur sur ArcGIS Enterprise ou par défaut sur ArcGIS Online, et qui offre une interface intégrée à votre portail pour créer vos scripts utilisant l'API Python ou ArcPy. 

Sachez qu'il est également possible d'installer l'API et de l'utiliser dans d'autres environnements, comme par exemple Jupyter Notebook ou JupyterLab si vous le souhaitez.

 

Analyse du script 

Connexion au gis, import des bibliothèques et gestion des avertissements

Le script commence par deux lignes permettant de ne pas afficher les avertissements dans le notebook grâce à la bibliothèque logging. Cette partie n'est pas indispensable, j'ai surtout fait cela pour éviter l'apparition de gros messages rouges durant la démo.

Nous continuons avec deux lignes beaucoup plus importantes, l'import de l'objet GIS à partir du module gis. L'objet GIS représente le SIG avec lequel vous travaillez, que ce soit ArcGIS Online ou une instance d'ArcGIS Enterprise. C'est cet objet qu'on utilise pour consommer et publier du contenu SIG et pour gérer les utilisateurs, les groupes et les datastores en tant qu'administrateur. Il est donc primordial car il représente le point d'entrée dans votre script Python lorsque vous utilisez l'API.

Nous importons également la bibliothèque pandas qui nous permettra de lire les tables attributaires en tant que pandas dataframe, et le module FeatureLayerCollection qui nous servira pour la création des vues.


Lecture et parcours de la couche

Nous allons utiliser la méthode .get() sur l'instance content de la classe ContentManager (disponible en tant que propriété de l'objet GIS) nous permet de récupérer la couche des enseignes à partir de son identifiant, et de la stocker dans une variable que l'on nomme enseignes. Notez que si vous connaissez uniquement le nom de la couche et pas son identifiant, il est possible de la retrouver avec la méthode .search() du ContentManager.

Une fois que la couche est accessible, nous allons utiliser la ligne ci-dessous pour obtenir un pandas dataframe à partir de la table attributaire. Cela nous permettra par la suite de lire les données de la table très facilement.

Nous allons parcourir une ce dataframe pour créer un dictionnaire où qui contiendra des couples clé/valeur pour associer chacun des responsables commerciaux à leur secteur commercial de manière automatique. Vous verrez par la suite que c'est ce dictionnaire que nous parcourons à chaque fois que nous voudrons boucler sur les secteurs ou sur les responsables.

Création des groupes et ajout des utilisateurs

Justement, il est temps de parcourir une première fois le dictionnaire pour créer les groupes. Dans la boucle, nous faisons appel à la méthode .create() de la classe GroupManager accessible via son instance groups. Nous allons renseigner un certain nombre d'arguments de la méthode (title, tags, description, snippet, access, is_invitation_only et thumbnail). Pour les chaines de caractère, nous faisons appel à la méthode .format() pour avoir des espaces réservés qui prendront la valeur d'une variable contenant le nom de chaque secteur à chaque itération de la boucle, ce qui nous permet d'adapter les noms, description, etc... au secteur.

Toujours dans la boucle, nous utilisons ensuite la méthode .search() de la classe UserManager pour retrouver le compte du manageur du secteur et l'ajouter au groupe qui vient d'être créé.

Je vois maintenant apparaître tous ces groupes dans mon portail.

Création des vues

Il faut maintenant alimenter ces différents groupes avec les données. Ici, je souhaite que les responsables de secteur aient accès uniquement aux données concernant les magasins de leur secteur. Pour cela, je vais utiliser des vues de couche d'entité qui permettent d'appliquer un filtre (le "viewDefinitionQuery" que vous retrouvez dans le code ci-dessous) sur les données.

On commence par créer une FeatureLayerCollection à partir de ma couche de magasin Jardi. En effet, nous travaillions jusqu'à présent avec cette couche en tant que Feature Service, mais la création d'une vue nécessite de travailler sur une FeatureLayerCollection.

En bouclant à nouveau dans le dictionnaire, on utilise ensuite la méthode .create_view() disponible dans le sous-module features.manager, que l'on applique sur la FeatureLayerCollection que l'on vient de créer. 

Pour l'instant, la vue contient l'entièreté de la couche, mais nous allons mettre à jour sa définition pour ne filtrer que les magasins qui nous intéressent. Pour cela, nous allons à nouveau faire appel à la méthode .search() pour récupérer l'identifiant de cette vue de couche nouvellement créée, et nous la transformons également en FeatureLayerCollection, de laquelle nous accédons ensuite directement à l'unique couche. Enfin, nous définissons quel sera le filtre (ici, le filtre ne gardera que les données dont le champ secteur_com contiendra la valeur égale au secteur commercial sur lequel se trouve l'itération de la boucle) et nous appliquons la méthode .update_definition() sur la couche de la FeatureLayer Collection créée à partir de la vue. Nous donnons en argument de cette méthode la définition du filtre définie juste au-dessus, ce qui aura pour effet de bien appliquer ce filtre dans la définition de la couche. Le responsable de secteur ne verra désormais que ses magasins.

Création des WebMaps et Dashboards associés

Pour faciliter  la visualisation des données, nous décidons d'afficher ces vues au sein de tableaux de bord ArcGIS Dashboards Classic, dont la création est fort heureusement pour nous API-sée.

Commençons par importer quelques modules supplémentaires : WebMap d'arcgis.mapping et Dashboard d'arcgis.apps.dashboard pour la création des WebMaps (nécessaires pour afficher une carte dans un Dashboard) et des Dashboards, ainsi qu'un certain nombre de modules permettant d'accéder aux éléments des Dashboards. Notez qu'arcgis.apps contient beaucoup d'autres modules et sous-modules vous permettant d'automatiser de nombreuses autres application de l'écosystème ArcGIS.

Nous parcourons une première fois le dictionnaire pour créer les différentes WebMaps. Nous commençons par récupérer la vue du secteur, puis nous créons une carte temporaire grâce à la méthode .map() dont nous donnons en argument une localisation ainsi qu'un niveau de zoom. Nous ajoutons la couche de vue à la carte. Nous définissons ensuite les différentes propriétés de la WebMap (titre, tags, description) avant sauvegarder la carte temporaire en tant que WebMap avec la méthode .save(), qui utilise en argument les propriétés fraîchement définies.

Nous parcourons ensuite une seconde fois le dictionnaire, cette fois-ci pour créer les Dashboards. Pour cela, nous récupérons les WebMaps créées pour chaque vues dont nous actionnons les popups et cachons les champs dont nous ne voulons pas. 

Nous configurons ensuite les tableaux de bord. Pour mieux appréhender cette étape, je vous conseille cet extrait vidéo commentant la création d'un Dashboards à partir de l'API Python.

Ainsi configurés, les Dashboards nous permettront de visualiser à gauche une carte représentant la vue du secteur commerciale, dont les points sont interrogeables grâce à la configuration des popups, et à droite une légende pour comprendre la symbologie ainsi que le chiffre d'affaire total du secteur pour les années 2020 et 2021.
 

Partage des vues, WebMaps et Dashboards dans les groupes

L'étape finale est de partager tout ce contenu dans mes différents groupes, pour que les responsables de secteur y aient accès. Un dernier parcours du dictionnaire nous permet, secteur par secteur, d'utiliser la méthode .get() pour récupérer la vue, la WebMap et le Dashboard du secteur. Puis, nous récupérons également le groupe du secteur avec la méthode .search(), et nous partageons le contenu avec la méthode .share() qui prend en argument la liste des groupes dans lesquels nous souhaitons faire le partage.

Je peux observer dans mon portail que mon groupe contient bien le contenu.

C'est tout pour aujourd'hui ! Je ne peux que vous inciter à vous laisser gagner par l'addiction à l'automatisation, et je vous laisse donc en compagnie de la documentation de l'API Python. On se retrouve dans le prochain article pour parler des nouvelles version des ArcGIS Maps SDKs for Native Apps et for Game Engines.



Aucun commentaire:

Enregistrer un commentaire