<?php

use Illuminate\Foundation\Inspiring;
use Illuminate\Support\Facades\Artisan;

/*
|--------------------------------------------------------------------------
| Console Routes
|--------------------------------------------------------------------------
|
| This file is where you may define all of your Closure based console
| commands. Each Closure is bound to a command instance allowing a
| simple approach to interacting with each command's IO methods.
|
*/

Artisan::command('inspire', function () {
    $this->comment(Inspiring::quote());
})->purpose('Display an inspiring quote');

// === Portail Client (Phase 5) =================================================
// La commande \App\Console\Commands\ExpireInactivePortalTokens est enregistrée
// dans AppServiceProvider::boot() via $this->commands(). Ici on définit juste
// le schedule (tous les jours à 00h30).
$schedule = app(\Illuminate\Console\Scheduling\Schedule::class);

$schedule
    ->command('portal:expire-inactive --days=90')
    ->dailyAt('00:30')
    ->withoutOverlapping(120)
    ->onOneServer()
    ->name('portal-expire-inactive');

// =============================================================================
// Phase 1 - F1 : Scheduler Infoparcelle (declarations CRM)
// =============================================================================
// Toutes ces commandes sont enregistrees soit via core-city-user
// (CityUserServiceProvider::loadCommands) soit localement.
//
// Prerequis d'execution : le job `Rootsud\Core\Jobs\Schedule` doit etre actif
// pour project_id=1 (Infoparcelle). Activation manuelle dans
// /administration -> /project/settings/1 -> bouton "Activer les automatisations"
// (status_schedule=1).
//
// Le job exec `schedule.sh {site_path}` qui lance `schedule:run`. Laravel filtre
// par expression cron, donc seules les commandes dont l'horaire matche
// s'executent reellement.
//
// `withoutOverlapping(N)` evite les doublons si une commande prend plus que
// l'intervalle de re-trigger. L'argument N (minutes) est OBLIGATOIRE ici : le
// defaut Laravel est 1440 min, donc une commande tuee en cours d'execution
// (worker atteint son --timeout=300, conteneur redemarre) laisse un mutex
// perime et n'est plus JAMAIS relancee pendant 24 h. Constate le 2026-07-29 :
// `leads:digest-morning`, tuee a 12:00:00, est restee bloquee jusqu'au
// lendemain midi. N est donc cale sous la cadence de chaque commande pour que
// le blocage se resorbe tout seul au tour suivant.
//
// Depuis le 2026-07-30 le job Schedule du core boucle a la MINUTE (et non plus
// chaque seconde) : `onOneServer()` verrouille deja par minute calendaire, donc
// relancer plus vite n'apportait aucune precision et saturait les workers.
//
// IMPORTANT : `App\Console\Kernel::schedule()` N'EST PAS invoquee car le
// `bootstrap/app.php` binde `Illuminate\Contracts\Console\Kernel` vers
// `Rootsud\Core\Console\Kernel`. Toutes les declarations doivent passer ici.
// =============================================================================

// Alerte de la commune pendant l'essai (levier E1, 2026-10-30) : nouvelles annonces de la commune de travail,
// au plus un jour sur deux et jamais le jour d'un e-mail de scénario (config/sector_alert.php).
$schedule
    ->command('infoparcelle:sector-alert')
    ->dailyAt('08:00')
    ->withoutOverlapping(60)
    ->onOneServer()
    ->name('sector-alert');

// RGPD - purge Lead_visit > 90j (commande active des Phase 1)
$schedule
    ->command('leads:cleanup-old-visits')
    ->weeklyOn(0, '02:00') // dimanche 2h
    ->withoutOverlapping(240)
    ->onOneServer()
    ->name('leads-cleanup-old-visits');

// RGPD - centre d'aide : consultations et recherches au-delà de 25 mois (les avis sont conservés)
$schedule
    ->command('help:purge-measures')
    ->weeklyOn(0, '02:30') // dimanche 2h30
    ->withoutOverlapping(60)
    ->onOneServer()
    ->name('help-purge-measures');

// ----------------------------------------------------------------------------
// Squelettes Phase 1 - implementations Phases 2-4
// ----------------------------------------------------------------------------
// Ces commandes existent mais sont des no-op log-only pour le moment.
// Elles sont declarees ici pour que le scheduler soit complet des Phase 1 et
// que l'activation dans /administration deverrouille tout le pipeline
// d'orchestration. Chaque implementation reelle sera fournie dans la Phase
// indiquee dans l'en-tete de la commande.
// ----------------------------------------------------------------------------

// [Phase 4 - N3] Notif taches en retard (matin pro)
$schedule
    ->command('leads:remind-overdue-tasks')
    ->dailyAt('07:30')
    ->withoutOverlapping(120)
    ->onOneServer()
    ->name('leads-remind-overdue-tasks');

// [Phase 4 - N1] Rappels RDV J-1 / H-2 (toutes les 5min pour granularite H-2)
$schedule
    ->command('leads:rdv-reminder')
    ->everyFiveMinutes()
    ->withoutOverlapping(10)
    ->onOneServer()
    ->name('leads-rdv-reminder');

// [Phase 4 - N5] Digest matin pro
// hourly() au lieu de dailyAt('07:00') pour permettre l'heure custom user
// (setting `digest_morning_hour` 5h-10h). La commande filtre côté code.
$schedule
    ->command('leads:digest-morning')
    ->hourly()
    ->withoutOverlapping(55)
    ->onOneServer()
    ->name('leads-digest-morning');

