# NETGESCON - GESTIONE CHIAVI E SICUREZZA

## 📋 OVERVIEW
Sistema completo per la gestione delle chiavi condominiali, accessi ai locali tecnici, sicurezza degli spazi comuni e tracciabilità di tutte le operazioni di consegna/ritiro chiavi.

## 🔑 SISTEMA ARCHIVIO CHIAVI

### Tipologie Chiavi Standardizzate

#### Chiavi Accesso Principale
```
🚪 PORTONI E INGRESSI
├── Portone Principale (MAIN-DOOR)
│   ├── Chiave Master (MAIN-MASTER)
│   ├── Chiavi Standard Condomini (MAIN-STD-001, 002...)
│   └── Chiavi Servizio (MAIN-SRV-001, 002...)
├── Porte Secondarie (SEC-DOOR)
│   ├── Ingresso Servizio (SRV-DOOR)
│   ├── Uscita Emergenza (EMG-DOOR)
│   └── Accesso Garage (GAR-DOOR)
└── Cancelli Automatici (AUTO-GATE)
    ├── Chiave Override (GATE-OVR)
    ├── Telecomandi (GATE-REM-001, 002...)
    └── Chiavi Manutenzione (GATE-MNT)
```

#### Chiavi Locali Tecnici
```
🔧 LOCALI TECNICI E SERVIZI
├── Centrale Termica (HEAT-PLANT)
│   ├── Chiave Principale (HEAT-MAIN)
│   ├── Chiave Emergenza Vigili Fuoco (HEAT-FIRE)
│   └── Chiave Manutenzione (HEAT-MNT)
├── Locale Contatori (METER-ROOM)
│   ├── Contatori Gas (MTR-GAS)
│   ├── Contatori Acqua (MTR-H2O)
│   └── Contatori Elettrici (MTR-ELEC)
├── Locale Pompe/Autoclave (PUMP-ROOM)
│   ├── Chiave Accesso (PUMP-ACC)
│   ├── Quadro Elettrico (PUMP-ELEC)
│   └── Valvole Principali (PUMP-VALV)
└── Locali Ascensori (ELEV-ROOM)
    ├── Vano Motore (ELEV-MOT-A, B...)
    ├── Quadro Comando (ELEV-CTL-A, B...)
    └── Chiave Emergenza (ELEV-EMG)
```

#### Chiavi Spazi Comuni
```
🏛️ SPAZI CONDOMINIALI
├── Giardino/Terrazza (GARDEN)
│   ├── Cancelletto Accesso (GARD-GATE)
│   ├── Deposito Attrezzi (GARD-TOOL)
│   └── Irrigazione (GARD-IRR)
├── Sala Comune (COMMON-HALL)
│   ├── Accesso Principale (HALL-MAIN)
│   ├── Deposito Sedie/Tavoli (HALL-STOR)
│   └── Cucina/Angolo Cottura (HALL-KITCH)
├── Lavanderia (LAUNDRY)
│   ├── Accesso Generale (LAUN-ACC)
│   ├── Quadro Elettrico (LAUN-ELEC)
│   └── Scarichi/Valvole (LAUN-DRAIN)
└── Locale Biciclette (BIKE-ROOM)
    ├── Accesso (BIKE-ACC)
    └── Catene/Lucchetti (BIKE-LOCK-001, 002...)
```

### Database Archivio Chiavi

#### Struttura Dati Principale
```sql
CREATE TABLE archivio_chiavi (
    id BIGINT PRIMARY KEY AUTO_INCREMENT,
    stabile_id BIGINT NOT NULL,
    
    -- Identificativi
    codice_chiave VARCHAR(20) UNIQUE NOT NULL, -- Es: MAIN-STD-001
    denominazione VARCHAR(100) NOT NULL, -- Es: "Portone Via Roma 15"
    descrizione_dettagliata TEXT,
    
    -- Categorizzazione
    categoria_principale ENUM('accesso', 'tecnico', 'comune', 'servizio', 'emergenza'),
    categoria_secondaria VARCHAR(50), -- portone, centrale_termica, giardino, etc.
    
    -- Localizzazione
    zona_stabile VARCHAR(50), -- Palazzina A, Scala 1, Piano -1, etc.
    ubicazione_dettagliata TEXT, -- "Centrale termica nel seminterrato, lato cortile"
    
    -- Gestione Copie
    numero_copie_totali INT DEFAULT 1,
    numero_copie_circolazione INT DEFAULT 0,
    numero_copie_archivio INT DEFAULT 1,
    numero_copie_perse INT DEFAULT 0,
    
    -- Sicurezza
    livello_sicurezza ENUM('basso', 'medio', 'alto', 'critico') DEFAULT 'medio',
    richiede_autorizzazione BOOLEAN DEFAULT FALSE,
    tempo_max_detenzione_giorni INT NULL, -- NULL = illimitato
    
    -- QR Code e Tracciabilità
    qr_code_uuid VARCHAR(36) UNIQUE,
    qr_code_attivo BOOLEAN DEFAULT TRUE,
    
    -- Stato
    stato ENUM('attiva', 'persa', 'sostituita', 'ritirata') DEFAULT 'attiva',
    data_creazione TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
    data_ultima_modifica TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
    
    -- Note
    note_particolari TEXT,
    istruzioni_utilizzo TEXT,
    
    FOREIGN KEY (stabile_id) REFERENCES stabili(id),
    INDEX idx_codice_chiave (codice_chiave),
    INDEX idx_categoria (categoria_principale, categoria_secondaria),
    INDEX idx_qr_code (qr_code_uuid)
);
```

