Torna al blog Self-Hosted Application Operations

Database integrato o esterno? Come scegliere un'architettura di database per un'applicazione self-hosted

La scelta tra un database integrato supportato dall'applicazione e un database gestito separatamente è soprattutto una decisione relativa a confini operativi, proprietà e capacità di ripristino. Usa questo framework per verificare i requisiti dell'applicazione, mappare ogni archivio di dati persistenti e assegnare responsabilità chiare prima del lancio.

Diagramma che mostra un'applicazione self-hosted connessa a un container di database integrato oppure a un database esterno gestito separatamente

Inizia dal confine operativo, non dall'opzione che sembra più sofisticata

Per un'applicazione basata su Docker, un database integrato significa di solito che l'applicazione e il relativo servizio database supportato sono definiti come parte della stessa applicazione Compose. Possono essere eseguiti in container separati, mentre il database rende persistenti i propri dati in un volume Docker. Un database esterno è un servizio database gestito separatamente, che l'applicazione raggiunge tramite una connessione configurata.

Nessuna delle due configurazioni è intrinsecamente più affidabile, sicura o professionale dell'altra. La domanda utile è: quale team possiede l'intero confine del servizio e quel team è in grado di gestirne bene dipendenze, modifiche e procedure di ripristino?

Un database integrato può essere il progetto a minor rischio quando l'applicazione lo supporta ufficialmente e un piccolo team necessita di uno stack circoscritto con un ciclo di vita chiaro. Un database separato può essere appropriato quando la documentazione dell'applicazione lo richiede, quando carichi di lavoro approvati necessitano realmente di un servizio condiviso oppure quando un team database o infrastruttura dispone già di procedure operative definite per quel servizio.

  • Scegli il più piccolo confine operativo che soddisfi i requisiti documentati dell'applicazione.
  • Non considerare “esterno” un sinonimo di resiliente né “integrato” un sinonimo di usa e getta.
  • Prendi la decisione per ogni applicazione e per ogni modello di deployment documentato, anziché adottare un'unica regola per tutti i carichi di lavoro.
Inizia dal confine operativo, non dall'opzione che sembra più sofisticata

Verifica il modello di deployment supportato dall'applicazione prima di progettare l'infrastruttura

La documentazione dell'applicazione stessa è l'autorità per stabilire se supporta un database integrato, un database esterno o entrambi. Svolgi questa verifica prima di predisporre un host o migrare dati di produzione. Una stringa di connessione tecnicamente possibile non dimostra che un modello di deployment sia supportato durante aggiornamenti, migrazioni o ripristino in caso di incidente.

Controlla i requisiti documentati per motore e versione del database. Verifica poi esattamente come l'applicazione riceve le impostazioni di connessione, come esegue le migrazioni dello schema, se richiede una particolare estensione del database o una fase di inizializzazione e se documenta ipotesi relative ad alta disponibilità o backup.

Anche il comportamento all'avvio è importante. In Compose, l'avvio di una dipendenza non significa di per sé che sia pronta ad accettare connessioni al database. Docker documenta che Compose normalmente attende che un container dipendente sia in esecuzione, non che sia pronto. Quando il deployment dell'applicazione lo richiede, un controllo di integrità del database e una condizione di dipendenza service_healthy possono impedire che l'applicazione tenti la connessione iniziale troppo presto.

  • Motore database supportato, versione principale ed eventuali estensioni richieste.
  • Impostazioni di connessione supportate e indicazione se TLS, certificati o regole di rete sono requisiti documentati.
  • Comando di migrazione, tempistica della migrazione, comportamento in caso di errore e indicazioni per il rollback.
  • Percorso di aggiornamento supportato sia per l'applicazione sia per il database.
  • Indicazioni su backup, ripristino e alta disponibilità pubblicate dal fornitore dell'applicazione.
  • Sequenza di avvio e aspettative relative ai controlli di integrità.
Verifica il modello di deployment supportato dall'applicazione prima di progettare l'infrastruttura

Mappa l'intero percorso dei dati: il database relazionale raramente è l'intero sistema

Prima di scegliere un'architettura di database, identifica ogni componente che conserva stato persistente o critico per la sicurezza. Il database relazionale può essere autorevole per i record dell'applicazione, ma la stessa applicazione può dipendere anche da archiviazione di file, object storage, cache, indice di ricerca, coda, file di configurazione e segreti. Ciascuno può avere un diverso modello di persistenza, backup e ripristino.

