אימות בגאדג'טים לבישים

מילות מפתח: Wear, משתמש, auth

אפליקציות Wear OS יכולות לפעול באופן עצמאי, ללא אפליקציה נלווית. כלומר, אפליקציית Wear OS צריכה לנהל את האימות בעצמה כשהיא ניגשת לנתונים מהאינטרנט. עם זאת, גודל המסך הקטן של השעון ויכולות הקלט המצומצמות של השעון מגבילות את אפשרויות האימות שאפשר להשתמש בהן באפליקציית Wear OS.

במדריך הזה מפורטות שיטות האימות המומלצות לאפליקציות ל-Wear OS, וגם שיטות חלופיות במקרים שבהם השיטות האלה לא מתאימות לתרחיש לדוגמה של האפליקציה.

למידע נוסף על תכנון חוויית כניסה טובה, אפשר לעיין במדריך בנושא חוויית משתמש בכניסה.

מצב אורח

לא דורשים אימות לכל הפונקציונליות. במקום זאת, כדאי לספק למשתמש כמה שיותר תכונות בלי לדרוש ממנו להיכנס לחשבון.

משתמשים עשויים למצוא ולהתקין את האפליקציה שלכם ל-Wear בלי להשתמש באפליקציה לנייד, ולכן יכול להיות שאין להם חשבון והם לא יודעים אילו תכונות היא מציעה. צריך לוודא שהפונקציונליות של מצב אורח מציגה באופן מדויק את תכונות האפליקציה.

יכול להיות שחלק מהמכשירים לא יינעלו יותר זמן

במכשירים נתמכים עם Wear OS 5 ואילך, המערכת מזהה אם המשתמש עונד את המכשיר על פרק כף היד. אם המשתמש משבית את זיהוי פרק כף היד ואז מסיר את המכשיר מהפרק, המערכת שומרת על ביטול הנעילה של המכשיר למשך זמן ארוך יותר מאשר במקרה אחר.

אם האפליקציה שלכם דורשת רמת אבטחה גבוהה יותר – למשל, כשמוצגים בה נתונים רגישים או פרטיים – תחילה צריך לבדוק אם זיהוי פרק כף היד מופעל:

val wristDetectionEnabled =
        isWristDetectionAutoLockingEnabled(applicationContext)

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

שיטות אימות מומלצות

אפשר להשתמש בשיטות האימות הבאות כדי לאפשר לאפליקציות נפרדות ל-Wear OS לקבל את פרטי הכניסה לאימות המשתמשים.

העברת אסימונים באמצעות שכבת הנתונים

אפליקציית התלווה לטלפון יכולה להעביר נתוני אימות לאפליקציית Wear OS בצורה מאובטחת באמצעות שכבת הנתונים של Wearables. העברת פרטי הכניסה כהודעות או כפריטי נתונים.

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

חשוב: אפליקציית Wear שלך צריכה להציע לפחות שיטת אימות אחת נוספת, כי האפשרות הזו פועלת רק בשעונים מותאמים ל-Android כשהאפליקציה המתאימה לנייד מותקנת. לספק שיטת אימות חלופית למשתמשים שאין להם את האפליקציה לנייד המתאימה, או שהמכשיר שלהם עם Wear OS מותאם למכשיר iOS.

העברת אסימונים באמצעות שכבת הנתונים מהאפליקציה לנייד, כפי שמתואר בדוגמה הבאה:

val token = "..." // Auth token to transmit to the wearable device.
val dataClient: DataClient = Wearable.getDataClient(context)
val putDataReq: PutDataRequest = PutDataMapRequest.create("/auth").run {
    dataMap.putString("token", token)
    asPutDataRequest()
}
val putDataTask: Task<DataItem> = dataClient.putDataItem(putDataReq)

האזנה לאירועי שינוי נתונים באפליקציית השעון כמו בדוגמה הבאה:

val dataClient: DataClient = Wearable.getDataClient(context)
dataClient.addListener{ dataEvents ->
    dataEvents.forEach { event ->
        if (event.type == DataEvent.TYPE_CHANGED) {
            val dataItemPath = event.dataItem.uri.path ?: ""
            if (dataItemPath.startsWith("/auth")) {
                val token = DataMapItem.fromDataItem(event.dataItem).dataMap.getString("token")
                // Display interstitial screen to notify the user they are being signed in.
                // Then, store the token and use it in network requests.
            }
        }
    }
}

