import { Injectable } from '@nestjs/common' import { debug, Debugger } from 'debug' import { GoogleInAppSubscription } from './types' import { GoogleClientService } from './google-client.service' const SCOPES = ['https://www.googleapis.com/auth/androidpublisher'] @Injectable() export class GoogleInAppSubscriptionService { private debug: Debugger = debug(`http:${this.constructor.name}`) constructor(readonly googleClient: GoogleClientService) {} get packageName(): string { return globalThis.secret.app_package_ids['default'].google } async get(token: string, planId: string, packageName: string): Promise { let purchaseSubscription: GoogleInAppSubscription = null try { purchaseSubscription = await this.fetch(planId, token, packageName) } catch (err) { const messages = [ 'The subscription purchase is no longer available for query because it has been expired for too long.', 'Invalid Value', 'The purchase token does not match the package name.', 'The purchase token is no longer valid.', ] if (!messages.includes(err.message)) throw err } return purchaseSubscription } private async fetch(subscriptionId: string, token: string, packageName: string = this.packageName): Promise { const client = await this.googleClient.get(SCOPES) const url = this.getURL(packageName, subscriptionId, token) this.debug.extend('request')(JSON.stringify({ url, scopes: SCOPES })) const response = await client.request({ url }) this.debug.extend('response')(JSON.stringify({ url, ...response })) return response?.data } private getURL(packageName: string, subscriptionId: string, token: string): string { return `https://androidpublisher.googleapis.com/androidpublisher/v3/applications/${packageName}/purchases/subscriptions/${subscriptionId}/tokens/${token}` } }