diff --git a/README.md b/README.md index 176e2901a..1040e9fa2 100644 --- a/README.md +++ b/README.md @@ -21,8 +21,18 @@ docker-compose run web scripts/migrate.sh **Load demo data** -Edit file `geocity/apps/submissions/management/commands/fixturize_data/fixturize.py` -There is some examples in same folder and you can create new ones +Create a file in `geocity/apps/submissions/management/commands/fixturize_data/`. + +There is some examples in same folder and you can create new ones. + +The file will automatically appear once it's created. + +`docker-compose run web python manage.py fixturize` is interactive and can use some arguments as : + +- `--help` : Shows description of command and available arguments +- `--list` : List available files to be used as fixtures +- `--file` : Use a specific file. Example : `--file=agenda` +- no args : Asks if you want to run default fixture file ```bash # Load demo data diff --git a/geocity/apps/submissions/management/commands/fixturize.py b/geocity/apps/submissions/management/commands/fixturize.py index 3248390fb..a60680ed8 100644 --- a/geocity/apps/submissions/management/commands/fixturize.py +++ b/geocity/apps/submissions/management/commands/fixturize.py @@ -1,9 +1,13 @@ +import importlib +import os import re import shutil +import sys import unicodedata from io import StringIO from constance import config +from django.conf import settings from django.contrib.auth import get_user_model from django.contrib.auth.models import Group, Permission from django.contrib.contenttypes.models import ContentType @@ -20,9 +24,6 @@ from geocity.apps.reports.models import * from geocity.apps.submissions.models import * -# import fixturize file -from ..fixturize_data.generic_example import * - def strip_accents(text): """ @@ -114,10 +115,62 @@ def setup_media(images_folder): class Command(BaseCommand): + help = "Create default datas using fixtures for dev, pre-prod or demo environment." + + def add_arguments(self, parser): + parser.add_argument("--file", type=str, help="Define the fixture file to run") + parser.add_argument( + "--list", action="store_true", help="List available fixture files" + ) + def handle(self, *args, **options): + if settings.ENV.upper() != "DEV": + self.stdout.write( + self.style.ERROR("Les fixtures ne peuvent être exécutés qu'en DEV") + ) + sys.exit() + + directory_path = "geocity/apps/submissions/management/fixturize_data" + available_fixtures = [ + os.path.splitext(f)[0] + for f in os.listdir(directory_path) + if os.path.isfile(os.path.join(directory_path, f)) + ] + + if options["list"]: + self.stdout.write(self.style.SUCCESS("Liste des fichiers disponibles")) + self.stdout.write("- " + "\n- ".join(available_fixtures)) + sys.exit() + elif options["file"]: + file_name = options["file"] + self.stdout.write((f"Fichier spécifié : {file_name}")) + + if file_name in available_fixtures: + module = importlib.import_module( + f"..fixturize_data.{file_name}", package=__package__ + ) + else: + self.stdout.write(self.style.ERROR("Ce fichier n'existe pas")) + sys.exit() + else: + self.stdout.write( + self.style.SUCCESS( + "Aucune option spécifiée. Utilisez --show-help pour afficher les commandes disponibles." + ) + ) + user_input = input( + "Voulez-vous executer les fixtures par défaut ? [Y/n] : " + ) + if user_input.lower() not in {"y", "yes", ""}: + sys.exit() + + module = importlib.import_module( + f"..fixturize_data.generic", package=__package__ + ) + self.stdout.write("Resetting database...") reset_db() - setup_media(images_folder) + setup_media(module.images_folder) self.stdout.write("") self.stdout.write("░██████╗███████╗███████╗██████╗░") self.stdout.write("██╔════╝██╔════╝██╔════╝██╔══██╗") @@ -130,17 +183,17 @@ def handle(self, *args, **options): with transaction.atomic(): self.stdout.write("Creating default site...") self.setup_necessary_default_site() - for idx, (domain, entity) in enumerate(entities.items()): + for idx, (domain, entity) in enumerate(module.entities.items()): self.stdout.write(f"Entity : {entity}") self.stdout.write(" • Creating site...") self.setup_site(entity) self.stdout.write(" • Creating administrative entity...") administrative_entity = self.create_administrative_entity( - entity, ofs_ids[idx], geoms[idx] + entity, module.ofs_ids[idx], module.geoms[idx] ) self.stdout.write(" • Creating users...") integrator_group = self.create_users( - iterations, entity, domain, administrative_entity + module.iterations, entity, domain, administrative_entity ) self.stdout.write(" • Setting administrative_entity integrator...") self.setup_administrative_entity_integrator( @@ -152,24 +205,24 @@ def handle(self, *args, **options): " • Setting form, form categories and complementary document type..." ) self.setup_form_and_form_categories( - form_categories, + module.form_categories, integrator_group, - form_additional_information, + module.form_additional_information, administrative_entity, ) self.stdout.write(" • Creating submissions...") self.setup_submission( entity, - iterations.get("user_iterations"), + module.iterations.get("user_iterations"), administrative_entity, - small_text, + module.small_text, ) self.stdout.write(" • Creating default report...") Report.create_default_report(administrative_entity.id) self.stdout.write("Creating template customizations...") self.create_template_customization() self.stdout.write("Setup template customizations...") - self.setup_homepage(entities, iterations) + self.setup_homepage(module.entities, module.iterations) self.stdout.write("Fixturize succeed ✔") def setup_necessary_default_site(self): diff --git a/geocity/apps/submissions/management/fixturize_data/demo_example.py b/geocity/apps/submissions/management/fixturize_data/demo.py similarity index 100% rename from geocity/apps/submissions/management/fixturize_data/demo_example.py rename to geocity/apps/submissions/management/fixturize_data/demo.py diff --git a/geocity/apps/submissions/management/fixturize_data/fixturize.py b/geocity/apps/submissions/management/fixturize_data/fixturize.py deleted file mode 100644 index 4b125ddf2..000000000 --- a/geocity/apps/submissions/management/fixturize_data/fixturize.py +++ /dev/null @@ -1,214 +0,0 @@ -# This file is the one used by commands.fixturize. -# Can be modified, the file is in gitignore - -# Variables to change the result of the fixturize - -# Defines the number of each type of user to create on each entity -iterations = { - "integrator_iterations": 1, - "pilot_iterations": 1, - "validator_iterations": 1, - "user_iterations": 1, -} - -# domain:entity -# Users created (password demo) : -# - ENTITY-superuser -# - ENTITY-integrator-ITERATION -# - ENTITY-pilot-ITERATION -# - ENTITY-validator-ITERATION -# - ENTITY-user-ITERATION -entities = { - "sports.ch": "sports", - "culture.ch": "culture", - "communication.ch": "communication", -} - -# Geometries for the entities -geoms = [ - "SRID=2056;MultiPolygon (((2538391 1176432, 2538027 1178201, 2538485 1178804, 2537777 1179199, 2536748 1178450, 2536123 1179647, 2537382 1180593, 2537143 1181623, 2538651 1183257, 2540368 1183236, 2541252 1181093, 2541460 1180458, 2540160 1179543, 2540097 1178877, 2538391 1176432)))", - "SRID=2056;MultiPolygon (((2538391 1176432, 2538027 1178201, 2538485 1178804, 2537777 1179199, 2536748 1178450, 2536123 1179647, 2537382 1180593, 2537143 1181623, 2538651 1183257, 2540368 1183236, 2541252 1181093, 2541460 1180458, 2540160 1179543, 2540097 1178877, 2538391 1176432)))", - "SRID=2056;MultiPolygon (((2538391 1176432, 2538027 1178201, 2538485 1178804, 2537777 1179199, 2536748 1178450, 2536123 1179647, 2537382 1180593, 2537143 1181623, 2538651 1183257, 2540368 1183236, 2541252 1181093, 2541460 1180458, 2540160 1179543, 2540097 1178877, 2538391 1176432)))", -] - -# Ofs_ids for the entities -ofs_ids = [5938, 5938, 5938] - -# Define the fields -field_title = { - "name": "Title", - "input_type": "text", - "is_mandatory": True, - "api_light": True, - "public_if_submission_public": True, -} -field_location = { - "name": "Location", - "input_type": "text", - "is_mandatory": True, - "api_light": True, - "public_if_submission_public": True, -} -field_location_details = { - "name": "Location details", - "input_type": "text", - "is_mandatory": True, - "api_light": False, - "public_if_submission_public": True, -} -field_summary = { - "name": "Summary", - "input_type": "text", - "is_mandatory": True, - "api_light": False, - "public_if_submission_public": True, -} -field_Pricing = { - "name": "Pricing", - "input_type": "text", - "is_mandatory": True, - "api_light": False, - "public_if_submission_public": True, -} -field_website = { - "name": "Website", - "input_type": "text", - "is_mandatory": True, - "api_light": False, - "public_if_submission_public": True, -} -field_schedule = { - "name": "Schedule", - "input_type": "text", - "is_mandatory": True, - "api_light": False, - "public_if_submission_public": True, -} -field_organizer_name = { - "name": "Organizer name", - "input_type": "text", - "is_mandatory": True, - "api_light": False, - "public_if_submission_public": True, -} -field_organizer_address = { - "name": "Organizer address", - "input_type": "text", - "is_mandatory": True, - "api_light": False, - "public_if_submission_public": True, -} -field_organizer_phone = { - "name": "Organizer phone", - "input_type": "text", - "is_mandatory": True, - "api_light": False, - "public_if_submission_public": True, -} -field_organizer_email = { - "name": "Organizer email", - "input_type": "text", - "is_mandatory": True, - "api_light": False, - "public_if_submission_public": True, -} -field_organizer_website = { - "name": "Organizer website", - "input_type": "text", - "is_mandatory": True, - "api_light": False, - "public_if_submission_public": True, -} -field_publics = { - "name": "Publics", - "input_type": "list_multiple", - "is_mandatory": True, - "api_light": False, - "public_if_submission_public": True, - "filter_for_api": True, - "choices": "Tous publics\nFamilles\nJeunes\nSeniors", -} -field_regions = { - "name": "Régions", - "input_type": "list_single", - "is_mandatory": True, - "api_light": False, - "public_if_submission_public": True, - "filter_for_api": True, - "choices": "Grandson\nOrbe\nRomainmôtier\nSainte-Croix\nVallée de Joux\nVallorbe\nYverdon\nYvonand", -} -field_types = { - "name": "Types", - "input_type": "list_multiple", - "is_mandatory": True, - "api_light": False, - "public_if_submission_public": True, - "filter_for_api": True, - "choices": "Concert\nSpectacle\nExposition\nFestival\nAtelier, Animation & Médiation\nPerformance\nInstallation\nCompétition", -} -field_domaines = { - "name": "Domaines", - "input_type": "list_multiple", - "is_mandatory": True, - "api_light": False, - "public_if_submission_public": True, - "filter_for_api": True, - "choices": "Art vivant\nArt visuel\nAudiovisuel\nPatrimoine & Architecture\nMusique\nLittérature\nArtisanat & Tradition\nSport", -} -field_poster = { - "name": "Poster", - "input_type": "file", - "is_mandatory": True, - "api_light": True, - "public_if_submission_public": True, -} -field_non_public = { - "name": "Champ pas public, ne doit pas s'afficher dans l'api et l'agenda", - "input_type": "text", - "is_mandatory": False, - "api_light": True, - "public_if_submission_public": False, -} - -# Define form_categories for each entity -# To create specific cases add in front of category name : -# - RENEWAL_REMINDER -# - NO_GEOM_NOR_TIME -form_categories = [ - ( - "AGENDA Agenda", - [ - ( - "Agenda", - field_title, - field_location, - field_location_details, - field_summary, - field_Pricing, - field_website, - field_schedule, - field_organizer_name, - field_organizer_address, - field_organizer_phone, - field_organizer_email, - field_organizer_website, - field_publics, - field_regions, - field_types, - field_domaines, - field_poster, - field_non_public, - ), - ], - ), -] - -form_additional_information = """ -Texte expliquant la ou les conditions particulière(s) s'appliquant à cette demande. -Un document pdf peut également être proposé à l'utilisateur, par exemple pour les conditions -de remise en état après une fouille sur le domaine public -""" - -small_text = "This is a small text" - -images_folder = "posters" diff --git a/geocity/apps/submissions/management/fixturize_data/generic_example.py b/geocity/apps/submissions/management/fixturize_data/generic.py similarity index 100% rename from geocity/apps/submissions/management/fixturize_data/generic_example.py rename to geocity/apps/submissions/management/fixturize_data/generic.py