#### Copie Singole Chiavi
```sql
CREATE TABLE copie_chiavi (
    id BIGINT PRIMARY KEY AUTO_INCREMENT,
    archivio_chiave_id BIGINT NOT NULL,
    
    -- Identificativo copia
    numero_copia VARCHAR(10) NOT NULL, -- 001, 002, 003...
    codice_completo VARCHAR(30), -- MAIN-STD-001-C001 (generato automaticamente)
    
    -- QR specifico copia
    qr_code_copia VARCHAR(36) UNIQUE,
    
    -- Stato copia
    stato_copia ENUM('disponibile', 'assegnata', 'persa', 'danneggiata') DEFAULT 'disponibile',
    
    -- Assegnazione corrente
    assegnata_a_persona_id BIGINT NULL,
    data_assegnazione TIMESTAMP NULL,
    data_riconsegna_prevista DATE NULL,
    
    -- Tracciabilità fisica
    posizione_attuale VARCHAR(100), -- "Cassetta chiavi ufficio amministratore"
    ultima_verifica_presenza DATE,
    
    FOREIGN KEY (archivio_chiave_id) REFERENCES archivio_chiavi(id),
    FOREIGN KEY (assegnata_a_persona_id) REFERENCES persone(id),
    UNIQUE KEY uk_archivio_numero (archivio_chiave_id, numero_copia)
);
```

## 📋 SISTEMA ASSEGNAZIONE E TRACCIABILITÀ

### Registro Movimenti Chiavi
```sql
CREATE TABLE movimenti_chiavi (
    id BIGINT PRIMARY KEY AUTO_INCREMENT,
    copia_chiave_id BIGINT NOT NULL,
    
    -- Tipologia movimento
    tipo_movimento ENUM('consegna', 'ritiro', 'trasferimento', 'verifica', 'sostituzione'),
    
    -- Persone coinvolte
    persona_consegnataria_id BIGINT NULL, -- Chi riceve
    persona_consegnante_id BIGINT NULL, -- Chi consegna (admin, portiere)
    persona_autorizzante_id BIGINT NULL, -- Chi autorizza (se richiesto)
    
    -- Dettagli movimento
    data_movimento TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
    motivo_richiesta TEXT NOT NULL,
    durata_prevista_giorni INT NULL,
    data_riconsegna_prevista DATE NULL,
    data_riconsegna_effettiva DATE NULL,
    
    -- Autorizzazioni
    richiede_autorizzazione BOOLEAN DEFAULT FALSE,
    autorizzazione_concessa BOOLEAN NULL,
    data_autorizzazione TIMESTAMP NULL,
    note_autorizzazione TEXT,
    
    -- Conferme e firme
    firma_digitale_consegnatario TEXT, -- Hash firma o file
    firma_digitale_consegnante TEXT,
    metodo_conferma ENUM('presenza_fisica', 'firma_digitale', 'sms', 'email'),
    
    -- Tracciabilità
    ip_address VARCHAR(45),
    user_agent TEXT,
    geolocalizzazione POINT, -- Se disponibile
    
    -- Note
    note_movimento TEXT,
    condizioni_particolari TEXT,
    
    FOREIGN KEY (copia_chiave_id) REFERENCES copie_chiavi(id),
    FOREIGN KEY (persona_consegnataria_id) REFERENCES persone(id),
    FOREIGN KEY (persona_consegnante_id) REFERENCES persone(id),
    FOREIGN KEY (persona_autorizzante_id) REFERENCES persone(id)
);
```

### Sistema Autorizzazioni Gerarchiche