למידע נוסף על השימוש בשכבת הנתונים הלבישת, אפשר לקרוא את המאמר שליחה וסנכרון של נתונים ב-Wear OS.

שימוש ב-OAuth 2.0

ב-Wear OS יש תמיכה בשני תהליכים שמבוססים על OAuth 2.0, שמפורטים בהמשך:

  • הענקת קוד הרשאה עם מפתח הוכחה ל-Code Exchange (PKCE), כפי שמוגדר ב-RFC 7636
  • הענקת הרשאת גישה למכשיר, כפי שמוגדר ב-RFC 8628

הערה: כדי לוודא שהאפליקציה לא תיסגר כשהשעון עובר למצב אווירה, צריך להפעיל את התכונה 'תמיד מופעל' באמצעות AmbientModeSupport.attach בפעילות שמבצעת את האימות. למידע נוסף על שיטות מומלצות במצב אווירה, ראו איך שומרים על האפליקציה גלויה ב-Wear.

מפתח הוכחה לחילופי קודים (PKCE)

כדי להשתמש ב-PKCE ביעילות, צריך להשתמש ב-RemoteAuthClient.

כדי לבצע בקשת אימות מאפליקציית Wear OS לספק OAuth, יוצרים אובייקט OAuthRequest. האובייקט הזה מורכב מכתובת URL של נקודת הקצה ב-OAuth לצורך קבלת אסימון ואובייקט CodeChallenge. הקוד הבא מציג דוגמה ליצירת בקשת אימות:

val request = OAuthRequest.Builder(this.applicationContext)
    .setAuthProviderUrl(Uri.parse("https://...."))
    .setClientId(clientId)
    .setCodeChallenge(codeChallenge)
    .build()

אחרי שיוצרים את בקשת האימות, שולחים אותה לאפליקציה הנלווית באמצעות השיטה sendAuthorizationRequest():

val client = RemoteAuthClient.create(this)
client.sendAuthorizationRequest(request,
    { command -> command?.run() },
    object : RemoteAuthClient.Callback() {
        override fun onAuthorizationResponse(
            request: OAuthRequest,
            response: OAuthResponse
        ) {
            // Extract the token from the response, store it and use it in network requests.
        }

        override fun onAuthorizationError(errorCode: Int) {
            // Handle error
        }
    }
)

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

אחרי הרשאה מוצלחת או כושלת, שרת OAuth 2.0 מפנה לכתובת ה-URL שצוינה בבקשה. אם המשתמש יאשר את בקשת הגישה, התשובה תכלול קוד הרשאה. אם המשתמש לא יאשר את הבקשה, התשובה תכלול הודעת שגיאה.

התגובה היא בצורת מחרוזת שאילתה, והיא נראית כמו אחת מהדוגמאות הבאות:

  https://wear.googleapis.com/3p_auth/com.your.package.name?code=xyz
  https://wear.googleapis-cn.com/3p_auth/com.your.package.name?code=xyz

הפעולה הזו טוענת דף שמפנה את המשתמש לאפליקציית האפליקציה. אפליקציית האפליקציה מאמתת את כתובת ה-URL של התגובה ומעבירה את התגובה לאפליקציית השעון של הצד השלישי באמצעות ה-API ‏onAuthorizationResponse.

לאחר מכן, אפליקציית השעון יכולה להחליף את קוד האימות באסימון גישה.

הערה: אחרי שהמאפיין OAuthRequest נוצר, אפשר למצוא את כתובת ה-URL להפניה אוטומטית על ידי גישה ל-redirectUrl.

הענקת הרשאת גישה למכשיר

כשמשתמשים בהענקת הרשאת אימות למכשיר, המשתמש פותח את ה-URI לאימות במכשיר אחר. לאחר מכן, שרת ההרשאות מבקש מהם לאשר או לדחות את הבקשה.

כדי להקל על התהליך, אפשר להשתמש ב-RemoteActivityHelper כדי לפתוח דף אינטרנט במכשיר הנייד המותאם של המשתמש, כפי שמתואר בדוגמה הבאה:

