From cf109984e5283450c128cbdc53bf546e1b213b4d Mon Sep 17 00:00:00 2001 From: Julien Froidefond Date: Thu, 27 Nov 2025 10:41:10 +0100 Subject: [PATCH] refactor: remove category rules and related logic from defaults, types, and services for cleaner codebase --- lib/defaults.ts | 53 ------------------------------------- lib/store.ts | 1 - lib/types.ts | 8 ------ prisma/schema.prisma | 18 ++----------- scripts/sync-categories.ts | 49 +--------------------------------- services/banking.service.ts | 11 ++------ 6 files changed, 5 insertions(+), 135 deletions(-) diff --git a/lib/defaults.ts b/lib/defaults.ts index 070e928..fcf53d8 100644 --- a/lib/defaults.ts +++ b/lib/defaults.ts @@ -1,4 +1,3 @@ -import type { CategoryRule } from "./types" // ═══════════════════════════════════════════════════════════════════════════ // STRUCTURE HIÉRARCHIQUE DES CATÉGORIES @@ -986,58 +985,6 @@ export const defaultCategories: CategoryDefinition[] = [ }, ] -// ═══════════════════════════════════════════════════════════════════════════ -// RÈGLES DE CATÉGORISATION AVANCÉES -// ═══════════════════════════════════════════════════════════════════════════ -export interface CategoryRuleDefinition extends Omit { - categorySlug: string // Référence au slug de la catégorie -} - -export const defaultCategoryRules: CategoryRuleDefinition[] = [ - // Salaire - patterns typiques de virements salaire - { categorySlug: "revenus-salaire", pattern: "^VIR(EMENT)? (RECU )?.*SALAIRE", isRegex: true }, - { categorySlug: "revenus-salaire", pattern: "^VIR(EMENT)? (RECU )?.*PAIE", isRegex: true }, - - // Loyer - patterns de prélèvement loyer - { categorySlug: "logement-loyer", pattern: "^PRLV.*LOYER", isRegex: true }, - { categorySlug: "logement-loyer", pattern: "^PRLV.*FONCIA", isRegex: true }, - { categorySlug: "logement-loyer", pattern: "^PRLV.*NEXITY", isRegex: true }, - - // EDF/Engie - { categorySlug: "logement-electricite", pattern: "^PRLV.*EDF", isRegex: true }, - { categorySlug: "logement-electricite", pattern: "^PRLV.*ENGIE", isRegex: true }, - { categorySlug: "logement-electricite", pattern: "^PRLV.*TOTAL.?ENERGIE", isRegex: true }, - - // Télécom - { categorySlug: "abonnements-telecom", pattern: "^PRLV.*FREE( MOBILE)?", isRegex: true }, - { categorySlug: "abonnements-telecom", pattern: "^PRLV.*ORANGE", isRegex: true }, - { categorySlug: "abonnements-telecom", pattern: "^PRLV.*SFR", isRegex: true }, - { categorySlug: "abonnements-telecom", pattern: "^PRLV.*BOUYGUES", isRegex: true }, - - // Assurances - { categorySlug: "finance-assurance", pattern: "^PRLV.*AXA", isRegex: true }, - { categorySlug: "finance-assurance", pattern: "^PRLV.*MAIF", isRegex: true }, - { categorySlug: "finance-assurance", pattern: "^PRLV.*MACIF", isRegex: true }, - { categorySlug: "finance-assurance", pattern: "^PRLV.*MATMUT", isRegex: true }, - - // Impôts - { categorySlug: "finance-impots", pattern: "^PRLV.*DGFIP", isRegex: true }, - { categorySlug: "finance-impots", pattern: "^PRLV.*TRESOR PUBLIC", isRegex: true }, - { categorySlug: "finance-impots", pattern: "IMPOT", isRegex: false }, - - // Remboursements - { categorySlug: "revenus-remboursements", pattern: "^VIR(EMENT)? (RECU )?.*CPAM", isRegex: true }, - { categorySlug: "revenus-remboursements", pattern: "^VIR(EMENT)? (RECU )?.*AMELI", isRegex: true }, - { categorySlug: "revenus-remboursements", pattern: "REMBOURSEMENT", isRegex: false }, - - // CAF - { categorySlug: "revenus-allocations", pattern: "^VIR(EMENT)? (RECU )?.*CAF", isRegex: true }, - { categorySlug: "revenus-allocations", pattern: "ALLOCATION", isRegex: false }, - - // Retraits - { categorySlug: "divers-retraits", pattern: "^RETRAIT DAB", isRegex: true }, - { categorySlug: "divers-retraits", pattern: "^RET DAB", isRegex: true }, -] // ═══════════════════════════════════════════════════════════════════════════ // DOSSIER RACINE diff --git a/lib/store.ts b/lib/store.ts index b92e23b..80c1773 100644 --- a/lib/store.ts +++ b/lib/store.ts @@ -48,7 +48,6 @@ const defaultData: BankingData = { transactions: [], folders: [defaultRootFolder], categories: buildCategoriesFromDefaults(), - categoryRules: [], } export function loadData(): BankingData { diff --git a/lib/types.ts b/lib/types.ts index bd45477..fe19f62 100644 --- a/lib/types.ts +++ b/lib/types.ts @@ -43,19 +43,11 @@ export interface Category { parentId: string | null } -export interface CategoryRule { - id: string - categoryId: string - pattern: string - isRegex: boolean -} - export interface BankingData { accounts: Account[] transactions: Transaction[] folders: Folder[] categories: Category[] - categoryRules: CategoryRule[] } // OFX Parsed types diff --git a/prisma/schema.prisma b/prisma/schema.prisma index 946e273..b8b521f 100644 --- a/prisma/schema.prisma +++ b/prisma/schema.prisma @@ -79,23 +79,9 @@ model Category { createdAt DateTime @default(now()) updatedAt DateTime @updatedAt - parent Category? @relation("CategoryHierarchy", fields: [parentId], references: [id], onDelete: Cascade) - children Category[] @relation("CategoryHierarchy") + parent Category? @relation("CategoryHierarchy", fields: [parentId], references: [id], onDelete: Cascade) + children Category[] @relation("CategoryHierarchy") transactions Transaction[] - rules CategoryRule[] @@index([parentId]) } - -model CategoryRule { - id String @id @default(cuid()) - categoryId String - pattern String - isRegex Boolean @default(false) - createdAt DateTime @default(now()) - updatedAt DateTime @updatedAt - - category Category @relation(fields: [categoryId], references: [id], onDelete: Cascade) - - @@index([categoryId]) -} diff --git a/scripts/sync-categories.ts b/scripts/sync-categories.ts index cdbac02..7b259fc 100644 --- a/scripts/sync-categories.ts +++ b/scripts/sync-categories.ts @@ -1,5 +1,5 @@ import { PrismaClient } from "@prisma/client" -import { defaultCategories, defaultCategoryRules, type CategoryDefinition } from "../lib/defaults" +import { defaultCategories, type CategoryDefinition } from "../lib/defaults" const prisma = new PrismaClient() @@ -113,51 +113,6 @@ async function main() { else unchanged++ } - // ═══════════════════════════════════════════════════════════════════════════ - // PHASE 3: Sync des règles (optionnel) - // ═══════════════════════════════════════════════════════════════════════════ - if (defaultCategoryRules.length > 0) { - console.log("\n" + "═".repeat(50)) - console.log("PHASE 3: Règles de catégorisation") - console.log("═".repeat(50)) - - let rulesCreated = 0 - let rulesSkipped = 0 - - for (const rule of defaultCategoryRules) { - const categoryId = slugToId.get(rule.categorySlug) - if (!categoryId) { - console.log(`⚠️ Catégorie introuvable pour règle: ${rule.categorySlug}`) - rulesSkipped++ - continue - } - - // Vérifier si la règle existe déjà - const existing = await prisma.categoryRule.findFirst({ - where: { - categoryId, - pattern: rule.pattern, - }, - }) - - if (!existing) { - await prisma.categoryRule.create({ - data: { - categoryId, - pattern: rule.pattern, - isRegex: rule.isRegex, - }, - }) - console.log(`✅ Règle créée: ${rule.pattern.substring(0, 40)}...`) - rulesCreated++ - } else { - rulesSkipped++ - } - } - - console.log(`\n📊 Règles: ${rulesCreated} créées, ${rulesSkipped} existantes`) - } - // ═══════════════════════════════════════════════════════════════════════════ // RÉSUMÉ // ═══════════════════════════════════════════════════════════════════════════ @@ -172,12 +127,10 @@ async function main() { const totalCategories = await prisma.category.count() const parentCount = await prisma.category.count({ where: { parentId: null } }) const childCount = await prisma.category.count({ where: { NOT: { parentId: null } } }) - const totalRules = await prisma.categoryRule.count() const totalKeywords = defaultCategories.reduce((sum, c) => sum + c.keywords.length, 0) console.log("\n📈 Base de données:") console.log(` Total catégories: ${totalCategories} (${parentCount} parents, ${childCount} enfants)`) - console.log(` Total règles: ${totalRules}`) console.log(` Total keywords: ${totalKeywords}`) } diff --git a/services/banking.service.ts b/services/banking.service.ts index 69d7883..bcbe591 100644 --- a/services/banking.service.ts +++ b/services/banking.service.ts @@ -1,9 +1,9 @@ import { prisma } from "@/lib/prisma" -import type { BankingData, Account, Transaction, Folder, Category, CategoryRule } from "@/lib/types" +import type { BankingData, Account, Transaction, Folder, Category } from "@/lib/types" export const bankingService = { async getAllData(): Promise { - const [accounts, transactions, folders, categories, categoryRules] = await Promise.all([ + const [accounts, transactions, folders, categories] = await Promise.all([ prisma.account.findMany({ include: { folder: true, @@ -17,7 +17,6 @@ export const bankingService = { }), prisma.folder.findMany(), prisma.category.findMany(), - prisma.categoryRule.findMany(), ]) // Transform Prisma models to match our types @@ -61,12 +60,6 @@ export const bankingService = { keywords: JSON.parse(c.keywords) as string[], parentId: c.parentId, })), - categoryRules: categoryRules.map((r): CategoryRule => ({ - id: r.id, - categoryId: r.categoryId, - pattern: r.pattern, - isRegex: r.isRegex, - })), } }, }