Android Developer Console API

Android Developer Console API یک سرویس RESTful است که به توسعه‌دهندگان درستی‌سنجی‌شده امکان می‌دهد گردش‌های کاری درستی‌سنجی توسعه‌دهنده Android را در Android Developer Console خودکارسازی کنند، ازجمله بازیابی حساب‌های توسعه‌دهنده، بررسی الزامات واجدشرایط بودن کلید، ثبت نام بسته‌های Android، ثبت کلیدهای امضای برنامه، و درستی‌سنجی مالکیت کلید.

نمای کلی، موارد استفاده، و بافت پیاده‌سازی

موارد استفاده و ویژگی‌های کلیدی

  • ثبت خودکار نام بسته CI/CD: ده‌ها یا صدها نام بسته Android را به‌صورت برنامه‌نویسی‌شده ثبت کنید (CreateAndroidPackage).
  • بازرسی خط‌مشی کلید سابقه پیش‌پرواز: به‌صورت برنامه‌نویسی‌شده بازرسی می‌کند که آیا Google قبلاً نام بسته‌ای را در بوم‌سازگان مشاهده کرده است یا نه و آیا ثبت گواهی امضای خاصی به درستی‌سنجی مالکیت کلید نیاز دارد یا نه (GetAndroidPackageRegistrationPolicy).
  • ثبت خودکار کلید امضای برنامه و درستی‌سنجی مالکیت: اثر انگشت‌های SHA-256 گواهی امضای عمومی را ثبت کنید (CreateAndroidPackageKey)، کدهای چالش درستی‌سنجی منحصربه‌فرد را بازیابی کنید (verificationToken)، و اثبات مالکیت کلید خصوصی را بااستفاده از بارگذاری‌های APK امضاشده ازسرگرفتنی یا تک‌درخواستی خودکار کنید (VerifyAndroidPackageKeyOwnership).
  • ارسال توجیه برنامه‌ای: توجیه مالکیت ارسال کنید (JustifyAndroidPackageKeyRegistration).
  • پایش وضعیت: پایش وضعیت ثبت در حساب‌های توسعه‌دهنده، نام‌های بسته، و کلیدهای امضای برنامه (GetDeveloperAccount، ListDeveloperAccounts، GetAndroidPackage، ListAndroidPackages، GetAndroidPackageKey، ListAndroidPackageKeys).

گردش کار پیاده‌سازی سرتاسر

  1. درستی‌سنجی هویت توسعه‌دهنده یک‌بار در میانای کاربر: درستی‌سنجی هویت توسعه‌دهنده (INDIVIDUAL یا ORGANIZATION) را در Android Developer Console تکمیل کنید تا verificationState VERIFIED شود.
  2. فعال کردن میانای برنامه‌سازی کاربردی و اصالت‌سنجی: androiddeveloperconsole.googleapis.com را در پروژه Google Cloud خود فعال کنید و یک کد دسترسی OAuth 2.0 Bearer با واگذاری کاربر با محدوده https://www.googleapis.com/auth/androiddeveloperconsole دریافت کنید.
  3. نام منبع حساب توسعه‌دهنده خود را پیدا کنید: با GET /v1/developerAccounts (ListDeveloperAccounts) تماس بگیرید تا developerAccounts/{developer_account} را بازیابی کنید و تأیید کنید که verificationState VERIFIED است.
  4. خط‌مشی ثبت نام بسته را بررسی کنید: با GET /v1/developerAccounts/{id}/androidPackages/{pkg}/registrationPolicy (GetAndroidPackageRegistrationPolicy) تماس بگیرید تا keySelectionStrategy (SELECT_KEY_FROM_LIST یا USE_ANY_KEY) و هرگونه کلید امضای شناخته‌شده قبلی (knownKeys) را بررسی کنید.
  5. منبع بسته Android را ایجاد کنید: با بدنه {"name": ""} با POST /v1/developerAccounts/{id}/androidPackages?androidPackageId={pkg} (CreateAndroidPackage) تماس بگیرید (منبع را در وضعیت DRAFT ایجاد می‌کند).
  6. اثر انگشت کلید امضای برنامه‌تان را ثبت کنید: با بدنه JSON {"certificateFingerprintSha256": "..."} با POST /v1/developerAccounts/{id}/androidPackages/{pkg}/keys (CreateAndroidPackageKey) تماس بگیرید. وضعیت برگردانده‌شده را بررسی کنید:
    • DRAFT: اثبات مالکیت کلید خصوصی الزامی است و پاسخ شامل یک verificationToken منحصربه‌فرد برای مرحله ۷ است.
    • IN_REVIEW: اثبات مالکیت و توجیه به‌طور خودکار رد می‌شود (برای مثال، هنگام ثبت نام بسته جدیدی که هرگز در Android دیده نشده است، یا وقتی قبلاً مالکیت این کلید امضا را برای نام بسته دیگری در همان DeveloperAccount درستی‌سنجی کرده‌اید). مرحله ۷ و فراخوانی توجیه در مرحله ۸ را رد کنید و مستقیماً به نظرسنجی GetAndroidPackage و GetAndroidPackageKey بروید.
  7. فایل APK درستی‌سنجی را بسازید و بارگذاری کنید (اگر وضعیت DRAFT است): رشته verificationToken برگردانده‌شده را در assets/adi-registration.properties داخل یک فایل APK حداقلی مطابق با packageName جاسازی کنید، آن را با کلید خصوصی امضای برنامه‌تان امضا کنید، و آن را بااستفاده از POST /upload/v1/developerAccounts/{id}/androidPackages/{pkg}/keys/{sha256}:verify (VerifyAndroidPackageKeyOwnership) بارگذاری کنید.
  8. ارسال توجیه (درصورت نیاز) و وضعیت ثبت نظرسنجی: اگر کلید در وضعیت OWNERSHIP_VERIFIED و registrationJustificationRequired true است، با POST /v1/developerAccounts/{id}/androidPackages/{pkg}/keys/{sha256}:justifyAndroidPackageKeyRegistration (JustifyAndroidPackageKeyRegistration) تماس بگیرید. نظرسنجی GetAndroidPackage و GetAndroidPackageKey تا زمانی که state به REGISTERED برسد.