Docker Compose distingue risorse quali servizi, volumi, configurazioni e segreti. Tale distinzione è operativamente importante. Un volume Docker con nome può sopravvivere alla rimozione di un container, separando il ciclo di vita di un container database da quello dei dati del database. Tuttavia, ciò non stabilisce che una semplice copia di una directory dati di un database in esecuzione costituisca un backup coerente del database.

Crea un inventario che identifichi la fonte autorevole per ogni tipo di dato. Questa è la base di un piano di ripristino, di un piano di migrazione e di una risposta accurata alla domanda: “Che cosa perdiamo se questo componente non è disponibile o viene ripristinato a un momento precedente?”

  • Database relazionale: record transazionali dell'applicazione, identità, impostazioni o metadati, dove documentato.
  • Archiviazione di file o oggetti: caricamenti, allegati, esportazioni generate, contenuti multimediali o documenti, dove utilizzati.
  • Cache: determina se può essere ricostruita in sicurezza o se contiene stato che influisce sul ripristino.
  • Indice di ricerca o vector store: determina se è autorevole o se può essere ricostruito da un'altra fonte.
  • Stato della coda o del workflow: identifica se il lavoro in sospeso deve essere conservato e come viene ripristinato.
  • Configurazione dell'applicazione e segreti: conserva la configurazione necessaria per ricollegare i componenti e decrittografare o accedere ai dati protetti.

Quando un database integrato è una scelta sensata

Un database integrato è spesso appropriato quando rappresenta un deployment dell'applicazione ufficialmente documentato, il carico di lavoro ha un perimetro ristretto e lo stesso team può gestire applicazione e database come un unico servizio. Limita il numero di sistemi indipendenti che devono essere configurati, monitorati, modificati e ripristinati insieme.

Questa scelta non significa trattare il database come un componente secondario irrilevante. Necessita comunque di archiviazione persistente, credenziali, copertura di backup, monitoraggio della crescita dello storage, un percorso di aggiornamento documentato e test di ripristino. Il vantaggio è un confine di proprietà più semplice, non l'assenza di operazioni sul database.

Per un piccolo team tecnico, questa soluzione può essere più semplice da comprendere rispetto a un servizio remoto con percorsi di rete separati, regole firewall, gestione degli account e finestre di modifica. Mantieni chiaro il confine: lo stack applicativo e il suo database vengono distribuiti, aggiornati e ripristinati come un sistema coordinato.

  • Il fornitore documenta il deployment integrato come supportato.
  • Un unico team possiede sia il ciclo di vita dell'applicazione sia quello del database.
  • Un servizio database dedicato non è richiesto da policy, architettura o indicazioni del fornitore.
  • Il team può eseguire backup e ripristino del database e di ogni archivio autorevole correlato.
  • Lo stack dispone di un chiaro modello di archiviazione persistente anziché basarsi sul filesystem transitorio del container.

Quando è giustificato un database esterno

Utilizza un database gestito separatamente quando esiste un requisito concreto, anziché una preferenza per la separazione. Motivi validi includono l'architettura documentata di un'applicazione, un team database esistente con proprietà e procedure di ripristino chiare oppure una reale necessità che più carichi di lavoro approvati utilizzino un servizio database condiviso.

Un servizio condiviso non dovrebbe diventare un deposito informale per applicazioni non correlate. Ogni carico di lavoro necessita comunque di ruoli database definiti, confini di accesso, coordinamento della manutenzione e una decisione sul ripristino. La condivisione di un motore o di un cluster non elimina la necessità di isolare le credenziali e decidere chi possa apportare modifiche.

Una piattaforma database specialistica o un team interno dell'infrastruttura può essere la soluzione più adatta quando l'organizzazione possiede già le competenze, i controlli e il modello di servizio per gestirla. Quel team dovrebbe poter indicare chi gestisce accessi, aggiornamenti, verifica dei backup, ripristino, capacità e risposta agli incidenti. Se queste risposte non sono chiare, spostare il database altrove può limitarsi a spostare lavoro senza proprietario.

  • Il fornitore dell'applicazione documenta un database esterno come richiesto o supportato per il deployment previsto.
  • Un team nominato possiede le operazioni del database e dispone di una procedura di ripristino testata.
  • La connettività di rete, l'autenticazione e la gestione del firewall hanno proprietari chiari.
  • La necessità di un servizio condiviso è reale, approvata e compatibile con un adeguato isolamento degli accessi.
  • La manutenzione di applicazione e database può essere coordinata, incluse migrazioni dello schema e aggiornamenti di versione principale.

Non confondere la separazione con la resilienza

