Nhà xuất bản chủ yếu sử dụng tính năng tích hợp phía máy chủ để quản lý độc giả và
các quyền. Chủ yếu, các nhà xuất bản sử dụng UpdateReaderEntitlements
để cập nhật
Bản ghi của Google về quyền sử dụng mã sản phẩm đối với PPID.
Thiết lập Google Cloud
Quá trình định cấu hình tính năng Liên kết gói thuê bao trong Google Cloud bao gồm 2 hoạt động chính:
- Bật API cho một dự án cụ thể
- Tạo tài khoản dịch vụ để truy cập API
Bật Subscription linking API (API Liên kết gói thuê bao)
Để sử dụng tài khoản dịch vụ và quản lý quyền của độc giả, Google Cloud
dự án phải bật cả Subscription linking API (API Liên kết gói thuê bao) và
tài khoản dịch vụ OAuth đã định cấu hình. Để bật Subscription linking API (API Liên kết gói thuê bao) cho một
dự án, hãy điều hướng từ trình đơn -> API và Dịch vụ -> Thư viện và tìm kiếm
Subscription Linking
hoặc truy cập trực tiếp vào trang:
https://console.cloud.google.com/apis/library?project=gcp_project_id
Hình 1. Chuyển đến Thư viện API và bật API cho một Dự án trên đám mây.
Tạo Tài khoản dịch vụ
Tài khoản dịch vụ được dùng để cho phép ứng dụng của bạn truy cập vào Subscription linking API (API Liên kết gói thuê bao).
- Tạo tài khoản dịch vụ trong Google Play.
- Tạo thông tin đăng nhập cho tài khoản dịch vụ rồi lưu trữ
tệp
credentials.json
ở một vị trí an toàn mà ứng dụng của bạn có thể truy cập. - Cấp cho vai trò IAM "Quản trị viên liên kết gói thuê bao" vào tài khoản dịch vụ bạn đã tạo. Để kiểm soát chi tiết các khả năng của tài khoản dịch vụ, bạn có thể chỉ định vai trò thích hợp trong bảng sau.
Chức năng / Vai trò | Quản trị viên liên kết gói thuê bao | Người xem liên kết gói thuê bao | Người xem có quyền liên kết gói thuê bao |
---|---|---|---|
Nhận quyền của độc giả | |||
Thu hút độc giả | |||
Cập nhật quyền của độc giả | |||
Xoá độc giả |
Sử dụng tài khoản dịch vụ bằng Subscription linking API (API Liên kết gói thuê bao)
Sử dụng tài khoản dịch vụ để xác thực lệnh gọi đến Subscription linking API (API Liên kết gói thuê bao),
với thư viện ứng dụng googleapis hoặc bằng cách ký các yêu cầu
bằng API REST. Thư viện ứng dụng tự động xử lý việc yêu cầu
access_token
thích hợp, trong khi API REST yêu cầu truy xuất một id_token
rồi đổi lấy access_token
.
Cả ứng dụng sau
thư viện và các ví dụ về API REST sử dụng điểm cuối getReader()
. Để phát trực tiếp
phần minh hoạ về tất cả các phương thức API, hãy xem
Trang web Bản minh hoạ về cách liên kết gói thuê bao hoặc mã của trang web đó.
Yêu cầu mẫu với thư viện ứng dụng googleapis củanode.js
import {readerrevenuesubscriptionlinking_v1, Auth} from 'googleapis';
const subscriptionLinking = readerrevenuesubscriptionlinking_v1.Readerrevenuesubscriptionlinking;
class SubscriptionLinking {
constructor() {
this.auth = new Auth.GoogleAuth({
keyFile: process.env.KEY_FILE,
scopes: [
'https://www.googleapis.com/auth/readerrevenue.subscriptionlinking.manage'
],
})
}
init() {
return new subscriptionLinking(
{version: 'v1', auth: this.auth})
}
}
const api = new SubscriptionLinking();
const client = api.init();
async function getReader(ppid) {
const publicationId = process.env.PUBLICATION_ID;
return await client.publications.readers.get({
name: `publications/${publicationId}/readers/${ppid}`,
});
};
async function updateEntitlements(ppid) {
const publicationId = process.env.PUBLICATION_ID;
const requestBody = {
/*
Refer to
https://developers.google.com/news/subscribe/subscription-linking/appendix/glossary#entitlements_object
*/
entitlements : [{
product_id: `${publicationId}:basic`,
subscription_token: 'abc1234',
detail: 'This is our basic plan',
expire_time: '2025-10-21T03:05:08.200564Z'
}]
};
return await client.publications.readers.updateEntitlements({
name: `publications/${publicationId}/readers/${ppid}/entitlements`,
requestBody
});
};
Ký yêu cầu API REST theo cách thủ công
import fetch from 'node-fetch'
import jwt from 'jsonwebtoken'
function getSignedJwt() {
/*
Either store the credentials string in an environmental variable
Or implement logic to fetch it.
*/
const key_file = process.env.CREDENTIALS_STRING
const issueDate = new Date()
const expireMinutes = 60
const offsetInSeconds = issueDate.getTimezoneOffset() * 60000
const expireDate = new Date(issueDate.getTime() + (expireMinutes * 60000))
const iat = Math.floor((issueDate.getTime() + offsetInSeconds) / 1000)
const exp = Math.floor((expireDate.getTime() + offsetInSeconds) / 1000)
const token = {
iss: key_file.client_email,
iat,
exp,
aud: 'https://oauth2.googleapis.com/token',
scope:'https://www.googleapis.com/auth/readerrevenue.subscriptionlinking.manage',
}
return jwt.sign(token, key_file.private_key, {
algorithm: 'RS256',
keyid: key_file.private_key_id,
})
}
async function getAccessToken(signedJwt) {
let body = new URLSearchParams();
body.set('grant_type', 'urn:ietf:params:oauth:grant-type:jwt-bearer')
body.set('assertion', signedJwt)
const request = await fetch('https://oauth2.googleapis.com/token', {
method: 'POST',
headers: {'Content-Type': 'application/x-www-form-urlencoded'},
body
})
const accessResponse = await accessFetch.json()
return accessResponse.access_token
}
async function getReader(ppid) {
const publicationId = process.env.PUBLICATION_ID
const base_url = 'https://readerrevenuesubscriptionlinking.googleapis.com/v1'
const endpoint = `${base_url}/publications/${publicationId}/readers/${ppid}`
const signedJwt = await getSignedJwt()
const accessToken = await getAccessToken(signedJwt)
const reader = await fetch(endpoint, {
method: 'GET',
headers: {
Authorization: `Bearer ${accessToken}`,
},
}).then((response) => {
return response.json()
})
return reader
}