Passwort verschlüsseln und wieder entschlüsseln

beta20

Top Contributor
Hallo,

ich habe folgendes Szenario:
a) User gibt Emailkonfiguration von seinem Provider ein um Emails von meinem Webinterface abzurufen
b) Passwort soll verschlüsselt in der Datenbank abgespeichert werden
c) Beim Abrufen der Emails, muss das Passwort dann natürlich wieder entschlüsselt werden

Nun meine Frage:
- Was kann ich hier verwenden?
- Wie macht man das am Besten?

Meines Wissens benötige ich ja einen privaten / public Key?
Stand jetzt habe ich einen privaten Key als String und AES. Ist das aber richtig?
Wäre es besser ein binäres File zu erstellen, was meinen privaten Key hat?

Wäre so etwas brauchbar?

oder:

Wie erzeuge ich solch ein File?

Für Tipps, Ratschläge bin ich sehr dankbar.
 

mihe7

Top Contributor
Meines Wissens benötige ich ja einen privaten / public Key?
Das wäre asymmetrische Verschlüsselung. AES ist symmetrisch.

Um das sicher zu machen, dürftest Du den Schlüssel, mit dem Du das Passwort entschlüsselst, nicht auf dem System speichern. Dazu erzeugt man den Schlüssel normalerweise aus dem Benutzerpasswort.
 

beta20

Top Contributor
Ja, der User muss ich zuvor in der WebApp anmelden, bevor er Mails abrufen kann.


Das wäre asymmetrische Verschlüsselung. AES ist symmetrisch.

Um das sicher zu machen, dürftest Du den Schlüssel, mit dem Du das Passwort entschlüsselst, nicht auf dem System speichern. Dazu erzeugt man den Schlüssel normalerweise aus dem Benutzerpasswort.
1) Wo speichere ich dann den Schlüssel ab? Ich habe doch nur zwei Möglichkeiten a) Datenbank b) FileDrive ?

2) Benutzerpasswort ist eher schlecht, denn:
-> Meine App hat 1....n Firmen (auch Mandanten genannt)
-> 1 Mandant ..... n Employee
-> 1 Mandant ... n Emailpostfächer
-> Jeder Employee sollte auch Zugriff auf das Emailpostfach haben können (mind. Emails versenden).
-> Jeder Employee hat sein eigenes Passwort
 

mihe7

Top Contributor
1) Gar nicht.
2) Benutzerpasswort ist != E-Mail-Passwort - das funktioniert natürlich nur, wenn sich der Benutzer an Deiner Web-Anwendung anmeldet.

EDIT: gerade gesehen, dass Du oben bereits geschrieben hast, dass sich der Benutzer anmeldet. Dieses Passwort wäre dann das Benutzerpasswort, aus diesem generierst Du einen Schlüssel, den Du für die Ver-/Entschlüsselung der Login-Daten des E-Mail-Accounts verwendest. Siehe z. B. https://de.wikipedia.org/wiki/PBKDF2 sowie https://www.baeldung.com/java-password-hashing
 
Zuletzt bearbeitet:

mrBrown

Super-Moderator
Mitarbeiter
1) Wo speichere ich dann den Schlüssel ab? Ich habe doch nur zwei Möglichkeiten a) Datenbank b) FileDrive ?
Den speicherst du gar nicht ab, sodern generierst ihn bei jedem Login neu aus dem Passwort.

Benutzerpasswort ist eher schlecht, denn:
-> Meine App hat 1....n Firmen (auch Mandanten genannt)
-> 1 Mandant ..... n Employee
-> 1 Mandant ... n Emailpostfächer
-> Jeder Employee sollte auch Zugriff auf das Emailpostfach haben können (mind. Emails versenden).
-> Jeder Employee hat sein eigenes Passwort
Sag doch gleich, dass du so einen Spezialfall abdecken musst :p

Ich weiß ehrlich gesagt nicht, ob es dafür eine Patentlösung gibt...
Eine Möglichkeit ist aber, die von @mihe7 um eine Ebene zu erweitern, in dem man einen Schlüssel (per User) für den eigentlichen Schlüssel einführt, keine Ahnung ob das in diesem Fall das sinnvollste ist...
 

beta20

Top Contributor
ich fasse es mal zusammen:
1) Schlüssel speichere ich nirgends
-> privater Schlüssel ist dann der HASH vom originalen Passwort der Benutzeranmeldung?
-> Ich verwende derzeit hierfür SHA512

2) Verschlüsseltes Email Passwort speichere ich in der Datenbank
3) Entschlüsselung des Email Passworts geschieht dann über den privaten Schlüssel (HASH von Benutzeranmeldung)

4) Ändert der User sein Passwort, muss ebenfalls das Emailpasswort in der DB geändert werden (da sich dann der private Schlüssel ändert)

_____________

