介绍
Cloudbase Open API 让开发者可以通过 HTTP 的方式,以管理员身份调用 CloudBase 的服务。
对于 CloudBase 尚未提供 SDK 的语言(如 Java、Go、C++ 等),开发者可以通过此种方式访问 Cloudbase。
#
了解请求结构- 服务地址
https://tcb-api.tencentcloudapi.com
- 请求方法
支持的 HTTP 请求方法:GET, POST, PUT, PATCH, DELETE
- 请求头构造
头部字段 | 类型 | 必填 | 说明 |
---|---|---|---|
X-CloudBase-Authorization | String | 是 | 结构为:"<凭证版本> <CloudBase 签名>" ,CloudBase Open API 标准凭证 |
X-CloudBase-SessionToken | String | 是 | 腾讯云 CAM 临时密钥的 Session Token |
X-CloudBase-TimeStamp | Number | 否 | Unix 时间戳,以秒为单位 |
content-type | String | 否 | POST 时请指定 application/json |
#
使用示例查询数据库文档
curl -X GET https://tcb-api.tencentcloudapi.com/api/v2/envs/{envId}/databases/{collectionName}/documents/{docId} \-H "X-CloudBase-Authorization: <authorization>" \-H "X-CloudBase-TimeStamp: 1551113065" \-H "X-CloudBase-SessionToken: <sessiontoken>" \
#
如何获取凭证#
1. 从云托管的请求头中获取凭证云托管的服务中,可以读取请求头中携带的凭证信息,凭证字段 x-cloudbase-authorization
,临时密钥字段 x-cloudbase-sessiontoken
。
以云托管中的 Node.js 服务为例:
const express = require("express");const got = require("got");const app = express();
app.get("/", async (req, res) => { // 从请求头中获取凭证信息 const authorization = req.headers["x-cloudbase-authorization"]; const sessiontoken = req.headers["x-cloudbase-sessiontoken"]; const timestamp = parseInt(Date.now() / 1000).toString();
// 使用凭证向 CloudBase Open API 发起请求 // 以查询文档为例,先拼接url const envId = "foo"; const collectionName = "bar"; const docId = "123"; const url = `https://tcb-api.tencentcloudapi.com/api/v2/envs/${envId}/databases/${collectionName}/documents/${docId}`;
// 发起请求,请求头中加入凭证信息 const response = await got(url, { headers: { "X-CloudBase-Authorization": authorization, "X-CloudBase-TimeStamp": timestamp, "X-CloudBase-SessionToken": sessiontoken, }, });
res.send(response.body);});
app.listen(3000);
#
2. Node.js 服务使用签名工具包计算凭证Node.js 开发者可以直接使用 Node.js 的签名工具包,无需自行实现签名计算流程:
import { sign } from "@cloudbase/signature-nodejs";
const tmpSecretId = "腾讯云临时密钥SecretId";const tmpSecretKey = "腾讯云临时密钥SecretKey";const token = "腾讯云临时密钥Token";
const headers = { host: "api.tcloudbase.com", "content-type": "application/json; charset=utf-8",};
const timestamp = Math.floor(new Date().getTime() / 1000);const version = "1.0";
const { authorization } = sign({ secretId: tmpSecretId, secretKey: tmpSecretKey, method: "POST", url: "https://api.tcloudbase.com/", headers, timestamp, params: {},});
// Open API 请求头const reqHeaders = {};reqHeaders["X-CloudBase-Authorization"] = version + " " + authorization;reqHeaders["X-CloudBase-SessionToken"] = token;reqHeaders["X-CloudBase-TimeStamp"] = timestamp;
tip
- 使用永久密钥时,可以忽略 sessionToken 字段,如何获取腾讯云永久密钥,进入腾讯云控制台访问密钥页面查看.
- 云函数环境中,可以读取环境变量 process.env.TENCENTCLOUD_SESSIONTOKEN 获取,使用临时密钥时务必设置该头部字段。 :::
#
3. 使用临时密钥自行计算凭证对于某些场景,开发者可自行拉取腾讯云临时密钥,计算出凭证,标准流程可以参考 腾讯云 CAM 签名流程。
CloudBase 标准凭证与腾讯云 CAM 签名的计算流程大体相同,但在参数上有所简化,以下步骤请配合 腾讯云 CAM 签名流程 阅读。 :::
#
(1) CanonicalRequest其中 CanonicalRequest
的各项参数有简化,api.tcloudbase.com
为假设域名,如下:
字段 | 取值 |
---|---|
HTTPRequestMethod | "POST" |
CanonicalURI | "//api.tcloudbase.com/" |
CanonicalQueryString | 空 |
CanonicalHeaders | "content-type:application/json charset=utf-8\nhost:api.tcloudbase.com\n" |
SignedHeaders | "content-type;host" |
HashedRequestPayload | 空 |
所以 CanonicalRequest
固定如下:
POST//api.tcloudbase.com/
content-type:application/json; charset=utf-8host:api.tcloudbase.com
content-type;hoste3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855
#
(2) StringToSign然后计算 StringToSign
,假设时间戳为 1600227242
,结果如下:
TC3-HMAC-SHA25616002272422020-09-16/tcb/tc3_request0b986c5cd287577210de28ce0ff9167ada0dbb88736b07ce307b45615a49307e
#
(3) Signature我们假设 SecretKey 为 wH72j2a5ZzhwgnXViwVNqdWhWn4AG4iasv26D4JdjBA=
,Date 为 2020-09-16
,那么 Signature 为:
0ce229810e251baa0ee2bb786c5f9eb6cb7758f55df28cbc161883c48a997e04
#
(4) 拼接 AuthorizationTC3-HMAC-SHA256 Credential=AKIDDo-bNhLNl3kEY5HRzEG-CNUotmyFSadvpKimESWTfND98qyfrpYLCtQJ92_z9yN8/2020-09-16/tcb/tc3_request, SignedHeaders=content-type;host, Signature=0ce229810e251baa0ee2bb786c5f9eb6cb7758f55df28cbc161883c48a997e04
#
(5) 加上 CloudBase 签名版本前面加上 1.0
即可:
1.0 TC3-HMAC-SHA256 Credential=AKIDDo-bNhLNl3kEY5HRzEG-CNUotmyFSadvpKimESWTfND98qyfrpYLCtQJ92_z9yN8/2020-09-16/tcb/tc3_request, SignedHeaders=content-type;host, Signature=0ce229810e251baa0ee2bb786c5f9eb6cb7758f55df28cbc161883c48a997e04
#
JS 凭证示例计算参考const crypto = require("crypto");const axios = require("axios");
// 密钥参数const SECRET_ID = "AKIDz8krbsJ5yKBZQpn74WFkmLPx3*******";const SECRET_KEY = "Gu5t9xGARNpq86cd98joQYCN3*******";const token = ""; //永久密钥则不需要tokenconst service = "tcb"; //固定值const timestamp = Math.floor(new Date().getTime() / 1000); //时间戳const version = "1.0"; //固定值const date = getDate(timestamp); //时间处理, 获取世界时间日期
// ************* 步骤 1:拼接规范请求串(此处无需操作,都是固定值) *************const signedHeaders = "content-type;host";const canonicalRequest = `POST\n//api.tcloudbase.com/\n\ncontent-type:application/json; charset=utf-8\nhost:api.tcloudbase.com\n\ncontent-type;host\ne3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855`;
// ************* 步骤 2:拼接待签名字符串(和示例代码基本无出入) *************const algorithm = "TC3-HMAC-SHA256";const hashedCanonicalRequest = getHash(canonicalRequest);const credentialScope = date + "/" + service + "/" + "tc3_request";const stringToSign = algorithm + "\n" + timestamp + "\n" + credentialScope + "\n" + hashedCanonicalRequest;console.log(stringToSign);
// ************* 步骤 3:计算签名(和示例代码基本无出入) *************const kDate = sha256(date, "TC3" + SECRET_KEY);const kService = sha256(service, kDate);const kSigning = sha256("tc3_request", kService);const signature = sha256(stringToSign, kSigning, "hex");console.log(signature);
// ************* 步骤 4:拼接 Authorization(和示例代码基本无出入) *************const authorization = algorithm + " " + "Credential=" + SECRET_ID + "/" + credentialScope + ", " + "SignedHeaders=" + signedHeaders + ", " + "Signature=" + signature;console.log(authorization);
// ************* 步骤 5:拼接 请求头(补充) *************const reqHeaders = {};reqHeaders["X-CloudBase-Authorization"] = version + " " + authorization;reqHeaders["X-CloudBase-SessionToken"] = token;reqHeaders["X-CloudBase-TimeStamp"] = timestamp;
// ************* 步骤 6:测试访问(请求数据库) *************axios({ method: "get", url: "https://tcb-api.tencentcloudapi.com/api/v2/envs/${envid}/databases/${dbname}/documents/${docid}", headers: reqHeaders,}).then((res) => res.data);
//以下代码为示例代码中有的
function sha256(message, secret = "", encoding) { const hmac = crypto.createHmac("sha256", secret); return hmac.update(message).digest(encoding);}
function getHash(message, encoding = "hex") { const hash = crypto.createHash("sha256"); return hash.update(message).digest(encoding);}
function getDate(timestamp) { const date = new Date(timestamp * 1000); const year = date.getUTCFullYear(); const month = ("0" + (date.getUTCMonth() + 1)).slice(-2); const day = ("0" + date.getUTCDate()).slice(-2); return `${year}-${month}-${day}`;}
#
Python 凭证示例计算参考# -*- coding: utf-8 -*-import hashlib, hmac, json, os, sys, timefrom datetime import datetime
# 密钥参数secret_id = "AKIDz8krbsJ5yKBZQpn74WFkmLPx3*******"secret_key = "Gu5t9xGARNpq86cd98joQYCN3*******"
service = "tcb"version = "1.0"algorithm = "TC3-HMAC-SHA256"timestamp = int(time.time())date = datetime.utcfromtimestamp(timestamp).strftime("%Y-%m-%d")
# ************* 步骤 1:拼接规范请求串 *************signed_headers = "content-type;host"canonical_request = "POST\n//api.tcloudbase.com/\n\ncontent-type:application/json; charset=utf-8\nhost:api.tcloudbase.com\n\ncontent-type;host\ne3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"
# ************* 步骤 2:拼接待签名字符串 *************credential_scope = date + "/" + service + "/" + "tc3_request"hashed_canonical_request = hashlib.sha256(canonical_request.encode("utf-8")).hexdigest()string_to_sign = (algorithm + "\n" + str(timestamp) + "\n" + credential_scope + "\n" + hashed_canonical_request)print(string_to_sign)
# ************* 步骤 3:计算签名 *************# 计算签名摘要函数def sign(key, msg): return hmac.new(key, msg.encode("utf-8"), hashlib.sha256).digest()secret_date = sign(("TC3" + secret_key).encode("utf-8"), date)secret_service = sign(secret_date, service)secret_signing = sign(secret_service, "tc3_request")signature = hmac.new(secret_signing, string_to_sign.encode("utf-8"), hashlib.sha256).hexdigest()print(signature)
# ************* 步骤 4:拼接 Authorization *************authorization = (algorithm + " " + "Credential=" + secret_id + "/" + credential_scope + ", " + "SignedHeaders=" + signed_headers + ", " + "Signature=" + signature)print(authorization)
#
Java 凭证实例计算参考import java.nio.charset.Charset;import java.nio.charset.StandardCharsets;import java.security.MessageDigest;import java.text.SimpleDateFormat;import java.util.Date;import java.util.TimeZone;import java.util.TreeMap;import javax.crypto.Mac;import javax.crypto.spec.SecretKeySpec;import javax.xml.bind.DatatypeConverter;
public class TencentCloudAPITC3Demo { private final static Charset UTF8 = StandardCharsets.UTF_8; private final static String SECRET_ID = "AKIDz8krbsJ5yKBZQpn74WFkmLPx3*******"; private final static String SECRET_KEY = "Gu5t9xGARNpq86cd98joQYCN3*******";
public static byte[] hmac256(byte[] key, String msg) throws Exception { Mac mac = Mac.getInstance("HmacSHA256"); SecretKeySpec secretKeySpec = new SecretKeySpec(key, mac.getAlgorithm()); mac.init(secretKeySpec); return mac.doFinal(msg.getBytes(UTF8)); }
public static String sha256Hex(String s) throws Exception { MessageDigest md = MessageDigest.getInstance("SHA-256"); byte[] d = md.digest(s.getBytes(UTF8)); return DatatypeConverter.printHexBinary(d).toLowerCase(); }
public static void main(String[] args) throws Exception { String service = "tcb";//固定值 String version = "1.0"; String algorithm = "TC3-HMAC-SHA256"; String timestamp = String.valueOf(System.currentTimeMillis() / 1000); SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd"); // 注意时区,否则容易出错 sdf.setTimeZone(TimeZone.getTimeZone("UTC")); String date = sdf.format(new Date(Long.valueOf(timestamp + "000")));
// ************* 步骤 1:拼接规范请求串(此处无需操作,都是固定值) ************* String signedHeaders = "content-type;host"; String canonicalRequest = `POST\n//api.tcloudbase.com/\n\ncontent-type:application/json; charset=utf-8\nhost:api.tcloudbase.com\n\ncontent-type;host\ne3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855`
// ************* 步骤 2:拼接待签名字符串(和示例代码基本无出入) ************* String credentialScope = date + "/" + service + "/" + "tc3_request"; String hashedCanonicalRequest = sha256Hex(canonicalRequest); String stringToSign = algorithm + "\n" + timestamp + "\n" + credentialScope + "\n" + hashedCanonicalRequest; System.out.println(stringToSign);
// ************* 步骤 3:计算签名(和示例代码基本无出入) ************* byte[] secretDate = hmac256(("TC3" + SECRET_KEY).getBytes(UTF8), date); byte[] secretService = hmac256(secretDate, service); byte[] secretSigning = hmac256(secretService, "tc3_request"); String signature = DatatypeConverter.printHexBinary(hmac256(secretSigning, stringToSign)).toLowerCase(); System.out.println(signature);
// ************* 步骤 4:拼接 Authorization(和示例代码基本无出入) ************* String authorization = algorithm + " " + "Credential=" + SECRET_ID + "/" + credentialScope + ", " + "SignedHeaders=" + signedHeaders + ", " + "Signature=" + signature; System.out.println(authorization);
// ************* 步骤 5:拼接 请求头(补充) ************* TreeMap<String, String> headers = new TreeMap<String, String>(); headers.put("X-CloudBase-Authorization", version + " " + authorization); headers.put("X-CloudBase-SessionToken", token); headers.put("X-CloudBase-TimeStamp", timestamp);
//请使用此headers进行网络请求,访问相关接口 //...相关网络请求代码 }}