ایجاد حساب‌های جدید با یک تک‌ضرب

اگر از ورود به سیستم با «حساب Google» پشتیبانی می‌کنید، می‌توانید از سرویس‌گیرنده ورود به سیستم One Tap استفاده کنید تا به کاربرانتان تجربه ایجاد حساب بدون مشکلی را ارائه دهید که هرگز آن‌ها را از بافت برنامه‌تان خارج نمی‌کند.

میانای کاربر ثبت‌نام با یک تک‌ضرب

وقتی One Tap UI را نمایش می‌دهید، از کاربران خواسته می‌شود بااستفاده از یکی از «حساب‌های Google» موجود در دستگاهشان، حساب جدیدی در برنامه‌تان ایجاد کنند. اگر کاربر انتخاب کند که ادامه دهد، یک شناسه با اطلاعات نمایه پایه (نام، عکس نمایه، و نشانی ایمیل تأییدشده) دریافت می‌کنید که می‌توانید از آن برای ایجاد حساب جدید استفاده کنید.

پیاده‌سازی ایجاد حساب با One Tap دو بخش دارد:

  • ادغام کردن کارخواه One Tap در برنامه‌تان که در این صفحه شرح داده شده است. این روش تا حد زیادی مشابه استفاده از ورود به سیستم با «تک‌ضرب» است، اما تفاوت‌هایی در پیکربندی دارد.
  • افزودن توانایی ایجاد حساب‌های کاربری از نشان‌های شناسه Google به باطن شما، که در استفاده از نشان‌های شناسه در باطن مورد بحث قرار گرفته است.

کجا باید از ثبت‌نام با «تک‌ضرب» استفاده کنم؟

تأثیرگذارترین جا برای ارائه ثبت‌نام با «تک‌ضرب» به کاربران، در زمینه‌ای است که ورود به سیستم ویژگی‌های جدیدی را فعال می‌کند. ابتدا سعی کنید کاربر را با اعتبارنامه ذخیره‌شده به سیستم وارد کنید. اگر اطلاعات کاربری ذخیره‌شده‌ای پیدا نشد، پیشنهاد دهید که حساب جدیدی برای کاربر ایجاد شود.

قبل‌از شروع

پروژه کنسول Google Cloud و پروژه Android خود را همان‌طور که در شروع به کار با ورود به سیستم با یک ضربه شرح داده شده است راه‌اندازی کنید.

۱. پیکربندی کردن کارخواه One Tap

برای پیکربندی کارخواه One Tap برای ایجاد حساب، کارهای زیر را انجام دهید:

  • درخواست‌های اطلاعات کاربری گذرواژه را فعال نکنید. (ثبت‌نام با «تک‌ضرب» فقط با اصالت‌سنجی مبتنی بر نمانام امکان‌پذیر است.)
  • درخواست‌های کد Google ID را بااستفاده از setGoogleIdTokenRequestOptions() و این تنظیمات فعال کنید:

    • شناسه کارخواه سرور را روی شناسه‌ای که در کنسول Google Cloud ایجاد کردید تنظیم کنید. توجه داشته باشید که این شناسه کارخواه سرور شما است، نه شناسه کارخواه Android شما.
    • کارخواه را طوری پیکربندی کنید که همه «حساب‌های Google» موجود در دستگاه را نشان دهد—یعنی براساس حساب‌های مجاز فیلتر نشود.
    • درصورت تمایل، می‌توانید شماره تلفن درستی‌سنجی‌شده حساب را نیز درخواست کنید.

جاوا

public class YourActivity extends AppCompatActivity {

    // ...

    private SignInClient oneTapClient;
    private BeginSignInRequest signUpRequest;