Un database esterno introduce un ulteriore confine di servizio. L'applicazione dipende ora dalla raggiungibilità di rete, dalla risoluzione del nome host, da regole firewall e di routing, dalle credenziali, dalle regole di autenticazione, dalla configurazione del listener del database e dal calendario di manutenzione del servizio esterno. Ognuna di queste dipendenze necessita di un proprietario e di un percorso di gestione degli incidenti.

Per PostgreSQL nello specifico, l'esposizione delle connessioni TCP/IP è regolata da impostazioni quali listen_addresses, mentre l'autenticazione dei client controlla chi può connettersi. PostgreSQL utilizza inoltre i ruoli per la gestione dei privilegi e l'utente database attivo determina l'accesso agli oggetti del database. Si tratta di controlli utili, ma devono essere progettati e mantenuti intenzionalmente.

La separazione può migliorare l'architettura di un'organizzazione quando corrisponde a capacità consolidate. Può anche aggiungere latenza, maggiore coordinamento nella gestione delle modifiche e una superficie di errore più ampia. Valuta l'intero percorso dal processo applicativo al database, non solo l'host del database.

  • L'applicazione può risolvere e raggiungere l'endpoint del database nelle condizioni di errore previste?
  • Quali percorsi di rete e regole firewall consentono la connessione?
  • Quale ruolo database utilizza l'applicazione e di quali privilegi necessita effettivamente?
  • Come vengono fornite, ruotate e revocate le credenziali?
  • Chi approva gli interventi di manutenzione che potrebbero influire sulla connettività dell'applicazione o sulla compatibilità dello schema?
  • Cosa accade quando il database è raggiungibile ma non è pronto, è sovraccarico o è in fase di ripristino?

Progetta il ripristino come una procedura per l'intero sistema

Un backup è utile solo se può ripristinare il servizio a un punto di recupero concordato. Pianifica il ripristino sull'intero percorso dei dati: il database, i file caricati o l'object storage, la configurazione dell'applicazione, i segreti o il materiale di crittografia e il corretto ordine di ripristino. Un ripristino riuscito del solo database può comunque lasciare un'applicazione incapace di trovare file, autenticarsi ai servizi o decrittografare dati protetti.

Per PostgreSQL, la pianificazione dei backup richiede una scelta consapevole tra dump logici, backup a livello di filesystem e archiviazione continua. PostgreSQL documenta questi approcci come differenti, con punti di forza e debolezze diversi. Un dump logico creato con pg_dump produce comandi che ricreano lo stato del database acquisito quando è iniziato il dump; non equivale alla semplice copia di un volume del container.

Gli obiettivi di ripristino dovrebbero guidare la scelta tecnica. Se il punto di recupero richiesto impone il ripristino a un momento compreso tra backup pianificati, sono necessarie capacità che vanno oltre i normali dump logici. Il ripristino point-in-time di PostgreSQL si basa su un backup di base più l'archiviazione continua dei write-ahead log; l'output di pg_dump e pg_dumpall non può essere utilizzato per la riproduzione dei write-ahead log.

Testa i ripristini in un ambiente isolato. Registra il tempo necessario per il ripristino, il punto recuperato, le verifiche di convalida eseguite, i passaggi manuali irrisolti e chi ha autorizzato il risultato. Considera le evidenze di un test di ripristino più preziose di un'ipotesi basata sul fatto che un processo di backup abbia segnalato successo.

  • Identifica la fonte autorevole e il metodo di backup per ogni componente persistente.
  • Definisci obiettivi di punto di recupero e tempo di ripristino che il team possa spiegare e testare.
  • Documenta l'ordine di ripristino, inclusi database, file, configurazione e segreti.
  • Verifica identità, ruoli e permessi necessari per ripristinare proprietà e privilegi del database.
  • Esegui test di ripristino periodici e conserva i risultati.
  • Verifica che la convalida a livello applicativo riesca dopo il ripristino, non solo che il servizio database si avvii.

Assegna le responsabilità prima del lancio in produzione

L'architettura è incompleta finché non vengono assegnate le responsabilità operative. Questo vale sia per database integrati sia per database esterni. Un database può essere tecnicamente raggiungibile ma comunque operativamente insicuro perché nessuno è responsabile degli accessi privilegiati, della crescita dello storage, degli errori di migrazione o della verifica dei ripristini.

Rendi esplicite le responsabilità in un runbook leggero o in un documento di proprietà del servizio. L'obiettivo non è la burocrazia: è garantire che una migrazione fallita, una credenziale scaduta, un volume in crescita o una richiesta di ripristino abbiano un percorso di risposta noto.

