Android Developer Console API

Android Developer Console API는 인증된 개발자가 Android Developer Console에서 Android 개발자 인증 워크플로를 자동화할 수 있는 RESTful 서비스입니다. 여기에는 개발자 계정 검색, 주요 자격 요건 확인, Android 패키지 이름 등록, 앱 서명 키 등록, 키 소유권 확인이 포함됩니다.

개요, 사용 사례, 구현 컨텍스트

주요 사용 사례 및 기능

  • 자동화된 CI/CD 패키지 이름 등록: 수십 또는 수백 개의 Android 패키지 이름을 프로그래매틱 방식으로 등록합니다 (CreateAndroidPackage).
  • 사전 기록 키 정책 검사: Google이 이전에 생태계에서 패키지 이름을 관찰했는지, 특정 서명 인증서를 등록하려면 키 소유권 확인 (GetAndroidPackageRegistrationPolicy)이 필요한지 프로그래매틱 방식으로 검사합니다.
  • 자동화된 앱 서명 키 등록 및 소유권 확인: 공개 서명 인증서 SHA-256 디지털 지문(CreateAndroidPackageKey)을 등록하고, 고유한 확인 질문 토큰(verificationToken)을 가져오고, 단일 요청 또는 재개 가능한 서명된 APK 업로드(VerifyAndroidPackageKeyOwnership)를 사용하여 비공개 키 소유 증명을 자동화합니다.
  • 프로그래매틱 근거 제출: 소유권 근거를 제출합니다(JustifyAndroidPackageKeyRegistration).
  • 상태 모니터링: 개발자 계정, 패키지 이름, 앱 서명 키 (GetDeveloperAccount, ListDeveloperAccounts, GetAndroidPackage, ListAndroidPackages, GetAndroidPackageKey, ListAndroidPackageKeys) 전반에서 등록 상태를 모니터링합니다.

엔드 투 엔드 구현 워크플로

  1. UI에서 개발자 신원 한 번 인증: Android Developer Console에서 개발자 신원 인증 (INDIVIDUAL 또는 ORGANIZATION)을 완료하여 verificationState가 VERIFIED가 되도록 합니다.
  2. API 사용 설정 및 인증: Google Cloud 프로젝트에서 androiddeveloperconsole.googleapis.com를 사용 설정하고 https://www.googleapis.com/auth/androiddeveloperconsole 범위의 사용자 위임 OAuth 2.0 Bearer 액세스 토큰을 가져옵니다.
  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: 비공개 키 소유권 증명이 필요하며 응답에는 7단계의 고유한 verificationToken가 포함됩니다.
    • IN_REVIEW: 소유권 증빙 및 근거가 자동으로 건너뛰어집니다 (예: Android에서 한 번도 사용된 적이 없는 새 패키지 이름을 등록하는 경우 또는 동일한 DeveloperAccount에서 다른 패키지 이름에 대해 이 서명 키의 소유권을 이미 인증한 경우). 7단계와 8단계의 근거 호출을 건너뛰고 GetAndroidPackage 및 GetAndroidPackageKey 폴링으로 바로 진행합니다.
  7. 확인 APK 빌드 및 업로드 (상태가 DRAFT인 경우): 반환된 verificationToken 문자열을 packageName과 일치하는 최소 APK 내의 assets/adi-registration.properties에 삽입하고 비공개 앱 서명 키로 서명한 후 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)를 호출합니다. state가 REGISTERED에 도달할 때까지 GetAndroidPackage 및 GetAndroidPackageKey를 폴링합니다.

키 지문 및 인증 APK를 준비하기 위한 로컬 CLI 명령어

  • 키 저장소에서 SHA-256 인증서 지문 추출 (keytool):

    keytool -list -v -keystore release-key.jks -alias my-key-alias
  • 빌드된 APK (apksigner)에서 SHA-256 서명 인증서 다이제스트 확인:

    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 UI 및 API 기능