// Request access from the authorization server and receive Device Authorization Response.
val verificationUri = "..." // Extracted from the Device Authorization Response.
RemoteActivityHelper.startRemoteActivity(
    this,
    Intent(Intent.ACTION_VIEW)
        .addCategory(Intent.CATEGORY_BROWSABLE)
        .setData(Uri.parse(verificationUri)),
    null
)
// Poll the authorization server to find out if the user completed the user authorization
// step on their mobile device.

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

שיטות אימות אחרות

ב-Wear OS יש תמיכה בשיטות נוספות לכניסה לחשבון, שמפורטות בקטעים הבאים.

כניסה באמצעות חשבון Google

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

אחרי שיטות האימות המומלצות שתוארו למעלה, כניסה באמצעות חשבון Google היא הפתרון המועדף הבא כי היא פועלת היטב גם ב-iOS. בקטע הבא מוסבר איך לבצע שילוב בסיסי של כניסה באמצעות חשבון Google.

דרישות מוקדמות

לפני שתוכלו להתחיל לשלב את 'כניסה באמצעות חשבון Google' באפליקציה שלכם ל-Wear OS, עליכם להגדיר פרויקט ב-Google API Console ולהגדיר את הפרויקט ב-Android Studio. למידע נוסף, ראו תחילת השילוב של כניסה באמצעות חשבון Google באפליקציה ל-Android.

אם אתם משתמשים בכניסה באמצעות חשבון Google באמצעות אפליקציה או אתר שמתקשרים עם שרת עורפי, יש עוד שתי דרישות מוקדמות:

  • יוצרים מזהה לקוח של אפליקציית אינטרנט ב-OAuth 2.0 בשביל שרת הקצה העורפי. מזהה הלקוח הזה שונה ממזהה הלקוח של האפליקציה. למידע נוסף, ראו הפעלת גישה בצד השרת.
  • זיהוי מאובטח של המשתמש שמחובר כרגע בשרת, על ידי שליחת אסימון המזהה של המשתמש באמצעות HTTPS. במאמר אימות באמצעות שרת לקצה העורפי מוסבר איך מאמתים את המשתמש בשרת לקצה העורפי.

שילוב של כניסה באמצעות חשבון Google באפליקציה

כדי לשלב את הכניסה באמצעות חשבון Google באפליקציה שלכם ל-Wear OS, עליכם לעיין בשלבים הבאים שמפורטים בקטעים הבאים ולהטמיע אותם:

  1. מגדירים כניסה באמצעות חשבון Google.
  2. מוסיפים לחצן לכניסה באמצעות חשבון Google.
  3. הפעלת תהליך הכניסה כשמקישים על לחצן הכניסה.

הגדרת Google Sign-In וליצור את האובייקט GoogleApiClient

בשיטה onCreate() של פעילות הכניסה, מגדירים את Google Sign-In לבקש את נתוני המשתמשים שנדרשים לאפליקציה. לאחר מכן יוצרים אובייקט GoogleApiClient עם גישה ל-Google Sign-In API ולאפשרויות שציינתם. השלבים האלה מוצגים בדוגמה הבאה:

public class MyNewActivity extends AppCompatActivity {

    private static final int RC_SIGN_IN = 9001;

    private GoogleSignInClient mSignInClient;

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        GoogleSignInOptions options =
                new GoogleSignInOptions.Builder(GoogleSignInOptions.DEFAULT_SIGN_IN)
                        .build();

        mSignInClient = GoogleSignIn.getClient(this, options);
    }
}

הוספת לחצן לכניסה באמצעות חשבון Google לאפליקציה

כדי להוסיף לחצן כניסה באמצעות חשבון Google:

  1. מוסיפים את SignInButton לפריסה של האפליקציה:
  2.  <com.google.android.gms.common.SignInButton
     android:id="@+id/sign_in_button"
     android:layout_width="wrap_content"
     android:layout_height="wrap_content" />
    
  3. בשיטה onCreate() של האפליקציה, רושמים את OnClickListener של הלחצן כדי להתחבר את המשתמש כשמקישים עליו:
  4. Kotlin

    findViewById<View>(R.id.sign_in_button).setOnClickListener(this)
    

    Java

    findViewById(R.id.sign_in_button).setOnClickListener(this);
    

יצירת כוונה לכניסה לחשבון והפעלת תהליך הכניסה

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