#### Matrice Autorizzazioni
```php
class ChiaveAuthorizationService {
    
    protected $autorizzazioni = [
        'amministratore' => [
            'accesso' => ['tutte'],
            'tecnico' => ['tutte'],
            'comune' => ['tutte'],
            'servizio' => ['tutte'],
            'emergenza' => ['tutte']
        ],
        'portiere' => [
            'accesso' => ['portone_principale', 'portone_servizio'],
            'tecnico' => ['previa_autorizzazione'],
            'comune' => ['tutte'],
            'servizio' => ['pulizie', 'manutenzione'],
            'emergenza' => ['limitato']
        ],
        'condomino_proprietario' => [
            'accesso' => ['portone_principale'],
            'tecnico' => ['previa_autorizzazione'],
            'comune' => ['con_prenotazione'],
            'servizio' => ['no'],
            'emergenza' => ['no']
        ],
        'condomino_inquilino' => [
            'accesso' => ['portone_principale'],
            'tecnico' => ['no'],
            'comune' => ['con_prenotazione'],
            'servizio' => ['no'],
            'emergenza' => ['no']
        ],
        'ditta_manutenzione' => [
            'accesso' => ['previa_autorizzazione'],
            'tecnico' => ['specifica_competenza'],
            'comune' => ['no'],
            'servizio' => ['temporaneo'],
            'emergenza' => ['no']
        ]
    ];
    
    public function verificaAutorizzazione($personaId, $chiaveId, $motivoRichiesta) {
        $persona = Persona::find($personaId);
        $chiave = ArchivioChinve::find($chiaveId);
        
        $ruolo = $this->determinaRuolo($persona);
        $categoria = $chiave->categoria_principale;
        
        $autorizzazioni = $this->autorizzazioni[$ruolo][$categoria] ?? ['no'];
        
        if (in_array('tutte', $autorizzazioni)) {
            return true;
        }
        
        if (in_array('previa_autorizzazione', $autorizzazioni)) {
            return $this->richiedeApprovazione($personaId, $chiaveId, $motivoRichiesta);
        }
        
        return false;
    }
    
    private function richiedeApprovazione($personaId, $chiaveId, $motivo) {
        return RichiestaAutorizzazione::create([
            'persona_richiedente_id' => $personaId,
            'chiave_id' => $chiaveId,
            'motivo' => $motivo,
            'stato' => 'pending',
            'data_richiesta' => now()
        ]);
    }
}
```

## 📱 SISTEMA QR CODE E APP MOBILE

### Generazione QR Code Unici
```php
class QRCodeChiaveService {
    
    /**
     * Genera QR code univoco per ogni copia chiave
     */
    public function generaQRCode($copiaChiaveId) {
        $copia = CopiaChiave::find($copiaChiaveId);
        $uuid = Str::uuid();
        
        $qrData = [
            'type' => 'netgescon_key',
            'version' => '1.0',
            'uuid' => $uuid,
            'key_id' => $copia->id,
            'key_code' => $copia->codice_completo,
            'stabile_id' => $copia->archivioChiave->stabile_id,
            'timestamp' => now()->timestamp,
            'checksum' => $this->generaChecksum($copia, $uuid)
        ];
        
        $copia->update(['qr_code_copia' => $uuid]);
        
        return QrCode::size(200)
                    ->format('png')
                    ->merge('/public/logo-netgescon.png', 0.1, true)
                    ->generate(json_encode($qrData));
    }
    
    /**
     * Verifica QR code scansionato
     */
    public function verificaQRCode($qrCodeData) {
        $data = json_decode($qrCodeData, true);
        
        if (!$this->verificaChecksum($data)) {
            throw new InvalidQRCodeException('QR Code non valido o manomesso');
        }
        
        $copia = CopiaChiave::where('qr_code_copia', $data['uuid'])->first();
        
        if (!$copia) {
            throw new ChiaveNotFoundException('Chiave non trovata nel sistema');
        }
        
        return [
            'copia_chiave' => $copia,
            'archivio_chiave' => $copia->archivioChiave,
            'stabile' => $copia->archivioChiave->stabile,
            'stato_attuale' => $copia->stato_copia,
            'assegnata_a' => $copia->assegnataAPersona,
            'ultimo_movimento' => $copia->movimenti()->latest()->first()
        ];
    }
}
```

### App Mobile Gestione Chiavi

#### Funzionalità Principali
1. **Scansione QR Code**
   - Identificazione immediata chiave
   - Cronologia movimenti
   - Stato attuale

2. **Richiesta Chiavi**
   - Form semplificato
   - Upload documenti
   - Notifica in tempo reale

3. **Riconsegna Chiavi**
   - Conferma tramite QR
   - Foto stato chiave
   - Geolocalizzazione

4. **Dashboard Personale**
   - Chiavi attualmente detenute
   - Scadenze riconsegna
   - Storico accessi

## 🔔 SISTEMA NOTIFICHE E ALERTING

