ACCESS_TOKEN.md 7.0 KB

飞书 Access Token 配置指南

概述

本模块支持两种消息推送方式:

  1. Webhook 方式(无需 access token)

    • 推送到群组
    • 通过 @user_id 提及群组中的个人
    • 简单易用,无需额外配置
  2. 开放平台 API 方式(需要 access token)

    • 直接推送到个人聊天
    • 批量推送到多人
    • 需要配置 app_id 和 app_secret

为什么需要 Access Token?

飞书的自定义机器人 Webhook 只能推送到群组,如果需要直接推送到个人聊天,就需要使用飞书开放平台 API,这需要:

  1. 创建企业自建应用
  2. 获取 app_id 和 app_secret
  3. 通过这两个参数获取 tenant_access_token
  4. 使用 token 调用发送消息 API

Token 管理机制

本模块实现了完整的 token 管理机制:

  • 自动获取:首次使用时自动从飞书 API 获取 token
  • 数据库存储:token 保存到 Parse Server 的 Store 表的 config 字段
  • 自动刷新:token 过期前自动刷新(提前 5 分钟)
  • 缓存优化:优先从数据库读取,避免频繁请求飞书 API

数据库存储格式

Token 保存在 Store 表的 config 字段中,格式如下:

{
  "feishu": {
    "accessToken": "t-xxx",
    "expireTime": 1709971200000
  }
}
  • accessToken: 飞书的 tenant_access_token
  • expireTime: 过期时间戳(毫秒),提前 5 分钟过期

配置步骤

1. 创建企业自建应用

  1. 访问 飞书开放平台
  2. 登录企业管理员账号
  3. 进入"开发者后台" → "企业自建应用"
  4. 点击"创建企业自建应用"
  5. 填写应用信息(名称、描述、图标等)
  6. 创建完成后,进入应用详情页

2. 获取 App ID 和 App Secret

在应用详情页的"凭证与基础信息"中,可以看到:

  • App ID:应用的唯一标识(格式:cli_xxx)
  • App Secret:应用的密钥(点击"查看"按钮显示)

重要提示:

  • App Secret 只显示一次,请妥善保管
  • 如果忘记,可以重置,但会导致旧的 token 失效

3. 配置应用权限

在应用详情页的"权限管理"中,需要开通以下权限:

  • im:message - 获取与发送单聊、群组消息
  • im:message:send_as_bot - 以应用的身份发消息

配置权限后,需要等待管理员审批(如果你是管理员,可以直接通过)。

4. 配置环境变量

在服务器上配置以下环境变量:

# Linux/Mac
export FEISHU_APP_ID="cli_xxx"
export FEISHU_APP_SECRET="your_app_secret"

# Windows (PowerShell)
$env:FEISHU_APP_ID="cli_xxx"
$env:FEISHU_APP_SECRET="your_app_secret"

# Windows (CMD)
set FEISHU_APP_ID=cli_xxx
set FEISHU_APP_SECRET=your_app_secret

或者在 .env 文件中配置(如果项目使用 dotenv):

FEISHU_APP_ID=cli_xxx
FEISHU_APP_SECRET=your_app_secret

5. 验证配置

启动服务后,调用任意需要 access token 的接口,系统会自动:

  1. 从环境变量读取 app_id 和 app_secret
  2. 调用飞书 API 获取 tenant_access_token
  3. 保存到数据库(Store 表的 config 字段)
  4. 返回成功响应

如果配置错误,会返回错误信息:

{
  "success": false,
  "error": "飞书配置无效:请设置 FEISHU_APP_ID 和 FEISHU_APP_SECRET 环境变量",
  "timestamp": "2026-03-09T14:00:00.000Z"
}

Token 生命周期

Token 有效期

  • 飞书的 tenant_access_token 有效期为 2 小时(7200 秒)
  • 本模块会提前 5 分钟刷新 token,避免边界情况

Token 刷新流程

1. 前端请求接口
   ↓
2. 后端检查数据库中的 token
   ↓
3. 判断是否过期
   ├─ 未过期:直接使用
   └─ 已过期:
      ├─ 调用飞书 API 获取新 token
      ├─ 保存到数据库
      └─ 使用新 token
   ↓
4. 调用飞书 API 发送消息
   ↓
5. 返回结果

手动刷新 Token

如果需要手动刷新 token(例如,怀疑 token 失效),可以:

  1. 删除数据库中的 token 记录
  2. 下次请求时会自动重新获取

或者,可以添加一个管理接口来手动刷新 token(需要自行实现)。

安全建议

  1. 保护 App Secret

    • 不要在前端代码中暴露 app_secret
    • 不要提交到 Git 仓库
    • 使用环境变量或密钥管理服务
  2. 限制应用权限

    • 只开通必要的权限
    • 定期审查应用权限
  3. 监控 Token 使用

    • 记录 token 获取和刷新日志
    • 监控异常的 token 使用情况
  4. 定期轮换密钥

    • 定期重置 app_secret
    • 更新环境变量配置

常见问题

Q1: 为什么获取 token 失败?

可能原因:

  • app_id 或 app_secret 配置错误
  • 应用未启用或已停用
  • 网络连接问题

解决方法:

  1. 检查环境变量配置是否正确
  2. 在飞书开放平台检查应用状态
  3. 检查服务器网络连接

Q2: Token 过期后会自动刷新吗?

是的,本模块会自动检查 token 是否过期,如果过期会自动刷新。

Q3: 可以手动指定 token 吗?

不建议。本模块已经实现了完整的 token 管理机制,手动指定 token 可能导致:

  • Token 过期后无法自动刷新
  • 多个服务实例之间 token 不一致

Q4: 数据库中的 token 丢失了怎么办?

不用担心,下次请求时会自动重新获取并保存。

Q5: 如何查看当前的 token?

可以直接查询 Parse Server 的 Store 表:

const query = new Parse.Query('Store');
query.equalTo('objectId', 'config');
const store = await query.first({ useMasterKey: true });
const config = store.get('config');
console.log(config.feishu);

技术实现

Token 管理器

本模块使用单例模式实现了 TokenManager 类,负责:

  • 从飞书 API 获取 token
  • 保存到数据库
  • 从数据库读取
  • 检查是否过期
  • 自动刷新

配置管理

配置管理模块从环境变量读取 app_id 和 app_secret:

export function getFeishuConfig(): FeishuConfig {
  return {
    app_id: process.env.FEISHU_APP_ID || '',
    app_secret: process.env.FEISHU_APP_SECRET || ''
  };
}

使用示例

在路由中使用 token:

import { getTokenManager } from './token-manager';

// 获取 token
const tokenManager = getTokenManager();
const accessToken = await tokenManager.getAccessToken();

// 使用 token 调用飞书 API
const response = await fetch('https://open.feishu.cn/open-apis/im/v1/messages', {
  method: 'POST',
  headers: {
    'Content-Type': 'application/json',
    'Authorization': `Bearer ${accessToken}`
  },
  body: JSON.stringify({...})
});

参考资料