Gli aggiornamenti del database meritano particolare attenzione. PostgreSQL documenta metodi di aggiornamento espliciti per le versioni principali, compresi gli approcci di dump e ripristino. Un backup a livello di filesystem non sostituisce il metodo documentato di aggiornamento tramite dump e ripristino. Coordina le versioni del database supportate dall'applicazione con la procedura di aggiornamento del database prima di una finestra di manutenzione.

  • Chi applica gli aggiornamenti del database e dell'applicazione?
  • Chi controlla l'accesso da amministratore e i ruoli database ordinari dell'applicazione?
  • Chi ruota le credenziali e aggiorna in sicurezza la configurazione dell'applicazione?
  • Chi monitora capacità, errori di connessione e crescita dello storage?
  • Chi approva ed esegue le migrazioni dello schema?
  • Chi interviene se una migrazione fallisce o richiede un rollback?
  • Chi possiede backup, test di ripristino e autorizzazione del recupero?
  • Chi coordina gli aggiornamenti delle versioni principali del database con la compatibilità dell'applicazione?

Domande frequenti

Un database integrato è meno affidabile di un database esterno?

Non necessariamente. L'affidabilità dipende dal modello di deployment documentato e dalla capacità del team di gestire, monitorare, sottoporre a backup e ripristinare l'intero sistema. Un database esterno aggiunge dipendenze di rete, credenziali, controllo degli accessi e gestione delle modifiche. Un database integrato può essere una scelta sensata per uno stack supportato, circoscritto e con una proprietà chiara.

Un volume Docker può essere considerato un backup del database?

Un volume Docker fornisce archiviazione persistente che può sopravvivere a un container e Docker documenta flussi di lavoro per eseguire backup e ripristinare volumi. Questo non dimostra di per sé che una copia di una directory dati di un database in esecuzione sia coerente dal punto di vista del database. Utilizza il metodo di backup documentato dal motore database e testa il ripristino.

Che cosa deve essere sottoposto a backup oltre al database?

Fai l'inventario di tutto lo stato autorevole e critico per la sicurezza. A seconda dell'applicazione, può includere file caricati o object storage, configurazione, credenziali o materiale di crittografia, stato delle code e dati conservati in altri servizi persistenti. Dopo il ripristino, l'applicazione deve poter utilizzare i dati ripristinati.

Perché un'applicazione può non funzionare anche se il suo container database è stato avviato?

Un container database in esecuzione potrebbe non essere ancora pronto ad accettare connessioni. Docker documenta che Compose normalmente attende che una dipendenza sia in esecuzione, non che sia pronta. Quando appropriato, utilizza un controllo di integrità del database e una condizione di dipendenza che attenda che il servizio diventi integro.

Quando un team interno dell'infrastruttura dovrebbe gestire il database?

È una scelta adatta quando quel team dispone di proprietà chiara, controlli di accesso, procedure di aggiornamento, verifica dei backup, test di ripristino, gestione della capacità e risposta agli incidenti. Se queste pratiche non sono definite, un servizio database separato può creare una dipendenza aggiuntiva senza risolvere il rischio operativo.

I deployment gestiti delle applicazioni eliminano le responsabilità relative a database e governance?

No. Un deployment gestito può semplificare il lavoro infrastrutturale attorno a un'applicazione, ma i proprietari dell'applicazione devono comunque prendere decisioni su conservazione dei dati, accesso, ruoli privilegiati, integrazioni approvate, obiettivi di ripristino e governance. Airbip esegue le istanze di applicazioni del catalogo come carichi di lavoro Docker su server cloud e fornisce gestione del ciclo di vita del servizio, automazione del routing e TLS, controlli DNS e backup giornalieri, settimanali e mensili configurabili; i team dovrebbero comunque verificare il percorso dei dati e i requisiti di ripristino di ogni applicazione.

Fonti e approfondimenti

  1. Volumes — Docker Docs
  2. Control startup and shutdown order in Compose — Docker Docs
  3. Compose file reference: Secrets — Docker Docs
  4. How Compose works — Docker Docs
  5. PostgreSQL Backup and Restore — PostgreSQL Global Development Group
  6. PostgreSQL SQL Dump — PostgreSQL Global Development Group
  7. PostgreSQL Continuous Archiving and Point-in-Time Recovery — PostgreSQL Global Development Group
  8. PostgreSQL Client Authentication — PostgreSQL Global Development Group
  9. PostgreSQL Connection Settings — PostgreSQL Global Development Group
  10. Upgrading a PostgreSQL Cluster — PostgreSQL Global Development Group