Android 앱에 reCAPTCHA Enterprise 통합

컬렉션을 사용해 정리하기 내 환경설정을 기준으로 콘텐츠를 저장하고 분류하세요.

이 페이지에서는 Android 앱에 reCAPTCHA Enterprise를 통합하는 방법을 설명합니다. 휴대기기의 화면 크기, 성능, UI 면에서 차이가 있으므로 모바일 앱에서는 시각적인 체크박스 reCAPTCHA 챌린지(로봇이 아닙니다)를 사용할 수 없습니다. 대신 MFA 흐름과 같은 자체 계층별 시행 전략을 구현하여 의심스러운 트래픽에 대한 대체 사용 경로를 제공할 수 있습니다.

시작하기 전에

  1. 환경에서 reCAPTCHA Enterprise를 설정하는 가장 좋은 방법을 선택하고 설정을 완료합니다.

  2. Android 앱 플랫폼의 reCAPTCHA 키를 만듭니다.

개발 환경 준비하기

  1. 최신 버전의 Android 스튜디오를 다운로드하고 설치하여 개발 환경을 준비합니다.

  2. 최소 Android SDK 값이 API 23: Android 6.0(Espresso)로 설정된 앱이 있는지 확인합니다. 앱의 최소 SDK를 API 23으로 설정하거나 새 모바일 앱을 만들 수 있습니다.

  3. 새 모바일 앱을 만드는 경우 새로운 Android 스튜디오 프로젝트를 시작하여 테스트 애플리케이션을 만듭니다.

    1. 빈 활동을 선택합니다. 앱에서 Jetpack Compose를 사용하려면 빈 Compose 활동을 선택합니다.
    2. 언어를 kotlin으로 설정합니다.
    3. 최소 SDK 값을 API 23: Android 6.0(Espresso)로 설정합니다.
  4. 다음 스니펫과 같이 Google의 Maven 저장소 google()이 프로젝트 수준 build.gradle 파일의 저장소 목록에 있는지 확인합니다.

    allprojects {
        repositories {
            google()
        }
    }
    

    자세한 내용은 Google의 Maven 저장소를 참조하세요.

  5. reCAPTCHA Enterprise API 종속 항목을 추가하려면 앱 수준 build.gradle 파일의 dependencies 섹션에 다음 빌드 규칙을 추가합니다.

       implementation 'com.google.android.recaptcha:recaptcha:18.0.0'
    

    Android 앱에 종속 항목을 추가하는 방법에 대한 자세한 내용은 빌드 종속 항목 추가를 참조하세요.

  6. 애플리케이션 매니페스트에서 첫 번째 <manifest> 태그와 첫 번째 <application> 태그 사이에 인터넷 권한을 추가합니다(예: AndroidManifest.xml). reCAPTCHA Enterprise API를 사용하려면 네트워크 작업이 필요하므로 이 권한이 필요합니다.

    <manifest ...>
    
        <uses-permission android:name="android.permission.INTERNET" />
    
        <application ...>
        ...
      </application>
    </manifest>
    
  7. 새 프로젝트에서 AndroidX 라이브러리를 사용하려면 SDK를 Android 9.0 이상으로 컴파일하고 다음 코드 스니펫을 gradle.properties에 추가하세요.

    android.useAndroidX=true
    android.enableJetifier=true
    

    자세한 내용은 AndroidX로 마이그레이션을 참조하세요.

Android 앱에 reCAPTCHA Enterprise 통합

  1. Android 앱용으로 만든 SITE_KEY를 사용하여 클라이언트를 인스턴스화합니다.

    Kotlin

    class MainActivity : AppCompatActivity() {
    
        private lateinit var recaptchaClient: RecaptchaClient
    
        override fun onCreate(savedInstanceState: Bundle?) {
          super.onCreate(savedInstanceState)
          setContentView(R.layout.activity_main)
          initializeRecaptchaClient()
          // ... rest of onCreate code
        }
    
        private fun initializeRecaptchaClient() {
          lifecycleScope.launch {
            Recaptcha.getClient(application, "YOUR_SITE_KEY")
              .onSuccess { client ->
                recaptchaClient = client
              }
              .onFailure { exception ->
                // Handle communication errors ...
                // See "Handle communication errors" section
              }
          }
        }
    
        // ... rest of activity code.
    }
    

    자바

    public final class MainActivity extends Activity {
      @Nullable private RecaptchaTasksClient recaptchaTasksClient = null;
    
      @Override
      protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        initializeRecaptchaClient();
        // ... rest of onCreate code
      }
    
      private void initializeRecaptchaClient() {
        Recaptcha
          .getTasksClient(getApplication(), "YOUR_SITE_KEY")
          .addOnSuccessListener(
              this,
              new OnSuccessListener<RecaptchaTasksClient>() {
                @Override
                public void onSuccess(RecaptchaTasksClient client) {
                  MainActivity.this.recaptchaTasksClient = client;
                }
              })
          .addOnFailureListener(
              this,
              new OnFailureListener() {
                @Override
                public void onFailure(@NonNull Exception e) {
                  // Handle communication errors ...
                  // See "Handle communication errors" section
                }
              });
      }
    
      // ... rest of activity code.
    }
    
  2. reCAPTCHA Enterprise를 사용하여 보호되는 앱의 각 작업에 대해 execute 메서드를 호출하여 RecaptchaAction을 전달합니다. reCAPTCHA Enterprise는 기본 제공 작업 집합을 제공하며 필요한 경우 커스텀 작업을 만들 수도 있습니다.

    다음 코드 스니펫은 execute를 사용하여 LOGIN 작업을 보호하는 방법을 보여줍니다.

    Kotlin

    private fun executeLoginAction() {
      lifecycleScope.launch {
        recaptchaClient
          .execute(RecaptchaAction.LOGIN)
          .onSuccess { token ->
            // Handle success ...
            // See "What's next" section for instructions
            // about handling tokens.
          }
          .onFailure { exception ->
            // Handle communication errors ...
            // See "Handle communication errors" section
          }
      }
    }
    

    자바

    private void executeLoginAction(View v) {
      assert recaptchaTasksClient != null;
      recaptchaTasksClient
        .executeTask(RecaptchaAction.LOGIN)
        .addOnSuccessListener(
            this,
            new OnSuccessListener<String>() {
              @Override
              public void onSuccess(String token) {
                // Handle success ...
                // See "What's next" section for instructions
                // about handling tokens.
              }
            })
        .addOnFailureListener(
            this,
            new OnFailureListener() {
              @Override
              public void onFailure(@NonNull Exception e) {
                // Handle communication errors ...
                // See "Handle communication errors" section
              }
            });
    }
    

