Hallo,
ich bin gerade dabei, mich mit Sicherheit in Bezug auf REST-Services zu beschäftigen und suche nach einer bestmöglichen Lösung. Im einfachsten Fall erfolgt die Identifizierung eines Nutzers über eine ID (Developer-ID) die bei jedem Request übertragen wird. Das ist natürlich unsicher, da die ID leicht abgehört werden kann.
Daneben scheint für zusätzliche Sicherheit folgendes Modell zu existieren:
- Neben einer Developer-ID erhalten Nutzer einen geheimen Schlüssel. Der Schlüssel ist dem Service-Provider bekannt.
- Bei einer Anfrage wird ein Hash aus Timestamp, geheimem Schlüssel und Service mitübertragen (zusätzlich zu der Developer-ID). Die Applikation kann in der Datenbank den geheimen Schlüssel für die Developer-ID nachsehen, die gleiche Hashsumme aus Nachricht und Timestamp generieren und damit die Berechtigung der Anfragen prüfen.
Nachteil dieser Lösung (wenn sie denn so eingesetzt wird) wäre offensichtlich, dass der geheime Schlüssel in der Datenbank abgelegt werden muss, also eben ein shared secret key ist.
Daneben bin ich mittels digitaler Signatur auf folgende Lösung gekommen:
- Der Nutzer erhält einen privaten und öffentlichen Schlüssel (die wie bei PGP eine asymetrische Verschlüsselung ermöglichen). Den öffentlichen Schlüssel verwendet man als Developer-ID und überträgt ihn mit. Auf dem Server wird nur der öffentliche Schlüssel gespeichert.
- Der Nutzer erstellt eine Hashsumme aus dem Inhalt der Anfrage und einer Timestamp. Dieser Message-Digest wird verschlüsselt mit dem secret key, der nur dem Nutzer bekannt ist. Auf Server-Seite wird der Digest entschlüsselt mit dem public key und mit einem neu generierten Hash aus Nachricht und Timestamp verglichen. Bei übereinstimmung kann davon ausgegangen werden, dass der Hash mit dem private key verschlüsselt wurde, da er mit dem zugehörigen public key korrekt dekodiert werden kann.
Sieht jemand einen Denkfehler in dieser Lösung?
Problematisch könnte vielleicht die technische Umsetzbarkeit sein, da ich über PHP die entsprechenden Verschlüsselungsmethoden und gpg zur Generierung der Schlüssel aufrufen muss, was vielleicht die Serverlast zu sehr erhöht. Da bin ich mir aber nicht sicher und es käme wohl auf einen Versuch an.
Wie siehts mit dem generellen Ansatz aus? Wäre sowas brauchbar?
Danke und Grüße,
Michael H.
ich bin gerade dabei, mich mit Sicherheit in Bezug auf REST-Services zu beschäftigen und suche nach einer bestmöglichen Lösung. Im einfachsten Fall erfolgt die Identifizierung eines Nutzers über eine ID (Developer-ID) die bei jedem Request übertragen wird. Das ist natürlich unsicher, da die ID leicht abgehört werden kann.
Daneben scheint für zusätzliche Sicherheit folgendes Modell zu existieren:
- Neben einer Developer-ID erhalten Nutzer einen geheimen Schlüssel. Der Schlüssel ist dem Service-Provider bekannt.
- Bei einer Anfrage wird ein Hash aus Timestamp, geheimem Schlüssel und Service mitübertragen (zusätzlich zu der Developer-ID). Die Applikation kann in der Datenbank den geheimen Schlüssel für die Developer-ID nachsehen, die gleiche Hashsumme aus Nachricht und Timestamp generieren und damit die Berechtigung der Anfragen prüfen.
Nachteil dieser Lösung (wenn sie denn so eingesetzt wird) wäre offensichtlich, dass der geheime Schlüssel in der Datenbank abgelegt werden muss, also eben ein shared secret key ist.
Daneben bin ich mittels digitaler Signatur auf folgende Lösung gekommen:
- Der Nutzer erhält einen privaten und öffentlichen Schlüssel (die wie bei PGP eine asymetrische Verschlüsselung ermöglichen). Den öffentlichen Schlüssel verwendet man als Developer-ID und überträgt ihn mit. Auf dem Server wird nur der öffentliche Schlüssel gespeichert.
- Der Nutzer erstellt eine Hashsumme aus dem Inhalt der Anfrage und einer Timestamp. Dieser Message-Digest wird verschlüsselt mit dem secret key, der nur dem Nutzer bekannt ist. Auf Server-Seite wird der Digest entschlüsselt mit dem public key und mit einem neu generierten Hash aus Nachricht und Timestamp verglichen. Bei übereinstimmung kann davon ausgegangen werden, dass der Hash mit dem private key verschlüsselt wurde, da er mit dem zugehörigen public key korrekt dekodiert werden kann.
Sieht jemand einen Denkfehler in dieser Lösung?
Problematisch könnte vielleicht die technische Umsetzbarkeit sein, da ich über PHP die entsprechenden Verschlüsselungsmethoden und gpg zur Generierung der Schlüssel aufrufen muss, was vielleicht die Serverlast zu sehr erhöht. Da bin ich mir aber nicht sicher und es käme wohl auf einen Versuch an.
Wie siehts mit dem generellen Ansatz aus? Wäre sowas brauchbar?
Danke und Grüße,
Michael H.
Kommentar