فرمان‌های CLI محلی برای آماده‌سازی اثر انگشت کلید و APK درستی‌سنجی

  • استخراج اثر انگشت گواهینامه SHA-256 از keystore (keytool):

    keytool -list -v -keystore release-key.jks -alias my-key-alias
  • درستی‌سنجی کردن خلاصه گواهی امضای SHA-256 در APK ساخته‌شده (apksigner):

    apksigner verify --print-certs app-release.apk
  • بررسی نام بسته APK و فایل کد جاسازی‌شده قبل‌از بارگذاری (aapt2 و unzip):

    aapt2 dump badging app-release.apk | head -n 1
    unzip -p app-release.apk assets/adi-registration.properties

قابلیت‌های میانای برنامه‌سازی کاربردی و واسط کاربر Android Developer Console

تکلیف رابط کاربری وب Android Developer Console (android.google.com/developerconsole) Android Developer Console API
درستی‌سنجی هویت توسعه‌دهنده (KYC/KYB) و پرداخت کارمزد پشتیبانی می‌شود (پیش‌نیاز یک‌باره لازم است) بااستفاده از API پشتیبانی نمی‌شود (بررسی وضعیت فقط خواندنی بااستفاده از GetDeveloperAccount و ListDeveloperAccounts)
مشاهده حساب‌های توسعه‌دهنده پیوندشده تغییردهنده حساب در سرصفحه کنسول ‫GET /v1/developerAccounts‏ (ListDeveloperAccounts)
کلیدهای امضا و خط‌مشی قبلی را برای نام بسته بررسی کنید درطول برنامه نصب «ثبت کردن نام بسته» نمایش داده می‌شود ‫GET /v1/.../registrationPolicy‏ (GetAndroidPackageRegistrationPolicy)
ثبت کردن نام بسته Android جدید نام بسته‌ها > ثبت کردن نام بسته ‫POST /v1/{parent}/androidPackages?androidPackageId=...‏ (CreateAndroidPackage)
مشاهده یا فهرست کردن نام بسته‌های ثبت‌شده و پیش‌نویس جدول داشبورد نام بسته‌ها GET /v1/{name} ‏(GetAndroidPackage)، ‏GET /v1/{parent}/androidPackages ‏(ListAndroidPackages)
کلید امضای برنامه اضافه کنید و کد چالش تولید کنید جزئیات بسته > افزودن کلید امضا ‫POST /v1/{parent}/keys‏ (CreateAndroidPackageKey)
اثبات مالکیت کلید خصوصی (adi-registration.properties) بارگذاری APK قطعه امضاشده در واسط کاربر کنسول ‫POST /upload/v1/{name}:verify‏ (VerifyAndroidPackageKeyOwnership)
ارسال توجیه وقتی کلید به بازبینی دستی نیاز دارد پیام‌واره نوشتاری درطول گردش کار ثبت کلید ‫POST /v1/{name}:justifyAndroidPackageKeyRegistration‏ (JustifyAndroidPackageKeyRegistration)

پیکربندی و اصالت‌سنجی سرویس

همه درخواست‌های میانای برنامه‌سازی کاربردی باید از HTTPS استفاده کنند و شامل سرصفحه Authorization: Bearer ACCESS_TOKEN باشند که بااستفاده از جریان سرور وب OAuth 2.0 برای «حساب Google» که درستی‌سنجی هویت توسعه‌دهنده را در کنسول توسعه‌دهنده Android تکمیل کرده است به‌دست آمده باشد.