Intent intent = mSignInClient.getSignInIntent();
startActivityForResult(intent, RC_SIGN_IN);

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

לסיום, בשיטה onActivityResult של הפעילות, מאחזרים את תוצאת הכניסה באמצעות getSignInResultFromIntent. אחרי שאתם מאחזרים את תוצאת הכניסה, אתם יכולים לבדוק אם הכניסה בוצעה בהצלחה באמצעות השיטה isSuccess. אם הכניסה תצליח, תוכלו להפעיל את השיטה getSignInAccount כדי לקבל אובייקט GoogleSignInAccount שמכיל מידע על המשתמש שמחובר, כמו שם המשתמש. השלבים האלה מוצגים בדוגמה הבאה:

Kotlin

override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent) {
    super.onActivityResult(requestCode, resultCode, data)

    // Result returned from launching the Intent from GoogleSignInApi.getSignInIntent(...).
    if (requestCode == RC_SIGN_IN) {
        Auth.GoogleSignInApi.getSignInResultFromIntent(data)?.apply {
            if (isSuccess) {
                // Get account information.
                fullName = signInAccount?.displayName
                mGivenName = signInAccount?.givenName
                mFamilyName = signInAccount?.familyName
                mEmail = signInAccount?.email
            }
        }
    }
}

Java

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    super.onActivityResult(requestCode, resultCode, data);

    // Result returned from launching the Intent from GoogleSignInApi.getSignInIntent(...).
    if (requestCode == RC_SIGN_IN) {
        GoogleSignInResult signInResult = Auth.GoogleSignInApi.getSignInResultFromIntent(data);
        if (signInResult.isSuccess()) {
            GoogleSignInAccount acct = signInResult.getSignInAccount();

            // Get account information.
            fullName = acct.getDisplayName();
            givenName = acct.getGivenName();
            familyName = acct.getFamilyName();
            email = acct.getEmail();
        }
    }
}

כדי לראות אפליקציה לדוגמה שמטמיעה את 'כניסה באמצעות חשבון Google', אפשר לעיין ב דוגמה של Horologist לכניסה באמצעות חשבון Google ב-GitHub.

אימות קוד בהתאמה אישית

כחלופה לשיטות האימות שתוארו למעלה, אפשר לדרוש מהמשתמש לבצע אימות ממכשיר אחר, כמו טלפון נייד או טאבלט, ולקבל קוד מספרי לטווח קצר. לאחר מכן, המשתמש מזין את הקוד במכשיר Wear OS כדי לאמת את הזהות שלו ומקבל אסימון אימות.

תהליך האימות הזה משתמש במודול ההתחברות של האפליקציה, או משליך באופן ידני שיטת כניסה של ספק אימות צד שלישי לקוד של האפליקציה. שיטת האימות הזו דורשת עבודה ידנית ומאמץ נוסף כדי לשפר את האבטחה שלה, אבל אפשר להשתמש בה אם אתם צריכים לבצע אימות בשלב מוקדם יותר באפליקציות העצמאיות של Wear OS.

תהליך האימות להגדרה הזו פועל כך:

  1. המשתמש מבצע פעולה באפליקציית Wear OS שמחייבת הרשאה.
  2. באפליקציה ל-Wear OS מוצג למשתמש מסך אימות, והוא מתבקש להזין קוד מכתובת URL שצוינה.
  3. המשתמש עובר למכשיר נייד, לטאבלט או למחשב, פותח דפדפן, מנווט לכתובת ה-URL שצוינה באפליקציית Wear OS ונכנס לחשבון.
  4. המשתמש מקבל קוד מספרי לטווח קצר שהוא צריך להזין במסך האימות של אפליקציית Wear OS באמצעות המקלדת המובנית ב-Wear OS:

  5. מכאן והלאה, תוכלו להשתמש בקוד שהוזן כהוכחה לכך שזה המשתמש הנכון, ולהחליף את הקוד באסימון אימות שמאוחסן ומאובטח במכשיר Wear OS, לשימוש בשיחות מאומתות בעתיד.

הערה: הקוד שהמשתמש יוצר חייב להיות מספרי בלבד ולא יכול להכיל תווים אלפביתיים.

תהליך האימות הזה מתואר בתרשים הבא: