SafetyNet Safe Browsing API

SafetyNet은 Google이 특정 URL을 알려진 위협으로 표시했는지 여부를 확인하는 서비스를 제공합니다.

앱은 이 API를 사용하여 Google이 특정 URL을 알려진 위협으로 분류했는지 여부를 확인할 수 있습니다. 내부적으로 SafetyNet은 Google이 개발한 세이프 브라우징 네트워크 프로토콜 v4용 클라이언트를 구현합니다. 클라이언트 코드와 v4 네트워크 프로토콜은 모두 사용자의 개인정보 보호를 유지하고 배터리 및 대역폭 소모를 최소한으로 유지하도록 설계되었습니다. 이 API를 사용하면 리소스에 가장 최적화된 방법으로 그리고 네트워크 프로토콜을 구현하지 않고 Google의 세이프 브라우징 서비스를 Android에서 최대한 활용할 수 있습니다.

이 문서에서는 SafetyNet을 사용하여 URL에 알려진 위협이 있는지 확인하는 방법을 설명합니다.

서비스 약관

Safe Browsing API를 사용하면 서비스 약관을 준수할 것에 동의하는 것으로 간주됩니다. Safe Browsing API에 액세스하기 전에 모든 관련 약관 및 정책을 자세히 읽고 숙지하시기 바랍니다.

Android API 키 요청 및 등록하기

API 키를 만들려면 다음 단계를 따르세요.

  1. Google Developers Console로 이동합니다.
  2. 상단 툴바에서 프로젝트 선택 > 프로젝트-이름을 선택합니다.
  3. 검색창에 Safe Browsing API를 입력한 후 표에 Safe Browsing API 이름이 표시되면 API를 선택합니다.
  4. 페이지가 다시 표시되면 사용 설정을 선택한 후 사용자 인증 정보로 이동을 선택합니다.
  5. 프로젝트에 사용자 인증 정보 추가 창이 표시되면 매개변수를 선택한 후 어떤 사용자 인증 정보가 필요한가요?를 선택합니다.
  6. API 키 이름을 입력한 후 API 키 만들기를 선택합니다.
  7. 새 API 키가 표시되면 나중에 사용하기 위해 이 키를 복사하고 저장합니다.

    참고: API 키를 사용하면 URL 확인을 하루 10,000번까지 수행할 수 있습니다. 이 인스턴스에서 이 키는 URL의 일부가 아니라 16진수 문자열이어야 합니다.

  8. 완료를 선택하여 프로세스를 완료합니다.

도움이 더 필요하다면 Google Developers Console 고객센터를 확인하세요.

API 초기화하기

Safe Browsing API를 사용하려면 initSafeBrowsing()을 호출한 후 완료되도록 대기하여 API를 초기화해야 합니다. 다음 코드 스니펫을 예로 확인하세요.

Kotlin

    Tasks.await(SafetyNet.getClient(this).initSafeBrowsing())
    

자바

    Tasks.await(SafetyNet.getClient(this).initSafeBrowsing());
    

참고: 앱 초기화의 영향을 최소화하려면 앱 활동의 onResume() 메서드에서 가능한 한 빨리 initSafeBrowsing()을 호출하세요.

URL 확인 요청하기

앱은 URL 확인을 사용하여 URL이 알려진 위협을 가하는지 여부를 파악할 수 있습니다. 일부 위협 유형은 특정 앱과 관련이 없을 수 있습니다. API를 사용하면 개발자의 요구에 따라 중요한 위협 유형을 선택할 수 있습니다. 알려진 위협 유형을 여러 개 지정할 수 있습니다.

관심 있는 위협 유형 지정하기

다음과 같이 SafeBrowsingThreat 클래스의 상수에는 현재 지원되는 위협 유형이 포함됩니다.

    package com.google.android.gms.safetynet;

    public class SafeBrowsingThreat {

      /**
       * This threat type identifies URLs of pages that are flagged as containing potentially
       * harmful applications.
       */
      public static final int TYPE_POTENTIALLY_HARMFUL_APPLICATION = 4;

      /**
       * This threat type identifies URLs of pages that are flagged as containing social
       * engineering threats.
       */
      public static final int TYPE_SOCIAL_ENGINEERING = 5;
    }
    

API를 사용할 때는 지원 중단으로 표시되지 않은 상수를 사용해야 합니다. API에 위협 유형 상수를 인수로 추가합니다. 앱에 필요한 만큼 얼마든지 위협 유형 상수를 추가할 수 있습니다.

URL 확인 요청 보내기

API는 사용된 스키마에 구속되지 않으므로, 스키마를 사용하거나 사용하지 않고 URL을 전달할 수 있습니다. 예를 들어 다음 URL과

Kotlin

    var url = "https://www.google.com"
    