작업 Android Developer Console 웹 UI (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) 콘솔 UI에서 서명된 스니펫 APK 업로드 POST /upload/v1/{name}:verify(VerifyAndroidPackageKeyOwnership)
키에 수동 검토가 필요한 경우 근거 제출 키 등록 워크플로 중 텍스트 프롬프트 POST /v1/{name}:justifyAndroidPackageKeyRegistration(JustifyAndroidPackageKeyRegistration)

서비스 구성 및 인증

모든 API 요청은 HTTPS를 사용해야 하며 Android Developer Console에서 개발자 본인 인증을 완료한 Google 계정의 OAuth 2.0 웹 서버 흐름을 사용하여 가져온 Authorization: Bearer ACCESS_TOKEN 헤더를 포함해야 합니다.

속성 값
기본 REST 엔드포인트 https://androiddeveloperconsole.googleapis.com
미디어 업로드 엔드포인트 https://androiddeveloperconsole.googleapis.com/upload
API 버전 v1
필수 OAuth 2.0 범위 https://www.googleapis.com/auth/androiddeveloperconsole
기본 할당량 한도 Google Cloud 프로젝트별 메서드당 일일 요청 2,000개

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

개발자 ID와 연결된 Android Developer Console의 계정을 나타냅니다.

필드 유형 설명
name string 식별자. developerAccounts/{developer_account} 형식의 리소스 이름입니다.
displayName string 출력 전용입니다. 개발자 계정과 연결된, 사람이 읽을 수 있는 이름 (개인 이름 또는 조직 이름)입니다.
verificationState enum (VerificationState) 출력 전용입니다. 계정의 현재 개발자 본인 인증 상태입니다.

Enum: DeveloperAccount.VerificationState

값 설명
VERIFIED Developer 본인 인증이 완료되었습니다. 계정에서 패키지 이름과 앱 서명 키를 등록할 수 있습니다.
NOT_VERIFIED Android Developer Console에서 개발자 본인 인증이 완료되지 않았습니다.

메서드: DeveloperAccount