    @Override
    public void onCreate(@Nullable Bundle savedInstanceState,
                         @Nullable PersistableBundle persistentState) {
        super.onCreate(savedInstanceState, persistentState);

        oneTapClient = Identity.getSignInClient(this);
        signUpRequest = BeginSignInRequest.builder()
                .setGoogleIdTokenRequestOptions(GoogleIdTokenRequestOptions.builder()
                        .setSupported(true)
                        // Your server's client ID, not your Android client ID.
                        .setServerClientId(getString(R.string.your_web_client_id))
                        // Show all accounts on the device.
                        .setFilterByAuthorizedAccounts(false)
                        .build())
                .build();

        // ...
    }
}

کاتلین

class YourActivity : AppCompatActivity() {
      // ...

      private lateinit var oneTapClient: SignInClient
      private lateinit var signUpRequest: BeginSignInRequest

      override fun onCreate(savedInstanceState: Bundle?) {
          super.onCreate(savedInstanceState)
          setContentView(R.layout.activity_main)

          oneTapClient = Identity.getSignInClient(this)
          signUpRequest = BeginSignInRequest.builder()
              .setGoogleIdTokenRequestOptions(
                  BeginSignInRequest.GoogleIdTokenRequestOptions.builder()
                      .setSupported(true)
                      // Your server's client ID, not your Android client ID.
                      .setServerClientId(getString(R.string.your_web_client_id))
                      // Show all accounts on the device.
                      .setFilterByAuthorizedAccounts(false)
                      .build())
              .build()
          // ...
      }
      // ...
  }

۲. ردگیری لغو رابط کاربری One Tap

باید پیگیری کنید که آیا کاربر قبلاً با بستن پیام‌واره یا تک‌ضرب زدن در خارج از آن، از استفاده از ثبت‌نام با «تک‌ضرب» خودداری کرده است یا نه. برای مثال، می‌توانید از ویژگی بولی «فعالیت» خود استفاده کنید. (به توقف نمایش One Tap UI در زیر مراجعه کنید.)

۳. نمایش واسط کاربر ثبت‌نام با «تک‌ضرب»

اگر کاربر از استفاده از «ورود با یک ضربه» برای ایجاد حساب جدید امتناع نکرده است، روش beginSignIn() شیء مشتری را فراخوانی کنید و شنوندگان را به Task که برمی‌گرداند متصل کنید. برنامه‌ها معمولاً این مرحله را زمانی انجام می‌دهند که درخواست ورود به سیستم One Tap هیچ اعتبارنامه ذخیره‌شده‌ای را پیدا نکند—یعنی در شنونده شکست درخواست ورود به سیستم:

  • شنونده موفقیت: اگر کاربر یک یا چند «حساب Google» در دستگاه راه‌اندازی کرده باشد، کارخواه One Tap شنونده موفقیت را فراخوانی می‌کند. در شنونده موفقیت، قصد معوق را از نتیجه Task دریافت کنید و آن را به startIntentSenderForResult() ارسال کنید تا واسط کاربر One Tap شروع شود.
  • شنونده شکست: اگر کاربر هیچ «حساب Google» در دستگاه نداشته باشد، کارخواه One Tap شنونده شکست را فراخوانی می‌کند. در این مورد، هیچ اقدامی لازم نیست: به ارائه تجربه خارج‌شده از سیستم برنامه ادامه دهید و کاربر می‌تواند با جریان عادی ایجاد حساب شما ثبت‌نام کند.

جاوا

oneTapClient.beginSignIn(signUpRequest)
        .addOnSuccessListener(this, new OnSuccessListener<BeginSignInResult>() {
            @Override
            public void onSuccess(BeginSignInResult result) {
                try {
                    startIntentSenderForResult(
                            result.getPendingIntent().getIntentSender(), REQ_ONE_TAP,
                            null, 0, 0, 0);
                } catch (IntentSender.SendIntentException e) {
                    Log.e(TAG, "Couldn't start One Tap UI: " + e.getLocalizedMessage());
                }
            }
        })
        .addOnFailureListener(this, new OnFailureListener() {
            @Override
            public void onFailure(@NonNull Exception e) {
                // No Google Accounts found. Just continue presenting the signed-out UI.
                Log.d(TAG, e.getLocalizedMessage());
            }
        });

