javascript - 使用默认凭据访问 Google 表格

标签 javascript node.js google-app-engine google-cloud-platform google-sheets-api

我在 Google 表格上有一些数据。我正在使用 Sheets API for Node.js访问此数据。对于身份验证,我使用服务帐户 JSON 生成 JWTClient。

我可以从工作表 api 访问数据,一切正常。代码托管在 Google App Engine Flexible environment 上.它适用于本地主机和 GAE。

唯一的问题是我需要提供服务帐户 key json 进行身份验证。这在本地环境中很好,但在 App Engine 上它提供了一个 default credential对于服务帐户(我使用的是相同的服务帐户)。所以我认为我不应该手动提供凭据并让 GAE 处理服务器上的凭据。

但它不会自动进行身份验证,仍然是一个身份验证参数。

这是我当前对工作表 api 的实现 -

const { promisify } = require('util');
const google = require('googleapis');
const auth = require('./auth');
const credentials = require('../configs/credentials');

const sheets = google.sheets('v4');
const getSheetValuesAsync = promisify(sheets.spreadsheets.values.get);
//region private
function readSheet(params) {
  return getSheetValuesAsync(params);
}
//endregion private

//region public
async function get(sheetConfigName) {
  const sheetConfig = credentials.sheets[sheetConfigName];
  //This is theJWTClient which authenticates the api request currently.
  //I want to remove this
  const authClient = await auth.authorizeWithServiceAccount('serviceAccountName', [
    'https://www.googleapis.com/auth/spreadsheets.readonly'
  ]);
  console.log('Client received');
  let params = {
    auth: authClient, //I tried removing this parameter, but it didn't work
    spreadsheetId: sheetConfig.id,
    range: 'A:M'
  };
  let data = await readSheet(params);
  return data;
}
//endregion public
module.exports = {
  get: get
};

我得到的错误如下:-

{
  code:403,
  message: 'The request is missing a valid API key.
}

我已经为本地环境设置了 GOOGLE_APPLICATION_CREDENTIALS 环境变量,它已经适用于 google-cloud API,但不适用于工作表。

那么 Application Default Credentials 是仅用于 google-cloud API 还是可以与 Sheets API 或任何其他 Drive API 一起使用?如果它也可以与驱动器 API 一起使用,如何实现?

最佳答案

在 Google 的 Node.js 客户端包 (28.x) 的最新更新中,他们有一种无需第二个包即可获取 authClient 的新方法。这是它是如何完成的 -

const { google } = require('googleapis');
  const authClient = await google.auth.getClient({
  credentials: credentials,
  scopes: scopes
});

credentials 只是服务帐户 JSON 对象。最好的部分是,如果您不提供该属性,它将检查 GOOGLE_APPLICATION_CREDENTIALS 环境变量,该变量将包含服务帐户 key JSON 的绝对路径,并自动将其用于身份验证。
您可以通过以下任一方式使用生成的 authClient 为 google sheets API 设置 auth 参数 -

首先是当您想为不同的 API 调用提供不同的身份验证时。

const { google } = require('googleapis');
const sheets = google.sheets('v4');
sheets.spreadsheets.values.getAsync = promisify(sheets.spreadsheets.values.get);
sheets.spreadsheets.values.getAsync({
    auth: authClient,
    spreadsheetId: spreadsheetId,
    range: range
  });

或者您可以直接向工作表对象提供授权。该对象上的所有 API 调用都将使用相同的 authClient,并且不需要 auth 参数。

const sheets = google.sheets({version:'v4',auth:authClient);

最好的方法是为所有 Google API 调用设置默认身份验证,这样您就不必将 authClient 传递给任何工作表对象或 API 调用。

google.options({
  auth: authClient
});

如果您计划为不同的 API 使用不同的服务帐户,您仍然可以在工作表(或驱动器或任何其他对象)API 对象或特定的任何 API 调用中覆盖 auth 参数。

要在本地进行测试,您始终可以设置环境路径,这样您实际上不必将服务帐户传递给 google.auth 对象。这是我的做法

let resolve = require('path').resolve;
if (process.env.NODE_ENV === 'production') {
  //Set config based on production environment. It won't be set in local environment, unless you specially set it.
} else if (!process.env.GOOGLE_APPLICATION_CREDENTIALS) {
  process.env.GOOGLE_APPLICATION_CREDENTIALS = resolve(
      './relative/path/to/the/json/key.json'
  ); //resolve will just convert relative path to the absolute path.
}

关于javascript - 使用默认凭据访问 Google 表格,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49563586/

相关文章:

node.js - WSL 上的 NodeJS+Webpack+Docker 项目使用 native 'fs' 库抛出错误

javascript正则表达式非捕获比根本没有括号更快

java - 从 App Engine (Java) 中删除命名空间

python - 替换 python 脚本中 self.response.write 的 webapp2 用法

java - 重定向到 AppEngine java 中的外部链接?

javascript - Jquery - 获取数组中数组项的名称

javascript - 通过插值引用对象中的对象(Angular 2+)

node.js - 连接到不同命名空间时的 socketIO 握手行为

javascript - 如何区分 localStorage 与单击时存储每个文件?

javascript - 设计 Google map - Javascript