// Sprint 2026-05-20 - Schedule "leads:relaunch-unopened-proposals" SUPPRIMÉE
// (fonctionnalité "Relances automatiques" abandonnée - voir RelaunchUnopenedProposalsCommand supprimée).

// [Phase 4 - N8] NPS post-vente J+7
$schedule
    ->command('leads:nps-after-sale')
    ->dailyAt('11:00')
    ->withoutOverlapping(120)
    ->onOneServer()
    ->name('leads-nps-after-sale');

// [Phase 4 - N7] Suggestion taches relance leads froids
// 2026-11-04 : a la premiere activation des automatisations en production, la simulation annoncait
// 22 658 taches d'un coup (23 089 anciennes prospections migrees, 23 751 dossiers sans contact).
// La commande (core-city-user) ne retient plus que les dossiers avec un contact et une activite de
// moins d'un an, 10 nouvelles taches au plus par compte et par jour. Cette tache ne tourne QUE si la
// version bornee du paquet est installee (constante MAX_PER_OWNER) : deployer le site avant le tag
// du paquet ne relance pas l'ancienne selection.
$schedule
    ->command('leads:cold-followup-suggest')
    ->dailyAt('06:00')
    ->when(fn () => defined(\Rootsud\City\User\Console\Commands\ColdFollowupSuggestCommand::class . '::MAX_PER_OWNER'))
    ->withoutOverlapping(120)
    ->onOneServer()
    ->name('leads-cold-followup-suggest');

// [Phase 4 - N6] Digest hebdo pro (lundi 7h)
$schedule
    ->command('leads:digest-weekly')
    ->mondays()
    ->at('07:00')
    ->withoutOverlapping(240)
    ->onOneServer()
    ->name('leads-digest-weekly');

// [Phase 2 - V5] Reporting hebdo au vendeur/bailleur (lundi 8h30)
$schedule
    ->command('leads:vendor-weekly-report')
    ->mondays()
    ->at('08:30')
    ->withoutOverlapping(240)
    ->onOneServer()
    ->name('leads-vendor-weekly-report');

// [Phase 3 - A3] Digest matches acheteur/locataire - quotidien 18h
$schedule
    ->command('leads:match-alerts-digest --frequency=daily')
    ->dailyAt('18:00')
    ->withoutOverlapping(120)
    ->onOneServer()
    ->name('leads-match-alerts-digest-daily');

// [Phase 3 - A3] Digest matches acheteur/locataire - hebdo (vendredi 9h)
$schedule
    ->command('leads:match-alerts-digest --frequency=weekly')
    ->fridays()
    ->at('09:00')
    ->withoutOverlapping(240)
    ->onOneServer()
    ->name('leads-match-alerts-digest-weekly');

// [Sprint A - A7] Alerte d'échéance de mandat (J-30 et J-7) - quotidien 10h
$schedule
    ->command('leads:mandate-expiry-alert')
    ->dailyAt('10:00')
    ->withoutOverlapping(120)
    ->onOneServer()
    ->name('leads-mandate-expiry-alert');

// [Sprint A - A3] Email J-1 fin de délai de rétractation SRU sur compromis - quotidien 09h
$schedule
    ->command('leads:sru-retractation-reminder')
    ->dailyAt('09:00')
    ->withoutOverlapping(120)
    ->onOneServer()
    ->name('leads-sru-retractation-reminder');

// [Sprint B - B5] Relance pièces vendeur non fournies > 7j - quotidien 10h30
$schedule
    ->command('leads:seller-docs-reminder')
    ->dailyAt('10:30')
    ->withoutOverlapping(120)
    ->onOneServer()
    ->name('leads-seller-docs-reminder');

// [2026-09-23] Relance automatique des acquereurs apres visite (OPT-IN par compte, reglage
// buyer_followup_auto_enabled, defaut desactive : sans lui la commande ne fait rien) - quotidien 11h
$schedule
    ->command('leads:visit-feedback-email')
    ->dailyAt('11:00')
    ->withoutOverlapping(120)
    ->onOneServer()
    ->name('leads-visit-feedback-email');

// [Sprint B - D3] Détecteur hot buyer (3 réactions/24h) - toutes les 30 min
$schedule
    ->command('leads:hot-buyer-detector')
    ->everyThirtyMinutes()
    ->withoutOverlapping(25)
    ->onOneServer()
    ->name('leads-hot-buyer-detector');

// [2026-09-23] Taches « Relancer X (visite du JJ/MM) » pour les acquereurs sans nouvelles - quotidien 8h
$schedule
    ->command('leads:buyer-followup-suggest')
    ->dailyAt('08:00')
    ->withoutOverlapping(120)
    ->onOneServer()
    ->name('leads-buyer-followup-suggest');

// Audit mobile 2026-11-01, C1 : identifiants de clic Google gardés pour l'envoi des abonnements à Google Ads,
// effacés après 90 jours (Google refuse un clic plus ancien) - quotidien 03h40.
$schedule
    ->command('ads:upload-conversions --purge')
    ->dailyAt('03:40')
    ->withoutOverlapping(30)
    ->onOneServer()
    ->name('ads-click-id-purge');

// Comptes supprimés par leur titulaire : données effacées 30 jours après (règle Google Play), factures conservées
// (Rootsud\Core\Services\AccountErasure) - quotidien 04h10.
$schedule
    ->command('users:erase-deleted')
    ->dailyAt('04:10')
    ->withoutOverlapping(60)
    ->onOneServer()
    ->name('users-erase-deleted');