메서드 HTTP 요청 설명
GetDeveloperAccount GET /v1/{name=developerAccounts/*} 단일 DeveloperAccount의 메타데이터 및 인증 상태를 가져옵니다.
ListDeveloperAccounts GET /v1/developerAccounts 인증된 Google 계정에서 액세스할 수 있는 모든 DeveloperAccount 객체를 나열합니다 (페이지로 나누지 않음).

리소스: AndroidPackage

DeveloperAccount에 등록되었거나 등록 중인 Android 패키지 이름을 나타냅니다.

필드 유형 설명
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에서 검토 중입니다. 패키지는 CreateAndroidPackageKey 직후 (키 소유권 확인을 건너뛰는 경우, 동일한 DeveloperAccount의 다른 패키지 이름에 대해 키가 이미 확인된 경우 포함) 또는 VerifyAndroidPackageKeyOwnership 및 필요한 경우 JustifyAndroidPackageKeyRegistration를 완료한 후 DRAFT에서 IN_REVIEW로 전환됩니다.
REGISTERED 패키지 이름이 Android 개발자 인증을 위해 이 개발자 계정에 활성 상태로 등록되어 있습니다.
PENDING_TRANSFER 패키지 이름이 다른 개발자 계정으로의 소유권 이전 완료를 기다리고 있습니다.

리소스: AndroidPackageRegistrationPolicy

패키지 이름에 대해 감지된 이전 공개 서명 키와 지정된 서명 키로 패키지 이름을 등록하는 데 서면 근거가 필요한지 여부를 설명하는 GetAndroidPackageRegistrationPolicy에서 반환하는 싱글톤 리소스입니다.

필드 유형 설명
name string 식별자. developerAccounts/{developer_account}/androidPackages/{android_package}/registrationPolicy 형식의 리소스 이름입니다.
knownKeys[] object (KnownKey) 이 패키지 이름으로 앱을 배포하는 것으로 이전에 확인된 이전 앱 서명 키 목록으로, certificateFingerprintSha256를 기준으로 사전순으로 정렬됩니다.
knownKeys[].certificateFingerprintSha256 string 출력 전용입니다. 이전 서명 인증서의 정규화된 64자 소문자 16진수 SHA-256 디지털 지문입니다 (콜론 없음).
knownKeys[].justificationRequirement enum (JustificationRequirement) 출력 전용입니다. 이 키를 등록하려면 JustifyAndroidPackageKeyRegistration (REQUIRED 또는 NOT_REQUIRED)를 호출해야 하는지 나타냅니다. 서명 키가 이전에 동일한 DeveloperAccount의 다른 패키지 이름에서 확인된 경우 justificationRequirement가 REQUIRED인 경우에도 VerifyAndroidPackageKeyOwnership와 JustifyAndroidPackageKeyRegistration가 모두 건너뛰어집니다.
keySelectionStrategy enum (KeySelectionStrategy) 출력 전용입니다. 이 패키지 이름을 등록하기 위한 키 선택 정책: SELECT_KEY_FROM_LIST (knownKeys의 키를 등록해야 함) 또는 USE_ANY_KEY (개발자가 소유한 유효한 앱 서명 키를 등록할 수 있음)

enum: KnownKey.JustificationRequirement

값 설명
REQUIRED 이 알려진 키를 등록하려면 VerifyAndroidPackageKeyOwnership를 완료한 후 JustifyAndroidPackageKeyRegistration를 사용하여 서면 근거를 제출해야 합니다 (키가 동일한 DeveloperAccount의 다른 패키지 이름에서 이전에 확인된 경우는 제외되며, 이 경우 VerifyAndroidPackageKeyOwnership 및 JustifyAndroidPackageKeyRegistration가 모두 건너뛰어짐).
NOT_REQUIRED 이 알려진 키를 등록하는 데는 사유가 필요하지 않습니다. 키는 VerifyAndroidPackageKeyOwnership 후에 (또는 키가 이전에 동일한 DeveloperAccount의 다른 패키지 이름에서 확인된 경우 CreateAndroidPackageKey 직후에) IN_REVIEW로 직접 전환됩니다.

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} DRAFT 상태에서 새 AndroidPackage 리소스를 만들어 패키지 이름 등록을 시작합니다.
GetAndroidPackage GET /v1/{name=developerAccounts/*/androidPackages/*} 기존 AndroidPackage의 세부정보와 현재 등록 상태를 가져옵니다.
ListAndroidPackages GET /v1/{parent=developerAccounts/*}/androidPackages DeveloperAccount 아래에 있는 AndroidPackage 객체를 나열합니다 (pageSize 최대 1000, pageToken).

리소스: AndroidPackageKey

AndroidPackage와 연결된 공개 앱 서명 인증서 지문을 나타내고 소유권 확인 및 등록 검토 상태를 추적합니다.

필드 유형 설명
name string 식별자. developerAccounts/{developer_account}/androidPackages/{android_package}/keys/{key} 형식의 서버 할당 리소스 이름입니다. 여기서 {key}은 콜론이 없는 정규화된 64자 소문자 16진수 SHA-256 지문입니다. CreateAndroidPackageKey를 호출할 때 생략하거나 비워 두어야 합니다.
certificateFingerprintSha256 string 필수 항목입니다. 변경할 수 없습니다. 앱 서명 인증서의 SHA-256 해시입니다. CreateAndroidPackageKey의 입력에서 일반 64자 16진수 (60e860e8...) 또는 콜론으로 구분된 16진수 (60:E8:60:E8:...)를 허용합니다. 출력에서는 항상 콜론이 없는 64자 소문자 16진수로 정규화됩니다.
state enum (AndroidPackageKey.State) 출력 전용입니다. 키의 현재 확인 및 등록 수명 주기 상태입니다.
verificationToken string 출력 전용입니다. Google에서 생성한 고유한 챌린지 토큰입니다. 상태가 DRAFT인 경우에만 사용됩니다 (CreateAndroidPackageKey에서 키를 IN_REVIEW로 직접 전환하는 경우 무시할 수 있음). 상태가 DRAFT인 경우 서명된 APK의 assets/adi-registration.properties 내에 이 문자열을 삽입하여 VerifyAndroidPackageKeyOwnership를 완료합니다.
registrationJustificationRequired boolean 출력 전용입니다. true이고 키가 OWNERSHIP_VERIFIED 상태인 경우 등록이 IN_REVIEW로 진행되기 전에 JustifyAndroidPackageKeyRegistration를 사용하여 서면 근거를 제출해야 합니다. CreateAndroidPackageKey가 키를 IN_REVIEW로 직접 전환하는 경우 (키가 이전에 동일한 DeveloperAccount의 다른 패키지 이름에서 확인되었기 때문) 근거가 건너뛰어집니다.

Enum: AndroidPackageKey.State

값 설명
DRAFT 키 리소스가 생성되었으며, 이 DeveloperAccount의 패키지 이름에서 이 키의 소유권이 아직 확인되지 않았으므로 서명된 APK 업로드 (VerifyAndroidPackageKeyOwnership)를 사용한 비공개 키 소유 증명이 여전히 필요합니다.
OWNERSHIP_VERIFIED 서명된 APK 업로드를 사용하여 비공개 키 소유권이 확인되었습니다. registrationJustificationRequired가 true인 경우 검토가 시작되기 전에 사유가 필요합니다.
IN_REVIEW Google에서 키 등록을 검토 중입니다. 소유권 증명이 필요하지 않은 경우 (예: Android에서 사용된 적이 없는 새 패키지 이름 또는 동일한 DeveloperAccount의 다른 패키지 이름에서 이전에 키가 확인된 경우, 이 경우 JustifyAndroidPackageKeyRegistration도 건너뜀) CreateAndroidPackageKey 직후에, VerifyAndroidPackageKeyOwnership 직후에 (registrationJustificationRequired가 false인 경우) 또는 JustifyAndroidPackageKeyRegistration 후에 (registrationJustificationRequired가 true인 경우) 키가 여기로 전환됩니다.
REGISTERED 앱 서명 키가 Android 개발자 인증을 위해 이 패키지 이름에 활성 상태로 등록되어 있습니다.
PENDING_TRANSFER 앱 서명 키 등록이 이전 완료를 기다리고 있습니다.

메서드: AndroidPackageKey

메서드 HTTP 요청 설명
CreateAndroidPackageKey POST /v1/{parent=developerAccounts/*/androidPackages/*}/keys AndroidPackage 아래에 새 앱 서명 인증서 SHA-256 지문을 등록합니다. DRAFT 상태 (VerifyAndroidPackageKeyOwnership를 사용한 소유권 증명이 필요한 경우) 또는 IN_REVIEW 상태 (Android에서 사용된 적이 없는 새 패키지 이름이나 동일한 DeveloperAccount의 다른 패키지 이름에서 이미 확인된 키와 같이 소유권 확인을 건너뛰는 경우)로 키를 반환합니다.
GetAndroidPackageKey GET /v1/{name=developerAccounts/*/androidPackages/*/keys/*} 특정 AndroidPackageKey의 상태, 디지털 지문, 확인 메타데이터를 가져옵니다.
ListAndroidPackageKeys GET /v1/{parent=developerAccounts/*/androidPackages/*}/keys AndroidPackage (pageSize 최대 1000, pageToken)에 등록된 모든 AndroidPackageKey 객체를 나열합니다.
VerifyAndroidPackageKeyOwnership POST /upload/v1/{name=developerAccounts/*/androidPackages/*/keys/*}:verify assets/adi-registration.properties에 verificationToken이 포함된 서명된 최소 APK를 업로드하여 비공개 키 소유권을 확인하고 검토를 위해 준비된 키를 제출합니다.
JustifyAndroidPackageKeyRegistration POST /v1/{name=developerAccounts/*/androidPackages/*/keys/*}:justifyAndroidPackageKeyRegistration registrationJustificationRequired가 true인 경우 추가 근거 컨텍스트를 제출하고 검토를 위해 확인된 키를 제출합니다.

오류 처리

API 요청이 실패하면 Android Developer Console API는 HTTP 4xx 또는 5xx 상태 코드와 표준 google.rpc.Status JSON 오류 본문을 반환합니다.

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

HTTP 상태 코드 및 일반적인 해결 방법

HTTP 코드 gRPC 상태 일반적인 원인 해상도
400 Bad Request INVALID_ARGUMENT Java 스타일 androidPackageId가 누락되었거나 잘못되었습니다. certificateFingerprintSha256 형식이 잘못되었습니다. CreateAndroidPackage 또는 CreateAndroidPackageKey의 name 필드가 비어 있지 않습니다. 업로드된 APK가 서명되지 않았거나, 손상되었거나, assets/adi-registration.properties가 누락되었거나, 일치하는 verificationToken가 누락되었거나, 일치하지 않는 인증서로 서명되었습니다. 리소스 스키마를 기준으로 요청 형식을 검증하고, 생성 호출 시 name를 생략하거나 비워 두고, 업로드하기 전에 apksigner verify --print-certs 및 unzip -p app-release.apk assets/adi-registration.properties를 사용하여 APK 서명과 삽입된 토큰을 확인합니다.
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 액세스 토큰이 누락되었거나 만료되었거나 잘못되었거나 API 키 또는 서비스 계정을 사용하여 인증을 시도했습니다. 범위가 https://www.googleapis.com/auth/androiddeveloperconsole인 새로운 사용자 위임 OAuth 2.0 Bearer 액세스 토큰을 가져옵니다.
403 Forbidden PERMISSION_DENIED 인증된 사용자에게 대상 DeveloperAccount 또는 AndroidPackage에 대한 권한이 없거나 Google Cloud 프로젝트에서 Android Developer Console API가 사용 설정되어 있지 않습니다. ListDeveloperAccounts를 사용하여 계정 멤버십을 확인하고 Google Cloud 콘솔에서 androiddeveloperconsole.googleapis.com가 사용 설정되어 있는지 확인합니다.
404 Not Found NOT_FOUND 지정된 DeveloperAccount, AndroidPackage 또는 AndroidPackageKey 리소스 경로가 없습니다. ListDeveloperAccounts, ListAndroidPackages 또는 ListAndroidPackageKeys를 사용하여 리소스 경로를 확인합니다. {key} ID는 콜론 없이 소문자 16진수를 사용해야 합니다.
409 Conflict ALREADY_EXISTS 패키지 이름 또는 SHA-256 인증서 지문이 이 개발자 계정 또는 다른 개발자 계정에 이미 등록되어 있습니다. GetAndroidPackage 또는 GetAndroidPackageKey를 사용하여 기존 등록을 검사하거나 GetAndroidPackageRegistrationPolicy를 사용하여 이전 소유권을 확인합니다.
429 Too Many Requests RESOURCE_EXHAUSTED Google Cloud 프로젝트당 일일 요청 2,000개의 메서드별 할당량을 초과했습니다. 지터로 지수 백오프를 구현하고 고주파 폴링 루프를 방지합니다.
500/503 INTERNAL/UNAVAILABLE 일시적인 백엔드 오류 또는 일시적인 서비스 사용 불가 잘린 지수 백오프로 멱등 요청을 재시도합니다.

HTTP 요청 및 응답 예시

ACCESS_TOKEN, 1234567890, com.example.myapp, 60e860e8...와 같은 플레이스홀더 값을 자체 값으로 바꿉니다.

1. GetDeveloperAccount

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

대답:

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

2. ListDeveloperAccounts

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

대답:

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

3. 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"
}

4. 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
}

5. 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
}

6. 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": ""
}

7. 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"
}

8. 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"
}

9. 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": ""
}

10. VerifyAndroidPackageKeyOwnership

옵션 A: 단일 요청 미디어 업로드

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"

옵션 B: 재개 가능한 업로드 프로토콜 (대형 APK 또는 CI/CD에 권장)

1단계: 재개 가능한 업로드 세션을 시작하고 반환된 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"
  }'

2단계: 서명된 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"
}

11. 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
}

추가 리소스