飞书群组管理
接口名称
飞书群组管理(用户令牌) - (IFeishuUserV1ChatGroup)
功能描述
飞书群组 OpenAPI 提供了群组管理能力,包括创建群、解散群、更新群信息、获取群信息、管理群置顶以及获取群分享链接等。当前接口使用用户令牌访问,适应于用户应用场景。
参考文档
接口详细文档请参见:飞书群组管理 API
函数列表
| 函数名称 | 功能描述 | 认证方式 | HTTP 方法 |
|---|---|---|---|
| UpdateChatGroupByIdAsync | 更新指定群的信息,包括群头像、群名称、群描述、群配置以及群主等 | 用户令牌 | PUT |
| DeleteChatGroupAsync | 通过 chat_id 解散指定群组。通过 API 解散群组后,群聊天记录将不会保存 | 用户令牌 | DELETE |
| UpdateChatModerationAsync | 更新指定群组的发言权限,可设置为所有群成员可发言、仅群主或管理员可发言、指定群成员可发言 | 用户令牌 | PUT |
| GetChatGroupInoByIdAsync | 获取指定群的基本信息,包括群名称、群描述、群头像、群主 ID 以及群权限配置等 | 用户令牌 | GET |
| PutChatGroupTopNoticeAsync | 更新群组中的群置顶信息,可以将群中的某一条消息,或群公告置顶展示 | 用户令牌 | POST |
| DeleteChatGroupTopNoticeAsync | 撤销指定群组中的置顶消息或群公告 | 用户令牌 | POST |
| GetChatGroupPageListAsync | 分页获取当前 access_token 所代表的用户或者机器人所在的群列表 | 用户令牌 | GET |
| GetChatGroupPageListByKeywordAsync | 分页获取当前身份(用户或机器人)可见的群列表,包括当前身份所在的群、对当前身份公开的群。支持关键词搜索、分页搜索 | 用户令牌 | GET |
| GetChatGroupModeratorPageListByIdAsync | 分页获取指定群组的发言模式、可发言用户名单等信息 | 用户令牌 | GET |
| GetChatGroupShareLinkByIdAsync | 获取指定群的分享链接,他人点击分享链接后可加入群组 | 用户令牌 | GET |
函数详细内容
更新群信息
函数签名:
csharp
Task<FeishuApiResult<CreateUpdateChatResult>?> UpdateChatGroupByIdAsync(
[Path] string chat_id,
[Body] UpdateChatRequest updateChatRequest,
[Query("user_id_type")] string user_id_type = Consts.User_Id_Type,
CancellationToken cancellationToken = default);认证:用户令牌
参数:
| 参数名 | 类型 | 必填 | 含义 | 示例值 |
|---|---|---|---|---|
| chat_id | string | ✅ | 群 ID | "oc_a0553eda9014c201e6969b478895c230" |
| updateChatRequest | UpdateChatRequest | ✅ | 更新群聊请求体 | 包含更新的群信息 |
| user_id_type | string | ⚪ | 用户 ID 类型 | "open_id" |
响应:
json
{
"code": 0,
"msg": "success",
"data": {
"chat_id": "oc_a0553eda9014c201e6969b478895c230",
"name": "更新后的群名称",
"description": "更新后的群描述"
}
}代码示例:
typescript
// 用户更新群信息示例
const updateRequest = {
name: "新的群名称",
description: "更新后的群描述",
avatar: "new_avatar_url"
};
const response = await feishuUserClient.updateChatGroupByIdAsync(
"oc_a0553eda9014c201e6969b478895c230",
updateRequest,
"open_id"
);
if (response.code === 0) {
console.log("群信息更新成功");
} else {
console.error("更新失败:", response.msg);
}解散群组
函数签名:
csharp
Task<FeishuNullDataApiResult?> DeleteChatGroupAsync(
[Path] string chat_id,
CancellationToken cancellationToken = default);认证:用户令牌
参数:
| 参数名 | 类型 | 必填 | 含义 | 示例值 |
|---|---|---|---|---|
| chat_id | string | ✅ | 群 ID | "oc_a0553eda9014c201e6969b478895c230" |
响应:
json
{
"code": 0,
"msg": "success"
}错误码:
- 33401: 群不存在
- 33403: 无权限解散群
- 33413: 群成员数超过限制,无法解散
说明:
- 通过 API 解散群组后,群聊天记录将不会保存
- 使用用户令牌时,只有群主可以解散群组
- 企业管理员设置的群组解散限制可能会影响操作权限
代码示例:
typescript
// 用户解散群组示例
const response = await feishuUserClient.deleteChatGroupAsync("oc_a0553eda9014c201e6969b478895c230");
if (response.code === 0) {
console.log("群组解散成功");
// 更新UI状态,移除群组显示
} else if (response.code === 33403) {
console.error("权限不足,只有群主可以解散群组");
} else {
console.error("解散失败:", response.msg);
}更新群发言权限
函数签名:
csharp
Task<FeishuNullDataApiResult?> UpdateChatModerationAsync(
[Path] string chat_id,
[Body] UpdateChatModerationRequest updateChatModerationRequest,
[Query("user_id_type")] string user_id_type = Consts.User_Id_Type,
CancellationToken cancellationToken = default);认证:用户令牌
参数:
| 参数名 | 类型 | 必填 | 含义 | 示例值 |
|---|---|---|---|---|
| chat_id | string | ✅ | 群 ID | "oc_a0553eda9014c201e6969b478895c230" |
| updateChatModerationRequest | UpdateChatModerationRequest | ✅ | 更新群发言权限请求体 | 包含发言权限配置 |
| user_id_type | string | ⚪ | 用户 ID 类型 | "open_id" |
响应:
json
{
"code": 0,
"msg": "success"
}错误码:
- 33401: 群不存在
- 33403: 无权限修改群设置
说明:
- 使用用户令牌时,只有群主和管理员可以修改发言权限
- 发言权限模式包括:all_members(所有成员)、admin_only(仅管理员)、some_members(指定成员)
代码示例:
typescript
// 管理员设置群发言权限示例
const moderationRequest = {
speak_permission: "some_members", // 限制部分成员发言
user_ids: ["user_001", "user_002"] // 允许发言的用户列表
};
const response = await feishuUserClient.updateChatModerationAsync(
"oc_a0553eda9014c201e6969b478895c230",
moderationRequest,
"open_id"
);
if (response.code === 0) {
console.log("群发言权限设置成功");
// 通知群成员权限变更
} else if (response.code === 33403) {
console.error("权限不足,需要群主或管理员权限");
}获取群信息
函数签名:
csharp
Task<FeishuApiResult<GetChatGroupInfoResult>?> GetChatGroupInoByIdAsync(
[Path] string chat_id,
[Query("user_id_type")] string user_id_type = Consts.User_Id_Type,
CancellationToken cancellationToken = default);认证:用户令牌
参数:
| 参数名 | 类型 | 必填 | 含义 | 示例值 |
|---|---|---|---|---|
| chat_id | string | ✅ | 群 ID | "oc_a0553eda9014c201e6969b478895c230" |
| user_id_type | string | ⚪ | 用户 ID 类型 | "open_id" |
响应:
json
{
"code": 0,
"msg": "success",
"data": {
"chat_id": "oc_a0553eda9014c201e6969b478895c230",
"name": "群聊名称",
"description": "群描述",
"avatar": "avatar_url",
"owner_id": "user_001",
"chat_mode": "group",
"chat_type": "private",
"external": false,
"tenant_key": "tenant_001",
"user_id_type": "open_id",
"join_permission": "all_members",
"share_permission": "all_members",
"at_permission": "all_members"
}
}错误码:
- 33401: 群不存在
- 33403: 无权限查看群信息
说明:
- 使用用户令牌时,只能查看用户所在群组的信息
- 返回的信息中包含用户在该群中的权限信息
代码示例:
typescript
// 用户获取群信息示例
const response = await feishuUserClient.getChatGroupInoByIdAsync(
"oc_a0553eda9014c201e6969b478895c230",
"open_id"
);
if (response.code === 0) {
const groupInfo = response.data;
console.log(`群名称: ${groupInfo.name}`);
console.log(`群主: ${groupInfo.owner_id}`);
console.log(`群类型: ${groupInfo.chat_type}`);
console.log(`加入权限: ${groupInfo.join_permission}`);
// 根据群类型显示不同的UI样式
if (groupInfo.chat_type === "external") {
console.log("这是一个外部群组");
}
} else {
console.error("获取群信息失败:", response.msg);
}设置群置顶消息
函数签名:
csharp
Task<FeishuNullDataApiResult?> PutChatGroupTopNoticeAsync(
[Path] string chat_id,
[Body] ChatTopNoticeRequest chatTopNoticeRequest,
CancellationToken cancellationToken = default);认证:用户令牌
参数:
| 参数名 | 类型 | 必填 | 含义 | 示例值 |
|---|---|---|---|---|
| chat_id | string | ✅ | 群 ID | "oc_a0553eda9014c201e6969b478895c230" |
| chatTopNoticeRequest | ChatTopNoticeRequest | ✅ | 群置顶操作请求体 | 包含置顶消息或公告信息 |
响应:
json
{
"code": 0,
"msg": "success"
}错误码:
- 33401: 群不存在
- 33403: 无权限设置置顶消息
- 33400: 请求参数错误
说明:
- 使用用户令牌时,只有群主和管理员可以设置置顶消息
- 可以置顶普通消息或群公告
代码示例:
typescript
// 管理员设置群置顶公告示例
const topNoticeRequest = {
message_type: "announcement", // 设置为群公告
content: {
title: "重要通知",
content: "请所有成员注意最新的项目安排..."
}
};
const response = await feishuUserClient.putChatGroupTopNoticeAsync(
"oc_a0553eda9014c201e6969b478895c230",
topNoticeRequest
);
if (response.code === 0) {
console.log("群置顶设置成功");
// 在群聊界面显示置顶内容
} else if (response.code === 33403) {
console.error("权限不足,需要管理员权限");
}取消群置顶消息
函数签名:
csharp
Task<FeishuNullDataApiResult?> DeleteChatGroupTopNoticeAsync(
[Path] string chat_id,
CancellationToken cancellationToken = default);认证:用户令牌
参数:
| 参数名 | 类型 | 必填 | 含义 | 示例值 |
|---|---|---|---|---|
| chat_id | string | ✅ | 群 ID | "oc_a0553eda9014c201e6969b478895c230" |
响应:
json
{
"code": 0,
"msg": "success"
}错误码:
- 33401: 群不存在
- 33403: 无权限取消置顶消息
说明:
- 使用用户令牌时,只有群主和管理员可以取消置顶消息
- 操作会同时清除消息和公告的置顶状态
代码示例:
typescript
// 管理员取消置顶消息示例
const response = await feishuUserClient.deleteChatGroupTopNoticeAsync(
"oc_a0553eda9014c201e6969b478895c230"
);
if (response.code === 0) {
console.log("置顶消息取消成功");
// 更新UI,移除置顶显示
} else if (response.code === 33403) {
console.error("权限不足,需要管理员权限");
} else {
console.error("操作失败:", response.msg);
}获取群列表
函数签名:
csharp
Task<FeishuApiPageListResult<ChatItemInfo>?> GetChatGroupPageListAsync(
[Query("user_id_type")] string user_id_type = Consts.User_Id_Type,
[Query("sort_type")] string sort_type = "ByCreateTimeAsc",
[Query("page_size")] int? page_size = 10,
[Query("page_token")] string? page_token = null,
CancellationToken cancellationToken = default);认证:用户令牌
参数:
| 参数名 | 类型 | 必填 | 含义 | 示例值 |
|---|---|---|---|---|
| user_id_type | string | ⚪ | 用户 ID 类型 | "open_id" |
| sort_type | string | ⚪ | 群组排序方式 | "ByCreateTimeAsc" |
| page_size | int? | ⚪ | 分页大小 | 10 |
| page_token | string? | ⚪ | 分页标记 | null |
响应:
json
{
"code": 0,
"msg": "success",
"data": {
"items": [
{
"chat_id": "oc_a0553eda9014c201e6969b478895c230",
"name": "群聊名称",
"avatar": "avatar_url",
"description": "群描述",
"owner_id": "user_001",
"chat_type": "private",
"external": false,
"is_member": true,
"is_owner": false,
"is_admin": true,
"member_count": 25,
"max_member_count": 500
}
],
"page_token": "next_page_token",
"has_more": true
}
}错误码:
- 33403: 无权限获取群列表
说明:
- 使用用户令牌时,只返回用户所在或可见的群组
- ByCreateTimeAsc:按群组创建时间升序排列
- ByActiveTimeDesc:按群组活跃时间降序排列(可能造成群组遗漏)
代码示例:
typescript
// 用户获取群列表示例
async function loadUserGroups() {
let pageToken = null;
let allGroups = [];
try {
while (true) {
const response = await feishuUserClient.getChatGroupPageListAsync(
"open_id",
"ByActiveTimeDesc", // 按活跃时间排序
50,
pageToken
);
if (response.code === 0) {
const groups = response.data.items;
allGroups = allGroups.concat(groups);
console.log(`获取到 ${groups.length} 个群组,总计 ${allGroups.length} 个`);
if (!response.data.has_more) {
break;
}
pageToken = response.data.page_token;
} else {
console.error("获取群列表失败:", response.msg);
break;
}
}
// 按群类型分类显示
const privateGroups = allGroups.filter(g => g.chat_type === "private");
const externalGroups = allGroups.filter(g => g.external);
console.log(`私有群组: ${privateGroups.length} 个`);
console.log(`外部群组: ${externalGroups.length} 个`);
return allGroups;
} catch (error) {
console.error("加载群列表出错:", error);
return [];
}
}
// 调用示例
loadUserGroups().then(groups => {
// 渲染群组列表UI
renderGroupList(groups);
});关键词搜索群列表
函数签名:
csharp
Task<FeishuApiPageListResult<ChatItemInfo>?> GetChatGroupPageListByKeywordAsync(
[Query("query")] string? query = "",
[Query("user_id_type")] string user_id_type = Consts.User_Id_Type,
[Query("sort_type")] string sort_type = "ByCreateTimeAsc",
[Query("page_size")] int? page_size = 10,
[Query("page_token")] string? page_token = null,
CancellationToken cancellationToken = default);认证:用户令牌
参数:
| 参数名 | 类型 | 必填 | 含义 | 示例值 |
|---|---|---|---|---|
| query | string? | ⚪ | 搜索关键词 | "项目讨论" |
| user_id_type | string | ⚪ | 用户 ID 类型 | "open_id" |
| sort_type | string | ⚪ | 群组排序方式 | "ByCreateTimeAsc" |
| page_size | int? | ⚪ | 分页大小 | 10 |
| page_token | string? | ⚪ | 分页标记 | null |
响应:
json
{
"code": 0,
"msg": "success",
"data": {
"items": [
{
"chat_id": "oc_a0553eda9014c201e6969b478895c230",
"name": "项目讨论群",
"description": "用于项目相关讨论",
"avatar": "avatar_url",
"is_member": true,
"member_count": 15
}
],
"page_token": null,
"has_more": false
}
}错误码:
- 33403: 无权限搜索群组
说明:
- 搜索范围包括用户所在的群和对用户公开的群
- 关键词匹配群名称和描述
代码示例:
typescript
// 用户搜索群组示例
class GroupSearchManager {
constructor(feishuUserClient) {
this.client = feishuUserClient;
this.searchHistory = [];
}
async searchGroups(keyword, pageSize = 20) {
if (!keyword.trim()) {
console.warn("搜索关键词不能为空");
return [];
}
try {
const response = await this.client.getChatGroupPageListByKeywordAsync(
keyword,
"open_id",
"ByActiveTimeDesc",
pageSize
);
if (response.code === 0) {
const groups = response.data.items;
// 记录搜索历史
this.searchHistory.unshift({
keyword,
count: groups.length,
timestamp: Date.now()
});
// 限制搜索历史数量
if (this.searchHistory.length > 10) {
this.searchHistory = this.searchHistory.slice(0, 10);
}
console.log(`搜索"${keyword}"找到 ${groups.length} 个群组`);
return groups;
} else {
console.error("搜索失败:", response.msg);
return [];
}
} catch (error) {
console.error("搜索出错:", error);
return [];
}
}
// 实时搜索(防抖)
createRealtimeSearch(delay = 300) {
let timeoutId;
return (keyword, callback) => {
clearTimeout(timeoutId);
if (!keyword.trim()) {
callback([]);
return;
}
timeoutId = setTimeout(async () => {
const results = await this.searchGroups(keyword);
callback(results);
}, delay);
};
}
}
// 使用示例
const searchManager = new GroupSearchManager(feishuUserClient);
const realtimeSearch = searchManager.createRealtimeSearch();
// 模拟用户输入搜索
const searchInput = document.getElementById('group-search');
searchInput.addEventListener('input', (e) => {
const keyword = e.target.value;
realtimeSearch(keyword, (results) => {
renderSearchResults(results);
});
});获取群发言权限列表
函数签名:
csharp
Task<FeishuApiResult<ChatGroupModeratorPageListResult>?> GetChatGroupModeratorPageListByIdAsync(
[Path] string chat_id,
[Query("user_id_type")] string user_id_type = Consts.User_Id_Type,
[Query("page_size")] int? page_size = 10,
[Query("page_token")] string? page_token = null,
CancellationToken cancellationToken = default);认证:用户令牌
参数:
| 参数名 | 类型 | 必填 | 含义 | 示例值 |
|---|---|---|---|---|
| chat_id | string | ✅ | 群 ID | "oc_a0553eda9014c201e6969b478895c230" |
| user_id_type | string | ⚪ | 用户 ID 类型 | "open_id" |
| page_size | int? | ⚪ | 分页大小 | 10 |
| page_token | string? | ⚪ | 分页标记 | null |
响应:
json
{
"code": 0,
"msg": "success",
"data": {
"speak_permission": "some_members",
"user_ids": ["user_001", "user_002", "user_003"],
"page_token": "next_page_token",
"has_more": false,
"total_count": 3
}
}错误码:
- 33401: 群不存在
- 33403: 无权限查看群权限设置
说明:
- 使用用户令牌时,只有群成员可以查看权限设置
- 返回的数据中包含当前用户是否有发言权限的信息
代码示例:
typescript
// 用户获取群发言权限示例
async function getGroupSpeakPermission(chatId) {
try {
const response = await feishuUserClient.getChatGroupModeratorPageListByIdAsync(
chatId,
"open_id",
100 // 一次获取所有数据
);
if (response.code === 0) {
const moderation = response.data;
console.log(`发言权限模式: ${moderation.speak_permission}`);
// 检查当前用户是否有发言权限
const currentUserId = getCurrentUserId(); // 获取当前用户ID
const canSpeak = checkUserSpeakPermission(
moderation.speak_permission,
moderation.user_ids,
currentUserId
);
console.log(`当前用户发言权限: ${canSpeak ? '有权限' : '无权限'}`);
return {
permission: moderation.speak_permission,
allowedUsers: moderation.user_ids,
userCanSpeak: canSpeak,
totalCount: moderation.total_count
};
} else {
console.error("获取权限失败:", response.msg);
return null;
}
} catch (error) {
console.error("获取权限出错:", error);
return null;
}
}
// 检查用户发言权限的辅助函数
function checkUserSpeakPermission(permissionMode, allowedUsers, userId) {
switch (permissionMode) {
case "all_members":
return true;
case "admin_only":
return isAdmin(userId); // 需要额外检查用户是否为管理员
case "some_members":
return allowedUsers.includes(userId);
default:
return false;
}
}
// 使用示例
getGroupSpeakPermission("oc_a0553eda9014c201e6969b478895c230").then(permission => {
if (permission) {
if (permission.userCanSpeak) {
enableMessageInput();
} else {
disableMessageInput("您没有发言权限");
}
}
});获取群分享链接
函数签名:
csharp
Task<FeishuApiResult<ShareLinkDataResult>?> GetChatGroupShareLinkByIdAsync(
[Path] string chat_id,
[Body] ShareLinkRequest shareLinkRequest,
CancellationToken cancellationToken = default);认证:用户令牌
参数:
| 参数名 | 类型 | 必填 | 含义 | 示例值 |
|---|---|---|---|---|
| chat_id | string | ✅ | 群 ID | "oc_a0553eda9014c201e6969b478895c230" |
| shareLinkRequest | ShareLinkRequest | ✅ | 获取群分享链接请求体 | 包含分享链接配置 |
响应:
json
{
"code": 0,
"msg": "success",
"data": {
"share_link": "https://example.com/join/group/abc123",
"expire_time": 1640995200,
"link_validity_period": 86400,
"qr_code": "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAA..."
}
}说明:
- 使用用户令牌时,只有群主和管理员可以获取分享链接
- 企业管理员可能限制了群组的分享链接功能
- 分享链接可以设置过期时间和访问权限
代码示例:
typescript
// 管理员获取群分享链接示例
class GroupShareManager {
constructor(feishuUserClient) {
this.client = feishuUserClient;
}
async generateShareLink(chatId, options = {}) {
const {
expireSeconds = 604800, // 默认7天
needQrCode = true,
password = null
} = options;
const shareLinkRequest = {
expire_seconds: expireSeconds,
need_qr_code: needQrCode
};
// 如果需要密码保护
if (password) {
shareLinkRequest.password = password;
shareLinkRequest.need_password = true;
}
try {
const response = await this.client.getChatGroupShareLinkByIdAsync(
chatId,
shareLinkRequest
);
if (response.code === 0) {
const linkData = response.data;
return {
shareLink: linkData.share_link,
expireTime: linkData.expire_time,
qrCode: linkData.qr_code,
validityPeriod: linkData.link_validity_period,
password: password
};
} else if (response.code === 33403) {
throw new Error("权限不足,需要群主或管理员权限");
} else if (response.code === 33414) {
throw new Error("该群组不允许生成分享链接");
} else {
throw new Error(response.msg || "生成分享链接失败");
}
} catch (error) {
console.error("生成分享链接出错:", error);
throw error;
}
}
// 复制分享链接到剪贴板
async copyShareLink(chatId, options) {
try {
const linkData = await this.generateShareLink(chatId, options);
// 复制链接到剪贴板
await navigator.clipboard.writeText(linkData.shareLink);
// 显示成功提示
showToast("分享链接已复制到剪贴板");
// 如果需要二维码,显示二维码弹窗
if (linkData.qrCode && options.showQrCode) {
showQrCodeDialog(linkData);
}
return linkData;
} catch (error) {
showToast(error.message, "error");
throw error;
}
}
// 预览分享链接
previewShareLink(chatId) {
// 生成一个短期有效的预览链接
return this.generateShareLink(chatId, {
expireSeconds: 300, // 5分钟有效期
needQrCode: true
});
}
}
// 使用示例
const shareManager = new GroupShareManager(feishuUserClient);
// 生成永久分享链接
shareManager.generateShareLink("oc_a0553eda9014c201e6969b478895c230", {
expireSeconds: 0, // 永久有效
password: "group123",
needQrCode: true
}).then(linkData => {
console.log("分享链接:", linkData.shareLink);
console.log("过期时间:", linkData.expireTime);
if (linkData.qrCode) {
document.getElementById('qr-code').src = linkData.qrCode;
}
}).catch(error => {
console.error("生成分享链接失败:", error);
});
// 一键复制分享链接
document.getElementById('copy-share-link').addEventListener('click', async () => {
await shareManager.copyShareLink("oc_a0553eda9014c201e6969b478895c230", {
expireSeconds: 604800, // 7天
showQrCode: true
});
});