المصادقة باستخدام خدمات ألعاب Google Play مع C ++

يمكنك استخدام خدمات ألعاب Google Play لتسجيل دخول اللاعبين إلى لعبة Android مبنية على Firebase ومكتوبة بلغة C ++. لاستخدام خدمات ألعاب Google Play ، قم بتسجيل الدخول باستخدام Firebase ، قم أولاً بتسجيل الدخول إلى المشغل باستخدام ألعاب Google Play ، واطلب رمز مصادقة OAuth 2.0 عند القيام بذلك. ثم، لتمرير قانون المصادقة على PlayGamesAuthProvider لتوليد الاعتماد Firebase، والتي يمكنك استخدامها لمصادقة مع Firebase.

قبل ان تبدأ

قبل أن تتمكن من استخدام مصادقة Firebase ، تحتاج إلى:

  • سجل مشروع C ++ الخاص بك وقم بتكوينه لاستخدام Firebase.

    إذا كان مشروع C ++ الخاص بك يستخدم Firebase بالفعل ، فهذا يعني أنه تم تسجيله بالفعل وتهيئته لـ Firebase.

  • إضافة ++ SDK Firebase C إلى C ++ المشروع الخاص بك.

ملاحظة أن إضافة Firebase إلى C ++ بك المشروع يتضمن المهام سواء في وحدة التحكم Firebase وفي المشروع C ++ مفتوحة (على سبيل المثال، يمكنك تحميل ملفات التكوين Firebase من وحدة التحكم، ثم نقلها إلى حسابك C ++ المشروع).

قم بإعداد مشروع Firebase الخاص بك

  1. إذا كنت لم تقم بذلك بالفعل، تعيين اللعبة لديك بصمة SHA-1 في إعدادات الصفحة من وحدة التحكم Firebase.

    يمكنك الحصول على تجزئة SHA شهادة للتوقيع مع gradle signingReport الأوامر:

    ./gradlew signingReport

  2. تمكين ألعاب Google Play كموفر لتسجيل الدخول:

    1. ابحث عن معرّف عميل خادم الويب الخاص بمشروعك وسر العميل. يحدد معرّف عميل خادم الويب مشروع Firebase لخوادم مصادقة Google Play.

      للعثور على هذه القيم:

      1. فتح مشروع Firebase الخاصة بك في وحدة التحكم جوجل واجهات برمجة التطبيقات صفحة بيانات الاعتماد.
      2. في قسم أوث 2.0 معرفات العميل، فتح عميل ويب (السيارات التي تم إنشاؤها بواسطة خدمة جوجل) تفاصيل الصفحة. تسرد هذه الصفحة معرف عميل خادم الويب والسر.
    2. ثم، في وحدة التحكم Firebase ، فتح الباب المصادقة.

    3. على علامة التبويب تسجيل الدخول الأسلوب، تمكين لعب الألعاب تسجيل الدخول الموفر. ستحتاج إلى تحديد معرف عميل خادم الويب الخاص بمشروعك وسر العميل ، والذي حصلت عليه من وحدة تحكم واجهات برمجة التطبيقات.

  1. في وحدة التحكم في Google Play ، افتح التطبيق الخاص بك أو إنشاء واحد.

  2. في قسم تنمو، انقر فوق تشغيل خدمات الألعاب> الإعداد والإدارة> التكوين.

  3. انقر فوق نعم، يستخدم لعبي Google APIs فعلا، حدد اسم المشروع Firebase من القائمة، ثم انقر فوق استخدام.

  4. على Play صفحة التكوين ألعاب الخدمات، انقر فوق إضافة الاعتمادات.

    1. حدد نوع الخادم لعبة.
    2. في مجال العميل أوث، تحديد هوية العميل المشروع على شبكة الإنترنت الخاص بك. تأكد من أن هذا هو نفس معرّف العميل الذي حددته عند تمكين تسجيل الدخول إلى ألعاب Play.
    3. احفظ تغييراتك.
  5. لا يزال على Play صفحة التكوين ألعاب الخدمات، انقر فوق إضافة الاعتماد مرة أخرى.

    1. حدد نوع الروبوت.
    2. في مجال العميل أوث، تحديد هوية العميل الروبوت المشروع الخاص بك. (إذا كنت لا ترى معرّف عميل Android ، فتأكد من تعيين بصمة SHA-1 للعبة في وحدة تحكم Firebase.)
    3. احفظ تغييراتك.
  6. على الصفحة اختبار، إضافة عناوين البريد الإلكتروني لأي مستخدمين الذين يحتاجون لتكون قادرة على الدخول الى اللعبة قبل الإفراج عنها على مخزن اللعب.

ادمج تسجيل الدخول إلى "ألعاب Play" في لعبتك

قبل أن تتمكن من تسجيل دخول اللاعبين إلى لعبتك ، يجب عليك دمج تسجيل الدخول إلى ألعاب Google Play.

الطريقة الأسهل والموصى بها لإضافة دعم لتشغيل الألعاب تسجيل الدخول إلى مشروع C ++ الروبوت هو استخدام جوجل الدخول في C ++ SDK .

