חדש: רמזים, בקשות מקור קשורות וסריאליזציה של JSON ל-WebAuthn ב-Chrome

בגרסאות Chrome 128 ו-129 נוספו תכונות חדשות ומעניינות ל-WebAuthn – ממשק ה-API הבסיסי ליצירת מערכות אימות שמבוססות על מפתחות גישה.

  • רמזים: רמזים מעניקים לצדדים נסמכים (RP) שליטה טובה יותר בממשק המשתמש של WebAuthn בדפדפן. הם שימושיים במיוחד למשתמשים ארגוניים שרוצים להשתמש במפתחות אבטחה.
  • בקשות מקור קשורות: בעזרת בקשות מקור קשורות, ספקי ה-RP יכולים להפוך מפתחות גישה לתקפים בכמה דומיינים. אם יש לכם כמה אתרים, עכשיו אתם יכולים לאפשר למשתמשים להשתמש שוב במפתח הגישה שלהם בכל האתרים שלכם, וכך להפחית את החיכוך בכניסה.
  • סריאליזציה של JSON: ממשקי API לסריאליזציה של JSON מאפשרים לכם לפשט את הקוד של הקצה הקדמי של RP על ידי קידוד ופענוח של אפשרויות ופרטי כניסה שמועברים אל WebAuthn API וממנו.

רמזים

בעזרת hints, צדדים נסמכים (RP) יכולים עכשיו לציין העדפות של ממשק משתמש ליצירת מפתח גישה או לאימות באמצעות מפתח גישה.

בעבר, כש-RP רצה להגביל את מאמת המשתמש שבו המשתמש יכול להשתמש כדי ליצור מפתח גישה או לבצע אימות, הוא יכול היה להשתמש ב-authenticatorSelection.authenticatorAttachment כדי לציין את "platform" או את "cross-platform". הן מגבילות את מאמת החשבונות למאמת פלטפורמה או למאמת נדידה, בהתאמה. בעזרת hints, המפרט הזה יכול להיות גמיש יותר.

ה-RP יכול להשתמש ב-hints האופציונלי ב-PublicKeyCredentialCreationOptions או ב-PublicKeyCredentialRequestOptions כדי לציין את "security-key",‏ "client-device" ו-"hybrid" בסדר העדפות במערך.

בדוגמה הבאה מוצגת בקשה לדוגמה ליצירת פרטי כניסה, שמעדיפה אימותים מסוג "cross-platform" עם "security-key" בתור רמז. כך Chrome יציג ממשק משתמש שמתמקד במפתחות אבטחה למשתמשים בארגון.

const credential = await navigator.credentials.create({
  publicKey: {
    challenge: *****,
    hints: ['security-key'],
    authenticatorSelection: {
      authenticatorAttachment: 'cross-platform'
    }
  }
});
כשמציינים את 'security-key' כתובנית, בדפדפן מוצגת תיבת דו-שיח שמתמקדת במפתח אבטחה.
הצגת 'security-key' כהצעה מובילה להצגת תיבת דו-שיח שמתמקדת במפתח אבטחה בדפדפן.

כש-RP רוצה לתת עדיפות לתרחיש אימות במכשירים שונים, הוא יכול לשלוח בקשת אימות שמעדיפה מאמתים מסוג "cross-platform" עם "hybrid" בתור רמז.

const credential = await navigator.credentials.create({
  publicKey: {
    challenge: *****,
    residentKey: true,
    hints: ['hybrid']
    authenticatorSelection: {
      authenticatorAttachment: 'cross-platform'
    }
  }
});
אם מציינים 'היברידי' כתובנית, בדפדפן תוצג תיבת דו-שיח שמתמקדת בכניסה במכשירים שונים.
כשמציינים 'היברידי' כתובת טיפים, בדפדפן מוצגת תיבת דו-שיח שמתמקדת בכניסה במכשירים שונים.

בעזרת בקשות מקור קשורות, ספקי ה-RP יכולים לאפשר שימוש במפתחות גישה מכמה דומיינים. יצירת חוויית כניסה מרוכזת ושימוש בפרוטוקולים של איחוד נותרו הפתרון המומלץ לרוב האתרים. עם זאת, אם יש לכם כמה דומיינים ולא ניתן לבצע איחוד, מקורות קשורים יכולים להיות פתרון.

