Come assegnare a un'applicazione Web una chiave per decrittografare i dati in un database

0

La mia situazione è che ho bisogno di memorizzare dati sensibili in un database per un'applicazione web. I dati sensibili includono cose come token di aggiornamento per i sistemi Oauth2, chiavi segrete per altre API ecc.

Sto cercando di costruire questo presupponendo che un utente malintenzionato abbia già accesso al server e possa vedere i file binari che eseguono l'applicazione (nessun codice sorgente sul server), le variabili di ambiente e i database ecc.

Quindi sostanzialmente la cosa che sto cercando di proteggere da qui è che un utente malintenzionato può leggere le informazioni sensibili dal database.

Per far ciò suppongo di dover crittografare i dati prima di archiviarli nel database, ma questo mi ha lasciato il problema di come fornire l'applicazione web con le chiavi per crittografare e decrittografare i dati in primo luogo.

Se un utente malintenzionato ha già accesso al server, le variabili di ambiente, i file di configurazione e persino altri server che l'applicazione può rendere richieste HTTP sembrano inutili perché l'autore dell'attacco potrebbe semplicemente fare le stesse cose che l'applicazione fa per richiedere le chiavi comunque.

Quindi, da quello che posso capire implementando un flusso di lavoro in cui l'applicazione richiede che le chiavi non funzionino. Invece ho bisogno di un flusso di lavoro in cui l'applicazione è data le chiavi invece.

Inizialmente pensavo di poter inserire le chiavi manualmente all'avvio dell'applicazione e tenerle in memoria, ma il problema è che avrei bisogno di intervenire manualmente per avviare ogni istanza dell'applicazione. Idealmente voglio che la startup sia automatizzata il più possibile, il che significherebbe dare le chiavi a qualche tipo di script o qualcosa del genere, nel qual caso sono tornato al punto di partenza.

Finora l'unico modo in cui sono arrivato a fornire l'applicazione con i tasti in qualche modo in modo automatico è implementare un endpoint di qualche tipo che può essere POST con i tasti.

L'idea è che avvii l'applicazione sul server, ma l'applicazione rifiuta tutte le richieste perché non ha ancora le chiavi. Le chiavi sono memorizzate su una macchina separata da qualche parte; questa macchina potrebbe essere in ufficio o in un altro server, ecc.

La macchina con le chiavi quindi POST s all'endpoint dell'applicazione per assegnarle le chiavi su una connessione HTTPS e l'applicazione memorizza le chiavi in memoria fino a quando non viene riavviata, a quel punto avrà bisogno delle chiavi POST ed ad esso di nuovo.

Una volta fornite le chiavi, l'applicazione accetterà richieste come normali e interromperà l'endpoint che ha accettato le chiavi.

Ciò significa che un utente malintenzionato potrebbe trovare l'endpoint e provare POST inserendo le chiavi direttamente, ma è altamente improbabile che forniscano comunque le chiavi corrette e anche se l'applicazione accetta le chiavi nella piccola finestra di tempo dove l'endpoint sarebbe disponibile i dati decrittografati sarebbero comunque incomprensibili.

Quindi ora le mie domande sono, sto pensando troppo a questo, e c'è un modo migliore, standard nel settore, di fornire le chiavi a un'applicazione web allo scopo di crittografare / decifrare i dati in un database?

Se non c'è un metodo concordato per farlo, la mia idea sarebbe fattibile e che tipo di cose sto trascurando potrebbe effettivamente indebolire la sicurezza invece di rafforzarla?

    
posta Jake Lucas 20.12.2017 - 03:34
fonte

2 risposte

1

Initially I thought that I could just enter the keys manually on application startup and keep them stored in memory, but the problem with that is then I would need to manually intervene to start up each instance of the application.

Anche se la memoria è in pratica notevolmente più sicura di quella sul disco se hanno abbastanza accesso alla macchina sottostante che esegue l'applicazione, possono semplicemente fare un core dump e sollevare le chiavi da lì.

So now my questions are, am I overthinking this, and is there a better, industry standard way of providing keys to a web application for the purpose of encrypting/decrypting data in a database?

L'approccio migliore che ho visto è quello di averli memorizzati sul server delle applicazioni in un file di configurazione che non è leggibile dall'utente che esegue l'applicazione. Vengono passati come argomenti o tramite IPC all'avvio dell'applicazione.

Questo significa che l'escalation dei privilegi sul server delle applicazioni è necessaria per ottenere le chiavi. Se il server DB è compromesso, le chiavi non ci sono.

    
risposta data 20.12.2017 - 10:45
fonte
1

Il nucleo ASP.net è integrato nel framework supportato per lo scenario che descrivi e che potresti utilizzare come esempio di implementazione nel tuo framework di scelta.

Questo articolo documenta un setup di esempio della Azure KeyVault Configuration Provider .

In sostanza utilizza Azure KeyVault per archiviare i tuoi segreti, protetti tramite il controllo dell'accesso basato sui ruoli.

Quindi ha un provider di configurazione che può caricare le impostazioni dell'applicazione dal keyvault. Il provider di configurazione è autorizzato a utilizzare keyvault tramite un "client secret" o un certificato che tipicamente verrà impostato durante la distribuzione dell'applicazione (e non verrà visualizzato nel controllo del codice sorgente).

Azure ha in beta la capacità di " identità del servizio gestito " il che significa essenzialmente che non devi preoccuparti di distribuire il segreto o il certificato del cliente da solo.

Questo potrebbe essere eccessivo per il tuo caso d'uso. Potresti semplicemente avere un file di configurazione crittografato (proteggendolo mentre sul file system) in cui la macchina può decodificare al volo.

    
risposta data 20.12.2017 - 23:38
fonte