لإضافة "ألعاب Play" ، قم بتسجيل الدخول إلى لعبتك باستخدام Google Sign-in C ++ SDK ، قم بما يلي:

  1. استنساخ أو تحميل جوجل تسجيل الدخول-الوحدة مستودع البرنامج المساعد ، الذي يحتوي أيضا على ++ C SDK.

  2. إنشاء المشروع الوارد في staging/native/ الدليل، إما باستخدام الروبوت ستوديو أو gradlew build .

    بناء نسخ انتاجها إلى دليل اسمه google-signin-cpp .

  3. قم بتضمين Google Sign-in C ++ SDK في ملف إنشاء الكود الأصلي للعبة:

    CMake

    في المستوى الأعلى الخاص بك CMakeLists.txt الملف:

    set(GSI_PACKAGE_DIR "/path/to/google-signin-cpp")
    add_library(lib-google-signin-cpp STATIC IMPORTED) set_target_properties(lib-google-signin-cpp PROPERTIES IMPORTED_LOCATION     ${GSI_PACKAGE_DIR}/lib/${ANDROID_ABI}/libgoogle-signin-cpp.a )
    ...
    target_link_libraries(     ...     lib-google-signin-cpp)

    ndk- بناء

    في الخاص Android.mk الملف:

    include $(CLEAR_VARS)
    LOCAL_MODULE := google-signin-cpp
    GSI_SDK_DIR := /path/to/google-signin-cpp
    LOCAL_SRC_FILES := $(GSI_SDK_DIR)/lib/$(TARGET_ARCH_ABI)/libgoogle-signin-cpp.a
    LOCAL_EXPORT_C_INCLUDES := $(GSI_SDK_DIR)/include
    include $(PREBUILT_STATIC_LIBRARY)
    

  4. بعد ذلك ، قم بتضمين مكون Java helper ، المطلوب بواسطة C ++ SDK.

    للقيام بذلك، في مستوى المشروع الخاص بك build.gradle الملف، إضافة الدليل الإخراج SDK بناء كمستودع المحلي:

    allprojects {
        repositories {
            // ...
            flatDir {
                dirs 'path/to/google-signin-cpp'
            }
        }
    }
    

    و، في مستوى الوحدة النمطية الخاصة بك build.gradle ملف، أن يعلن العنصر المساعد ك تبعية:

    dependencies {
        implementation 'com.google.android.gms:play-services-auth:19.2.0'
        // Depend on the AAR built with the Google Sign-in SDK in order to add
        // the Java helper classes, which are used by the C++ library.
        compile(name:'google-signin-cpp-release', ext:'aar')
    }
    
  5. ثم، في اللعبة، تكوين GoogleSignIn الكائن إلى استخدام اللعب ألعاب تسجيل الدخول ولاسترداد رمز الملقم المصادقة:

    #include "google_signin.h"
    #include "future.h"
    
    using namespace google::signin;
    
    // ...
    
    GoogleSignIn::Configuration config = {};
    config.web_client_id = "YOUR_WEB_CLIENT_ID_HERE";
    config.request_id_token = false;
    config.use_game_signin = true;
    config.request_auth_code = true;
    
    GoogleSignIn gsi = GoogleSignIn(GetActivity(), GetJavaVM());
    gsi.Configure(config);
    
  6. وأخيرا، ندعو SignIn() في التعاقد مع اللاعب في اللعب ألعاب:

    Future<GoogleSignIn::SignInResult> &future = gsi.SignIn();
    

    عندما عاد المستقبل عن طريق SignIn() يقرر، يمكنك الحصول على رمز الخادم المصادقة من النتيجة:

    if (!future.Pending()) {
        const GoogleSignIn::StatusCode status =
                static_cast<GoogleSignIn::StatusCode>(future.Status());
        if (status == GoogleSignIn::kStatusCodeSuccess) {
            // Player successfully signed in to Google Play! Get auth code to
            //   pass to Firebase
            const GoogleSignIn::SignInResult result =
                    static_cast<GoogleSignIn::SignInResult>(future.Result());
            const char* server_auth_code = result.User.GetServerAuthCode();
        }
    }
    

مصادقة مع Firebase

