P2P 연결을 위한 Wi-Fi 네트워크 요청 API

Android 10(API 수준 29) 이상 기기에서는 새로운 P2P API를 사용하여 Chromecast, Google Home 하드웨어와 같은 보조 기기의 구성을 부트스트랩할 수 있습니다. 이 기능을 사용하면 앱에서 사용자에게 액세스 권한을 변경하라는 메시지를 표시할 수 있습니다. 장치가 연결된 지점의 위치를 WifiNetworkSpecifier 요청된 네트워크의 속성을 설명할 수 있습니다.

이 API를 사용하는 방법은 다음과 같습니다.

  1. WifiNetworkSpecifier.Builder를 사용하여 Wi-Fi 네트워크 지정자를 생성합니다.

  2. 연결할 네트워크에 맞는 네트워크 필터를 필수 항목과 함께 설정합니다. 사용자 인증 정보를 제공합니다

  3. SSID, SSID pattern, BSSID, BSSID pattern을 어떻게 조합할지 결정하여 각 요청에서 네트워크 필터를 설정합니다. 여기에는 다음과 같은 요구 사항이 적용됩니다.

    • 각 요청은 SSID, SSID pattern, BSSID 또는 BSSID pattern
    • 각 요청은 SSID 또는 SSID pattern 중 하나만 설정할 수 있습니다.
    • 각 요청은 BSSID 또는 BSSID pattern 중 하나만 설정할 수 있습니다.
  4. NetworkCallback 인스턴스와 함께 네트워크 요청에 지정자를 추가하여 요청 상태를 추적합니다.

    사용자가 요청을 수락하고 네트워크에 연결되면 콜백 객체에서 NetworkCallback.onAvailable()이 호출됩니다. 사용자가 요청을 거부하거나 네트워크에 연결되지 않은 경우 NetworkCallback.onUnavailable() 콜백 객체에서 호출됩니다.

피어 기기 연결 요청을 시작하면 해당 기기의 사용자가 연결 요청을 수락할 수 있습니다.

사용자 승인 우회

사용자가 특정 앱의 요청에 응답하여 네트워크 연결을 승인하면 기기에서 특정 액세스 포인트에 관한 승인을 저장합니다. 앱이 다시 해당 액세스 포인트에 연결하기 위한 요청을 보내면 기기는 사용자 승인 단계를 건너뛰고 네트워크에 자동으로 연결합니다. 사용자가 네트워크에 연결된 동안에 네트워크의 상태를 변경할 수 없으므로 이 데이터는 해당 앱과 네트워크 조합에 대한 승인이 삭제되며 사용자의 승인을 다시 받아야 합니다. 앱이 SSID 또는 BSSID 패턴과 같이 구체적이지 않은 요청을 한 경우 사용자가 요청을 승인해야 합니다.

코드 샘플

다음 코드 샘플은 SSID를 사용하여 개방형 네트워크에 연결하는 방법을 보여줍니다. 접두사 "test" 및 BSSID OUI "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);