Sto sviluppando un'API REST ma non riesco a utilizzare HTTPS senza utilizzare certificati autofirmati . Capisco che potrebbe essere accettabile per alcuni, ma non voglio che i messaggi di sicurezza saltino fuori sui browser dei client.
Le informazioni trasmesse sulla rete non sono sensibili, quindi non mi interessa l'intercettazione, ma voglio assicurarmi che solo i client autorizzati siano in grado di effettuare richieste e prevenire attacchi di riproduzione. Ecco la mia idea:
Un utente è registrato con l'applicazione Web che esegue il servizio. Vogliono registrare un client API, ma non sono uno sviluppatore, quindi scaricano un'applicazione client fornita (in questo caso, un lettore di schede IC che utilizzeranno con un computer in grado di comunicare i dati letti dalle carte scansionate al servizio web tramite l'API).
Passaggio uno : l'applicazione client API genera una coppia di chiavi (ad esempio OpenSSL) e invia la chiave pubblica al server (può trattarsi di un passaggio di caricamento manuale quando l'utente registra il client con il server ). Il server memorizza la chiave pubblica nel database associato all'utente e una descrizione del client (ad esempio "IC Card Reader su PC01").
Perché voglio usare una coppia di chiavi (come SSH)? Sento che un segreto condiviso è vulnerabile alle intercettazioni perché deve essere trasferito sulla rete almeno una volta. Mentre questo potrebbe essere evitato inserendo manualmente la chiave sul terminale del server anziché trasportarlo sulla rete, un obiettivo di progettazione del sistema è quello di consentire agli utenti diversi da me di registrare i client e ottenere un token di accesso API utilizzando l'interfaccia web per il applicazione. In questa circostanza, un intercettatore potrebbe intercettare una chiave segreta condivisa, mentre una coppia di chiavi generata dal client lo impedirebbe.
Passaggio due : quando si effettua una richiesta, il client ottiene prima un nonce dal server (che lo memorizza in un elenco o database di nonces e timestamp emessi) e quindi effettua la richiesta incluso il nonce mentre firmando la richiesta con la loro chiave privata. Il server verifica che il messaggio sia autentico (è stato firmato dal client e nessun altro) prima dell'esecuzione della richiesta.
Il mio obiettivo con questo approccio è quello di garantire che solo i client validi stiano accedendo all'API, impedendo allo stesso tempo gli attacchi di riproduzione. Un utente malintenzionato dovrebbe essere in grado di vedere il contenuto dei messaggi (non molto sensibile), ma non dovrebbe essere in grado di modificarli. Al cliente non importa se i dati provenienti dal server sono autentici (perché in questo caso il client sta cambiando lo stato del server, non il contrario).
- Questo approccio soddisfa questi obiettivi di progettazione?
- E impedisce contro gli attacchi man-in-the-middle (assumendo l'originale la registrazione del cliente era con il server reale e non un quello falso dell'attaccante)?