بعد أن يقوم اللاعب بتسجيل الدخول باستخدام "ألعاب Play" ، يمكنك استخدام رمز المصادقة للمصادقة باستخدام Firebase.

  1. بعد أن ينجح اللاعب في تسجيل الدخول باستخدام "ألعاب Play" ، احصل على رمز مصادقة لحساب اللاعب.

  2. بعد ذلك ، استبدل رمز المصادقة من خدمات ألعاب Play ببيانات اعتماد Firebase ، واستخدم بيانات اعتماد Firebase لمصادقة المشغل:

    firebase::auth::Credential credential =
        firebase::auth::PlayGamesAuthProvider::GetCredential(server_auth_code);
    firebase::Future<firebase::auth::User*> result =
        auth->SignInWithCredential(credential);
    
  3. إذا كان البرنامج يحتوي على حلقة التحديث الذي يعمل بانتظام (ويقول في 30 أو 60 مرة في الثانية الواحدة)، يمكنك التحقق من النتائج مرة واحدة في التحديث مع Auth::SignInWithCredentialLastResult :

    firebase::Future<firebase::auth::User*> result =
        auth->SignInWithCredentialLastResult();
    if (result.status() == firebase::kFutureStatusComplete) {
      if (result.error() == firebase::auth::kAuthErrorNone) {
        firebase::auth::User* user = *result.result();
        printf("Sign in succeeded for `%s`\n", user->display_name().c_str());
      } else {
        printf("Sign in failed with error '%s'\n", result.error_message());
      }
    }

    أو، إذا كان البرنامج هو الدافع وراء الحدث، قد تفضل تسجيل رد على المستقبل .

تسجيل معاودة الاتصال على المستقبل

بعض البرامج لديها Update الوظائف التي تسمى 30 أو 60 مرة في الثانية الواحدة. على سبيل المثال ، تتبع العديد من الألعاب هذا النموذج. ويمكن لهذه البرامج استدعاء LastResult وظائف لاستطلاع المكالمات غير متزامن. ومع ذلك ، إذا كان برنامجك مدفوعًا بالأحداث ، فقد تفضل تسجيل وظائف رد الاتصال. يتم استدعاء وظيفة رد الاتصال عند الانتهاء من المستقبل.
void OnCreateCallback(const firebase::Future<firebase::auth::User*>& result,
                      void* user_data) {
  // The callback is called when the Future enters the `complete` state.
  assert(result.status() == firebase::kFutureStatusComplete);

  // Use `user_data` to pass-in program context, if you like.
  MyProgramContext* program_context = static_cast<MyProgramContext*>(user_data);

  // Important to handle both success and failure situations.
  if (result.error() == firebase::auth::kAuthErrorNone) {
    firebase::auth::User* user = *result.result();
    printf("Create user succeeded for email %s\n", user->email().c_str());

    // Perform other actions on User, if you like.
    firebase::auth::User::UserProfile profile;
    profile.display_name = program_context->display_name;
    user->UpdateUserProfile(profile);

  } else {
    printf("Created user failed with error '%s'\n", result.error_message());
  }
}

void CreateUser(firebase::auth::Auth* auth) {
  // Callbacks work the same for any firebase::Future.
  firebase::Future<firebase::auth::User*> result =
      auth->CreateUserWithEmailAndPasswordLastResult();

  // `&my_program_context` is passed verbatim to OnCreateCallback().
  result.OnCompletion(OnCreateCallback, &my_program_context);
}
وظيفة رد الاتصال يمكن أيضا أن يكون لامدا، إذا كنت تفضل ذلك.
void CreateUserUsingLambda(firebase::auth::Auth* auth) {
  // Callbacks work the same for any firebase::Future.
  firebase::Future<firebase::auth::User*> result =
      auth->CreateUserWithEmailAndPasswordLastResult();

  // The lambda has the same signature as the callback function.
  result.OnCompletion(
      [](const firebase::Future<firebase::auth::User*>& result,
         void* user_data) {
        // `user_data` is the same as &my_program_context, below.
        // Note that we can't capture this value in the [] because std::function
        // is not supported by our minimum compiler spec (which is pre C++11).
        MyProgramContext* program_context =
            static_cast<MyProgramContext*>(user_data);

        // Process create user result...
        (void)program_context;
      },
      &my_program_context);
}

الخطوات التالية

بعد تسجيل دخول المستخدم لأول مرة ، يتم إنشاء حساب مستخدم جديد وربطه بمعرف ألعاب Play الخاص به. يتم تخزين هذا الحساب الجديد كجزء من مشروع Firebase الخاص بك ، ويمكن استخدامه لتحديد مستخدم عبر كل تطبيق في مشروعك.

في اللعبة، يمكنك الحصول على Firebase UID المستخدم من firebase::auth::User جوه:

firebase::auth::User* user = auth->current_user();
if (user != nullptr) {
  std::string playerName = user->displayName();

  // The user's ID, unique to the Firebase project.
  // Do NOT use this value to authenticate with your backend server,
  // if you have one. Use firebase::auth::User::Token() instead.
  std::string uid = user->uid();
}

في قاعدة البيانات الخاصة بك Firebase الحقيقي والكلمة الدلالية ضوابط الأمن التخزين، يمكنك الحصول على قعت في هوية المستخدم الفريد المستخدم من auth متغير، واستخدامها للسيطرة على ما هي البيانات على وصول ويمكن للمستخدم.

للحصول على اللعب ألعاب المعلومات اعب المستخدم أو إلى خدمات الألعاب وصول اللعب، واستخدام واجهات برمجة التطبيقات التي توفرها خدمات Google Play ألعاب C ++ SDK .

تسجيل الخروج مستخدم، استدعاء SignOut() :

auth->SignOut();