### Notifiche Automatiche
```php
class ChiaveNotificationService {
    
    /**
     * Notifiche scadenze riconsegna
     */
    public function notificheScadenze() {
        $scadenzeImminenti = CopiaChiave::whereNotNull('assegnata_a_persona_id')
                                      ->where('data_riconsegna_prevista', '<=', now()->addDays(3))
                                      ->get();
        
        foreach($scadenzeImminenti as $copia) {
            $this->inviaNotificaScadenza($copia);
        }
    }
    
    /**
     * Alert chiavi non riconsegnate
     */
    public function alertChiaviScadute() {
        $chiavi_scadute = CopiaChiave::whereNotNull('assegnata_a_persona_id')
                                    ->where('data_riconsegna_prevista', '<', now())
                                    ->get();
        
        foreach($chiavi_scadute as $copia) {
            $this->inviaAlertAmministratore($copia);
            $this->inviaRichiestaSollecito($copia);
        }
    }
    
    /**
     * Notifica movimenti sospetti
     */
    public function monitoraggioSicurezza() {
        // Troppi accessi in poco tempo
        $accessiFrequenti = MovimentoChiave::where('created_at', '>', now()->subHours(1))
                                          ->select('copia_chiave_id')
                                          ->groupBy('copia_chiave_id')
                                          ->havingRaw('COUNT(*) > 5')
                                          ->get();
        
        // Accessi fuori orario normale
        $accessiFuoriOrario = MovimentoChiave::whereTime('data_movimento', '<', '06:00')
                                           ->orWhereTime('data_movimento', '>', '22:00')
                                           ->where('created_at', '>', now()->subDays(1))
                                           ->get();
        
        foreach($accessiFrequenti as $movimento) {
            $this->inviaAlertSicurezza('accessi_frequenti', $movimento);
        }
        
        foreach($accessiFuoriOrario as $movimento) {
            $this->inviaAlertSicurezza('accessi_fuori_orario', $movimento);
        }
    }
}
```

## 📊 REPORTING E STATISTICHE

### Dashboard Gestione Chiavi
- **Panoramica chiavi per categoria**
- **Chiavi attualmente assegnate**
- **Scadenze imminenti**
- **Chiavi perse/da sostituire**
- **Statistiche utilizzo spazi comuni**

### Report Sicurezza
- **Log accessi per periodo**
- **Analisi pattern utilizzo**
- **Audit trail movimenti**
- **Report conformità assicurativa**

### Integrazione Assicurazioni
- **Export dati per polizze**
- **Certificazione sistemi sicurezza**
- **Documentazione accessi autorizzati**
- **Prove implementazione misure sicurezza**

## 🎯 ROADMAP IMPLEMENTAZIONE

### Fase 1: Archivio Base (2 settimane)
- ✅ Database archivio chiavi
- ✅ CRUD gestione chiavi
- ✅ Sistema copie multiple

### Fase 2: Tracciabilità (2 settimane)
- ✅ Movimenti e assegnazioni
- ✅ Sistema autorizzazioni
- ✅ Notifiche automatiche

### Fase 3: QR Code e Mobile (3 settimane)
- ✅ Generazione QR code
- ✅ App mobile base
- ✅ Scansione e verifica

### Fase 4: Sicurezza Avanzata (2 settimane)
- ✅ Monitoring accessi
- ✅ Alert automatici
- ✅ Reporting compliance

### Fase 5: Integrazione (1 settimana)
- ✅ Dashboard principale
- ✅ Export assicurazioni
- ✅ Ottimizzazione UX

## 5. SISTEMA ETICHETTATURA E QR CODES

### 5.1 Gestione Etichette Fisiche
- **Stampa Etichette per Organizzazione**
  - Etichette per cassette postali
  - Numerazione unità immobiliari
  - Etichette per chiavi e badge
  - Codici QR per accesso rapido a documenti
  - Etichette per attrezzature condominiali

### 5.2 QR Code per Accesso Digitale
- **QR Linking a Sistema**
  - QR su cassette postali → dati proprietario
  - QR su chiavi → registro movimenti
  - QR su impianti → schede tecniche
  - QR per documenti → accesso immediato PDF

### 5.3 Stampante Integrata
```php
// Esempio implementazione stampa etichette
class EtichettaService {
    public function stampaEtichettaCassetta($unitaId) {
        $unita = UnitaImmobiliare::find($unitaId);
        $qrCode = QrCode::size(50)->generate(
            route('unita.show', $unitaId)
        );
        
        return view('stampa.etichetta-cassetta', [
            'unita' => $unita,
            'qrCode' => $qrCode
        ]);
    }
    
    public function stampaEtichettaChiave($chiaveId) {
        $chiave = ChiaveStabile::find($chiaveId);
        $qrCode = QrCode::size(40)->generate(
            route('chiavi.movimento', $chiaveId)
        );
        
        return view('stampa.etichetta-chiave', [
            'chiave' => $chiave,
            'qrCode' => $qrCode
        ]);
    }
}
```
