[스타트업/이슈] Google Play 인앱 결제 API | "insufficient permissions" 오류

지난 시간을 통해 만든 서버에서 구글 플레이(Google Play) 인앱 결제 영수증 검증을 위해 백엔드 서버에서 API를 호출하는 과정 중 참 황당한 에러를 마주했다.

서버 로그에 남은 에러 메시지는 다음과 같았다.

error_code: "internal"
error_message: "The current user has insufficient permissions to perform the requested operation."
event_name: "billing.request.failed"

에러 메시지 자체는 명확했다. API를 호출하는 주체에게 권한이 부족하다. 

하지만 이를 해결하기 위해 파고든 원인은 겉보기처럼 단순하지 않았다. 이 글에서 구글 클라우드(GCP)와 플레이 콘솔 간의 권한이 어떻게 얽혀 있는지, 그리고 어떻게 해결했는지 정리해봤다.



1. 첫 번째 시도, 사용자 추가 실패

가장 먼저 'GCP 서비스 계정에 Play Console 접근 권한이 없다'는 것에 집중했다. 백엔드가 배포된 Cloud Run 환경에서 구글 API를 호출하고 있었으므로, 해당 Cloud Run Admin 권한을 가진 IAM 서비스 계정을 Google Play Console에 관리자 권한으로 추가했다.
(사실 GCP에 이미 Play Integrity API를 연결해뒀었어서 될거라고 생각했는데, 이거랑 결제를 검증하는 Android Developer API랑은 또 다른거였다;;)

대부분의 자료에서는 이렇게 하면 된다고 했다.


이제는 당연히 해결될 것이라 믿고 다시 테스트를 진행했다. 하지만 결과는 동일했다. 여전히 insufficient permissions 오류가 발생했다.




2. 문제의 근본 원인: 계정 이전

그러다 찾게 된 한 블로그...

그리고 시스템 로그와 과거 작업 히스토리를 천천히 되짚어 보았다. 생각해보니 구글 결제 프로필 설정 과정에서 있었던 하나의 이벤트를 발견했다.

이번에 사업자 등록을 진행하며 계정 이전을 진행하였다. 이 과정에서 기존에 등록해 두었던 '인앱 상품' 데이터는 새로운 계정으로 무사히 마이그레이션 되었다. 표면적으로는 아무런 문제가 없어 보였다.

하지만 문제는 보이지 않는 '권한'에 있었다. 구글 플레이 콘솔에 새로 추가한 IAM 계정은 콘솔 자체에 대한 권한은 얻었지만, 계정 이전 전에 생성되었던 기존 Legacy Products에 대한 API 접근 권한까지 온전히 상속받지 못한 상태였다.

즉, 데이터(상품)는 이전되었지만, 결제 검증에 필요한 내부적인 리소스 권한 맵핑은 과거의 결제 프로필에 머물러 있거나 단절된 것이다. 새로운 권한을 아무리 부여해도 시스템은 과거의 식별자와 충돌하며 '권한 없음'을 반환하고 있었던 셈이다.




3. 해결: 초기화와 재등록

해결 방법은 위 글에 나온 대로 초기화에 가까운 접근이었다. (앱 이전 정상적으로 해준다며...구글...)

기존에 등록되어 있던 인앱 상품들을 모두 비활성화(또는 삭제)하고, 현재의 올바른 권한이 세팅된 상태에서 상품을 처음부터 새로 등록했다. 새로 등록된 상품은 현재의 결제 프로필과 새롭게 추가된 IAM 계정의 권한 하에 온전하게 생성된다고 한다.

상품을 재등록한 후, 다시 영수증 검증 API를 호출했다.

결과는 성공이었다. internal 에러가 사라지고 정상적인 검증 응답 데이터가 반환되었다.



아, 그리고 '라이센스 계정' 등록을 해줘야 실구매 없이 테스트 결제가 가능하다!
그냥 테스트용 앱이라고 테스트 결제만 된다고 생각했다가 실제로 돈이 빠져나간다




마치며

이번 이슈를 통해 클라우드 인프라와 플랫폼 서비스(BaaS)를 다룰 때 명심해야 할 중요한 교훈을 얻었다.

첫째, 플랫폼 간의 연동(GCP - Play Console)에서 발생하는 권한 문제는 단순히 UI 상의 체크박스를 켜고 끄는 것으로 끝나지 않을 때가 많다. 특히 '계정 이전'이나 '결제 프로필 변경'과 같은 굵직한 메타 데이터의 변화가 있을 때는, 리소스 간의 내부 참조(Reference)가 깨질 수 있음을 항상 염두에 두어야 한다.

둘째, 원인을 알 수 없는 권한 오류가 발생했을 때, 권한을 계속해서 높이는 것(Escalation)은 정답이 아니다. 리소스 자체가 가진 상태(State)와 권한이 부여된 시점(Lifecycle)을 의심해 보아야 한다.

단순한 상품 재등록으로 끝난 문제였지만, 그 이면에 숨겨진 분산 시스템의 권한 동기화 문제를 엿볼 수 있었던 의미 있는 시간이었다.




추천글

[스타트업/기술] Node.js & Google Play 인앱결제 | 결제 시스템 아키텍처 설계 (Part 1)

[스타트업/기술] Node.js & App Store 인앱결제 | 결제 시스템 아키텍처 (Part 2)



hyeon_B

안녕하세요! AI 기술을 이용해 더 나은 세상을 만들어 나가고 싶은 과기원생 Hyeon이라고 합니다. 저는 앞으로 인공지능 시대에는 지식을 '활용'하는 능력이 중요해질 것이라고 생각합니다. 대부분의 일들은 인공지능이 뛰어난 모습을 보이지만, 인공지능은 데이터로 부터 연관관계를 학습하기 때문에 지식들을 새로 통합해서 활용하는 능력이 부족합니다. 인공지능이 뉴턴 전에 만들어졌다면 사과가 떨어지는 이유에 대답하지 못했을 것이고, 아인슈타인 전에 만들어졌다면 중력이 어떻게 생기는지 설명하지 못했을 것입니다. 따라서 앞으로 우리는 '본질'을 탐구하고 그 본질로부터 다른 곳에 적용하며 인공지능을 현명하게 활용해야 할 것입니다. 함께 인공지능 시대를 준비합시다!

댓글 쓰기

다음 이전

POST ADS1

POST ADS 2