Gemeinsamer Zugriff:
- Um den gemeinsamen Zugriff ermöglichen:
-> Eine neue Tabelle einführen, die so aussieht:
a) User b) Schlüssel
-> Durch den Schlüssel je User, bekomme ich dann den eigentlichen Schlüssel für die Email?

Könnte das so aussehen? Bei dem gemeinsamen Zugriff sind mir die Erstellung der utnerschiedlichen Schlüssel noch nicht ganz klar. Insbesondere der Zugriff auf den "globalen Schlüssel"
 

Thallius

Top Contributor
Da du den Hash des Passwortes ja sicher in deiner DB speicherst um beim Login zu schaun ob der User das richtige Passwort eingegeben hat, wäre es nicht schlau diesen eh in der DB stehenden Hash zu nehmen um das Email-Passwrot zu verschlüsseln. Hier solltest du das richtige Passwort nehmen und nicht dessen Hash. Damit must du zwar das PW übers Netz schicken (Was auch nicht so schön ist) aber solange Du nur mit TLS arbeitest sollte das nicht so schlimm sein.

Gruß

Claus
 

mrBrown

Super-Moderator
Mitarbeiter
1) Schlüssel speichere ich nirgends
-> privater Schlüssel ist dann der HASH vom originalen Passwort der Benutzeranmeldung?
-> Ich verwende derzeit hierfür SHA512
DU darfst *nicht* den Hash als Schlüssel nutzen, den du schon in der DB gespeichert hast. Für das Passwort nimmt man im Idealfall eine extra für Passwörter entwickelte Hash-Funktion, für den Schlüssel dann etwas anderes.


Damit must du zwar das PW übers Netz schicken (Was auch nicht so schön ist) aber solange Du nur mit TLS arbeitest sollte das nicht so schlimm sein.
Wo, außer dem initialen Login, wird das Passwort dabei übers Netz geschickt?
 

Thallius

Top Contributor
Wo, außer dem initialen Login, wird das Passwort dabei übers Netz geschickt?

Habe ich das behauptet? Aber für den intialen Login muss man das Passwort ja auch nicht zwangsweise übers Netz schicken. Das geht auch eleganter indem man sich vom Server einen Schlüssel zum Hashen holt und dann nur den Hash verschickt.

Gruß

Claus
 

mrBrown

Super-Moderator
Mitarbeiter
Gemeinsamer Zugriff:
- Um den gemeinsamen Zugriff ermöglichen:
-> Eine neue Tabelle einführen, die so aussieht:
a) User b) Schlüssel
-> Durch den Schlüssel je User, bekomme ich dann den eigentlichen Schlüssel für die Email?

Könnte das so aussehen? Bei dem gemeinsamen Zugriff sind mir die Erstellung der utnerschiedlichen Schlüssel noch nicht ganz klar. Insbesondere der Zugriff auf den "globalen Schlüssel"
Für das Mail-Passwort wird ein zufälliger Schlüssel generiert, das Mail-Passwort wird dann mit diesem verschlüsselt gespeichert.
Der Schlüssel wird für jeden Nutzer mit dessen Passwort (bzw, daraus abgeleiteten Schlüssel) verschlüsselt und pro Nutzer gespeichert.

Beim entschlüsseln wird mit dem Nutzer-Passwort der Schlüssel entschlüsselt, und mit diesem dann das Mail-Passwort.
 

mihe7

Top Contributor
Im zweiten Link ist ein Beispiel für PBKDF unter Java angegeben. Es ist hier nicht einfach nur ein Hash, sondern ein spezieller Hash des Benutzerpassworts. Am besten wäre es, wenn die Hashfunktion für den Schlüssel eine andere ist als die, mit der Du den Hash für die Benutzer-DB erzeugst (sonst hast Du einen Angriffspunkt für den Schlüssel in der DB stehen).

Hintergrund ist, dass Passwörter in der Regel nicht genau die erforderliche Bitlänge des Schlüssels haben und oft nicht über ausreichende Entropie verfügen. Daher wird das Passwort mit einer Hash-Funktion auf den Schlüssel abgebildet. Ein einfacher Hash ist sehr schnell berechnet, weshalb Angriffe über das Passwort durchaus möglich wären. Aus diesem Grund setzt man hier ein Verfahren ein, das "möglichst" lange dauert. Wenn Du für vier Versuche 1 Sekunde benötigst, vergeht Dir schnell die Lust am Durchprobieren, weil Du in den nächsten Jahren keinen Erfolg haben wirst.
 

beta20

Top Contributor
OK, heißt das dann.

MailPasswort:
- Zufälliger Schlüssel generiert (createRandomKey)
- Mail-Passwort wird verschlüsselt mit dem "Zufälligen Schlüssel" generiert und in der DB gespeichert

Schlüssel Nutzer:
- "Zufälliger Schlüssel" wird mit dem Benutzerpasswort verschlüsselt. Der verschlüsselte Schlüssel wird dann in der DB gespeichert
-> Extra Tabelle (ID, Passwort, Employee_FK, EmailSetting_FK)

