Signatur
Beschreibung
Die schreibgeschützte Eigenschaft navigator.credentials ist der Einstiegspunkt der Credential Management API. Sie liefert ein CredentialsContainer-Objekt mit den Methoden get(), create(), store() und preventSilentAccess().
Darüber lassen sich verschiedene Arten von Anmeldeinformationen einheitlich verwalten:
- Passkeys / WebAuthn (
PublicKeyCredential) – passwortlose Anmeldung mit Hardware-Schlüsseln, Fingerabdruck oder Face ID, - Passwörter (
PasswordCredential) – gespeicherte Benutzername-Passwort-Paare aus dem Passwortmanager des Browsers (nur Chromium), - Föderierte Identitäten (
IdentityCredentialüber FedCM, früherFederatedCredential), - Einmalcodes (
OTPCredential) – automatisches Auslesen von SMS-Codes (WebOTP, nur Chromium/Android).
Man verwendet die Eigenschaft immer dann, wenn eine Anmeldung ohne manuelles Eintippen ablaufen soll, etwa für automatisches Wiederanmelden, Passkey-Registrierung oder die Abfrage von SMS-Bestätigungscodes. Alle Methoden arbeiten asynchron und geben Promises zurück.
Rückgabewert
CredentialsContainer-Objekt des aktuellen Dokuments. In unsicheren Kontexten (HTTP) ist die Eigenschaft undefined.Beispiele
Unterstützung prüfen
const hasCredentials = window.isSecureContext && 'credentials' in navigator;
const hasWebAuthn = hasCredentials && typeof window.PublicKeyCredential === 'function';
console.log({ hasCredentials, hasWebAuthn });
Mit Passkey anmelden (WebAuthn)
const loginWithPasskey = async () => {
// Challenge muss vom Server stammen (hier vereinfacht)
const { challenge } = await fetch('/api/webauthn/challenge').then((r) => r.json());
const credential = await navigator.credentials.get({
publicKey: {
challenge: Uint8Array.from(atob(challenge), (c) => c.charCodeAt(0)),
rpId: location.hostname,
userVerification: 'preferred',
timeout: 60000
}
});
console.log('Credential-ID:', credential.id);
// credential.response an den Server senden und dort prüfen
};
document.querySelector('#login').addEventListener('click', () => {
loginWithPasskey().catch((err) => console.error(err.name, err.message));
});
SMS-Einmalcode automatisch einlesen (WebOTP)
if ('OTPCredential' in window) {
const controller = new AbortController();
const input = document.querySelector('input[autocomplete="one-time-code"]');
navigator.credentials
.get({ otp: { transport: ['sms'] }, signal: controller.signal })
.then((otp) => {
input.value = otp.code;
input.form.requestSubmit();
})
.catch((err) => console.warn('OTP nicht erhalten:', err.name));
// Nach 2 Minuten abbrechen
setTimeout(() => controller.abort(), 120000);
}
Automatische Anmeldung nach Abmelden unterbinden
const logout = async () => {
await fetch('/api/logout', { method: 'POST' });
// Verhindert, dass get() mit mediation: 'silent' sofort wieder anmeldet
await navigator.credentials.preventSilentAccess();
console.log('Abgemeldet');
};
logout();
// Wichtig · Fallstricke
- Nur sichere Kontexte: Unter HTTP ist
navigator.credentialsundefined– immer per Feature-Erkennung prüfen.localhostgilt als sicher. - Browser-Unterschiede: WebAuthn (
publicKey) wird überall unterstützt.PasswordCredential,FederatedCredentialundOTPCredentialgibt es nur in Chromium-Browsern; FedCM (identity) ist ebenfalls hauptsächlich Chromium. - Nutzeraktion:
create()undget()für Passkeys benötigen meist eine vorherige Nutzerinteraktion (Klick), besonders in Safari. Sonst droht einNotAllowedError. - iframes: In eingebetteten Frames müssen Berechtigungen per Permissions Policy freigegeben werden, z. B.
allow="publickey-credentials-get"bzw.otp-credentials. - Sicherheit: Die WebAuthn-Challenge muss zufällig und serverseitig erzeugt werden; die Antwort (Signatur, Origin,
rpId) ist immer auf dem Server zu prüfen. Clientseitige Prüfung allein ist wertlos. - Abgelehnte Dialoge oder Zeitüberschreitungen erscheinen als
NotAllowedError– dieser Fall sollte in der Oberfläche freundlich behandelt werden.