def ranger_sections_xml(chemin_base, coll_sections, coll_articles, entree_texte, entree_version_texte, section_parente, version_section_parente, dates_changement, ensemble_versions_sections, ensemble_articles, cidTexte, niv): # Prévenir les récursions infinies - les specs indiquent un max de 10 if niv == 10: raise Exception() # Traiter les articles à ce niveau dates_changement, ensemble_articles = ranger_articles_xml( chemin_base, coll_articles, version_section_parente, entree_texte, entree_version_texte, dates_changement, ensemble_articles, cidTexte) for i in range(len(coll_sections)): print('{}/{}'.format(i + 1, len(coll_sections)), end='') sys.stdout.flush() cid = coll_sections[i]['cid'] id = coll_sections[i]['id'] nom = coll_sections[i].text etat_juridique = coll_sections[i]['etat'] niveau = coll_sections[i]['niv'] debut = normalise_date(coll_sections[i]['debut']) fin = normalise_date(coll_sections[i]['fin']) url = coll_sections[i]['url'][1:] numero = i + 1 # Enregistrement de la section try: entree_section = Section.get(Section.cid == cid) except: entree_section = Section.create(cid=cid, cid_parent=section_parente, niveau=niveau, texte=entree_texte) # Ajout des dates limites pour préparer l’édition de liens dates_changement |= {debut, fin} # Enregistrement de version de section # TODO gérer les mises à jour try: entree_version_section = Version_section.get( Version_section.id == id) except: entree_version_section = Version_section.create( cid=cid, id=id, id_parent=version_section_parente, nom=nom, etat_juridique=etat_juridique, niveau=niveau, numero=numero, debut=debut, fin=fin, texte=entree_texte, version_texte=entree_version_texte) # Ajout de cette version de section ensemble_versions_sections |= {entree_version_section} print(' → ', end='') sys.stdout.flush() # Continuer récursivement chemin_section_ta = os.path.join(chemin_base, 'section_ta', url) f_section_ta = open(chemin_section_ta, 'r') soup = BeautifulSoup(f_section_ta.read(), 'xml') section_ta_STRUCTURE_TA = soup.find('STRUCTURE_TA') section_ta_LIEN_SECTION_TA = section_ta_STRUCTURE_TA.find_all( 'LIEN_SECTION_TA') section_ta_LIEN_ART = section_ta_STRUCTURE_TA.find_all('LIEN_ART') dates_changement, ensemble_versions_sections, ensemble_articles = ranger_sections_xml( chemin_base, section_ta_LIEN_SECTION_TA, section_ta_LIEN_ART, entree_texte, entree_version_texte, entree_section, entree_version_section, dates_changement, ensemble_versions_sections, ensemble_articles, cidTexte, niv + 1) print('\033[3D \033[3D', end='') nb_chiffres = len('{}/{}'.format(i + 1, len(coll_sections))) print('\033[' + str(nb_chiffres) + 'D' + (''.join([' ' * nb_chiffres])) + '\033[' + str(nb_chiffres) + 'D', end='') return dates_changement, ensemble_versions_sections, ensemble_articles
def ranger_sections_xml(chemin_base, coll_sections, coll_articles, entree_texte, entree_version_texte, section_parente, version_section_parente, dates_changement, ensemble_versions_sections, ensemble_articles, cidTexte, niv): # Prévenir les récursions infinies - les specs indiquent un max de 10 if niv == 10: raise Exception() # Traiter les articles à ce niveau dates_changement, ensemble_articles = ranger_articles_xml(chemin_base, coll_articles, version_section_parente, entree_texte, entree_version_texte, dates_changement, ensemble_articles, cidTexte) for i in range(len(coll_sections)): print('{}/{}'.format(i+1, len(coll_sections)), end='') sys.stdout.flush() cid = coll_sections[i]['cid'] id = coll_sections[i]['id'] nom = coll_sections[i].text etat_juridique = coll_sections[i]['etat'] niveau = coll_sections[i]['niv'] debut = normalise_date(coll_sections[i]['debut']) fin = normalise_date(coll_sections[i]['fin']) url = coll_sections[i]['url'][1:] numero = i+1 # Enregistrement de la section try: entree_section = Section.get(Section.cid == cid) except: entree_section = Section.create( cid=cid, cid_parent=section_parente, niveau=niveau, texte=entree_texte ) # Ajout des dates limites pour préparer l’édition de liens dates_changement |= {debut, fin} # Enregistrement de version de section # TODO gérer les mises à jour try: entree_version_section = Version_section.get(Version_section.id == id) except: entree_version_section = Version_section.create( cid=cid, id=id, id_parent=version_section_parente, nom=nom, etat_juridique=etat_juridique, niveau=niveau, numero=numero, debut=debut, fin=fin, texte=entree_texte, version_texte=entree_version_texte ) # Ajout de cette version de section ensemble_versions_sections |= {entree_version_section} print(' → ', end='') sys.stdout.flush() # Continuer récursivement chemin_section_ta = os.path.join(chemin_base, 'section_ta', url) f_section_ta = open(chemin_section_ta, 'r') soup = BeautifulSoup(f_section_ta.read(), 'xml') section_ta_STRUCTURE_TA = soup.find('STRUCTURE_TA') section_ta_LIEN_SECTION_TA = section_ta_STRUCTURE_TA.find_all('LIEN_SECTION_TA') section_ta_LIEN_ART = section_ta_STRUCTURE_TA.find_all('LIEN_ART') dates_changement, ensemble_versions_sections, ensemble_articles = ranger_sections_xml(chemin_base, section_ta_LIEN_SECTION_TA, section_ta_LIEN_ART, entree_texte, entree_version_texte, entree_section, entree_version_section, dates_changement, ensemble_versions_sections, ensemble_articles, cidTexte, niv+1) print('\033[3D \033[3D', end='') nb_chiffres=len('{}/{}'.format(i+1, len(coll_sections))) print('\033[' + str(nb_chiffres) + 'D' + (''.join([' ' * nb_chiffres])) + '\033[' + str(nb_chiffres) + 'D', end='') return dates_changement, ensemble_versions_sections, ensemble_articles
def creer_historique_texte(texte, format, dossier, cache): # Créer le dossier si besoin nom = texte[0] cid = texte[1] sousdossier = '.' path(dossier).mkdir_p() path(os.path.join(dossier, 'codes')).mkdir_p() path(os.path.join(dossier, 'constitutions')).mkdir_p() path(os.path.join(dossier, 'lois')).mkdir_p() path(os.path.join(dossier, 'décrets')).mkdir_p() path(os.path.join(dossier, 'ordonnances')).mkdir_p() if texte[2]: identifiant, tmp1 = normalisation_code(nom) dossier = os.path.join(dossier, 'codes', identifiant) sousdossier = '.' path(dossier).mkdir_p() path(os.path.join(dossier, sousdossier)).mkdir_p() chemin_base = chemin_texte(cid, True) fichier = os.path.join(dossier, sousdossier, nom+'.md') # Créer le dépôt Git if not os.path.exists(os.path.join(dossier,'.git')): subprocess.Popen(['git', 'init'], cwd=dossier) else: subprocess.Popen(['git', 'checkout', '--', sousdossier], cwd=dossier) if os.path.exists(fichier): raise Exception('Fichier existant : la mise à jour de fichiers existants n’est pas encore prise en charge.') # Vérifier que les articles ont été transformés en Markdown ou les créer le cas échéant creer_markdown_texte(texte, cache) # Sélection des versions du texte versions_texte = Version_texte.select().where(Version_texte.texte == texte[1]) # Pour chaque version # - rechercher les sections et articles associés # - créer le fichier texte au format demandé # - commiter le fichier for (i_version,version_texte) in enumerate(versions_texte): # Passer les versions 'nulles' if version_texte.base is None: continue # Sélectionner les versions d’articles et sections présentes dans cette version de texte, c’est-à-dire celles créées avant et détruites après (ou jamais) articles = \ Article.select() \ .where( (Article.texte == cid) \ & (Article.debut <= version_texte.debut) \ & ((Article.fin >= version_texte.fin)|(Article.fin == None)) \ ) versions_sections = \ Version_section.select() \ .where( (Version_section.texte == cid) \ & (Version_section.debut <= version_texte.debut) \ & ((Version_section.fin >= version_texte.fin)|(Version_section.fin == None)) \ ) # Créer l’en-tête date_fr = '{} {} {}'.format(version_texte.debut.day, MOIS2[int(version_texte.debut.month)], version_texte.debut.year) if version_texte.debut.day == 1: date_fr = '1er {} {}'.format(MOIS2[int(version_texte.debut.month)], version_texte.debut.year) contenu = nom + '\n' \ + '\n' \ + '- Date de consolidation : '+date_fr+'\n' \ + '- [Lien permanent Légifrance](http://legifrance.gouv.fr/affichCode.do?cidTexte='+cid+'&dateTexte='+str(version_texte.debut.year)+'{:02d}'.format(version_texte.debut.month)+'{:02d}'.format(version_texte.debut.day)+')\n' \ + '\n' \ + '\n' # Créer les sections (donc tout le texte) contenu = creer_sections(contenu, 1, None, versions_sections, articles, version_texte, cid, cache) # Enregistrement du fichier f_texte = open(fichier, 'w') f_texte.write(contenu.encode('utf-8')) f_texte.close() # Exécuter Git subprocess.call(['git', 'add', os.path.join(sousdossier, nom+'.md')], cwd=dossier) subprocess.call(['git', 'commit', '--author="Législateur <>"', '--date="'+str(version_texte.debut)+'T00:00:00Z"', '-m', 'Version consolidée au {}'.format(date_fr), '-q', '--no-status'], cwd=dossier) if version_texte.fin == None: logger.info('Version {} enregistrée (du {} à maintenant)'.format(i_version, version_texte.debut)) else: logger.info('Version {} enregistrée (du {} au {})'.format(i_version, version_texte.debut, version_texte.fin))
def creer_historique_texte(texte, format, dossier, cache): # Créer le dossier si besoin nom = texte[0] cid = texte[1] sousdossier = '.' path(dossier).mkdir_p() path(os.path.join(dossier, 'codes')).mkdir_p() path(os.path.join(dossier, 'constitutions')).mkdir_p() path(os.path.join(dossier, 'lois')).mkdir_p() path(os.path.join(dossier, 'décrets')).mkdir_p() path(os.path.join(dossier, 'ordonnances')).mkdir_p() if texte[2]: identifiant, tmp1 = normalisation_code(nom) dossier = os.path.join(dossier, 'codes', identifiant) sousdossier = '.' path(dossier).mkdir_p() path(os.path.join(dossier, sousdossier)).mkdir_p() chemin_base = chemin_texte(cid, True) fichier = os.path.join(dossier, sousdossier, nom + '.md') # Créer le dépôt Git if not os.path.exists(os.path.join(dossier, '.git')): subprocess.Popen(['git', 'init'], cwd=dossier) else: subprocess.Popen(['git', 'checkout', '--', sousdossier], cwd=dossier) if os.path.exists(fichier): raise Exception( 'Fichier existant : la mise à jour de fichiers existants n’est pas encore prise en charge.' ) # Vérifier que les articles ont été transformés en Markdown ou les créer le cas échéant creer_markdown_texte(texte, cache) # Sélection des versions du texte versions_texte = Version_texte.select().where( Version_texte.texte == texte[1]) # Pour chaque version # - rechercher les sections et articles associés # - créer le fichier texte au format demandé # - commiter le fichier for (i_version, version_texte) in enumerate(versions_texte): # Passer les versions 'nulles' if version_texte.base is None: continue # Sélectionner les versions d’articles et sections présentes dans cette version de texte, c’est-à-dire celles créées avant et détruites après (ou jamais) articles = \ Article.select() \ .where( (Article.texte == cid) \ & (Article.debut <= version_texte.debut) \ & ((Article.fin >= version_texte.fin)|(Article.fin == None)) \ ) versions_sections = \ Version_section.select() \ .where( (Version_section.texte == cid) \ & (Version_section.debut <= version_texte.debut) \ & ((Version_section.fin >= version_texte.fin)|(Version_section.fin == None)) \ ) # Créer l’en-tête date_fr = '{} {} {}'.format(version_texte.debut.day, MOIS2[int(version_texte.debut.month)], version_texte.debut.year) if version_texte.debut.day == 1: date_fr = '1er {} {}'.format(MOIS2[int(version_texte.debut.month)], version_texte.debut.year) contenu = nom + '\n' \ + '\n' \ + '- Date de consolidation : '+date_fr+'\n' \ + '- [Lien permanent Légifrance](http://legifrance.gouv.fr/affichCode.do?cidTexte='+cid+'&dateTexte='+str(version_texte.debut.year)+'{:02d}'.format(version_texte.debut.month)+'{:02d}'.format(version_texte.debut.day)+')\n' \ + '\n' \ + '\n' # Créer les sections (donc tout le texte) contenu = creer_sections(contenu, 1, None, versions_sections, articles, version_texte, cid, cache) # Enregistrement du fichier f_texte = open(fichier, 'w') f_texte.write(contenu.encode('utf-8')) f_texte.close() # Exécuter Git subprocess.call(['git', 'add', os.path.join(sousdossier, nom + '.md')], cwd=dossier) subprocess.call([ 'git', 'commit', '--author="Législateur <>"', '--date="' + str(version_texte.debut) + 'T00:00:00Z"', '-m', 'Version consolidée au {}'.format(date_fr), '-q', '--no-status' ], cwd=dossier) if version_texte.fin == None: logger.info('Version {} enregistrée (du {} à maintenant)'.format( i_version, version_texte.debut)) else: logger.info('Version {} enregistrée (du {} au {})'.format( i_version, version_texte.debut, version_texte.fin))