API eUICC

In Android 9, API di gestione del profilo (pubblici e @SystemApi) sono disponibili tramite la classe EuiccManager . API di comunicazione eUICC (solo @SystemApi) sono disponibili tramite la classe EuiccCardManager .

Informazioni su eUICC

Gli operatori possono creare app dell'operatore utilizzando EuiccManager per gestire i profili, come mostrato nella Figura 1. Le app dell'operatore non devono essere app di sistema ma devono disporre dei privilegi dell'operatore concessi dai profili eUICC. Un LPA app (LUI e LPA backend) ha bisogno di essere un'applicazione di sistema (vale a dire, incluso l'immagine di sistema a) per chiamare il @SystemApi.

Telefono Android con app Carrier e LPA OEM

Telefoni Figura 1. Android con app carrier e OEM LPA

Oltre la logica di chiamare EuiccCardManager e parlando con eUICC, applicazioni LPA devono implementare le seguenti:

  • Il client SM-DP+ parla con il server SM-DP+ per autenticare e scaricare i profili
  • [Facoltativo] SM-DS per ottenere più potenziali profili scaricabili
  • Gestione delle notifiche per inviare notifiche al server per aggiornare lo stato del profilo
  • [Facoltativo] Gestione degli slot inclusa la commutazione tra logica eSIM e pSIM. Questo è facoltativo se il telefono ha solo un chip eSIM.
  • eSIM OTA

Anche se più di un LPA applicazione può essere presente in un telefono Android, un solo LPA può essere selezionato per essere la LPA di lavoro effettivo in base alla priorità definita nel AndroidManifest.xml del file di ogni app.

Utilizzo di EuiccManager

Le API sono LPA pubblica attraverso EuiccManager (nell'ambito del pacchetto android.telephony.euicc ). Un app vettore può ottenere l'istanza di EuiccManager , e chiamare i metodi in EuiccManager per ottenere le informazioni eUICC e gestire le sottoscrizioni (di seguito i profili nei documenti GSMA RSP) come istanze SubscriptionInfo.

Per chiamare le API pubbliche, incluse le operazioni di download, cambio ed eliminazione dell'abbonamento, l'app dell'operatore deve disporre dei privilegi richiesti. I privilegi dell'operatore vengono aggiunti dall'operatore di telefonia mobile nei metadati del profilo. L'API eUICC applica di conseguenza le regole sui privilegi dell'operatore.

La piattaforma Android non gestisce le regole dei criteri del profilo. Se una regola della policy è dichiarata nei metadati del profilo, l'LPA può scegliere come gestire la procedura di download e installazione del profilo. Ad esempio, è possibile che un LPA OEM di terze parti gestisca le regole dei criteri utilizzando un codice di errore speciale (il codice di errore viene passato dall'LPA OEM alla piattaforma, quindi la piattaforma passa il codice all'LUI OEM).

API

Le seguenti API possono essere trovati nella EuiccManager documentazione di riferimento e EuiccManager.java .

Ottieni istanza (pubblica)

Ottiene l'istanza di EuiccManager attraverso Context#getSystemService .

EuiccManager mgr = (EuiccManager) context.getSystemService(Context.EUICC_SERVICE);

Verifica abilitata (pubblica)

Controlla se la sottoscrizione incorporata è abilitata. Questo dovrebbe essere controllato prima di accedere alle API LPA.

boolean isEnabled = mgr.isEnabled();
if (!isEnabled) {
    return;
}

Ottieni EID (pubblico)

Ottiene l'EID che identifica l'hardware eUICC. Questo può essere null se l'eUICC non è pronto. Il chiamante deve avere privilegi di vettore o il READ_PRIVILEGED_PHONE_STATE permesso.

String eid = mgr.getEid();
if (eid == null) {
  // Handle null case.
}

Ottieni EuiccInfo (pubblico)

Ottiene informazioni sull'eUICC. Questo contiene la versione del sistema operativo.

EuiccInfo info = mgr.getEuiccInfo();
String osVer = info.getOsVersion();

Scarica abbonamento (pubblico)

Scarica l'abbonamento specificato (denominato "profilo" nei documenti GSMA RSP). L'abbonamento può essere creato da un codice di attivazione. Ad esempio, un codice di attivazione può essere analizzato da un codice QR. Il download di un abbonamento è un'operazione asincrona.

Il chiamante deve o avere il WRITE_EMBEDDED_SUBSCRIPTIONS permesso o avere privilegi di vettore per la sottoscrizione di destinazione.

// Register receiver.
String action = "download_subscription";
BroadcastReceiver receiver =
        new BroadcastReceiver() {
            @Override
            public void onReceive(Context context, Intent intent) {
                if (!action.equals(intent.getAction())) {
                    return;
                }
                resultCode = getResultCode();
                detailedCode = intent.getIntExtra(
                    EuiccManager.EXTRA_EMBEDDED_SUBSCRIPTION_DETAILED_CODE,
                    0 /* defaultValue*/);
                resultIntent = intent;
            }
        };
context.registerReceiver(
        receiver,
        new IntentFilter(action),
        "example.broadcast.permission" /* broadcastPermission*/, null /* handler */);

// Download subscription asynchronously.
DownloadableSubscription sub =
        DownloadableSubscription.forActivationCode(code /* encodedActivationCode*/);
Intent intent = new Intent(action);
PendingIntent callbackIntent = PendingIntent.getBroadcast(
        getContext(), 0 /* requestCode */, intent, PendingIntent.FLAG_UPDATE_CURRENT);
mgr.downloadSubscription(sub, true /* switchAfterDownload */, callbackIntent);

Cambia abbonamento (pubblico)

Passa a (abilita) l'abbonamento specificato. Il chiamante deve o avere WRITE_EMBEDDED_SUBSCRIPTIONS o avere privilegi vettore relativi alla corrente ha permesso di sottoscrizione e la sottoscrizione di destinazione.

// Register receiver.
String action = "switch_to_subscription";
BroadcastReceiver receiver =
        new BroadcastReceiver() {
            @Override
            public void onReceive(Context context, Intent intent) {
                if (!action.equals(intent.getAction())) {
                    return;
                }
                resultCode = getResultCode();
                detailedCode = intent.getIntExtra(
                    EuiccManager.EXTRA_EMBEDDED_SUBSCRIPTION_DETAILED_CODE, 0 /* defaultValue*/);
                resultIntent = intent;
            }
        };
context.registerReceiver(receiver, new IntentFilter(action),
        "example.broadcast.permission" /* broadcastPermission*/, null /* handler */);

// Switch to a subscription asynchronously.
Intent intent = new Intent(action);
PendingIntent callbackIntent = PendingIntent.getBroadcast(
        getContext(), 0 /* requestCode */, intent, PendingIntent.FLAG_UPDATE_CURRENT);
mgr.switchToSubscription(1 /* subscriptionId */, callbackIntent);

Elimina abbonamento (pubblico)

Elimina un abbonamento con un ID abbonamento. Se l'abbonamento è attualmente attivo, viene prima disabilitato. Il chiamante deve avere sia WRITE_EMBEDDED_SUBSCRIPTIONS o privilegi di supporto per la sottoscrizione di destinazione.

// Register receiver.
String action = "delete_subscription";
BroadcastReceiver receiver =
        new BroadcastReceiver() {
            @Override
            public void onReceive(Context context, Intent intent) {
                if (!action.equals(intent.getAction())) {
                    return;
                }
                resultCode = getResultCode();
                detailedCode = intent.getIntExtra(
                    EuiccManager.EXTRA_EMBEDDED_SUBSCRIPTION_DETAILED_CODE,
                    0 /* defaultValue*/);
                resultIntent = intent;
            }
        };
context.registerReceiver(receiver, new IntentFilter(action),
        "example.broadcast.permission" /* broadcastPermission*/,
        null /* handler */);

// Delete a subscription asynchronously.
Intent intent = new Intent(action);
PendingIntent callbackIntent = PendingIntent.getBroadcast(
        getContext(), 0 /* requestCode */, intent, PendingIntent.FLAG_UPDATE_CURRENT);
mgr.deleteSubscription(1 /* subscriptionId */, callbackIntent);

Cancella tutti gli abbonamenti (API di sistema)

Cancella tutti gli abbonamenti su un dispositivo. A partire dal 11 Android, è necessario fornire un EuiccCardManager#ResetOption valore enum per specificare se cancellare tutti i test, operativi, o entrambi i tipi di abbonamenti. Il chiamante deve avere WRITE_EMBEDDED_SUBSCRIPTIONS permesso.

// Register receiver.
String action = "delete_subscription";
BroadcastReceiver receiver =
        new BroadcastReceiver() {
            @Override
            public void onReceive(Context context, Intent intent) {
                if (!action.equals(intent.getAction())) {
                    return;
                }
                resultCode = getResultCode();
                detailedCode = intent.getIntExtra(
                    EuiccManager.EXTRA_EMBEDDED_SUBSCRIPTION_DETAILED_CODE,
                    0 /* defaultValue*/);
                resultIntent = intent;
            }
        };
context.registerReceiver(receiver, new IntentFilter(action),
        "example.broadcast.permission" /* broadcastPermission*/,
        null /* handler */);

// Erase all operational subscriptions asynchronously.
Intent intent = new Intent(action);
PendingIntent callbackIntent = PendingIntent.getBroadcast(
        getContext(), 0 /* requestCode */, intent, PendingIntent.FLAG_UPDATE_CURRENT);
mgr.eraseSubscriptions(
        EuiccCardManager.RESET_OPTION_DELETE_OPERATIONAL_PROFILES, callbackIntent);

Avvia attività di risoluzione (pubblica)

Avvia un'attività per risolvere un errore risolvibile dall'utente. Se un'operazione ritorna EuiccManager#EMBEDDED_SUBSCRIPTION_RESULT_RESOLVABLE_ERROR , questo metodo può essere chiamato per richiedere all'utente per risolvere il problema. Questo metodo può essere chiamato solo una volta per un particolare errore.

...
mgr.startResolutionActivity(getActivity(), 0 /* requestCode */, resultIntent, callbackIntent);

costanti

Per visualizzare un elenco dei public costanti in EuiccManager , vedere Costanti .