کاتلین

oneTapClient.beginSignIn(signUpRequest)
    .addOnSuccessListener(this) { result ->
        try {
            startIntentSenderForResult(
                result.pendingIntent.intentSender, REQ_ONE_TAP,
                null, 0, 0, 0)
        } catch (e: IntentSender.SendIntentException) {
            Log.e(TAG, "Couldn't start One Tap UI: ${e.localizedMessage}")
        }
    }
    .addOnFailureListener(this) { e ->
        // No Google Accounts found. Just continue presenting the signed-out UI.
        Log.d(TAG, e.localizedMessage)
    }

۴. مدیریت پاسخ کاربر

پاسخ کاربر به پیام‌واره ثبت‌نام با «تک‌ضرب» بااستفاده از روش onActivityResult() «فعالیت» شما به برنامه‌تان گزارش خواهد شد. اگر کاربر انتخاب کند که حساب ایجاد کند، نتیجه یک کد شناسه Google خواهد بود. اگر کاربر با بستن واسط کاربر «ثبت‌نام با یک ضربه» یا ضربه زدن در خارج از آن از ثبت‌نام خودداری کند، نتیجه با کد RESULT_CANCELED برگردانده می‌شود. برنامه‌تان باید هر دو احتمال را مدیریت کند.

ایجاد حساب با شناسه Google ID

اگر کاربر انتخاب کند که با «حساب Google» ثبت‌نام کند، می‌توانید با ارسال داده‌های هدف از onActivityResult() به روش getSignInCredentialFromIntent() کارخواه One Tap، یک شناسه برای کاربر دریافت کنید. اعتبارنامه دارای خصوصیت googleIdToken غیرتهی خواهد بود.

از کد شناسه برای ایجاد حساب در پس‌بخش خود استفاده کنید (به اصالت‌سنجی با پس‌بخش بااستفاده از کدهای شناسه مراجعه کنید) و کاربر را به سیستم وارد کنید.

اعتبارنامه همچنین حاوی جزئیات اضافی‌ای است که درخواست کرده‌اید، مثل شماره تلفن تأییدشده حساب (درصورت وجود).

جاوا

public class YourActivity extends AppCompatActivity {

    // ...
    private static final int REQ_ONE_TAP = 2;  // Can be any integer unique to the Activity.
    private boolean showOneTapUI = true;
    // ...

    @Override
    protected void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) {
        super.onActivityResult(requestCode, resultCode, data);

        switch (requestCode) {
            case REQ_ONE_TAP:
                try { 
                    SignInCredential credential = oneTapClient.getSignInCredentialFromIntent(data);
                    String idToken = credential.getGoogleIdToken();
                    if (idToken !=  null) {
                        // Got an ID token from Google. Use it to authenticate
                        // with your backend.
                        Log.d(TAG, "Got ID token.");
                    }
                } catch (ApiException e) {
                    // ...
                }
                break;
        }
    }
}

کاتلین

class YourActivity : AppCompatActivity() {

      // ...
      private val REQ_ONE_TAP = 2  // Can be any integer unique to the Activity
      private var showOneTapUI = true
      // ...

      override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
          super.onActivityResult(requestCode, resultCode, data)

          when (requestCode) {
               REQ_ONE_TAP -> {
                  try { 
                      val credential = oneTapClient.getSignInCredentialFromIntent(data)
                      val idToken = credential.googleIdToken
                      when {
                          idToken != null -> {
                              // Got an ID token from Google. Use it to authenticate
                              // with your backend.
                              Log.d(TAG, "Got ID token.")
                          }
                          else -> {
                              // Shouldn't happen.
                              Log.d(TAG, "No ID token!")
                          }
                      }
                  } catch (e: ApiException) {
                      // ...
              }
          }
      }
      // ...
  }

نمایش One Tap UI متوقف شود