دارایی مقدار
نقطه پایان REST پایه https://androiddeveloperconsole.googleapis.com
نقطه پایانی بارگذاری رسانه https://androiddeveloperconsole.googleapis.com/upload
نسخه میانای برنامه‌سازی کاربردی v1
محدوده OAuth 2.0 الزامی https://www.googleapis.com/auth/androiddeveloperconsole
حد سهمیه پیش‌فرض 2,000 درخواست در روز برای هر پروژه Google Cloud برای هر روش

منابع و نقاط پایان API

Android Developer Console API منابع را در سلسله‌مراتب زیر سازمان‌دهی می‌کند:

  • DeveloperAccount (developerAccounts/{developer_account})
    • AndroidPackage (developerAccounts/{developer_account}/androidPackages/{android_package})
      • ‫AndroidPackageRegistrationPolicy (developerAccounts/{developer_account}/androidPackages/{android_package}/registrationPolicy)
      • ‫AndroidPackageKey (developerAccounts/{developer_account}/androidPackages/{android_package}/keys/{key})

منبع: DeveloperAccount

نشان‌دهنده حسابی در Android Developer Console است که با هویت توسعه‌دهنده مرتبط است.

فیلد نوع شرح
name string شناسه. نام منبع در قالب developerAccounts/{developer_account}.
displayName string فقط خروجی. نام قابل‌خواندن برای انسان که با حساب توسعه‌دهنده مرتبط است (نام فرد یا نام سازمان).
verificationState enum (VerificationState) فقط خروجی. وضعیت فعلی درستی‌سنجی هویت توسعه‌دهنده حساب.

Enum: DeveloperAccount.VerificationState

مقدار شرح
VERIFIED درستی‌سنجی هویت توسعه‌دهنده تکمیل شده است. این حساب می‌تواند نام بسته‌ها و کلیدهای امضای برنامه را ثبت کند.
NOT_VERIFIED درستی‌سنجی هویت توسعه‌دهنده در Android Developer Console تکمیل نشده است.

روش‌ها: DeveloperAccount