자바

    String url = "https://www.google.com";
    

다음 URL은

Kotlin

    var url = "www.google.com"
    

자바

    String url = "www.google.com";
    

모두 유효합니다.

Kotlin

    SafetyNet.getClient(this).lookupUri(
            url,
            SAFE_BROWSING_API_KEY,
            SafeBrowsingThreat.TYPE_POTENTIALLY_HARMFUL_APPLICATION,
            SafeBrowsingThreat.TYPE_SOCIAL_ENGINEERING
    )
            .addOnSuccessListener(this) { sbResponse ->
                // Indicates communication with the service was successful.
                // Identify any detected threats.
                if (sbResponse.detectedThreats.isEmpty()) {
                    // No threats found.
                } else {
                    // Threats found!
                }
            }
            .addOnFailureListener(this) { e: Exception ->
                if (e is ApiException) {
                    // An error with the Google Play Services API contains some
                    // additional details.
                    Log.d(TAG, "Error: ${CommonStatusCodes.getStatusCodeString(e.statusCode)}")

                    // Note: If the status code, s.statusCode,
                    // is SafetyNetstatusCode.SAFE_BROWSING_API_NOT_INITIALIZED,
                    // you need to call initSafeBrowsing(). It means either you
                    // haven't called initSafeBrowsing() before or that it needs
                    // to be called again due to an internal error.
                } else {
                    // A different, unknown type of error occurred.
                    Log.d(TAG, "Error: ${e.message}")
                }
            }
    

자바

    SafetyNet.getClient(this).lookupUri(url,
              SAFE_BROWSING_API_KEY,
              SafeBrowsingThreat.TYPE_POTENTIALLY_HARMFUL_APPLICATION,
              SafeBrowsingThreat.TYPE_SOCIAL_ENGINEERING)
        .addOnSuccessListener(this,
            new OnSuccessListener<SafetyNetApi.SafeBrowsingResponse>() {
                @Override
                public void onSuccess(SafetyNetApi.SafeBrowsingResponse sbResponse) {
                    // Indicates communication with the service was successful.
                    // Identify any detected threats.
                    if (sbResponse.getDetectedThreats().isEmpty()) {
                        // No threats found.
                    } else {
                        // Threats found!
                    }
             }
        })
        .addOnFailureListener(this, new OnFailureListener() {
                @Override
                public void onFailure(@NonNull Exception e) {
                    // An error occurred while communicating with the service.
                    if (e instanceof ApiException) {
                        // An error with the Google Play Services API contains some
                        // additional details.
                        ApiException apiException = (ApiException) e;
                        Log.d(TAG, "Error: " + CommonStatusCodes
                            .getStatusCodeString(apiException.getStatusCode()));

                        // Note: If the status code, apiException.getStatusCode(),
                        // is SafetyNetstatusCode.SAFE_BROWSING_API_NOT_INITIALIZED,
                        // you need to call initSafeBrowsing(). It means either you
                        // haven't called initSafeBrowsing() before or that it needs
                        // to be called again due to an internal error.
                    } else {
                        // A different, unknown type of error occurred.
                        Log.d(TAG, "Error: " + e.getMessage());
                    }
                }
        });
    

URL 확인 응답 읽기

반환된 SafetyNetApi.SafeBrowsingResponse 객체를 사용하여 getDetectedThreats() 메서드를 호출합니다. 이 메서드는 SafeBrowsingThreat 객체의 목록을 반환합니다. 반환된 목록이 비어 있다면 API가 알려진 위협을 감지하지 않은 것입니다. 하지만 목록이 비어 있지 않으면 목록의 각 요소에서 getThreatType()을 호출하여 API가 감지한 알려진 위협을 확인할 수 있습니다.

세이프 브라우징 세션 종료하기

앱이 오랫동안 Safe Browsing API를 사용하지 않을 예정이면 앱 내에서 모든 필수 URL을 확인한 후 다음과 같이 shutdownSafeBrowsing() 메서드를 사용하여 세이프 브라우징 세션을 종료하세요.

Kotlin

    SafetyNet.getClient(this).shutdownSafeBrowsing()
    

자바

    SafetyNet.getClient(this).shutdownSafeBrowsing();
    

활동의 onPause() 메서드에서 shutdownSafeBrowsing()을 호출하고 활동의 onResume() 메서드에서 initSafeBrowsing()을 호출하는 것이 좋습니다. 그러나 lookupUri()를 호출하기 전에 initSafeBrowsing()의 실행이 완료되었는지 확인해야 합니다. 세션을 항상 새롭게 유지하면 앱의 내부 오류를 줄이는 데 도움이 됩니다.

권장 경고 언어

권장되는 경고 언어를 보려면 Safe Browsing API 개발자 가이드를 참고하세요.