اگر کاربر ورود به سیستم را رد کند، تماس با getSignInCredentialFromIntent() یک ApiException با کد وضعیت CommonStatusCodes.CANCELED ایجاد می‌کند. وقتی این اتفاق می‌افتد، باید موقتاً نمایش میانای کاربری ورود به سیستم با «یک ضربه» را متوقف کنید تا با درخواست‌های مکرر کاربران را آزار ندهید. مثال زیر این کار را با تنظیم یک ویژگی در «فعالیت» انجام می‌دهد که از آن برای تعیین اینکه آیا ورود به سیستم با «یک ضربه» را به کاربر پیشنهاد دهد یا نه استفاده می‌کند؛ بااین‌حال، می‌توانید مقداری را در SharedPreferences ذخیره کنید یا از روش دیگری استفاده کنید.

مهم است که محدودیت نرخ خودتان را برای پیام‌واره‌های ورود به سیستم با «تک‌ضرب» پیاده‌سازی کنید. اگر این کار را نکنید و کاربر چندین پیام‌واره را پشت‌سرهم لغو کند، سرویس‌گیرنده One Tap تا ۲۴ ساعت آینده به کاربر پیام‌واره نشان نخواهد داد.

جاوا

public class YourActivity extends AppCompatActivity {

    // ...
    private static final int REQ_ONE_TAP = 2;  // Can be any integer unique to the Activity.
    private boolean showOneTapUI = true;
    // ...

    @Override
    protected void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) {
        super.onActivityResult(requestCode, resultCode, data);

        switch (requestCode) {
            case REQ_ONE_TAP:
                try {
                    // ...
                } catch (ApiException e) {
                    switch (e.getStatusCode()) {
                        case CommonStatusCodes.CANCELED:
                            Log.d(TAG, "One-tap dialog was closed.");
                            // Don't re-prompt the user.
                            showOneTapUI = false;
                            break;
                        case CommonStatusCodes.NETWORK_ERROR:
                            Log.d(TAG, "One-tap encountered a network error.");
                            // Try again or just ignore.
                            break;
                        default:
                            Log.d(TAG, "Couldn't get credential from result."
                                    + e.getLocalizedMessage());
                            break;
                    }
                }
                break;
        }
    }
}

کاتلین

class YourActivity : AppCompatActivity() {

      // ...
      private val REQ_ONE_TAP = 2  // Can be any integer unique to the Activity
      private var showOneTapUI = true
      // ...

      override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
          super.onActivityResult(requestCode, resultCode, data)

          when (requestCode) {
              REQ_ONE_TAP -> {
                  try {
                      // ...
                  } catch (e: ApiException) {
                      when (e.statusCode) {
                          CommonStatusCodes.CANCELED -> {
                              Log.d(TAG, "One-tap dialog was closed.")
                              // Don't re-prompt the user.
                              showOneTapUI = false
                          }
                          CommonStatusCodes.NETWORK_ERROR -> {
                              Log.d(TAG, "One-tap encountered a network error.")
                              // Try again or just ignore.
                          }
                          else -> {
                              Log.d(TAG, "Couldn't get credential from result." +
                                  " (${e.localizedMessage})")
                          }
                      }
                  }
              }
          }
      }
      // ...
  }

مراحل بعدی

وقتی کاربر جریان ثبت‌نام با «تک‌ضرب» را تکمیل می‌کند، یک شناسه Google دریافت می‌کنید که شامل برخی اطلاعات نمایه پایه است: نشانی ایمیل کاربر، نام کامل، و نشانی وب عکس نمایه. برای بسیاری از برنامه‌ها، این اطلاعات برای شما کافی است تا اصالت کاربر را در پس‌بخش تأیید کنید و حساب جدیدی ایجاد کنید.

اگر برای تکمیل ایجاد حساب به اطلاعات بیشتری نیاز دارید (مثلاً تاریخ تولد کاربر)، جریان جزئیات ثبت‌نام را به کاربر ارائه دهید و این اطلاعات اضافی را درخواست کنید. سپس، آن را به باطن خود ارسال کنید تا ایجاد حساب تکمیل شود.