כל הבקשות ל-WebAuthn חייבות לציין מזהה צד נסמך (RP ID), וכל מפתחות הגישה משויכים למזהה RP יחיד. בעבר, מקור יכול היה לציין רק מזהה RP על סמך הדומיין שלו, כך שבמקרה כזה www.example.co.uk יכול היה לציין מזהה RP של example.co.uk, אבל לא של example.com. באמצעות בקשות מקור קשורות, אפשר לאמת מזהה RP שצוין על ידי אחזור קובץ JSON ידוע שנמצא בכתובת /.well-known/webauthn מהדומיין היעד. לכן, example.co.uk (וגם example.in, ‏ example.de וכו') יכולים להשתמש במזהה RP של example.com אם example.com מציין אותם בפורמט הבא:

כתובת אתר: https://example.com/.well-known/webauthn

{
  "origins": [
    "https://example.co.uk",
    "https://example.de",
    "https://example.sg",
    "https://example.net",
    "https://exampledelivery.com",
    "https://exampledelivery.co.uk",
    "https://exampledelivery.de",
    "https://exampledelivery.sg",
    "https://myexamplerewards.com",
    "https://examplecars.com"
  ]
}

במאמר איך מאפשרים שימוש חוזר במפתחות גישה באתרים שונים באמצעות בקשות של מקורות קשורים מוסבר איך מגדירים בקשות של מקורות קשורים.

סריאליזציה של JSON

אובייקטים של בקשה ותגובה ב-WebAuthn מכילים כמה שדות שמכילים נתונים בינאריים גולמיים ב-ArrayBuffer, כמו מזהה פרטי הכניסה, מזהה המשתמש או האתגר. אם אתר רוצה להשתמש ב-JSON כדי להחליף את הנתונים האלה עם השרת שלו, צריך קודם לקודד את הנתונים הבינאריים, למשל באמצעות Base64URL. המצב הזה מוסיף מורכבות מיותרת למפתחים שרוצים להתחיל להשתמש במפתחות גישה באתרים שלהם.

WebAuthn מציע עכשיו ממשקי API לניתוח אובייקטים של בקשות WebAuthn מסוג PublicKeyCredentialCreationOptions ו-PublicKeyCredentialRequestOptions ישירות מ-JSON, ולסריאליזציה של התשובה מסוג PublicKeyCredential ישירות ל-JSON. כל השדות עם ערך ArrayBuffer שנושאים נתונים בינאריים גולמיים עוברים המרה אוטומטית מהערכים שלהם בקידוד Base64URL או אליהם. ממשקי ה-API האלה זמינים החל מגרסה 129 של Chrome.

לפני יצירת מפתח גישה, מאחזרים מהשרת אובייקט PublicKeyCredentialCreationOptions מקודד ב-JSON ומפענחים אותו באמצעות PublicKeyCredential.parseCreationOptionsFromJSON().

Browser Support

  • Chrome: 129.
  • Edge: 129.
  • Firefox: 119.
  • Safari: 18.4.

Source

export async function registerCredential() {

  // Fetch encoded `PublicKeyCredentialCreationOptions`
  // and JSON decode it.
  const options = await fetch('/auth/registerRequest').json();

  // Decode `PublicKeyCredentialCreationOptions` JSON object
  const decodedOptions = PublicKeyCredential.parseCreationOptionsFromJSON(options);  

  // Invoke the WebAuthn create() function.
  const cred = await navigator.credentials.create({
    publicKey: decodedOptions,
  });
  ...

אחרי שיוצרים מפתח גישה, צריך לקודד את פרטי הכניסה שנוצרו באמצעות toJSON() כדי שאפשר יהיה לשלוח אותם לשרת.

Browser Support

  • Chrome: 129.
  • Edge: 129.
  • Firefox: 119.
  • Safari: 18.4.

Source

  ...
  const cred = await navigator.credentials.create({
    publicKey: options,
  });

  // Encode the credential to JSON and stringify
  const credential = JSON.stringify(cred.toJSON());

  // Send the encoded credential to the server
  await fetch('/auth/registerResponse', credential);
  ...

לפני האימות באמצעות מפתח גישה, צריך לאחזר מהשרת את הערך PublicKeyRequestCreationOptions המקודד ב-JSON ולפענח אותו באמצעות PublicKeyCredential.parseRequestOptionsFromJSON().

Browser Support

  • Chrome: 129.
  • Edge: 129.
  • Firefox: 119.
  • Safari: 18.4.

Source

export async function authenticate() {

  // Fetch encoded `PublicKeyCredentialRequestOptions`
  // and JSON decode it.
  const options = await fetch('/auth/signinRequest').json();

  // Decode `PublicKeyCredentialRequestOptions` JSON object
  const decodedOptions = PublicKeyCredential.parseRequestOptionsFromJSON(options);

  // Invoke the WebAuthn get() function.
  const cred = await navigator.credentials.get({
    publicKey: options
  });
  ...

אחרי האימות באמצעות מפתח גישה, צריך לקודד את פרטי הכניסה שנוצרו באמצעות השיטה toJSON() כדי שניתן יהיה לשלוח אותם לשרת.

Browser Support

  • Chrome: 129.
  • Edge: 129.
  • Firefox: 119.
  • Safari: 18.4.

Source

  ...
  const cred = await navigator.credentials.get({
    publicKey: options
  });

  // Encode the credential to JSON and stringify
  const credential = JSON.stringify(cred.toJSON());

  // Send the encoded credential to the server
  await fetch(`/auth/signinResponse`, credential);
  ...

מידע נוסף

מידע נוסף על WebAuthn ועל מפתחות גישה זמין במקורות המידע הבאים: