API de Wi-Fi Network Request para la conectividad entre pares

En dispositivos con Android 10 (nivel de API 29) y versiones posteriores, puedes usar una nueva API de par a par para iniciar la configuración de dispositivos secundarios, como el hardware de Chromecast y Google Home. Esta función permite que tu app le pida al usuario que cambie el punto de acceso al que está conectado el dispositivo mediante el uso WifiNetworkSpecifier para describir las propiedades de una red solicitada.

Para usar esta API, haz lo siguiente:

  1. Crea un especificador de red Wi-Fi por medio de WifiNetworkSpecifier.Builder.

  2. Establece un filtro de red para que coincida con las redes a las que debes conectarte junto con las credenciales requeridas.

  3. Decide una combinación de SSID, SSID pattern, BSSID, y BSSID pattern para establecer el filtro de red en cada solicitud, sujeto a los siguientes requisitos:

    • Cada solicitud debe proporcionar al menos uno de los siguientes: SSID, SSID pattern, BSSID, o BSSID pattern.
    • Cada solicitud solo puede establecer uno de los siguientes: SSID o SSID pattern.
    • Cada solicitud solo puede establecer uno de los siguientes: BSSID o BSSID pattern.
  4. Agrega los especificadores a la solicitud de red junto con una NetworkCallback instancia para realizar el seguimiento del estado de la solicitud.

    Si el usuario acepta la solicitud y la conexión a la red es exitosa, NetworkCallback.onAvailable() se invoca en el objeto de devolución de llamada. Si el usuario rechaza esta solicitud o la conexión a la red no es exitosa, NetworkCallback.onUnavailable() se invoca en el objeto de devolución de llamada.

Cuando se inicia la solicitud para conectarse a un dispositivo de pares, se abre un cuadro de diálogo en el mismo dispositivo, en el que su usuario puede aceptar la solicitud de conexión.

Omite la aprobación del usuario

Una vez que el usuario aprueba una red para que se conecte como respuesta a una solicitud de una app específica, el dispositivo almacena la aprobación para ese punto de acceso específico. Si la app realiza una solicitud específica para volver a conectarse a ese punto de acceso, el dispositivo omite la fase de aprobación del usuario y se conecta automáticamente a la red. Si el usuario decide olvidar la red mientras está conectado a una red solicitada por la API, entonces se quita la aprobación almacenada para esa combinación de app y red, y el usuario deberá aprobar cualquier solicitud futura de la app. Si la app realiza una solicitud que no es específica, como un SSID o patrón BSSID, el usuario deberá aprobarla.

Muestra de código

En la siguiente muestra de código, podrás ver cómo conectarte a una red abierta con un prefijo SSID de "test" y un OUI de BSSID de "10:03:23":

Kotlin

val specifier = WifiNetworkSpecifier.Builder()
    .setSsidPattern(PatternMatcher("test", PatternMatcher.PATTERN_PREFIX))
    .setBssidPattern(MacAddress.fromString("10:03:23:00:00:00"), MacAddress.fromString("ff:ff:ff:00:00:00"))
    .build()

val request = NetworkRequest.Builder()
    .addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
    .removeCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET)
    .setNetworkSpecifier(specifier)
    .build()

val connectivityManager = context.getSystemService(Context.CONNECTIVITY_SERVICE) as ConnectivityManager

val networkCallback = object : ConnectivityManager.NetworkCallback() {
    ...
    override fun onAvailable(network: Network?) {
        // do success processing here..
    }

    override fun onUnavailable() {
        // do failure processing here..
    }
    ...
}
connectivityManager.requestNetwork(request, networkCallback)
...
// Release the request when done.
connectivityManager.unregisterNetworkCallback(networkCallback)

Java

final NetworkSpecifier specifier =
  new WifiNetworkSpecifier.Builder()
  .setSsidPattern(new PatternMatcher("test", PatternMatcher.PATTERN_PREFIX))
  .setBssidPattern(MacAddress.fromString("10:03:23:00:00:00"), MacAddress.fromString("ff:ff:ff:00:00:00"))
  .build();

final NetworkRequest request =
  new NetworkRequest.Builder()
  .addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
  .removeCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET)
  .setNetworkSpecifier(specifier)
  .build();

final ConnectivityManager connectivityManager = (ConnectivityManager)
  context.getSystemService(Context.CONNECTIVITY_SERVICE);

final NetworkCallback networkCallback = new NetworkCallback() {
  ...
  @Override
  void onAvailable(...) {
      // do success processing here..
  }

  @Override
  void onUnavailable(...) {
      // do failure processing here..
  }
  ...
};
connectivityManager.requestNetwork(request, networkCallback);
...
// Release the request when done.
connectivityManager.unregisterNetworkCallback(networkCallback);