ממשק API של הצעות Wi-Fi לחיבור אינטרנט

מכשירים עם Android 10 (API ברמה 29) ואילך מאפשרים לאפליקציה להוסיף רשת פרטי הכניסה של מכשיר להתחברות אוטומטית לנקודת גישה ל-Wi-Fi. אפשר לספק הצעות לרשת שאליה צריך להתחבר באמצעות WifiNetworkSuggestion בסופו של דבר הפלטפורמה בוחרת איזו נקודת גישה לאשר בהתאם קלט מהאפליקציה שלכם ומאחרים.

ב-Android 11 (רמת API 30) ואילך:

  • ה-framework אוכף דרישות בעלות ל-Enterprise שמבוססת על EAP-SIM הצעות (EAP-SIM, EAP-AKA, EAP-AKA-PRIME); הצעות כאלה מותרים רק באפליקציות חתומות על ידי ספק.
  • להצעות שמסופקות על ידי אפליקציה שחתומה על ידי ספק, ה-framework באופן אוטומטי מקצה להם מזהה ספק שתואם חתימת ספק. כאלה ההצעות מושבתות באופן אוטומטי אם מסירים את כרטיס ה-SIM התואם מהמכשיר.

ב-Android 12 (רמת API 31) ואילך:

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

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

  • isDecoratedIdentitySupported(): כשמבצעים אימות לרשתות עם קידומת, המערכת מקושטת תחילית הזהות מאפשרת למפעילי רשת לעדכן את הגישה לרשת מזהה (NAI) שמאפשר לבצע ניתוב מפורש דרך מספר שרתי proxy בתוך של רשת AAA (ראו RFC 7542 עבור בנושא).

    ב-Android 12 התכונה הזו מוטמעת כדי לעמוד בדרישות של מפרט WBA PPS-MO תוספים. באפליקציות שמציעות רשתות Passpoint שנדרשת להן זהות מקושטת צריך להפעיל את ה-API הזה קודם כדי לוודא שהמכשיר תומך ביכולת. אם המיקום המכשיר לא תומך ביכולת, הזהות לא תופיע והאימות ברשת עלול להיכשל.

כדי ליצור הצעה של Passpoint, האפליקציות חייבות להשתמש ב PasspointConfiguration Credential, וגם HomeSp כיתות. האלה מחלקות מתארות את פרופיל Passpoint, שמוגדר ב-Wi-Fi Alliance פרוטוקול Passpoint המפרט.

דוגמת הקוד הבאה ממחישה איך לספק פרטי כניסה לחשבון פתוח אחד WPA2, רשת WPA3 אחת ורשת Passpoint אחת:

Kotlin

val suggestion1 = WifiNetworkSuggestion.Builder()
        .setSsid("test111111")
        .setIsAppInteractionRequired(true) // Optional (Needs location permission)
        .build();

val suggestion2 = WifiNetworkSuggestion.Builder()
        .setSsid("test222222")
        .setWpa2Passphrase("test123456")
        .setIsAppInteractionRequired(true) // Optional (Needs location permission)
        .build();

val suggestion3 = WifiNetworkSuggestion.Builder()
        .setSsid("test333333")
        .setWpa3Passphrase("test6789")
        .setIsAppInteractionRequired(true) // Optional (Needs location permission)
        .build();

val passpointConfig = PasspointConfiguration(); // configure passpointConfig to include a valid Passpoint configuration
val suggestion4 = WifiNetworkSuggestion.Builder()
        .setPasspointConfig(passpointConfig)
        .setIsAppInteractionRequired(true) // Optional (Needs location permission)
        .build();

val suggestionsList = listOf(suggestion1, suggestion2, suggestion3, suggestion4);

val wifiManager = context.getSystemService(Context.WIFI_SERVICE) as WifiManager;

val status = wifiManager.addNetworkSuggestions(suggestionsList);
if (status != WifiManager.STATUS_NETWORK_SUGGESTIONS_SUCCESS) {
    // do error handling here
}

// Optional (Wait for post connection broadcast to one of your suggestions)
val intentFilter = IntentFilter(WifiManager.ACTION_WIFI_NETWORK_SUGGESTION_POST_CONNECTION);

val broadcastReceiver = object : BroadcastReceiver() {
    override fun onReceive(context: Context, intent: Intent) {
        if (!intent.action.equals(WifiManager.ACTION_WIFI_NETWORK_SUGGESTION_POST_CONNECTION)) {
            return;
        }
        // do post connect processing here
    }
};
context.registerReceiver(broadcastReceiver, intentFilter);

Java

final WifiNetworkSuggestion suggestion1 =
  new WifiNetworkSuggestion.Builder()
  .setSsid("test111111")
  .setIsAppInteractionRequired(true) // Optional (Needs location permission)
  .build();

final WifiNetworkSuggestion suggestion2 =
  new WifiNetworkSuggestion.Builder()
  .setSsid("test222222")
  .setWpa2Passphrase("test123456")
  .setIsAppInteractionRequired(true) // Optional (Needs location permission)
  .build();

final WifiNetworkSuggestion suggestion3 =
  new WifiNetworkSuggestion.Builder()
  .setSsid("test333333")
  .setWpa3Passphrase("test6789")
  .setIsAppInteractionRequired(true) // Optional (Needs location permission)
  .build();

final PasspointConfiguration passpointConfig = new PasspointConfiguration();
// configure passpointConfig to include a valid Passpoint configuration

final WifiNetworkSuggestion suggestion4 =
  new WifiNetworkSuggestion.Builder()
  .setPasspointConfig(passpointConfig)
  .setIsAppInteractionRequired(true) // Optional (Needs location permission)
  .build();

final List<WifiNetworkSuggestion> suggestionsList =
  new ArrayList<WifiNetworkSuggestion> {{
    add(suggestion1);
    add(suggestion2);
    add(suggestion3);
    add(suggestion4);
  }};

final WifiManager wifiManager =
  (WifiManager) context.getSystemService(Context.WIFI_SERVICE);

final int status = wifiManager.addNetworkSuggestions(suggestionsList);
if (status != WifiManager.STATUS_NETWORK_SUGGESTIONS_SUCCESS) {
// do error handling here…
}

// Optional (Wait for post connection broadcast to one of your suggestions)
final IntentFilter intentFilter =
  new IntentFilter(WifiManager.ACTION_WIFI_NETWORK_SUGGESTION_POST_CONNECTION);

final BroadcastReceiver broadcastReceiver = new BroadcastReceiver() {
  @Override
  public void onReceive(Context context, Intent intent) {
    if (!intent.getAction().equals(
      WifiManager.ACTION_WIFI_NETWORK_SUGGESTION_POST_CONNECTION)) {
      return;
    }
    // do post connect processing here...
  }
};
context.registerReceiver(broadcastReceiver, intentFilter);

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

  • ב-Android מגרסה 11 (רמת API 30) ואילך, המשתמש רואה תיבת דו-שיח אם האפליקציה פועלת בחזית, והתראה אם האפליקציה פועלת רקע.
  • ב-Android 10 (רמת API 29), המשתמש רואה התראה, בלי קשר אם האפליקציה פועלת בחזית או ברקע.

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

טיפול בניתוקי משתמשים

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

שינוי סטטוס האישור של האפליקציה

משתמש שדוחה את ההתראה על הצעת רשת מסיר את הרשאה CHANGE_WIFI_STATE מהאפליקציה. המשתמש יכול להעניק את האישור הזה מאוחר יותר באמצעות מעבר לתפריט בקרת ה-Wi-Fi (הגדרות > אפליקציות התראות > אפליקציה מיוחדת גישה > בקרת Wi-Fi > App name).