fonzarely/regine-photos-archiverpublic Fork
⑂ main
Commits
⬇ Clone ▾
git clone https://git.rickub.com/fonzarely/regine-photos-archiver.git
git clone ssh://git@rickub.com/fonzarely/regine-photos-archiver.git

Host key fingerprint (ed25519): SHA256:iycHnxEyq0Q7uyVpB7JlznP0G7JrTPXLYRcAU5CSLhc — verify it before your first connect.

Download ZIP
plan 40fcb39 · on main · Fabien Champigny · Sep 18, 2026
plan.md · 100 lines · 9.8 KBmarkdown
Blame HistoryOpen raw

Implementation Plan: Catégorisation des dossiers à la racine de l'archive

Branch: 004-categorisation-dossiers | Date: 2026-09-18 | Spec: spec.md

Input: Feature specification from /specs/004-categorisation-dossiers/spec.md

Summary

Ajoute, au-dessus des conventions de nommage de dossier déjà spécifiées (specs/001-import-photos), un niveau de placement racine à la création d'un dossier ou d'un dossier parent : un répertoire d'année par défaut, ou un répertoire de catégorie thématique (mariage, vacances, voyage, anniversaire, extensible) quand l'utilisateur le choisit explicitement à l'étape de destination déjà prévue. Ce placement est une propriété du dossier de plus haut niveau, héritée par ses sous-dossiers, et une recatégorisation a posteriori est traitée comme un simple déplacement détecté par somme de contrôle de contenu (aucun mécanisme dédié). Approche technique : une fonction de résolution de chemin (determine_root) dans le module dossier de regine-core (monorepo posé par specs/003-config-contexte-travail), consommée par le flux de destination du futur module import ; les catégories déjà utilisées sont mises en cache dans la base de contexte centralisée déjà définie par specs/003-config-contexte-travail, pour permettre une suggestion instantanée sans dépendre d'un accès au NAS.

Technical Context

Language/Version: Python 3.11+ (cohérent avec regine-core, cf. specs/003-config-contexte-travail/plan.md)

Primary Dependencies: bibliothèque standard uniquement (pathlib pour la construction de chemin, difflib.get_close_matches pour suggérer une catégorie proche d'une catégorie déjà utilisée, cf. Edge Case orthographe) ; pas de dépendance tierce nouvelle

Storage: réutilise la base de contexte centralisée SQLite déjà définie par specs/003-config-contexte-travail (même fichier, mêmes conventions PRAGMA user_version/application_id) — nouvelle table categories (nom, date de première utilisation), en complément de la table boitiers existante ; les répertoires d'année ne sont pas mis en cache (dérivés directement de la date, aucune ambiguïté de frappe possible)

Testing: pytest ; tests unitaires sur la résolution de chemin (année vs catégorie, casse/collision), tests d'intégration sur l'héritage du placement racine par un sous-dossier, tests de contrat sur la présentation du répertoire racine dans le résumé de confirmation

Target Platform: identique à specs/003-config-contexte-travail (poste de bureau, macOS en priorité) — cette fonctionnalité ne touche pas au montage SMB, elle consomme le même contexte de travail déjà résolu

Project Type: Monorepo existant (cf. specs/003-config-contexte-travail/plan.md) — cette fonctionnalité ajoute du code dans regine-core (module dossier, nouvelle table dans regine-core/config) et modifie la façade regine-cli au point d'intégration du futur module import ; aucun nouveau paquet créé

Performance Goals: la résolution du répertoire racine et la suggestion de catégories proches DOIVENT rester quasi instantanées (lecture locale seule, pas d'accès réseau), cohérent avec SC-006 de specs/003-config-contexte-travail (pas de parcours NAS implicite)

Constraints: le placement racine est immuable après création sauf déplacement explicite détecté par hash (FR-008) — aucune opération de « recatégorisation » en écriture directe à inventer ; les répertoires de catégorie restent plats (FR-009, pas de sous-organisation par année dans cette itération)

Scale/Scope: nombre de catégories distinctes attendu faible à modéré (dizaines, pas milliers) sur la durée de vie d'une archive personnelle ; la table categories n'a pas de contrainte de volumétrie particulière

Constitution Check

GATE: Must pass before Phase 0 research. Re-check after Phase 1 design.

Principe / contrainte Évaluation Justification
I. Fichier maître intouchable N/A Cette fonctionnalité ne touche à aucun fichier maître, seulement à l'emplacement du dossier qui les contient.
II. Confirmation explicite avant toute action à risque PASS FR-010 impose l'affichage du répertoire racine dans le résumé déjà requis avant toute écriture sur l'archive (cf. specs/001-import-photos FR-018) ; aucune écriture supplémentaire non confirmée n'est introduite.
III. Identité par contenu, jamais par nom de fichier seul PASS FR-008 est une application directe de ce principe au niveau du dossier : une recatégorisation a posteriori est un déplacement détecté par somme de contrôle de contenu inchangé, jamais par comparaison de chemin ou de nom seul.
IV. Métadonnées ouvertes et embarquées PASS La catégorie n'est pas une métadonnée séparée du fichier au sens du Principe IV (légende, mots-clés, personnes, crédit, copyright, licence) : elle est directement visible dans le chemin du dossier sur le système de fichiers, lisible sans Régine ni outil spécialisé — cohérent avec l'exigence de « traçabilité humaine hors application » déjà actée par la constitution pour le nommage de dossier.
V. L'utilisateur décide, Régine suggère PASS FR-005 : Régine ne devine ni n'assigne jamais de catégorie ; FR-004/Edge Case : les catégories déjà utilisées sont proposées comme suggestions, jamais imposées.
VI. Bibliothèque centrale, façades minces PASS La résolution de chemin et le cache de catégories vivent dans regine-core (modules dossier et config) ; regine-cli ne fait qu'appeler cette logique à l'étape de destination et afficher son résultat.
CLI-first PASS Aucune interaction visuelle spécifique requise ; la question de catégorie s'intègre au même protocole texte in/out que le reste de l'étape de destination.
Exécution sans démon PASS Aucun état en arrière-plan requis ; la résolution de chemin est un calcul synchrone dans le même processus que l'import.
Formats ouverts et documentés PASS Réutilise la base SQLite déjà actée, aucun nouveau format introduit.

Aucune violation identifiée ; la section Complexity Tracking reste vide.

Re-check post Phase 1 (après génération de data-model.md, contracts/regine-core-api.md, quickstart.md) : le modèle de données (table categories dans la base de contexte centralisée existante, aucune nouvelle base) et le contrat d'API interne (fonctions pures retournant des objets structurés, consommées identiquement par regine-cli aujourd'hui et par regine-gui/regine-agent demain) confirment chaque évaluation PASS ci-dessus. Aucune violation nouvelle introduite par la conception détaillée.

Project Structure

Documentation (this feature)

specs/004-categorisation-dossiers/
├── plan.md              # This file (/speckit-plan command output)
├── research.md          # Phase 0 output (/speckit-plan command)
├── data-model.md        # Phase 1 output (/speckit-plan command)
├── quickstart.md        # Phase 1 output (/speckit-plan command)
├── contracts/           # Phase 1 output (/speckit-plan command)
│   └── regine-core-api.md
└── tasks.md             # Phase 2 output (/speckit-tasks command - NOT created by /speckit-plan)

Source Code (repository root) — extension du monorepo posé par specs/003

packages/
├── regine-core/
│   └── src/
│       └── regine_core/
│           ├── config/
│           │   ├── db.py                  # (existant, specs/003) étendu : migration ajoutant la table `categories`
│           │   └── categories.py          # NOUVEAU : list_known_categories(), suggest_categories(query), register_category_usage(nom)
│           └── dossier/                   # NOUVEAU module (premier code du module `dossier`, cf. architecture)
│               ├── __init__.py
│               └── root.py                # NOUVEAU : determine_root(date, categorie=None) -> RootLocation ; construit le chemin archive + local en miroir
│
├── regine-cli/
│   └── src/
│       └── regine_cli/
│           └── config_cmd.py              # (existant, specs/003) étendu si besoin d'une commande `regine config categories list`
│           # Le point d'intégration réel (question de catégorie à l'étape de destination de l'import)
│           # relève de la future façade CLI du module import (specs/001-import-photos, pas encore implémentée) ;
│           # ce plan ne crée pas ce point d'intégration, il expose l'API que ce futur code appellera.
│
└── regine-core/tests/
    ├── unit/
    │   ├── test_root_resolution.py        # Année par défaut, catégorie explicite, une seule catégorie à la fois
    │   └── test_categories_cache.py       # Suggestion de catégories proches (orthographe), pas de doublon silencieux
    └── integration/
        └── test_root_inheritance.py       # Sous-dossier hérite du placement racine du dossier parent

Structure Decision: Extension du monorepo déjà posé par specs/003-config-contexte-travail — aucun nouveau paquet, seulement deux ajouts dans regine-core : la table categories dans la base de contexte centralisée existante (regine_core/config/), et le premier code du module dossier (regine_core/dossier/root.py), qui n'existait pas encore. regine-cli n'a pas de nouveau point d'entrée propre à cette fonctionnalité : l'intégration réelle (poser la question de catégorie) se fera dans le futur code CLI du module import (specs/001-import-photos), qui consommera l'API exposée ici. regine-gui et regine-agent restent des paquets vides, inchangés par ce plan.

Complexity Tracking

Aucune violation de gate à justifier — section laissée vide intentionnellement.

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
# Implementation Plan: Catégorisation des dossiers à la racine de l'archive

**Branch**: `004-categorisation-dossiers` | **Date**: 2026-09-18 | **Spec**: [spec.md](./spec.md)

**Input**: Feature specification from `/specs/004-categorisation-dossiers/spec.md`

## Summary

Ajoute, au-dessus des conventions de nommage de dossier déjà spécifiées (`specs/001-import-photos`), un niveau de placement racine à la création d'un dossier ou d'un dossier parent : un répertoire d'année par défaut, ou un répertoire de catégorie thématique (mariage, vacances, voyage, anniversaire, extensible) quand l'utilisateur le choisit explicitement à l'étape de destination déjà prévue. Ce placement est une propriété du dossier de plus haut niveau, héritée par ses sous-dossiers, et une recatégorisation a posteriori est traitée comme un simple déplacement détecté par somme de contrôle de contenu (aucun mécanisme dédié). Approche technique : une fonction de résolution de chemin (`determine_root`) dans le module `dossier` de `regine-core` (monorepo posé par `specs/003-config-contexte-travail`), consommée par le flux de destination du futur module `import` ; les catégories déjà utilisées sont mises en cache dans la base de contexte centralisée déjà définie par `specs/003-config-contexte-travail`, pour permettre une suggestion instantanée sans dépendre d'un accès au NAS.

## Technical Context

**Language/Version**: Python 3.11+ (cohérent avec `regine-core`, cf. `specs/003-config-contexte-travail/plan.md`)

**Primary Dependencies**: bibliothèque standard uniquement (`pathlib` pour la construction de chemin, `difflib.get_close_matches` pour suggérer une catégorie proche d'une catégorie déjà utilisée, cf. Edge Case orthographe) ; pas de dépendance tierce nouvelle

**Storage**: réutilise la base de contexte centralisée SQLite déjà définie par `specs/003-config-contexte-travail` (même fichier, mêmes conventions `PRAGMA user_version`/`application_id`) — nouvelle table `categories` (nom, date de première utilisation), en complément de la table `boitiers` existante ; les répertoires d'année ne sont pas mis en cache (dérivés directement de la date, aucune ambiguïté de frappe possible)

**Testing**: pytest ; tests unitaires sur la résolution de chemin (année vs catégorie, casse/collision), tests d'intégration sur l'héritage du placement racine par un sous-dossier, tests de contrat sur la présentation du répertoire racine dans le résumé de confirmation

**Target Platform**: identique à `specs/003-config-contexte-travail` (poste de bureau, macOS en priorité) — cette fonctionnalité ne touche pas au montage SMB, elle consomme le même contexte de travail déjà résolu

**Project Type**: Monorepo existant (cf. `specs/003-config-contexte-travail/plan.md`) — cette fonctionnalité ajoute du code dans `regine-core` (module `dossier`, nouvelle table dans `regine-core/config`) et modifie la façade `regine-cli` au point d'intégration du futur module `import` ; aucun nouveau paquet créé

**Performance Goals**: la résolution du répertoire racine et la suggestion de catégories proches DOIVENT rester quasi instantanées (lecture locale seule, pas d'accès réseau), cohérent avec SC-006 de `specs/003-config-contexte-travail` (pas de parcours NAS implicite)

**Constraints**: le placement racine est immuable après création sauf déplacement explicite détecté par hash (FR-008) — aucune opération de « recatégorisation » en écriture directe à inventer ; les répertoires de catégorie restent plats (FR-009, pas de sous-organisation par année dans cette itération)

**Scale/Scope**: nombre de catégories distinctes attendu faible à modéré (dizaines, pas milliers) sur la durée de vie d'une archive personnelle ; la table `categories` n'a pas de contrainte de volumétrie particulière

## Constitution Check

*GATE: Must pass before Phase 0 research. Re-check after Phase 1 design.*

| Principe / contrainte | Évaluation | Justification |
|---|---|---|
| I. Fichier maître intouchable | N/A | Cette fonctionnalité ne touche à aucun fichier maître, seulement à l'emplacement du dossier qui les contient. |
| II. Confirmation explicite avant toute action à risque | PASS | FR-010 impose l'affichage du répertoire racine dans le résumé déjà requis avant toute écriture sur l'archive (cf. `specs/001-import-photos` FR-018) ; aucune écriture supplémentaire non confirmée n'est introduite. |
| III. Identité par contenu, jamais par nom de fichier seul | PASS | FR-008 est une application directe de ce principe au niveau du dossier : une recatégorisation a posteriori est un déplacement détecté par somme de contrôle de contenu inchangé, jamais par comparaison de chemin ou de nom seul. |
| IV. Métadonnées ouvertes et embarquées | PASS | La catégorie n'est pas une métadonnée séparée du fichier au sens du Principe IV (légende, mots-clés, personnes, crédit, copyright, licence) : elle est directement visible dans le chemin du dossier sur le système de fichiers, lisible sans Régine ni outil spécialisé — cohérent avec l'exigence de « traçabilité humaine hors application » déjà actée par la constitution pour le nommage de dossier. |
| V. L'utilisateur décide, Régine suggère | PASS | FR-005 : Régine ne devine ni n'assigne jamais de catégorie ; FR-004/Edge Case : les catégories déjà utilisées sont proposées comme suggestions, jamais imposées. |
| VI. Bibliothèque centrale, façades minces | PASS | La résolution de chemin et le cache de catégories vivent dans `regine-core` (modules `dossier` et `config`) ; `regine-cli` ne fait qu'appeler cette logique à l'étape de destination et afficher son résultat. |
| CLI-first | PASS | Aucune interaction visuelle spécifique requise ; la question de catégorie s'intègre au même protocole texte in/out que le reste de l'étape de destination. |
| Exécution sans démon | PASS | Aucun état en arrière-plan requis ; la résolution de chemin est un calcul synchrone dans le même processus que l'import. |
| Formats ouverts et documentés | PASS | Réutilise la base SQLite déjà actée, aucun nouveau format introduit. |

Aucune violation identifiée ; la section Complexity Tracking reste vide.

**Re-check post Phase 1** (après génération de `data-model.md`, `contracts/regine-core-api.md`, `quickstart.md`) : le modèle de données (table `categories` dans la base de contexte centralisée existante, aucune nouvelle base) et le contrat d'API interne (fonctions pures retournant des objets structurés, consommées identiquement par `regine-cli` aujourd'hui et par `regine-gui`/`regine-agent` demain) confirment chaque évaluation PASS ci-dessus. Aucune violation nouvelle introduite par la conception détaillée.

## Project Structure

### Documentation (this feature)

```text
specs/004-categorisation-dossiers/
├── plan.md              # This file (/speckit-plan command output)
├── research.md          # Phase 0 output (/speckit-plan command)
├── data-model.md        # Phase 1 output (/speckit-plan command)
├── quickstart.md        # Phase 1 output (/speckit-plan command)
├── contracts/           # Phase 1 output (/speckit-plan command)
│   └── regine-core-api.md
└── tasks.md             # Phase 2 output (/speckit-tasks command - NOT created by /speckit-plan)
```

### Source Code (repository root) — extension du monorepo posé par specs/003

```text
packages/
├── regine-core/
│   └── src/
│       └── regine_core/
│           ├── config/
│           │   ├── db.py                  # (existant, specs/003) étendu : migration ajoutant la table `categories`
│           │   └── categories.py          # NOUVEAU : list_known_categories(), suggest_categories(query), register_category_usage(nom)
│           └── dossier/                   # NOUVEAU module (premier code du module `dossier`, cf. architecture)
│               ├── __init__.py
│               └── root.py                # NOUVEAU : determine_root(date, categorie=None) -> RootLocation ; construit le chemin archive + local en miroir
│
├── regine-cli/
│   └── src/
│       └── regine_cli/
│           └── config_cmd.py              # (existant, specs/003) étendu si besoin d'une commande `regine config categories list`
│           # Le point d'intégration réel (question de catégorie à l'étape de destination de l'import)
│           # relève de la future façade CLI du module import (specs/001-import-photos, pas encore implémentée) ;
│           # ce plan ne crée pas ce point d'intégration, il expose l'API que ce futur code appellera.
│
└── regine-core/tests/
    ├── unit/
    │   ├── test_root_resolution.py        # Année par défaut, catégorie explicite, une seule catégorie à la fois
    │   └── test_categories_cache.py       # Suggestion de catégories proches (orthographe), pas de doublon silencieux
    └── integration/
        └── test_root_inheritance.py       # Sous-dossier hérite du placement racine du dossier parent
```

**Structure Decision**: Extension du monorepo déjà posé par `specs/003-config-contexte-travail` — aucun nouveau paquet, seulement deux ajouts dans `regine-core` : la table `categories` dans la base de contexte centralisée existante (`regine_core/config/`), et le premier code du module `dossier` (`regine_core/dossier/root.py`), qui n'existait pas encore. `regine-cli` n'a pas de nouveau point d'entrée propre à cette fonctionnalité : l'intégration réelle (poser la question de catégorie) se fera dans le futur code CLI du module import (`specs/001-import-photos`), qui consommera l'API exposée ici. `regine-gui` et `regine-agent` restent des paquets vides, inchangés par ce plan.

## Complexity Tracking

*Aucune violation de gate à justifier — section laissée vide intentionnellement.*