______________________________________________

Folgende Fälle müssen beachtet werden:

a) Benutzer ändert sein Passwort.
-> Dann muss in der Datenbank das verschlüsselte Passwort (Schlüssel Nutzer) ebenfalls geupdatet werden

b) Neuer Benutzer wird erstellt
-> Dieser hat ja zunächst kein Tabelleneintrag auf das Emailpostfach. Hierzu muss dann für jedes Mailpostfach ein Tabelleneintrag erstellt werden (Schlüssel Nutzer)

-> Bitte um Prüfung, ob das so passt...
 

mihe7

Top Contributor
Dann muss in der Datenbank das verschlüsselte Passwort (Schlüssel Nutzer) ebenfalls geupdatet werden
Richtig.
Hierzu muss dann für jedes Mailpostfach ein Tabelleneintrag erstellt werden (Schlüssel Nutzer)
Richtig. EDIT: beim Hinzufügen der Mailbox müssen die von Dir unter "MailboxPasswort" und "Schlüssel Nutzer" genannten Schritte ausgeführt werden. Das muss nicht unbedingt etwas mit dem "neuen" Benutzer zu tun haben.
 

mrBrown

Super-Moderator
Mitarbeiter
a) Benutzer ändert sein Passwort.
-> Dann muss in der Datenbank das verschlüsselte Passwort (Schlüssel Nutzer) ebenfalls geupdatet werden
Ja, bei der Änderung hast du ja immer altes und neues Passwort, also gespeicherten, verschlüsselten Schlüssel mit altem Entschlüsseln und mit neuem verschlüsselt speichern.

b) Neuer Benutzer wird erstellt
-> Dieser hat ja zunächst kein Tabelleneintrag auf das Emailpostfach. Hierzu muss dann für jedes Mailpostfach ein Tabelleneintrag erstellt werden (Schlüssel Nutzer)
Ja.
Für das erstellen des Tabelleneintrags brauchst du aber den entschlüsselten, "zufälligen Schlüssel", daher muss dabei immer ein weitere Nutzer beteiligt sein, der Zugriff darauf hat.
 

mrBrown

Super-Moderator
Mitarbeiter
Ist doch das gleiche Prinzip. Ob ich nun einen Token abhole und den benutze oder einen Salt den ich zum hashen benutze ist doch nur eine Frage der Begrifflichkeit
Wie 2FA umgesetz ist, ist reines Implementierungsdetail, es muss also nicht mal einen Token der abgeholt wird geben.
Ein einmaliger Token ist keineswegs mit einem Salt zum Hashen vergleichbar...


Einfach https nutzen, dann ist das Passwort immer verschlüsselt und man muss es nicht selbst noch irgendwie umsetzen und dabei uU das ganze schwächer machen...
 

mihe7

Top Contributor
@Thallius vielleicht habe ich Dich tatsächlich falsch verstanden. Gegenfrage: wenn Du den Hash zu Anwendung geschickt hast, was macht die damit? Womit wird der Hash verglichen?
 
X

Xyz1

Gast
@beta20 Also gängig ist, das Passwort im Klartext zu speichern. Zum zusätzlichen Schutz kann der Benutzer ein Passwort eingeben, um das Passwort zu speichern.
 

petebocs

Mitglied
Ich dachte es ist eindeutig: "Ein Endbenutzer (User oder Resource Owner) kann mit Hilfe dieses Protokolls einer Anwendung (Client oder Third-Party) den Zugriff auf seine Daten erlauben (Autorisierung), die von einem anderen Dienst (Resource Server) bereitgestellt werden, ohne geheime Details seiner Zugangsberechtigung(Authentifizierung) dem Client preiszugeben."

Zum Beispiel Gmail unterstützt Oauth:
 
X

Xyz1

Gast
Nach den Stakeholdern habe ich mich auch schon gefragt... Imho ist ein "Endbenutzer" hier gleichzusetzen mit einem "Client". Damit bringts wohl nix.
 

mrBrown

Super-Moderator
Mitarbeiter
Ich dachte es ist eindeutig: "..."
Wikipedia kann ich auch lesen...

Mir war bisher kein Multi-User, OAuth-fähiger Mail-Provider bekannt, deshalb die Frage ^^

Ok, wie ich es verstanden diese Protokoll könnte hier die Lösung sein. :)
Hier gibt es eine Liste mit den Providern:
https://en.wikipedia.org/wiki/List_of_OAuth_providers
Interessanter wären Mail-Provider mit XOAuth(2)...Microsoft unterstützt das sieht auch, aber sonst?
 

mihe7

Top Contributor
Wir können das, wie mir scheint, abkürzen: XOAuth ist nicht weit verbreitet -> kein Standard -> keine Lösung.
 

Ähnliche Java Themen

Neue Themen


Oben