Architecture Decision Records - ADR251104

2025/11/04

Costi non attribuibili in AWS S3 dovuti a versioning non governato

Autore: Marco Orlandin, Architect
Data: 04 Novembre 2025
Status: Implementato con successo
Settore: Enterprise / Cloud governance
Consumo storage coinvolto: Centinaia di GB accumulati in versioni obsolete
Constraint principali: Visibilità limitata (regione senza Storage Lens), migrazione in corso verso altra piattaforma cloud, zero downtime tollerato, rispetto NDA cliente

Nota: Progetto reale, anonimizzato per riservatezza (NDA). Metriche e dettagli semplificati, ma decisioni e lezioni apprese fedeli alla realtà.

Contesto e problema

Durante un assessment preliminare a una migrazione cloud (da AWS verso un'altra piattaforma), il cliente segnalava costi mensili significativi ma non chiaramente attribuibili.

La fatturazione AWS mostrava un consumo stabile e dominante su S3, senza apparenti eventi applicativi o crescite di traffico che lo giustificassero.

Analizzando Cost Explorer e i bucket principali, emergeva un pattern classico:

  • Versioning attivato sui bucket (scelta iniziale "per sicurezza").
  • Cancellazioni logiche gestite a livello applicativo (delete marker).
  • Assenza di lifecycle policy configurate per rimuovere versioni non-current e delete marker.

Risultato: centinaia di GB occupati da versioni obsolete e marker di cancellazione, dati che "non esistevano più" dal punto di vista applicativo ma continuavano a generare costi di storage.

A complicare la diagnosi: i bucket erano in regione eu-south-1 (Milano), che al momento non supportava S3 Storage Lens – strumento nativo per analisi dettagliata dell'inventario. Questo riduceva drasticamente la visibilità interna sui costi. Il problema non era la migrazione in sé, ma il rischio di portarsi dietro un "debito tecnico silenzioso": cambiare provider senza governare lo storage avrebbe solo spostato il costo, non risolto.

Requisiti non funzionali

  • Riduzione costi S3 significativa (>50%) senza perdita dati attivi
  • Zero downtime o impatto applicativo
  • Visibilità completa su versioni obsolete e delete marker
  • Soluzione eseguibile in poche giornate (assessment in corso)
  • Nessun costo aggiuntivo per tool/licenze

Opzioni valutate

Opzione 1: Ignorare e procedere con la migrazione

  • Pro: Velocità – si migra "as-is".
  • Contro: Costi trasferiti sul nuovo provider, debito tecnico perpetuato, nessuna lezione appresa.

Opzione 2: Spostare bucket in regione con Storage Lens (es. eu-west-1)

  • Pro: Accesso immediato a inventory e analytics nativi.
  • Contro: Cross-region copy costosa e lunga, potenziale impatto su applicazioni che referenziano URL specifici, complessità non necessaria.

Opzione 3: Pulizia manuale via console/CLI

  • Pro: Controllo totale.
  • Contro: Rischio elevato di errori umani, tempo proibitivo su centinaia di GB e milioni di oggetti.

Opzione 4: S3 Batch Operations + lifecycle policy automatizzata

  • Pro: Nativo, scalabile, safe (dry-run disponibile), costo irrisorio.
  • Contro: Richiede scripting iniziale, ma minimo.

Decisione

Scelta l'Opzione 4: configurazione di lifecycle policy per rimuovere automaticamente versioni non-current >90 giorni e delete marker, combinata con S3 Batch Operations per pulizia retroattiva delle versioni esistenti.

Motivazioni principali:

  • Soluzione nativa AWS, zero tool esterni.
  • Eseguibile in safe mode (dry-run) prima del commit.
  • Impatto zero su dati attivi.
  • Risultati rapidi e misurabili.

Implementazione passo-passo

  1. Analisi inventario: Interrogazione diretta del bucket via AWS CLI (comandi list-object-versions) per identificare versioni non-current e delete marker.
  2. Script Python preparatorio: Uso boto3 per iterare su versioni, generare report dettagliato e preparare manifesto per operazioni batch.
  3. Configurazione lifecycle policy: Regole per expire non-current versions (90 giorni) e delete marker permanenti.
  4. S3 Batch Operations job: Manifesto generato dallo script, job per delete versioni obsolete (dry-run prima, poi execute).
  5. Verifica post-cleanup: Monitoraggio Cost Explorer e storage metrics per 7 giorni.
  6. Documentazione: Aggiunta policy e procedure al repository IaC del cliente.

Conseguenze osservate (dopo cleanup)

  • Riduzione consumo storage S3 del 70-80% in pochi giorni.
  • Costi mensili S3 calati drasticamente (da dominante a marginale nel bill complessivo).
  • Visibilità migliorata anche senza Storage Lens (grazie a inventory e script).
  • Migrazione proseguita con storage "pulito", senza eredità di debito.
  • Lezioni apprese:
    • Versioning è potente, ma va sempre abbinato a lifecycle policy dal giorno zero.
    • Scegliere regione solo per compliance: valuta anche feature parity (Storage Lens, analytics).
    • Costi "fantasma" sono quasi sempre governance mancante, non cloud "caro".
    • Inizia sempre con inventory e report automatizzati.

Stack utilizzato

  • Storage: Amazon S3 (eu-south-1)
  • Analisi costi: AWS Cost Explorer + Billing reports
  • Automazione: Python + boto3 + AWS CLI
  • Operazioni batch: S3 Batch Operations

Quando considerare questo approccio

Se hai:

  • Versioning attivo su bucket con cancellazioni frequenti
  • Costi S3 inspiegabili o stabili nonostante bassa attività
  • Regione senza Storage Lens ma bisogno urgente di visibilità
  • Assessment/migrazione in corso e storage "ereditato"

...applica lifecycle + Batch Operations prima di qualsiasi spostamento. È la pulizia più efficace e a costo zero.

Se invece il versioning è intenzionale per retention lunga (compliance), configura policy esplicite e monitora proattivamente.

Hai un caso simile (costi cloud inspiegabili, storage non governato, migrazione in vista)?

Contattami. Valutiamo insieme se basta una pulizia mirata o se serve ridisegnare la governance dello storage.