다음 샘플 코드 스니펫은 단일 활동 앱에서 getClient()execute() 메서드의 전체 통합을 보여줍니다.

Kotlin

class MainActivity : AppCompatActivity() {

  private lateinit var recaptchaClient: RecaptchaClient

  override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)
    setContentView(R.layout.activity_main)
    initializeRecaptchaClient()
    findViewById<View>(R.id.btn_login).setOnClickListener { executeLoginAction() }
    findViewById<View>(R.id.btn_redeem).setOnClickListener { executeRedeemAction() }
  }

  private fun initializeRecaptchaClient() {
    lifecycleScope.launch {
      Recaptcha.getClient(application, "YOUR_SITE_KEY")
        .onSuccess { client ->
          recaptchaClient = client
        }
        .onFailure { exception ->
          // Handle communication errors ...
          // See "Handle communication errors" section
        }
    }
  }

  private fun executeLoginAction() {
    lifecycleScope.launch {
      recaptchaClient
        .execute(RecaptchaAction.LOGIN)
        .onSuccess { token ->
          // Handle success ...
          // See "What's next" section for instructions
          // about handling tokens.
        }
        .onFailure { exception ->
          // Handle communication errors ...
          // See "Handle communication errors" section
        }
    }
  }

  private fun executeRedeemAction(){
    lifecycleScope.launch {
      recaptchaClient
        .execute(RecaptchaAction.custom("redeem"))
        .onSuccess { token ->
          // Handle success ...
          // See "What's next" section for instructions
          // about handling tokens.
        }
        .onFailure { exception ->
          // Handle communication errors ...
          // See "Handle communication errors" section
        }
    }
  }
}

자바

public final class MainActivity extends Activity {
  @Nullable private RecaptchaTasksClient recaptchaTasksClient = null;

  @Override
  protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    initializeRecaptchaClient();
    findViewById(R.id.btn_login).setOnClickListener(this::executeLoginAction);
    findViewById(R.id.btn_redeem).setOnClickListener(this::executeRedeemAction);
  }

  private void initializeRecaptchaClient() {
    Recaptcha
      .getTasksClient(getApplication(), "YOUR_SITE_KEY")
      .addOnSuccessListener(
          this,
          new OnSuccessListener<RecaptchaTasksClient>() {
            @Override
            public void onSuccess(RecaptchaTasksClient client) {
              MainActivity.this.recaptchaTasksClient = client;
            }
          })
      .addOnFailureListener(
          this,
          new OnFailureListener() {
            @Override
            public void onFailure(@NonNull Exception e) {
              // Handle communication errors ...
              // See "Handle communication errors" section
            }
          });
  }

  private void executeLoginAction(View v) {
    assert recaptchaTasksClient != null;
    recaptchaTasksClient
      .executeTask(RecaptchaAction.LOGIN)
      .addOnSuccessListener(
          this,
          new OnSuccessListener<String>() {
            @Override
            public void onSuccess(String token) {
              // Handle success ...
              // See "What's next" section for instructions
              // about handling tokens.
            }
          })
      .addOnFailureListener(
          this,
          new OnFailureListener() {
            @Override
            public void onFailure(@NonNull Exception e) {
              // Handle communication errors ...
              // See "Handle communication errors" section
            }
          });
  }

  private void executeRedeemAction(View v) {
    assert recaptchaTasksClient != null;
    recaptchaTasksClient
      .executeTask(RecaptchaAction.custom("redeem"))
      .addOnSuccessListener(
          this,
          new OnSuccessListener<String>() {
            @Override
            public void onSuccess(String token) {
              // Handle success ...
              // See "What's next" section for instructions
              // about handling tokens.
            }
          })
      .addOnFailureListener(
          this,
          new OnFailureListener() {
            @Override
            public void onFailure(@NonNull Exception e) {
              // Handle communication errors ...
              // See "Handle communication errors" section
            }
          });
  }
}

통신 오류 처리하기

앱이 reCAPTCHA 서비스와 성공적으로 통신할 수 없으면 API에 오류가 발생한 것일 수 있습니다. 이러한 오류를 정상적으로 처리하는 로직을 앱에 추가해야 합니다.

일반적인 API 오류의 완화에 대한 자세한 내용은 RecaptchaStatusCode를 참조하세요.

API 참조

Android용 reCAPTCHA API의 전체 참조는 com.google.android.recaptcha를 참조하세요.

다음 단계