روش درخواست HTTP شرح
GetDeveloperAccount GET /v1/{name=developerAccounts/*} فراداده و وضعیت درستی‌سنجی را برای یک DeveloperAccount بازیابی می‌کند.
ListDeveloperAccounts GET /v1/developerAccounts همه اشیای DeveloperAccount را که برای «حساب Google» اصالت‌سنجی‌شده قابل‌دسترسی است فهرست می‌کند (صفحه‌بندی‌نشده).

منبع: AndroidPackage

نشان‌دهنده نام بسته Android است که تحت DeveloperAccount ثبت شده است یا درحال ثبت شدن است.

فیلد نوع شرح
name string شناسه. نام منبع در قالب developerAccounts/{developer_account}/androidPackages/{android_package}، که {android_package} نام بسته Android است (برای مثال، com.example.myapp).
packageName string فقط خروجی. نام بسته Android (برای مثال، com.example.myapp).
state enum (AndroidPackage.State) فقط خروجی. وضعیت چرخه حیات ثبت فعلی نام بسته.
registeredAppStore boolean فقط خروجی. نشان می‌دهد که آیا این نام بسته درحال‌حاضر به‌عنوان فروشگاه برنامه‌های ثبت‌شده فعال است یا نه.

Enum: AndroidPackage.State

مقدار شرح
DRAFT منبع نام بسته ایجاد شده است و ثبت کلید امضای برنامه یا درستی‌سنجی مالکیت هنوز درحال انجام است.
IN_REVIEW ثبت نام بسته و هرگونه توجیه کلید لازم ارسال شده است و Google درحال بررسی آن‌ها است. بسته از DRAFT به IN_REVIEW منتقل می‌شود، یا بلافاصله پس‌از CreateAndroidPackageKey (وقتی درستی‌سنجی مالکیت کلید رد می‌شود، ازجمله وقتی کلید قبلاً برای نام بسته دیگری در همان DeveloperAccount درستی‌سنجی شده باشد) یا پس‌از تکمیل VerifyAndroidPackageKeyOwnership و، درصورت نیاز، JustifyAndroidPackageKeyRegistration.
REGISTERED نام بسته به‌طور فعال برای درستی‌سنجی توسعه‌دهنده نرم‌افزار Android در این حساب توسعه‌دهنده ثبت شده است.
PENDING_TRANSFER نام بسته درانتظار تکمیل انتقال مالکیت به حساب توسعه‌دهنده دیگری است.

منبع: AndroidPackageRegistrationPolicy

منبع تک‌عضوی برگردانده‌شده توسط GetAndroidPackageRegistrationPolicy که کلیدهای امضای عمومی قدیمی شناسایی‌شده برای نام بسته را شرح می‌دهد و اینکه آیا ثبت نام بسته با کلید امضای داده‌شده به توجیه کتبی نیاز دارد یا نه.

فیلد نوع شرح
name string شناسه. نام منبع در قالب developerAccounts/{developer_account}/androidPackages/{android_package}/registrationPolicy.
knownKeys[] object (KnownKey) فهرست کلیدهای امضای برنامه قدیمی که قبلاً برای توزیع برنامه‌هایی با این نام بسته مشاهده شده‌اند، به‌ترتیب الفبایی براساس certificateFingerprintSha256 مرتب شده‌اند.
knownKeys[].certificateFingerprintSha256 string فقط خروجی. اثر انگشت SHA-256 شانزده‌شانزدهی حروف کوچک ۶۴ نویسه‌ای نرمال‌شده گواهینامه امضای قدیمی (بدون دونقطه).
knownKeys[].justificationRequirement enum (JustificationRequirement) فقط خروجی. نشان می‌دهد که آیا ثبت این کلید مستلزم فراخوانی JustifyAndroidPackageKeyRegistration (REQUIRED یا NOT_REQUIRED) است یا نه. اگر کلید امضا قبلاً در نام بسته دیگری تحت همان DeveloperAccount درستی‌سنجی شده باشد، هم VerifyAndroidPackageKeyOwnership و هم JustifyAndroidPackageKeyRegistration نادیده گرفته می‌شوند، حتی اگر justificationRequirement REQUIRED باشد.
keySelectionStrategy enum (KeySelectionStrategy) فقط خروجی. خط‌مشی انتخاب کلید برای ثبت این نام بسته: SELECT_KEY_FROM_LIST (باید کلیدی از knownKeys ثبت شود) یا USE_ANY_KEY (هر کلید امضای برنامه معتبری که متعلق به توسعه‌دهنده باشد می‌تواند ثبت شود).

Enum: KnownKey.JustificationRequirement

مقدار شرح
REQUIRED ثبت این کلید شناخته‌شده مستلزم ارسال توجیه کتبی بااستفاده از JustifyAndroidPackageKeyRegistration پس‌از تکمیل VerifyAndroidPackageKeyOwnership است (مگر اینکه کلید قبلاً در نام بسته دیگری تحت همان DeveloperAccount درستی‌سنجی شده باشد که دراین‌صورت از هر دو VerifyAndroidPackageKeyOwnership و JustifyAndroidPackageKeyRegistration صرف‌نظر می‌شود).
NOT_REQUIRED ثبت این کلید شناخته‌شده نیازی به توجیه ندارد. کلید مستقیماً پس‌از VerifyAndroidPackageKeyOwnership به IN_REVIEW منتقل می‌شود (یا بلافاصله پس‌از CreateAndroidPackageKey اگر کلید قبلاً در نام بسته دیگری تحت همان DeveloperAccount درستی‌سنجی شده باشد).

Enum: AndroidPackageRegistrationPolicy.KeySelectionStrategy

مقدار شرح
SELECT_KEY_FROM_LIST تماس‌گیرنده باید یکی از کلیدهای تاریخی فهرست‌شده در knownKeys را ثبت کند.
USE_ANY_KEY علاوه‌بر کلیدهای موجود در knownKeys، فراخواننده می‌تواند هر کلید امضای برنامه معتبری را که قبلاً در بوم‌سازگان Android مشاهده نشده است ثبت کند.

روش‌ها: AndroidPackage

روش درخواست HTTP شرح
GetAndroidPackageRegistrationPolicy GET /v1/{name=developerAccounts/*/androidPackages/*/registrationPolicy} استراتژی انتخاب کلید و کلیدهای امضای تاریخی شناخته‌شده را برای نام بسته بازیابی می‌کند.
CreateAndroidPackage POST /v1/{parent=developerAccounts/*}/androidPackages?androidPackageId={package_name} منبع AndroidPackage جدیدی در وضعیت DRAFT ایجاد می‌کند تا ثبت نام بسته را شروع کند.
GetAndroidPackage GET /v1/{name=developerAccounts/*/androidPackages/*} جزئیات و وضعیت ثبت‌نام فعلی را برای AndroidPackage موجود بازیابی می‌کند.
ListAndroidPackages GET /v1/{parent=developerAccounts/*}/androidPackages اشیاء AndroidPackage را تحت DeveloperAccount فهرست می‌کند (pageSize حداکثر 1000، pageToken).

منبع: AndroidPackageKey

نشان‌دهنده اثر انگشت گواهی امضای برنامه عمومی منسوب به AndroidPackage است و وضعیت بازبینی ثبت و درستی‌سنجی مالکیت را ردیابی می‌کند.

فیلد نوع شرح
name string شناسه. نام منبع اختصاص‌داده‌شده توسط سرور در قالب developerAccounts/{developer_account}/androidPackages/{android_package}/keys/{key}، که در آن {key} اثر انگشت SHA-256 شانزده‌شانزدهی با حروف کوچک ۶۴ نویسه‌ای نرمال‌شده بدون دونقطه است. هنگام تماس با CreateAndroidPackageKey باید حذف یا خالی باشد.
certificateFingerprintSha256 string الزامی. تغییرناپذیر. درهم‌سازی SHA-256 گواهی امضای برنامه. در ورودی در CreateAndroidPackageKey، کد مبنای ۱۶ ساده ۶۴ نویسه‌ای (60e860e8...) یا کد مبنای ۱۶ جداشده با دونقطه (60:E8:60:E8:...) را می‌پذیرد. در خروجی، همیشه به کد مبنای ۱۶ حروف کوچک ۶۴ نویسه‌ای بدون دونقطه نرمال‌سازی می‌شود.
state enum (AndroidPackageKey.State) فقط خروجی. وضعیت چرخه حیات فعلی درستی‌سنجی و ثبت کلید.
verificationToken string فقط خروجی. کد چالش یکتایی که Google تولید کرده است. فقط زمانی استفاده می‌شود که وضعیت DRAFT باشد (وقتی CreateAndroidPackageKey کلید را مستقیماً به IN_REVIEW منتقل می‌کند، می‌توان آن را نادیده گرفت). وقتی وضعیت DRAFT است، این رشته را در assets/adi-registration.properties در APK امضاشده جاسازی کنید تا VerifyAndroidPackageKeyOwnership تکمیل شود.
registrationJustificationRequired boolean فقط خروجی. اگر true و کلید در وضعیت OWNERSHIP_VERIFIED باشد، باید قبل‌از اینکه ثبت به IN_REVIEW ادامه یابد، توجیه کتبی بااستفاده از JustifyAndroidPackageKeyRegistration ارسال کنید. اگر CreateAndroidPackageKey کلید را مستقیماً به IN_REVIEW منتقل کند (چون کلید قبلاً در نام بسته دیگری در همان DeveloperAccount تأیید شده است)، توجیه رد می‌شود.

Enum: AndroidPackageKey.State

مقدار شرح
DRAFT منبع کلید ایجاد شده است و هنوز اثبات مالکیت کلید خصوصی بااستفاده از بارگذاری APK امضاشده (VerifyAndroidPackageKeyOwnership) لازم است زیرا مالکیت این کلید هنوز در هیچ نام بسته‌ای تحت این DeveloperAccount درستی‌سنجی نشده است.
OWNERSHIP_VERIFIED مالکیت کلید خصوصی بااستفاده از بارگذاری APK امضاشده درستی‌سنجی شده است. اگر registrationJustificationRequired true باشد، همچنان قبل‌از شروع بازبینی به توجیه نیاز است.
IN_REVIEW ثبت کلید دردست بررسی Google است. کلید در اینجا یا بلافاصله پس‌از CreateAndroidPackageKey (وقتی اثبات مالکیت لازم نباشد، مثلاً در نام بسته جدیدی که قبلاً هرگز در Android دیده نشده است، یا وقتی کلید قبلاً در نام بسته دیگری تحت همان DeveloperAccount درستی‌سنجی شده باشد، که در این صورت JustifyAndroidPackageKeyRegistration نیز نادیده گرفته می‌شود)، مستقیماً پس‌از VerifyAndroidPackageKeyOwnership (اگر registrationJustificationRequired false باشد)، یا پس‌از JustifyAndroidPackageKeyRegistration (اگر registrationJustificationRequired true باشد) منتقل می‌شود.
REGISTERED کلید امضای برنامه به‌طور فعال برای این نام بسته برای درستی‌سنجی توسعه‌دهنده نرم‌افزار Android ثبت شده است.
PENDING_TRANSFER ثبت کلید امضای برنامه درانتظار تکمیل انتقال است.

روش‌ها: AndroidPackageKey

روش درخواست HTTP شرح
CreateAndroidPackageKey POST /v1/{parent=developerAccounts/*/androidPackages/*}/keys اثر انگشت SHA-256 گواهینامه امضای برنامه جدیدی را تحت AndroidPackage ثبت می‌کند. کلید را در حالت DRAFT (زمانی که اثبات مالکیت بااستفاده از VerifyAndroidPackageKeyOwnership لازم است) یا مستقیماً در حالت IN_REVIEW (زمانی که درستی‌سنجی مالکیت نادیده گرفته می‌شود، مثلاً برای نام بسته جدیدی که هرگز در Android دیده نشده است یا کلیدی که قبلاً در نام بسته دیگری در همان DeveloperAccount درستی‌سنجی شده است) برمی‌گرداند.
GetAndroidPackageKey GET /v1/{name=developerAccounts/*/androidPackages/*/keys/*} وضعیت، اثر انگشت، و فراداده درستی‌سنجی AndroidPackageKey خاصی را بازیابی می‌کند.
ListAndroidPackageKeys GET /v1/{parent=developerAccounts/*/androidPackages/*}/keys همه اشیای AndroidPackageKey ثبت‌شده تحت AndroidPackage را فهرست می‌کند (pageSize حداکثر 1000، pageToken).
VerifyAndroidPackageKeyOwnership POST /upload/v1/{name=developerAccounts/*/androidPackages/*/keys/*}:verify یک APK حداقلی امضاشده حاوی verificationToken در assets/adi-registration.properties بارگذاری می‌کند تا مالکیت کلید خصوصی را درستی‌سنجی کند و کلیدهای آماده را برای بازبینی ارسال کند.
JustifyAndroidPackageKeyRegistration POST /v1/{name=developerAccounts/*/androidPackages/*/keys/*}:justifyAndroidPackageKeyRegistration وقتی registrationJustificationRequired برابر با true باشد، زمینه توجیهی اضافی ارسال می‌کند و کلیدهای درستی‌سنجی‌شده را برای بازبینی ارسال می‌کند.

مدیریت کردن خطا

وقتی درخواست API ناموفق باشد، Android Developer Console API رمز وضعیت HTTP 4xx یا 5xx و بدنه خطای JSON استاندارد google.rpc.Status را برمی‌گرداند:

{
  "error": {
    "code": 400,
    "message": "Invalid certificate fingerprint SHA256 format.",
    "status": "INVALID_ARGUMENT",
    "details": []
  }
}

رمزهای وضعیت HTTP و راه‌حل‌های رایج

کد HTTP وضعیت gRPC دلایل متداول برطرف کردن مشکل
400 Bad Request INVALID_ARGUMENT ‫androidPackageId به‌سبک Java وجود ندارد یا نامعتبر است؛ قالب certificateFingerprintSha256 نامعتبر است؛ فیلد name در CreateAndroidPackage یا CreateAndroidPackageKey خالی نیست؛ APK بارگذاری‌شده امضا نشده است، خراب است، assets/adi-registration.properties ندارد، verificationToken منطبق ندارد، یا با گواهینامه نامنطبق امضا شده است. قالب‌های درخواست را دربرابر طرح‌واره‌های منبع اعتبارسنجی کنید، name را در تماس‌های ایجاد حذف یا خالی کنید، و امضای APK و کد جاسازی‌شده را بااستفاده از apksigner verify --print-certs و unzip -p app-release.apk assets/adi-registration.properties قبل‌از بارگذاری تأیید کنید.
400 Bad Request FAILED_PRECONDITION DeveloperAccount دارای verificationState: NOT_VERIFIED است؛ انتخاب کلید AndroidPackageRegistrationPolicy (SELECT_KEY_FROM_LIST) را نقض می‌کند؛ تماس با VerifyAndroidPackageKeyOwnership یا JustifyAndroidPackageKeyRegistration در وضعیت غیرواجدشرایط. درستی‌سنجی هویت توسعه‌دهنده را در Android Developer Console تکمیل کنید، ابتدا GetAndroidPackageRegistrationPolicy را بررسی کنید، و state فعلی منبع را بازرسی کنید.
401 Unauthorized UNAUTHENTICATED کد دسترسی OAuth 2.0 Bearer وجود ندارد، منقضی شده، یا نامعتبر است، یا تلاش برای اصالت‌سنجی بااستفاده از کلید میانای برنامه‌سازی کاربردی یا حساب سرویس. کد دسترسی OAuth 2.0 Bearer جدیدی با دامنه https://www.googleapis.com/auth/androiddeveloperconsole که به کاربر واگذار شده است دریافت کنید.
403 Forbidden PERMISSION_DENIED کاربر اصالت‌سنجی‌شده اجازه لازم را در DeveloperAccount یا AndroidPackage هدف ندارد، یا Android Developer Console API در پروژه Google Cloud فعال نیست. عضویت حساب را بااستفاده از ListDeveloperAccounts درستی‌سنجی کنید و مطمئن شوید androiddeveloperconsole.googleapis.com در «کنسول Google Cloud» فعال باشد.
404 Not Found NOT_FOUND مسیر منبع DeveloperAccount، AndroidPackage، یا AndroidPackageKey مشخص‌شده وجود ندارد. مسیرهای منبع را بااستفاده از ListDeveloperAccounts، ListAndroidPackages، یا ListAndroidPackageKeys تأیید کنید. مطمئن شوید شناسه‌های {key} از هگزادسیمال حروف کوچک بدون دونقطه استفاده می‌کنند.
409 Conflict ALREADY_EXISTS نام بسته یا اثر انگشت گواهینامه SHA-256 قبلاً تحت این حساب توسعه‌دهنده یا حساب توسعه‌دهنده دیگری ثبت شده است. ثبت‌های موجود را بااستفاده از GetAndroidPackage یا GetAndroidPackageKey بازرسی کنید، یا مالکیت تاریخی را بااستفاده از GetAndroidPackageRegistrationPolicy بررسی کنید.
429 Too Many Requests RESOURCE_EXHAUSTED از سهمیه هر روش که 2,000 درخواست در روز برای هر پروژه Google Cloud است فراتر رفته‌اید. عقب‌نشینی نمایی را با لرزش اجرا کنید و از حلقه‌های نظرسنجی با فرکانس بالا اجتناب کنید.
500 / 503 INTERNAL / UNAVAILABLE خطای گذرا در پس‌زمینه یا عدم دسترسی موقت به سرویس. درخواست‌های یکسان‌توان را با عقب‌گرد نمایی کوتاه امتحان مجدد کنید.

نمونه‌های درخواست و پاسخ اچ‌تی‌تی‌پی

مقادیر جای‌بان مثل ACCESS_TOKEN، 1234567890، com.example.myapp، و 60e860e8... را با مقادیر خودتان جایگزین کنید.

۱. GetDeveloperAccount

curl -X GET \
  -H "Authorization: Bearer ACCESS_TOKEN" \
  "https://androiddeveloperconsole.googleapis.com/v1/developerAccounts/1234567890"

پاسخ:

{
  "name": "developerAccounts/1234567890",
  "displayName": "Example Developer",
  "verificationState": "VERIFIED"
}

۲. ListDeveloperAccounts

curl -X GET \
  -H "Authorization: Bearer ACCESS_TOKEN" \
  "https://androiddeveloperconsole.googleapis.com/v1/developerAccounts"

پاسخ:

{
  "developerAccounts": [
    {
      "name": "developerAccounts/1234567890",
      "displayName": "Example Developer",
      "verificationState": "VERIFIED"
    }
  ]
}

۳. GetAndroidPackageRegistrationPolicy

curl -X GET \
  -H "Authorization: Bearer ACCESS_TOKEN" \
  "https://androiddeveloperconsole.googleapis.com/v1/developerAccounts/1234567890/androidPackages/com.example.myapp/registrationPolicy"

پاسخ:

{
  "name": "developerAccounts/1234567890/androidPackages/com.example.myapp/registrationPolicy",
  "knownKeys": [
    {
      "certificateFingerprintSha256": "60e860e8d77251234567890abcdef1234567890abcdef1234567890abcdef123",
      "justificationRequirement": "NOT_REQUIRED"
    }
  ],
  "keySelectionStrategy": "SELECT_KEY_FROM_LIST"
}

۴. CreateAndroidPackage

curl -X POST \
  -H "Authorization: Bearer ACCESS_TOKEN" \
  -H "Content-Type: application/json; charset=utf-8" \
  -d '{"name": ""}' \
  "https://androiddeveloperconsole.googleapis.com/v1/developerAccounts/1234567890/androidPackages?androidPackageId=com.example.myapp"

پاسخ:

{
  "name": "developerAccounts/1234567890/androidPackages/com.example.myapp",
  "packageName": "com.example.myapp",
  "state": "DRAFT",
  "registeredAppStore": false
}

۵. GetAndroidPackage

curl -X GET \
  -H "Authorization: Bearer ACCESS_TOKEN" \
  "https://androiddeveloperconsole.googleapis.com/v1/developerAccounts/1234567890/androidPackages/com.example.myapp"

پاسخ:

{
  "name": "developerAccounts/1234567890/androidPackages/com.example.myapp",
  "packageName": "com.example.myapp",
  "state": "REGISTERED",
  "registeredAppStore": false
}

۶. ListAndroidPackages

curl -X GET \
  -H "Authorization: Bearer ACCESS_TOKEN" \
  "https://androiddeveloperconsole.googleapis.com/v1/developerAccounts/1234567890/androidPackages?pageSize=100"

پاسخ:

{
  "androidPackages": [
    {
      "name": "developerAccounts/1234567890/androidPackages/com.example.myapp",
      "packageName": "com.example.myapp",
      "state": "REGISTERED",
      "registeredAppStore": false
    }
  ],
  "nextPageToken": ""
}

‫۷. CreateAndroidPackageKey

curl -X POST \
  -H "Authorization: Bearer ACCESS_TOKEN" \
  -H "Content-Type: application/json; charset=utf-8" \
  -d '{
    "certificateFingerprintSha256": "60e860e8d77251234567890abcdef1234567890abcdef1234567890abcdef123"
  }' \
  "https://androiddeveloperconsole.googleapis.com/v1/developerAccounts/1234567890/androidPackages/com.example.myapp/keys"

پاسخ:

{
  "name": "developerAccounts/1234567890/androidPackages/com.example.myapp/keys/60e860e8d77251234567890abcdef1234567890abcdef1234567890abcdef123",
  "certificateFingerprintSha256": "60e860e8d77251234567890abcdef1234567890abcdef1234567890abcdef123",
  "state": "DRAFT",
  "verificationToken": "token_xyz987654321"
}

‫۸. GetAndroidPackageKey

curl -X GET \
  -H "Authorization: Bearer ACCESS_TOKEN" \
  "https://androiddeveloperconsole.googleapis.com/v1/developerAccounts/1234567890/androidPackages/com.example.myapp/keys/60e860e8d77251234567890abcdef1234567890abcdef1234567890abcdef123"

پاسخ:

{
  "name": "developerAccounts/1234567890/androidPackages/com.example.myapp/keys/60e860e8d77251234567890abcdef1234567890abcdef1234567890abcdef123",
  "certificateFingerprintSha256": "60e860e8d77251234567890abcdef1234567890abcdef1234567890abcdef123",
  "state": "REGISTERED"
}

‫۹. ListAndroidPackageKeys

curl -X GET \
  -H "Authorization: Bearer ACCESS_TOKEN" \
  "https://androiddeveloperconsole.googleapis.com/v1/developerAccounts/1234567890/androidPackages/com.example.myapp/keys?pageSize=100"

پاسخ:

{
  "androidPackageKeys": [
    {
      "name": "developerAccounts/1234567890/androidPackages/com.example.myapp/keys/60e860e8d77251234567890abcdef1234567890abcdef1234567890abcdef123",
      "certificateFingerprintSha256": "60e860e8d77251234567890abcdef1234567890abcdef1234567890abcdef123",
      "state": "REGISTERED"
    }
  ],
  "nextPageToken": ""
}

‫۱۰. VerifyAndroidPackageKeyOwnership

گزینه الف: بارگذاری رسانه با درخواست واحد

curl -X POST \
  -H "Authorization: Bearer ACCESS_TOKEN" \
  -H "Content-Type: application/octet-stream" \
  --data-binary @app-release.apk \
  "https://androiddeveloperconsole.googleapis.com/upload/v1/developerAccounts/1234567890/androidPackages/com.example.myapp/keys/60e860e8d77251234567890abcdef1234567890abcdef1234567890abcdef123:verify?uploadType=media"

گزینه ب: پروتکل بارگذاری ازسرگرفتنی (برای فایل‌های APK بزرگ یا CI/CD توصیه می‌شود)

مرحله ۱: جلسه بارگذاری ازسرگرفتنی را شروع کنید و سرصفحه X-Goog-Upload-URL برگردانده‌شده را استخراج کنید:

curl -i -X POST \
  "https://androiddeveloperconsole.googleapis.com/upload/v1/developerAccounts/1234567890/androidPackages/com.example.myapp/keys/60e860e8d77251234567890abcdef1234567890abcdef1234567890abcdef123:verify" \
  -H "Authorization: Bearer ACCESS_TOKEN" \
  -H "X-Goog-Upload-Protocol: resumable" \
  -H "X-Goog-Upload-Command: start" \
  -H "X-Goog-Upload-Header-Content-Length: FILE_SIZE_IN_BYTES" \
  -H "X-Goog-Upload-Header-Content-Type: application/vnd.android.package-archive" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "developerAccounts/1234567890/androidPackages/com.example.myapp/keys/60e860e8d77251234567890abcdef1234567890abcdef1234567890abcdef123"
  }'

مرحله ۲: فایل دودویی APK امضاشده را در UPLOAD_SESSION_URI بارگذاری کنید و جلسه را نهایی کنید:

curl -X PUT \
  "UPLOAD_SESSION_URI" \
  -H "Content-Length: FILE_SIZE_IN_BYTES" \
  -H "X-Goog-Upload-Offset: 0" \
  -H "X-Goog-Upload-Command: upload, finalize" \
  --data-binary "@app-release.apk"

پاسخ:

{
  "name": "developerAccounts/1234567890/androidPackages/com.example.myapp/keys/60e860e8d77251234567890abcdef1234567890abcdef1234567890abcdef123",
  "certificateFingerprintSha256": "60e860e8d77251234567890abcdef1234567890abcdef1234567890abcdef123",
  "state": "IN_REVIEW"
}

‫۱۱. JustifyAndroidPackageKeyRegistration

curl -X POST \
  -H "Authorization: Bearer ACCESS_TOKEN" \
  -H "Content-Type: application/json; charset=utf-8" \
  -d '{
    "justification": "We previously distributed com.example.myapp directly from https://downloads.example.com and are migrating to our rotated production key."
  }' \
  "https://androiddeveloperconsole.googleapis.com/v1/developerAccounts/1234567890/androidPackages/com.example.myapp/keys/60e860e8d77251234567890abcdef1234567890abcdef1234567890abcdef123:justifyAndroidPackageKeyRegistration"

پاسخ:

{
  "name": "developerAccounts/1234567890/androidPackages/com.example.myapp/keys/60e860e8d77251234567890abcdef1234567890abcdef1234567890abcdef123",
  "certificateFingerprintSha256": "60e860e8d77251234567890abcdef1234567890abcdef1234567890abcdef123",
  "state": "IN_REVIEW",
  "registrationJustificationRequired": true
}

منابع بیشتر