@lark-project/openclaw-lark-project 2026.3.131
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +80 -0
- package/README.zh.md +80 -0
- package/dist/index.js +172 -0
- package/dist/index.js.map +7 -0
- package/dist/skills/feishu-bitable/SKILL.md +248 -0
- package/dist/skills/feishu-bitable/references/examples.md +813 -0
- package/dist/skills/feishu-bitable/references/field-properties.md +763 -0
- package/dist/skills/feishu-bitable/references/record-values.md +911 -0
- package/dist/skills/feishu-calendar/SKILL.md +244 -0
- package/dist/skills/feishu-channel-rules/SKILL.md +18 -0
- package/dist/skills/feishu-channel-rules/references/markdown-syntax.md +138 -0
- package/dist/skills/feishu-create-doc/SKILL.md +719 -0
- package/dist/skills/feishu-fetch-doc/SKILL.md +93 -0
- package/dist/skills/feishu-im-read/SKILL.md +163 -0
- package/dist/skills/feishu-project/SKILL.md +122 -0
- package/dist/skills/feishu-task/SKILL.md +293 -0
- package/dist/skills/feishu-troubleshoot/SKILL.md +70 -0
- package/dist/skills/feishu-update-doc/SKILL.md +285 -0
- package/dist/src/card/builder.js +293 -0
- package/dist/src/card/builder.js.map +7 -0
- package/dist/src/card/cardkit.js +126 -0
- package/dist/src/card/cardkit.js.map +7 -0
- package/dist/src/card/flush-controller.js +107 -0
- package/dist/src/card/flush-controller.js.map +7 -0
- package/dist/src/card/markdown-style.js +57 -0
- package/dist/src/card/markdown-style.js.map +7 -0
- package/dist/src/card/reply-dispatcher-types.js +39 -0
- package/dist/src/card/reply-dispatcher-types.js.map +7 -0
- package/dist/src/card/reply-dispatcher.js +245 -0
- package/dist/src/card/reply-dispatcher.js.map +7 -0
- package/dist/src/card/reply-mode.js +29 -0
- package/dist/src/card/reply-mode.js.map +7 -0
- package/dist/src/card/streaming-card-controller.js +653 -0
- package/dist/src/card/streaming-card-controller.js.map +7 -0
- package/dist/src/card/unavailable-guard.js +76 -0
- package/dist/src/card/unavailable-guard.js.map +7 -0
- package/dist/src/channel/abort-detect.js +79 -0
- package/dist/src/channel/abort-detect.js.map +7 -0
- package/dist/src/channel/chat-queue.js +50 -0
- package/dist/src/channel/chat-queue.js.map +7 -0
- package/dist/src/channel/config-adapter.js +89 -0
- package/dist/src/channel/config-adapter.js.map +7 -0
- package/dist/src/channel/directory.js +133 -0
- package/dist/src/channel/directory.js.map +7 -0
- package/dist/src/channel/event-handlers.js +175 -0
- package/dist/src/channel/event-handlers.js.map +7 -0
- package/dist/src/channel/monitor.js +108 -0
- package/dist/src/channel/monitor.js.map +7 -0
- package/dist/src/channel/onboarding-config.js +76 -0
- package/dist/src/channel/onboarding-config.js.map +7 -0
- package/dist/src/channel/onboarding-migrate.js +55 -0
- package/dist/src/channel/onboarding-migrate.js.map +7 -0
- package/dist/src/channel/onboarding.js +285 -0
- package/dist/src/channel/onboarding.js.map +7 -0
- package/dist/src/channel/plugin.js +260 -0
- package/dist/src/channel/plugin.js.map +7 -0
- package/dist/src/channel/probe.js +14 -0
- package/dist/src/channel/probe.js.map +7 -0
- package/dist/src/channel/types.js +1 -0
- package/dist/src/channel/types.js.map +7 -0
- package/dist/src/commands/auth.js +73 -0
- package/dist/src/commands/auth.js.map +7 -0
- package/dist/src/commands/diagnose.js +658 -0
- package/dist/src/commands/diagnose.js.map +7 -0
- package/dist/src/commands/doctor.js +327 -0
- package/dist/src/commands/doctor.js.map +7 -0
- package/dist/src/commands/index.js +124 -0
- package/dist/src/commands/index.js.map +7 -0
- package/dist/src/core/accounts.js +129 -0
- package/dist/src/core/accounts.js.map +7 -0
- package/dist/src/core/agent-config.js +60 -0
- package/dist/src/core/agent-config.js.map +7 -0
- package/dist/src/core/api-error.js +55 -0
- package/dist/src/core/api-error.js.map +7 -0
- package/dist/src/core/app-owner-fallback.js +17 -0
- package/dist/src/core/app-owner-fallback.js.map +7 -0
- package/dist/src/core/app-scope-checker.js +95 -0
- package/dist/src/core/app-scope-checker.js.map +7 -0
- package/dist/src/core/auth-errors.js +120 -0
- package/dist/src/core/auth-errors.js.map +7 -0
- package/dist/src/core/chat-info-cache.js +102 -0
- package/dist/src/core/chat-info-cache.js.map +7 -0
- package/dist/src/core/config-schema.js +150 -0
- package/dist/src/core/config-schema.js.map +7 -0
- package/dist/src/core/device-flow.js +174 -0
- package/dist/src/core/device-flow.js.map +7 -0
- package/dist/src/core/feishu-fetch.js +12 -0
- package/dist/src/core/feishu-fetch.js.map +7 -0
- package/dist/src/core/footer-config.js +16 -0
- package/dist/src/core/footer-config.js.map +7 -0
- package/dist/src/core/lark-client.js +322 -0
- package/dist/src/core/lark-client.js.map +7 -0
- package/dist/src/core/lark-logger.js +92 -0
- package/dist/src/core/lark-logger.js.map +7 -0
- package/dist/src/core/lark-ticket.js +18 -0
- package/dist/src/core/lark-ticket.js.map +7 -0
- package/dist/src/core/message-unavailable.js +119 -0
- package/dist/src/core/message-unavailable.js.map +7 -0
- package/dist/src/core/owner-policy.js +25 -0
- package/dist/src/core/owner-policy.js.map +7 -0
- package/dist/src/core/permission-url.js +37 -0
- package/dist/src/core/permission-url.js.map +7 -0
- package/dist/src/core/project-auth.js +177 -0
- package/dist/src/core/project-auth.js.map +7 -0
- package/dist/src/core/project-oauth-flow.js +124 -0
- package/dist/src/core/project-oauth-flow.js.map +7 -0
- package/dist/src/core/project-token-store.js +172 -0
- package/dist/src/core/project-token-store.js.map +7 -0
- package/dist/src/core/raw-request.js +45 -0
- package/dist/src/core/raw-request.js.map +7 -0
- package/dist/src/core/scope-manager.js +62 -0
- package/dist/src/core/scope-manager.js.map +7 -0
- package/dist/src/core/security-check.js +118 -0
- package/dist/src/core/security-check.js.map +7 -0
- package/dist/src/core/shutdown-hooks.js +37 -0
- package/dist/src/core/shutdown-hooks.js.map +7 -0
- package/dist/src/core/targets.js +55 -0
- package/dist/src/core/targets.js.map +7 -0
- package/dist/src/core/token-store.js +215 -0
- package/dist/src/core/token-store.js.map +7 -0
- package/dist/src/core/tool-client.js +335 -0
- package/dist/src/core/tool-client.js.map +7 -0
- package/dist/src/core/tool-scopes.js +207 -0
- package/dist/src/core/tool-scopes.js.map +7 -0
- package/dist/src/core/tools-config.js +57 -0
- package/dist/src/core/tools-config.js.map +7 -0
- package/dist/src/core/types.js +1 -0
- package/dist/src/core/types.js.map +7 -0
- package/dist/src/core/uat-client.js +124 -0
- package/dist/src/core/uat-client.js.map +7 -0
- package/dist/src/core/version.js +27 -0
- package/dist/src/core/version.js.map +7 -0
- package/dist/src/messaging/converters/audio.js +19 -0
- package/dist/src/messaging/converters/audio.js.map +7 -0
- package/dist/src/messaging/converters/calendar.js +46 -0
- package/dist/src/messaging/converters/calendar.js.map +7 -0
- package/dist/src/messaging/converters/content-converter.js +61 -0
- package/dist/src/messaging/converters/content-converter.js.map +7 -0
- package/dist/src/messaging/converters/file.js +18 -0
- package/dist/src/messaging/converters/file.js.map +7 -0
- package/dist/src/messaging/converters/folder.js +18 -0
- package/dist/src/messaging/converters/folder.js.map +7 -0
- package/dist/src/messaging/converters/hongbao.js +14 -0
- package/dist/src/messaging/converters/hongbao.js.map +7 -0
- package/dist/src/messaging/converters/image.js +16 -0
- package/dist/src/messaging/converters/image.js.map +7 -0
- package/dist/src/messaging/converters/index.js +48 -0
- package/dist/src/messaging/converters/index.js.map +7 -0
- package/dist/src/messaging/converters/interactive/card-converter.js +1040 -0
- package/dist/src/messaging/converters/interactive/card-converter.js.map +7 -0
- package/dist/src/messaging/converters/interactive/card-utils.js +36 -0
- package/dist/src/messaging/converters/interactive/card-utils.js.map +7 -0
- package/dist/src/messaging/converters/interactive/index.js +19 -0
- package/dist/src/messaging/converters/interactive/index.js.map +7 -0
- package/dist/src/messaging/converters/interactive/legacy.js +53 -0
- package/dist/src/messaging/converters/interactive/legacy.js.map +7 -0
- package/dist/src/messaging/converters/interactive/types.js +23 -0
- package/dist/src/messaging/converters/interactive/types.js.map +7 -0
- package/dist/src/messaging/converters/location.js +17 -0
- package/dist/src/messaging/converters/location.js.map +7 -0
- package/dist/src/messaging/converters/merge-forward.js +143 -0
- package/dist/src/messaging/converters/merge-forward.js.map +7 -0
- package/dist/src/messaging/converters/post.js +113 -0
- package/dist/src/messaging/converters/post.js.map +7 -0
- package/dist/src/messaging/converters/share.js +22 -0
- package/dist/src/messaging/converters/share.js.map +7 -0
- package/dist/src/messaging/converters/sticker.js +16 -0
- package/dist/src/messaging/converters/sticker.js.map +7 -0
- package/dist/src/messaging/converters/system.js +25 -0
- package/dist/src/messaging/converters/system.js.map +7 -0
- package/dist/src/messaging/converters/text.js +12 -0
- package/dist/src/messaging/converters/text.js.map +7 -0
- package/dist/src/messaging/converters/todo.js +37 -0
- package/dist/src/messaging/converters/todo.js.map +7 -0
- package/dist/src/messaging/converters/types.js +1 -0
- package/dist/src/messaging/converters/types.js.map +7 -0
- package/dist/src/messaging/converters/unknown.js +13 -0
- package/dist/src/messaging/converters/unknown.js.map +7 -0
- package/dist/src/messaging/converters/utils.js +35 -0
- package/dist/src/messaging/converters/utils.js.map +7 -0
- package/dist/src/messaging/converters/video-chat.js +21 -0
- package/dist/src/messaging/converters/video-chat.js.map +7 -0
- package/dist/src/messaging/converters/video.js +30 -0
- package/dist/src/messaging/converters/video.js.map +7 -0
- package/dist/src/messaging/converters/vote.js +24 -0
- package/dist/src/messaging/converters/vote.js.map +7 -0
- package/dist/src/messaging/inbound/dedup.js +82 -0
- package/dist/src/messaging/inbound/dedup.js.map +7 -0
- package/dist/src/messaging/inbound/dispatch-builders.js +98 -0
- package/dist/src/messaging/inbound/dispatch-builders.js.map +7 -0
- package/dist/src/messaging/inbound/dispatch-commands.js +94 -0
- package/dist/src/messaging/inbound/dispatch-commands.js.map +7 -0
- package/dist/src/messaging/inbound/dispatch-context.js +96 -0
- package/dist/src/messaging/inbound/dispatch-context.js.map +7 -0
- package/dist/src/messaging/inbound/dispatch.js +150 -0
- package/dist/src/messaging/inbound/dispatch.js.map +7 -0
- package/dist/src/messaging/inbound/enrich.js +137 -0
- package/dist/src/messaging/inbound/enrich.js.map +7 -0
- package/dist/src/messaging/inbound/gate-effects.js +28 -0
- package/dist/src/messaging/inbound/gate-effects.js.map +7 -0
- package/dist/src/messaging/inbound/gate.js +163 -0
- package/dist/src/messaging/inbound/gate.js.map +7 -0
- package/dist/src/messaging/inbound/handler.js +132 -0
- package/dist/src/messaging/inbound/handler.js.map +7 -0
- package/dist/src/messaging/inbound/media-resolver.js +70 -0
- package/dist/src/messaging/inbound/media-resolver.js.map +7 -0
- package/dist/src/messaging/inbound/mention.js +50 -0
- package/dist/src/messaging/inbound/mention.js.map +7 -0
- package/dist/src/messaging/inbound/parse-io.js +41 -0
- package/dist/src/messaging/inbound/parse-io.js.map +7 -0
- package/dist/src/messaging/inbound/parse.js +79 -0
- package/dist/src/messaging/inbound/parse.js.map +7 -0
- package/dist/src/messaging/inbound/permission.js +30 -0
- package/dist/src/messaging/inbound/permission.js.map +7 -0
- package/dist/src/messaging/inbound/policy.js +83 -0
- package/dist/src/messaging/inbound/policy.js.map +7 -0
- package/dist/src/messaging/inbound/reaction-handler.js +162 -0
- package/dist/src/messaging/inbound/reaction-handler.js.map +7 -0
- package/dist/src/messaging/inbound/user-name-cache.js +172 -0
- package/dist/src/messaging/inbound/user-name-cache.js.map +7 -0
- package/dist/src/messaging/outbound/actions.js +239 -0
- package/dist/src/messaging/outbound/actions.js.map +7 -0
- package/dist/src/messaging/outbound/chat-manage.js +74 -0
- package/dist/src/messaging/outbound/chat-manage.js.map +7 -0
- package/dist/src/messaging/outbound/deliver.js +162 -0
- package/dist/src/messaging/outbound/deliver.js.map +7 -0
- package/dist/src/messaging/outbound/fetch.js +7 -0
- package/dist/src/messaging/outbound/fetch.js.map +7 -0
- package/dist/src/messaging/outbound/forward.js +31 -0
- package/dist/src/messaging/outbound/forward.js.map +7 -0
- package/dist/src/messaging/outbound/media-url-utils.js +101 -0
- package/dist/src/messaging/outbound/media-url-utils.js.map +7 -0
- package/dist/src/messaging/outbound/media.js +463 -0
- package/dist/src/messaging/outbound/media.js.map +7 -0
- package/dist/src/messaging/outbound/outbound.js +95 -0
- package/dist/src/messaging/outbound/outbound.js.map +7 -0
- package/dist/src/messaging/outbound/reactions.js +312 -0
- package/dist/src/messaging/outbound/reactions.js.map +7 -0
- package/dist/src/messaging/outbound/send.js +194 -0
- package/dist/src/messaging/outbound/send.js.map +7 -0
- package/dist/src/messaging/outbound/typing.js +77 -0
- package/dist/src/messaging/outbound/typing.js.map +7 -0
- package/dist/src/messaging/shared/message-lookup.js +84 -0
- package/dist/src/messaging/shared/message-lookup.js.map +7 -0
- package/dist/src/messaging/types.js +1 -0
- package/dist/src/messaging/types.js.map +7 -0
- package/dist/src/tools/auto-auth.js +714 -0
- package/dist/src/tools/auto-auth.js.map +7 -0
- package/dist/src/tools/helpers.js +133 -0
- package/dist/src/tools/helpers.js.map +7 -0
- package/dist/src/tools/mcp/doc/create.js +35 -0
- package/dist/src/tools/mcp/doc/create.js.map +7 -0
- package/dist/src/tools/mcp/doc/fetch.js +33 -0
- package/dist/src/tools/mcp/doc/fetch.js.map +7 -0
- package/dist/src/tools/mcp/doc/index.js +32 -0
- package/dist/src/tools/mcp/doc/index.js.map +7 -0
- package/dist/src/tools/mcp/doc/update.js +61 -0
- package/dist/src/tools/mcp/doc/update.js.map +7 -0
- package/dist/src/tools/mcp/project/endpoint.js +25 -0
- package/dist/src/tools/mcp/project/endpoint.js.map +7 -0
- package/dist/src/tools/mcp/project/index.js +27 -0
- package/dist/src/tools/mcp/project/index.js.map +7 -0
- package/dist/src/tools/mcp/project/tools.js +579 -0
- package/dist/src/tools/mcp/project/tools.js.map +7 -0
- package/dist/src/tools/mcp/shared.js +170 -0
- package/dist/src/tools/mcp/shared.js.map +7 -0
- package/dist/src/tools/oapi/bitable/app-table-field.js +244 -0
- package/dist/src/tools/oapi/bitable/app-table-field.js.map +7 -0
- package/dist/src/tools/oapi/bitable/app-table-record.js +501 -0
- package/dist/src/tools/oapi/bitable/app-table-record.js.map +7 -0
- package/dist/src/tools/oapi/bitable/app-table-view.js +226 -0
- package/dist/src/tools/oapi/bitable/app-table-view.js.map +7 -0
- package/dist/src/tools/oapi/bitable/app-table.js +278 -0
- package/dist/src/tools/oapi/bitable/app-table.js.map +7 -0
- package/dist/src/tools/oapi/bitable/app.js +200 -0
- package/dist/src/tools/oapi/bitable/app.js.map +7 -0
- package/dist/src/tools/oapi/bitable/index.js +13 -0
- package/dist/src/tools/oapi/bitable/index.js.map +7 -0
- package/dist/src/tools/oapi/calendar/calendar.js +131 -0
- package/dist/src/tools/oapi/calendar/calendar.js.map +7 -0
- package/dist/src/tools/oapi/calendar/event-attendee.js +301 -0
- package/dist/src/tools/oapi/calendar/event-attendee.js.map +7 -0
- package/dist/src/tools/oapi/calendar/event.js +834 -0
- package/dist/src/tools/oapi/calendar/event.js.map +7 -0
- package/dist/src/tools/oapi/calendar/freebusy.js +111 -0
- package/dist/src/tools/oapi/calendar/freebusy.js.map +7 -0
- package/dist/src/tools/oapi/calendar/index.js +11 -0
- package/dist/src/tools/oapi/calendar/index.js.map +7 -0
- package/dist/src/tools/oapi/chat/chat.js +132 -0
- package/dist/src/tools/oapi/chat/chat.js.map +7 -0
- package/dist/src/tools/oapi/chat/index.js +11 -0
- package/dist/src/tools/oapi/chat/index.js.map +7 -0
- package/dist/src/tools/oapi/chat/members.js +83 -0
- package/dist/src/tools/oapi/chat/members.js.map +7 -0
- package/dist/src/tools/oapi/common/get-user.js +95 -0
- package/dist/src/tools/oapi/common/get-user.js.map +7 -0
- package/dist/src/tools/oapi/common/index.js +7 -0
- package/dist/src/tools/oapi/common/index.js.map +7 -0
- package/dist/src/tools/oapi/common/search-user.js +67 -0
- package/dist/src/tools/oapi/common/search-user.js.map +7 -0
- package/dist/src/tools/oapi/drive/doc-comments.js +310 -0
- package/dist/src/tools/oapi/drive/doc-comments.js.map +7 -0
- package/dist/src/tools/oapi/drive/doc-media.js +314 -0
- package/dist/src/tools/oapi/drive/doc-media.js.map +7 -0
- package/dist/src/tools/oapi/drive/file.js +548 -0
- package/dist/src/tools/oapi/drive/file.js.map +7 -0
- package/dist/src/tools/oapi/drive/index.js +29 -0
- package/dist/src/tools/oapi/drive/index.js.map +7 -0
- package/dist/src/tools/oapi/helpers.js +199 -0
- package/dist/src/tools/oapi/helpers.js.map +7 -0
- package/dist/src/tools/oapi/im/format-messages.js +128 -0
- package/dist/src/tools/oapi/im/format-messages.js.map +7 -0
- package/dist/src/tools/oapi/im/index.js +15 -0
- package/dist/src/tools/oapi/im/index.js.map +7 -0
- package/dist/src/tools/oapi/im/message-read.js +404 -0
- package/dist/src/tools/oapi/im/message-read.js.map +7 -0
- package/dist/src/tools/oapi/im/message.js +179 -0
- package/dist/src/tools/oapi/im/message.js.map +7 -0
- package/dist/src/tools/oapi/im/resource.js +126 -0
- package/dist/src/tools/oapi/im/resource.js.map +7 -0
- package/dist/src/tools/oapi/im/time-utils.js +169 -0
- package/dist/src/tools/oapi/im/time-utils.js.map +7 -0
- package/dist/src/tools/oapi/im/user-name-uat.js +103 -0
- package/dist/src/tools/oapi/im/user-name-uat.js.map +7 -0
- package/dist/src/tools/oapi/index.js +56 -0
- package/dist/src/tools/oapi/index.js.map +7 -0
- package/dist/src/tools/oapi/sdk-types.js +1 -0
- package/dist/src/tools/oapi/sdk-types.js.map +7 -0
- package/dist/src/tools/oapi/search/doc-search.js +215 -0
- package/dist/src/tools/oapi/search/doc-search.js.map +7 -0
- package/dist/src/tools/oapi/search/index.js +25 -0
- package/dist/src/tools/oapi/search/index.js.map +7 -0
- package/dist/src/tools/oapi/sheets/index.js +25 -0
- package/dist/src/tools/oapi/sheets/index.js.map +7 -0
- package/dist/src/tools/oapi/sheets/sheet.js +652 -0
- package/dist/src/tools/oapi/sheets/sheet.js.map +7 -0
- package/dist/src/tools/oapi/task/comment.js +151 -0
- package/dist/src/tools/oapi/task/comment.js.map +7 -0
- package/dist/src/tools/oapi/task/index.js +11 -0
- package/dist/src/tools/oapi/task/index.js.map +7 -0
- package/dist/src/tools/oapi/task/subtask.js +175 -0
- package/dist/src/tools/oapi/task/subtask.js.map +7 -0
- package/dist/src/tools/oapi/task/task.js +405 -0
- package/dist/src/tools/oapi/task/task.js.map +7 -0
- package/dist/src/tools/oapi/task/tasklist.js +366 -0
- package/dist/src/tools/oapi/task/tasklist.js.map +7 -0
- package/dist/src/tools/oapi/wiki/index.js +27 -0
- package/dist/src/tools/oapi/wiki/index.js.map +7 -0
- package/dist/src/tools/oapi/wiki/space-node.js +311 -0
- package/dist/src/tools/oapi/wiki/space-node.js.map +7 -0
- package/dist/src/tools/oapi/wiki/space.js +148 -0
- package/dist/src/tools/oapi/wiki/space.js.map +7 -0
- package/dist/src/tools/oauth-batch-auth.js +125 -0
- package/dist/src/tools/oauth-batch-auth.js.map +7 -0
- package/dist/src/tools/oauth-cards.js +269 -0
- package/dist/src/tools/oauth-cards.js.map +7 -0
- package/dist/src/tools/oauth.js +538 -0
- package/dist/src/tools/oauth.js.map +7 -0
- package/dist/src/tools/onboarding-auth.js +101 -0
- package/dist/src/tools/onboarding-auth.js.map +7 -0
- package/dist/src/tools/project-oauth.js +305 -0
- package/dist/src/tools/project-oauth.js.map +7 -0
- package/dist/src/tools/tat/im/index.js +9 -0
- package/dist/src/tools/tat/im/index.js.map +7 -0
- package/dist/src/tools/tat/im/resource.js +123 -0
- package/dist/src/tools/tat/im/resource.js.map +7 -0
- package/package.json +64 -0
|
@@ -0,0 +1,207 @@
|
|
|
1
|
+
const TOOL_SCOPES = {
|
|
2
|
+
"feishu_bitable_app.create": ["base:app:create"],
|
|
3
|
+
"feishu_bitable_app.get": ["base:app:read"],
|
|
4
|
+
"feishu_bitable_app.list": ["space:document:retrieve"],
|
|
5
|
+
"feishu_bitable_app.patch": ["base:app:update"],
|
|
6
|
+
"feishu_bitable_app.copy": ["base:app:copy"],
|
|
7
|
+
"feishu_bitable_app_table.create": ["base:table:create"],
|
|
8
|
+
"feishu_bitable_app_table.list": ["base:table:read"],
|
|
9
|
+
"feishu_bitable_app_table.patch": ["base:table:update"],
|
|
10
|
+
"feishu_bitable_app_table.delete": ["base:table:delete"],
|
|
11
|
+
"feishu_bitable_app_table.batch_create": ["base:table:create"],
|
|
12
|
+
"feishu_bitable_app_table.batch_delete": ["base:table:delete"],
|
|
13
|
+
"feishu_bitable_app_table_record.create": ["base:record:create"],
|
|
14
|
+
"feishu_bitable_app_table_record.update": ["base:record:update"],
|
|
15
|
+
"feishu_bitable_app_table_record.delete": ["base:record:delete"],
|
|
16
|
+
"feishu_bitable_app_table_record.batch_create": ["base:record:create"],
|
|
17
|
+
"feishu_bitable_app_table_record.batch_update": ["base:record:update"],
|
|
18
|
+
"feishu_bitable_app_table_record.batch_delete": ["base:record:delete"],
|
|
19
|
+
"feishu_bitable_app_table_record.list": ["base:record:retrieve"],
|
|
20
|
+
"feishu_bitable_app_table_field.create": ["base:field:create"],
|
|
21
|
+
"feishu_bitable_app_table_field.list": ["base:field:read"],
|
|
22
|
+
"feishu_bitable_app_table_field.update": ["base:field:read", "base:field:update"],
|
|
23
|
+
"feishu_bitable_app_table_field.delete": ["base:field:delete"],
|
|
24
|
+
"feishu_bitable_app_table_view.create": ["base:view:write_only"],
|
|
25
|
+
"feishu_bitable_app_table_view.get": ["base:view:read"],
|
|
26
|
+
"feishu_bitable_app_table_view.list": ["base:view:read"],
|
|
27
|
+
"feishu_bitable_app_table_view.patch": ["base:view:write_only"],
|
|
28
|
+
"feishu_bitable_app_table_view.delete": ["base:view:write_only"],
|
|
29
|
+
"feishu_calendar_calendar.list": ["calendar:calendar:read"],
|
|
30
|
+
"feishu_calendar_calendar.get": ["calendar:calendar:read"],
|
|
31
|
+
"feishu_calendar_calendar.primary": ["calendar:calendar:read"],
|
|
32
|
+
"feishu_calendar_event.create": ["calendar:calendar.event:create", "calendar:calendar.event:update"],
|
|
33
|
+
"feishu_calendar_event.list": ["calendar:calendar.event:read"],
|
|
34
|
+
"feishu_calendar_event.get": ["calendar:calendar.event:read"],
|
|
35
|
+
"feishu_calendar_event.patch": ["calendar:calendar.event:update"],
|
|
36
|
+
"feishu_calendar_event.delete": ["calendar:calendar.event:delete"],
|
|
37
|
+
"feishu_calendar_event.search": ["calendar:calendar.event:read"],
|
|
38
|
+
"feishu_calendar_event.reply": ["calendar:calendar.event:reply"],
|
|
39
|
+
"feishu_calendar_event.instances": ["calendar:calendar.event:read"],
|
|
40
|
+
"feishu_calendar_event.instance_view": ["calendar:calendar.event:read"],
|
|
41
|
+
"feishu_calendar_event_attendee.create": ["calendar:calendar.event:update"],
|
|
42
|
+
"feishu_calendar_event_attendee.list": ["calendar:calendar.event:read"],
|
|
43
|
+
"feishu_calendar_event_attendee.batch_delete": ["calendar:calendar.event:read", "calendar:calendar.event:update"],
|
|
44
|
+
"feishu_calendar_freebusy.list": ["calendar:calendar.free_busy:read"],
|
|
45
|
+
"feishu_task_task.create": ["task:task:write", "task:task:writeonly"],
|
|
46
|
+
"feishu_task_task.get": ["task:task:read", "task:task:write"],
|
|
47
|
+
"feishu_task_task.list": ["task:task:read", "task:task:write"],
|
|
48
|
+
"feishu_task_task.patch": ["task:task:write", "task:task:writeonly"],
|
|
49
|
+
"feishu_task_tasklist.create": ["task:tasklist:write"],
|
|
50
|
+
"feishu_task_tasklist.get": ["task:tasklist:read", "task:tasklist:write"],
|
|
51
|
+
"feishu_task_tasklist.list": ["task:tasklist:read", "task:tasklist:write"],
|
|
52
|
+
"feishu_task_tasklist.tasks": ["task:tasklist:read", "task:tasklist:write"],
|
|
53
|
+
"feishu_task_tasklist.patch": ["task:tasklist:write"],
|
|
54
|
+
"feishu_task_tasklist.delete": ["task:tasklist:write"],
|
|
55
|
+
"feishu_task_tasklist.add_members": ["task:tasklist:write"],
|
|
56
|
+
"feishu_task_tasklist.remove_members": ["task:tasklist:write"],
|
|
57
|
+
"feishu_task_comment.create": ["task:comment:write"],
|
|
58
|
+
"feishu_task_comment.list": ["task:comment:read", "task:comment:write"],
|
|
59
|
+
"feishu_task_comment.get": ["task:comment:read", "task:comment:write"],
|
|
60
|
+
"feishu_task_subtask.create": ["task:task:write"],
|
|
61
|
+
"feishu_task_subtask.list": ["task:task:read", "task:task:write"],
|
|
62
|
+
"feishu_chat.search": ["im:chat:read"],
|
|
63
|
+
"feishu_chat.get": ["im:chat:read"],
|
|
64
|
+
"feishu_chat_members.default": ["im:chat.members:read"],
|
|
65
|
+
"feishu_drive_file.list": ["space:document:retrieve"],
|
|
66
|
+
"feishu_drive_file.get_meta": ["drive:drive.metadata:readonly"],
|
|
67
|
+
"feishu_drive_file.copy": ["docs:document:copy"],
|
|
68
|
+
"feishu_drive_file.move": ["space:document:move"],
|
|
69
|
+
"feishu_drive_file.delete": ["space:document:delete"],
|
|
70
|
+
"feishu_drive_file.upload": ["drive:file:upload"],
|
|
71
|
+
"feishu_drive_file.download": ["drive:file:download"],
|
|
72
|
+
"feishu_doc_media.download": ["board:whiteboard:node:read", "docs:document.media:download"],
|
|
73
|
+
"feishu_doc_media.insert": ["docx:document:write_only", "docs:document.media:upload"],
|
|
74
|
+
"feishu_doc_comments.list": ["wiki:node:read", "docs:document.comment:read"],
|
|
75
|
+
"feishu_doc_comments.create": ["wiki:node:read", "docs:document.comment:create"],
|
|
76
|
+
"feishu_doc_comments.patch": ["docs:document.comment:update"],
|
|
77
|
+
"feishu_wiki_space.list": ["wiki:space:retrieve"],
|
|
78
|
+
"feishu_wiki_space.get": ["wiki:space:read"],
|
|
79
|
+
"feishu_wiki_space.create": ["wiki:space:write_only"],
|
|
80
|
+
"feishu_wiki_space_node.list": ["wiki:node:retrieve"],
|
|
81
|
+
"feishu_wiki_space_node.get": ["wiki:node:read"],
|
|
82
|
+
"feishu_wiki_space_node.create": ["wiki:node:create"],
|
|
83
|
+
"feishu_wiki_space_node.move": ["wiki:node:move"],
|
|
84
|
+
"feishu_wiki_space_node.copy": ["wiki:node:copy"],
|
|
85
|
+
"feishu_im_user_message.send": ["im:message", "im:message.send_as_user"],
|
|
86
|
+
"feishu_im_user_message.reply": ["im:message", "im:message.send_as_user"],
|
|
87
|
+
"feishu_im_user_fetch_resource.default": [
|
|
88
|
+
"im:message.group_msg:get_as_user",
|
|
89
|
+
"im:message.p2p_msg:get_as_user",
|
|
90
|
+
"im:message:readonly"
|
|
91
|
+
],
|
|
92
|
+
"feishu_im_user_get_messages.default": [
|
|
93
|
+
"im:chat:read",
|
|
94
|
+
"im:message:readonly",
|
|
95
|
+
"im:message.group_msg:get_as_user",
|
|
96
|
+
"im:message.p2p_msg:get_as_user",
|
|
97
|
+
"contact:contact.base:readonly",
|
|
98
|
+
"contact:user.base:readonly"
|
|
99
|
+
],
|
|
100
|
+
"feishu_im_user_search_messages.default": [
|
|
101
|
+
"im:chat:read",
|
|
102
|
+
"im:message:readonly",
|
|
103
|
+
"im:message.group_msg:get_as_user",
|
|
104
|
+
"im:message.p2p_msg:get_as_user",
|
|
105
|
+
"contact:contact.base:readonly",
|
|
106
|
+
"contact:user.base:readonly",
|
|
107
|
+
"search:message"
|
|
108
|
+
],
|
|
109
|
+
"feishu_search_doc_wiki.search": ["search:docs:read"],
|
|
110
|
+
"feishu_get_user.default": ["contact:contact.base:readonly", "contact:user.base:readonly"],
|
|
111
|
+
"feishu_search_user.default": ["contact:user:search"],
|
|
112
|
+
"feishu_create_doc.default": [
|
|
113
|
+
"board:whiteboard:node:create",
|
|
114
|
+
"docx:document:create",
|
|
115
|
+
"docx:document:readonly",
|
|
116
|
+
"docx:document:write_only",
|
|
117
|
+
"wiki:node:create",
|
|
118
|
+
"wiki:node:read",
|
|
119
|
+
"docs:document.media:upload"
|
|
120
|
+
],
|
|
121
|
+
"feishu_fetch_doc.default": ["docx:document:readonly", "wiki:node:read"],
|
|
122
|
+
"feishu_update_doc.default": [
|
|
123
|
+
"board:whiteboard:node:create",
|
|
124
|
+
"docx:document:create",
|
|
125
|
+
"docx:document:readonly",
|
|
126
|
+
"docx:document:write_only"
|
|
127
|
+
],
|
|
128
|
+
"feishu_sheet.info": ["sheets:spreadsheet.meta:read", "sheets:spreadsheet:read"],
|
|
129
|
+
"feishu_sheet.read": ["sheets:spreadsheet.meta:read", "sheets:spreadsheet:read"],
|
|
130
|
+
"feishu_sheet.write": [
|
|
131
|
+
"sheets:spreadsheet.meta:read",
|
|
132
|
+
"sheets:spreadsheet:read",
|
|
133
|
+
"sheets:spreadsheet:create",
|
|
134
|
+
"sheets:spreadsheet:write_only"
|
|
135
|
+
],
|
|
136
|
+
"feishu_sheet.append": [
|
|
137
|
+
"sheets:spreadsheet.meta:read",
|
|
138
|
+
"sheets:spreadsheet:read",
|
|
139
|
+
"sheets:spreadsheet:create",
|
|
140
|
+
"sheets:spreadsheet:write_only"
|
|
141
|
+
],
|
|
142
|
+
"feishu_sheet.find": ["sheets:spreadsheet.meta:read", "sheets:spreadsheet:read"],
|
|
143
|
+
"feishu_sheet.create": [
|
|
144
|
+
"sheets:spreadsheet.meta:read",
|
|
145
|
+
"sheets:spreadsheet:read",
|
|
146
|
+
"sheets:spreadsheet:create",
|
|
147
|
+
"sheets:spreadsheet:write_only"
|
|
148
|
+
],
|
|
149
|
+
"feishu_sheet.export": ["docs:document:export"]
|
|
150
|
+
};
|
|
151
|
+
const REQUIRED_APP_SCOPES = [
|
|
152
|
+
"contact:contact.base:readonly",
|
|
153
|
+
"docx:document:readonly",
|
|
154
|
+
"im:chat:read",
|
|
155
|
+
"im:chat:update",
|
|
156
|
+
"im:message.group_at_msg:readonly",
|
|
157
|
+
"im:message.p2p_msg:readonly",
|
|
158
|
+
"im:message.pins:read",
|
|
159
|
+
"im:message.pins:write_only",
|
|
160
|
+
"im:message.reactions:read",
|
|
161
|
+
"im:message.reactions:write_only",
|
|
162
|
+
"im:message:readonly",
|
|
163
|
+
"im:message:recall",
|
|
164
|
+
"im:message:send_as_bot",
|
|
165
|
+
"im:message:send_multi_users",
|
|
166
|
+
"im:message:send_sys_msg",
|
|
167
|
+
"im:message:update",
|
|
168
|
+
"im:resource",
|
|
169
|
+
"application:application:self_manage",
|
|
170
|
+
"cardkit:card:write",
|
|
171
|
+
"cardkit:card:read"
|
|
172
|
+
];
|
|
173
|
+
const REQUIRED_SCOPE_DESCRIPTIONS = {
|
|
174
|
+
"contact:contact.base:readonly": "\u83B7\u53D6\u7528\u6237\u57FA\u672C\u4FE1\u606F\uFF08\u59D3\u540D\u3001\u5934\u50CF\uFF09",
|
|
175
|
+
"docx:document:readonly": "\u8BFB\u53D6\u6587\u6863\u5185\u5BB9\u3001\u9884\u89C8\u6587\u6863\u94FE\u63A5",
|
|
176
|
+
"im:chat:read": "\u8BFB\u53D6\u7FA4\u804A\u4FE1\u606F\u3001\u83B7\u53D6\u7FA4\u6210\u5458\u5217\u8868",
|
|
177
|
+
"im:chat:update": "\u4FEE\u6539\u7FA4\u804A\u8BBE\u7F6E\uFF08\u7FA4\u540D\u79F0\u3001\u7FA4\u516C\u544A\u7B49\uFF09",
|
|
178
|
+
"im:message.group_at_msg:readonly": "\u63A5\u6536\u7FA4\u804A\u4E2D @ \u673A\u5668\u4EBA\u7684\u6D88\u606F",
|
|
179
|
+
"im:message.p2p_msg:readonly": "\u63A5\u6536\u79C1\u804A\u6D88\u606F",
|
|
180
|
+
"im:message.pins:read": "\u8BFB\u53D6\u6D88\u606F\u7F6E\u9876\u72B6\u6001",
|
|
181
|
+
"im:message.pins:write_only": "\u7F6E\u9876/\u53D6\u6D88\u7F6E\u9876\u6D88\u606F",
|
|
182
|
+
"im:message.reactions:read": "\u8BFB\u53D6\u6D88\u606F\u8868\u60C5\u56DE\u590D",
|
|
183
|
+
"im:message.reactions:write_only": "\u6DFB\u52A0/\u5220\u9664\u6D88\u606F\u8868\u60C5\u56DE\u590D",
|
|
184
|
+
"im:message:readonly": "\u8BFB\u53D6\u6D88\u606F\u5185\u5BB9\u3001\u5386\u53F2\u6D88\u606F",
|
|
185
|
+
"im:message:recall": "\u21A9\u64A4\u56DE\u673A\u5668\u4EBA\u53D1\u9001\u7684\u6D88\u606F",
|
|
186
|
+
"im:message:send_as_bot": "\u4EE5\u673A\u5668\u4EBA\u8EAB\u4EFD\u53D1\u9001\u6D88\u606F",
|
|
187
|
+
"im:message:send_multi_users": "\u6279\u91CF\u53D1\u9001\u79C1\u804A\u6D88\u606F",
|
|
188
|
+
"im:message:send_sys_msg": "\u53D1\u9001\u7CFB\u7EDF\u901A\u77E5\u6D88\u606F",
|
|
189
|
+
"im:message:update": "\u66F4\u65B0/\u7F16\u8F91\u5DF2\u53D1\u9001\u7684\u6D88\u606F",
|
|
190
|
+
"im:resource": "\u4E0A\u4F20/\u4E0B\u8F7D\u6D88\u606F\u8D44\u6E90\uFF08\u56FE\u7247\u3001\u6587\u4EF6\u7B49\uFF09",
|
|
191
|
+
"application:application:self_manage": "\u67E5\u8BE2\u5E94\u7528\u81EA\u8EAB\u6743\u9650\u72B6\u6001\uFF08\u8BCA\u65AD\u57FA\u7840\uFF09",
|
|
192
|
+
"cardkit:card:write": "\u521B\u5EFA\u548C\u66F4\u65B0\u6D88\u606F\u5361\u7247",
|
|
193
|
+
"cardkit:card:read": "\u8BFB\u53D6\u6D88\u606F\u5361\u7247\u72B6\u6001"
|
|
194
|
+
};
|
|
195
|
+
const SENSITIVE_SCOPES = ["im:message.send_as_user"];
|
|
196
|
+
function filterSensitiveScopes(scopes) {
|
|
197
|
+
const sensitiveSet = new Set(SENSITIVE_SCOPES);
|
|
198
|
+
return scopes.filter((scope) => !sensitiveSet.has(scope));
|
|
199
|
+
}
|
|
200
|
+
export {
|
|
201
|
+
REQUIRED_APP_SCOPES,
|
|
202
|
+
REQUIRED_SCOPE_DESCRIPTIONS,
|
|
203
|
+
SENSITIVE_SCOPES,
|
|
204
|
+
TOOL_SCOPES,
|
|
205
|
+
filterSensitiveScopes
|
|
206
|
+
};
|
|
207
|
+
//# sourceMappingURL=tool-scopes.js.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../../src/core/tool-scopes.ts"],
|
|
4
|
+
"sourcesContent": ["/**\n * Copyright (c) 2026 ByteDance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n *\n * Tool Scopes \u914D\u7F6E\n *\n * \u5B9A\u4E49\u6240\u6709\u5DE5\u5177\u52A8\u4F5C\u6240\u9700\u7684\u98DE\u4E66\u6743\u9650\u6620\u5C04\u3002\n *\n * ## \u7EF4\u62A4\u65B9\u5F0F\n *\n * \u26A0\uFE0F \u6B64\u6587\u4EF6\u91C7\u7528**\u624B\u52A8\u7EF4\u62A4**\uFF0C\u65B0\u589E\u6216\u4FEE\u6539\u5DE5\u5177\u65F6\u9700\u540C\u6B65\u66F4\u65B0\u3002\n *\n * ### \u65B0\u589E\u5DE5\u5177\u52A8\u4F5C\n *\n * 1. \u5728 `ToolActionKey` \u7C7B\u578B\u4E2D\u6DFB\u52A0\u65B0\u952E\uFF1A\n * ```typescript\n * export type ToolActionKey =\n * | \"feishu_calendar_event.create\"\n * | \"feishu_new_tool.action\" // \u65B0\u589E\n * ```\n *\n * 2. \u5728 `TOOL_SCOPES` \u5BF9\u8C61\u4E2D\u6DFB\u52A0\u5BF9\u5E94\u914D\u7F6E\uFF1A\n * ```typescript\n * export const TOOL_SCOPES: ToolScopeMapping = {\n * \"feishu_new_tool.action\": [\n * \"required:scope:here\"\n * ],\n * };\n * ```\n *\n * 3. \u8FD0\u884C TypeScript \u7C7B\u578B\u68C0\u67E5\u9A8C\u8BC1\u4E00\u81F4\u6027\uFF1A\n * ```bash\n * cd openclaw/feishu && npx tsc --noEmit\n * ```\n *\n * ### \u5982\u4F55\u786E\u5B9A\u6240\u9700 Scope\n *\n * 1. **\u67E5\u9605\u98DE\u4E66\u5F00\u653E\u5E73\u53F0 API \u6587\u6863**\uFF1Ahttps://open.feishu.cn/document\n * 2. **\u4F7F\u7528 feishu-oapi-search skill**\uFF1A\u5728 Claude Code \u4E2D\u641C\u7D22 API \u6587\u6863\n * 3. **\u53C2\u8003\u7C7B\u4F3C\u5DE5\u5177**\uFF1A\u67E5\u770B\u529F\u80FD\u76F8\u8FD1\u7684\u5DE5\u5177\u7684 scope \u914D\u7F6E\n * 4. **\u5B9E\u9645\u6D4B\u8BD5**\uFF1A\u89C2\u5BDF API \u8C03\u7528\u7684\u9519\u8BEF\u7801\uFF08LARK_ERROR.APP_SCOPE_MISSING/99991672=\u5E94\u7528\u7F3A\u6743\u9650\uFF0CLARK_ERROR.USER_SCOPE_INSUFFICIENT/99991679=\u7528\u6237\u7F3A\u6388\u6743\uFF09\n *\n * \u6700\u540E\u66F4\u65B0: 2026-03-03\n */\n\n// ===== \u7C7B\u578B\u5B9A\u4E49 =====\n\n/**\n * \u6240\u6709\u53EF\u7528\u7684\u5DE5\u5177\u52A8\u4F5C\u952E\n *\n * \u683C\u5F0F\uFF1A{tool_name}.{action_name}\n *\n * \u793A\u4F8B\uFF1A\n * - \"feishu_calendar_event.create\"\n * - \"feishu_bitable_app_table_record.update\"\n *\n * \u603B\u8BA1\uFF1A98 \u4E2A\u5DE5\u5177\u52A8\u4F5C\n */\nexport type ToolActionKey =\n | 'feishu_bitable_app.copy'\n | 'feishu_bitable_app.create'\n | 'feishu_bitable_app.get'\n | 'feishu_bitable_app.list'\n | 'feishu_bitable_app.patch'\n | 'feishu_bitable_app_table.batch_create'\n | 'feishu_bitable_app_table.batch_delete'\n | 'feishu_bitable_app_table.create'\n | 'feishu_bitable_app_table.delete'\n | 'feishu_bitable_app_table.list'\n | 'feishu_bitable_app_table.patch'\n | 'feishu_bitable_app_table_field.create'\n | 'feishu_bitable_app_table_field.delete'\n | 'feishu_bitable_app_table_field.list'\n | 'feishu_bitable_app_table_field.update'\n | 'feishu_bitable_app_table_record.batch_create'\n | 'feishu_bitable_app_table_record.batch_delete'\n | 'feishu_bitable_app_table_record.batch_update'\n | 'feishu_bitable_app_table_record.create'\n | 'feishu_bitable_app_table_record.delete'\n | 'feishu_bitable_app_table_record.list'\n | 'feishu_bitable_app_table_record.update'\n | 'feishu_bitable_app_table_view.create'\n | 'feishu_bitable_app_table_view.delete'\n | 'feishu_bitable_app_table_view.get'\n | 'feishu_bitable_app_table_view.list'\n | 'feishu_bitable_app_table_view.patch'\n | 'feishu_calendar_calendar.get'\n | 'feishu_calendar_calendar.list'\n | 'feishu_calendar_calendar.primary'\n | 'feishu_calendar_event.create'\n | 'feishu_calendar_event.delete'\n | 'feishu_calendar_event.get'\n | 'feishu_calendar_event.instance_view'\n | 'feishu_calendar_event.instances'\n | 'feishu_calendar_event.list'\n | 'feishu_calendar_event.patch'\n | 'feishu_calendar_event.reply'\n | 'feishu_calendar_event.search'\n | 'feishu_calendar_event_attendee.batch_delete'\n | 'feishu_calendar_event_attendee.create'\n | 'feishu_calendar_event_attendee.list'\n | 'feishu_calendar_freebusy.list'\n | 'feishu_chat.get'\n | 'feishu_chat.search'\n | 'feishu_chat_members.default'\n | 'feishu_create_doc.default'\n | 'feishu_doc_comments.create'\n | 'feishu_doc_comments.list'\n | 'feishu_doc_comments.patch'\n | 'feishu_doc_media.download'\n | 'feishu_doc_media.insert'\n | 'feishu_drive_file.copy'\n | 'feishu_drive_file.delete'\n | 'feishu_drive_file.download'\n | 'feishu_drive_file.get_meta'\n | 'feishu_drive_file.list'\n | 'feishu_drive_file.move'\n | 'feishu_drive_file.upload'\n | 'feishu_fetch_doc.default'\n | 'feishu_get_user.default'\n | 'feishu_im_user_fetch_resource.default'\n | 'feishu_im_user_get_messages.default'\n | 'feishu_im_user_message.reply'\n | 'feishu_im_user_message.send'\n | 'feishu_im_user_search_messages.default'\n | 'feishu_search_doc_wiki.search'\n | 'feishu_search_user.default'\n | 'feishu_task_comment.create'\n | 'feishu_task_comment.get'\n | 'feishu_task_comment.list'\n | 'feishu_task_subtask.create'\n | 'feishu_task_subtask.list'\n | 'feishu_task_task.create'\n | 'feishu_task_task.get'\n | 'feishu_task_task.list'\n | 'feishu_task_task.patch'\n | 'feishu_task_tasklist.add_members'\n | 'feishu_task_tasklist.create'\n | 'feishu_task_tasklist.delete'\n | 'feishu_task_tasklist.get'\n | 'feishu_task_tasklist.list'\n | 'feishu_task_tasklist.patch'\n | 'feishu_task_tasklist.remove_members'\n | 'feishu_task_tasklist.tasks'\n | 'feishu_update_doc.default'\n | 'feishu_wiki_space.create'\n | 'feishu_wiki_space.get'\n | 'feishu_wiki_space.list'\n | 'feishu_wiki_space_node.copy'\n | 'feishu_wiki_space_node.create'\n | 'feishu_wiki_space_node.get'\n | 'feishu_wiki_space_node.list'\n | 'feishu_wiki_space_node.move'\n | 'feishu_sheet.info'\n | 'feishu_sheet.read'\n | 'feishu_sheet.write'\n | 'feishu_sheet.append'\n | 'feishu_sheet.find'\n | 'feishu_sheet.create'\n | 'feishu_sheet.export';\n/**\n * Tool Scope \u6620\u5C04\u7C7B\u578B\n *\n * \u5C06\u6BCF\u4E2A ToolActionKey \u6620\u5C04\u5230\u5176\u6240\u9700\u7684 scope \u6570\u7EC4\n */\nexport type ToolScopeMapping = Record<ToolActionKey, string[]>;\n\n// ===== \u6570\u636E =====\n\n/**\n * Tool Scope \u6570\u636E\n *\n * \u6BCF\u4E2A\u5DE5\u5177\u52A8\u4F5C\u6240\u9700\u7684\u98DE\u4E66\u6743\u9650\u5217\u8868\uFF08Required Scopes\uFF09\n *\n * ## \u6570\u636E\u8BF4\u660E\n *\n * - \u7A7A\u6570\u7EC4 `[]` \u8868\u793A\u8BE5\u5DE5\u5177\u52A8\u4F5C\u4E0D\u9700\u8981\u4EFB\u4F55\u6743\u9650\n * - \u591A\u4E2A\u6743\u9650\u8868\u793A\u9700\u8981\u540C\u65F6\u62E5\u6709\u6240\u6709\u6743\u9650\uFF08AND \u5173\u7CFB\uFF09\n * - \u6240\u6709 scope \u90FD\u662F user scopes\uFF08\u7528\u6237\u7EA7\u6743\u9650\uFF09\n *\n * ## \u793A\u4F8B\n *\n * ```typescript\n * TOOL_SCOPES[\"feishu_calendar_event.create\"]\n * // \u8FD4\u56DE: [\"calendar:calendar.event:create\", \"calendar:calendar.event:update\"]\n * ```\n *\n * @see {@link ToolActionKey} \u6240\u6709\u53EF\u7528\u7684\u5DE5\u5177\u52A8\u4F5C\u952E\n */\nexport const TOOL_SCOPES: ToolScopeMapping = {\n 'feishu_bitable_app.create': ['base:app:create'],\n 'feishu_bitable_app.get': ['base:app:read'],\n 'feishu_bitable_app.list': ['space:document:retrieve'],\n 'feishu_bitable_app.patch': ['base:app:update'],\n 'feishu_bitable_app.copy': ['base:app:copy'],\n 'feishu_bitable_app_table.create': ['base:table:create'],\n 'feishu_bitable_app_table.list': ['base:table:read'],\n 'feishu_bitable_app_table.patch': ['base:table:update'],\n 'feishu_bitable_app_table.delete': ['base:table:delete'],\n 'feishu_bitable_app_table.batch_create': ['base:table:create'],\n 'feishu_bitable_app_table.batch_delete': ['base:table:delete'],\n 'feishu_bitable_app_table_record.create': ['base:record:create'],\n 'feishu_bitable_app_table_record.update': ['base:record:update'],\n 'feishu_bitable_app_table_record.delete': ['base:record:delete'],\n 'feishu_bitable_app_table_record.batch_create': ['base:record:create'],\n 'feishu_bitable_app_table_record.batch_update': ['base:record:update'],\n 'feishu_bitable_app_table_record.batch_delete': ['base:record:delete'],\n 'feishu_bitable_app_table_record.list': ['base:record:retrieve'],\n 'feishu_bitable_app_table_field.create': ['base:field:create'],\n 'feishu_bitable_app_table_field.list': ['base:field:read'],\n 'feishu_bitable_app_table_field.update': ['base:field:read', 'base:field:update'],\n 'feishu_bitable_app_table_field.delete': ['base:field:delete'],\n 'feishu_bitable_app_table_view.create': ['base:view:write_only'],\n 'feishu_bitable_app_table_view.get': ['base:view:read'],\n 'feishu_bitable_app_table_view.list': ['base:view:read'],\n 'feishu_bitable_app_table_view.patch': ['base:view:write_only'],\n 'feishu_bitable_app_table_view.delete': ['base:view:write_only'],\n 'feishu_calendar_calendar.list': ['calendar:calendar:read'],\n 'feishu_calendar_calendar.get': ['calendar:calendar:read'],\n 'feishu_calendar_calendar.primary': ['calendar:calendar:read'],\n 'feishu_calendar_event.create': ['calendar:calendar.event:create', 'calendar:calendar.event:update'],\n 'feishu_calendar_event.list': ['calendar:calendar.event:read'],\n 'feishu_calendar_event.get': ['calendar:calendar.event:read'],\n 'feishu_calendar_event.patch': ['calendar:calendar.event:update'],\n 'feishu_calendar_event.delete': ['calendar:calendar.event:delete'],\n 'feishu_calendar_event.search': ['calendar:calendar.event:read'],\n 'feishu_calendar_event.reply': ['calendar:calendar.event:reply'],\n 'feishu_calendar_event.instances': ['calendar:calendar.event:read'],\n 'feishu_calendar_event.instance_view': ['calendar:calendar.event:read'],\n 'feishu_calendar_event_attendee.create': ['calendar:calendar.event:update'],\n 'feishu_calendar_event_attendee.list': ['calendar:calendar.event:read'],\n 'feishu_calendar_event_attendee.batch_delete': ['calendar:calendar.event:read', 'calendar:calendar.event:update'],\n 'feishu_calendar_freebusy.list': ['calendar:calendar.free_busy:read'],\n 'feishu_task_task.create': ['task:task:write', 'task:task:writeonly'],\n 'feishu_task_task.get': ['task:task:read', 'task:task:write'],\n 'feishu_task_task.list': ['task:task:read', 'task:task:write'],\n 'feishu_task_task.patch': ['task:task:write', 'task:task:writeonly'],\n 'feishu_task_tasklist.create': ['task:tasklist:write'],\n 'feishu_task_tasklist.get': ['task:tasklist:read', 'task:tasklist:write'],\n 'feishu_task_tasklist.list': ['task:tasklist:read', 'task:tasklist:write'],\n 'feishu_task_tasklist.tasks': ['task:tasklist:read', 'task:tasklist:write'],\n 'feishu_task_tasklist.patch': ['task:tasklist:write'],\n 'feishu_task_tasklist.delete': ['task:tasklist:write'],\n 'feishu_task_tasklist.add_members': ['task:tasklist:write'],\n 'feishu_task_tasklist.remove_members': ['task:tasklist:write'],\n 'feishu_task_comment.create': ['task:comment:write'],\n 'feishu_task_comment.list': ['task:comment:read', 'task:comment:write'],\n 'feishu_task_comment.get': ['task:comment:read', 'task:comment:write'],\n 'feishu_task_subtask.create': ['task:task:write'],\n 'feishu_task_subtask.list': ['task:task:read', 'task:task:write'],\n 'feishu_chat.search': ['im:chat:read'],\n 'feishu_chat.get': ['im:chat:read'],\n 'feishu_chat_members.default': ['im:chat.members:read'],\n 'feishu_drive_file.list': ['space:document:retrieve'],\n 'feishu_drive_file.get_meta': ['drive:drive.metadata:readonly'],\n 'feishu_drive_file.copy': ['docs:document:copy'],\n 'feishu_drive_file.move': ['space:document:move'],\n 'feishu_drive_file.delete': ['space:document:delete'],\n 'feishu_drive_file.upload': ['drive:file:upload'],\n 'feishu_drive_file.download': ['drive:file:download'],\n 'feishu_doc_media.download': ['board:whiteboard:node:read', 'docs:document.media:download'],\n 'feishu_doc_media.insert': ['docx:document:write_only', 'docs:document.media:upload'],\n 'feishu_doc_comments.list': ['wiki:node:read', 'docs:document.comment:read'],\n 'feishu_doc_comments.create': ['wiki:node:read', 'docs:document.comment:create'],\n 'feishu_doc_comments.patch': ['docs:document.comment:update'],\n 'feishu_wiki_space.list': ['wiki:space:retrieve'],\n 'feishu_wiki_space.get': ['wiki:space:read'],\n 'feishu_wiki_space.create': ['wiki:space:write_only'],\n 'feishu_wiki_space_node.list': ['wiki:node:retrieve'],\n 'feishu_wiki_space_node.get': ['wiki:node:read'],\n 'feishu_wiki_space_node.create': ['wiki:node:create'],\n 'feishu_wiki_space_node.move': ['wiki:node:move'],\n 'feishu_wiki_space_node.copy': ['wiki:node:copy'],\n 'feishu_im_user_message.send': ['im:message', 'im:message.send_as_user'],\n 'feishu_im_user_message.reply': ['im:message', 'im:message.send_as_user'],\n 'feishu_im_user_fetch_resource.default': [\n 'im:message.group_msg:get_as_user',\n 'im:message.p2p_msg:get_as_user',\n 'im:message:readonly',\n ],\n 'feishu_im_user_get_messages.default': [\n 'im:chat:read',\n 'im:message:readonly',\n 'im:message.group_msg:get_as_user',\n 'im:message.p2p_msg:get_as_user',\n 'contact:contact.base:readonly',\n 'contact:user.base:readonly',\n ],\n 'feishu_im_user_search_messages.default': [\n 'im:chat:read',\n 'im:message:readonly',\n 'im:message.group_msg:get_as_user',\n 'im:message.p2p_msg:get_as_user',\n 'contact:contact.base:readonly',\n 'contact:user.base:readonly',\n 'search:message',\n ],\n 'feishu_search_doc_wiki.search': ['search:docs:read'],\n 'feishu_get_user.default': ['contact:contact.base:readonly', 'contact:user.base:readonly'],\n 'feishu_search_user.default': ['contact:user:search'],\n 'feishu_create_doc.default': [\n 'board:whiteboard:node:create',\n 'docx:document:create',\n 'docx:document:readonly',\n 'docx:document:write_only',\n 'wiki:node:create',\n 'wiki:node:read',\n 'docs:document.media:upload',\n ],\n 'feishu_fetch_doc.default': ['docx:document:readonly', 'wiki:node:read'],\n 'feishu_update_doc.default': [\n 'board:whiteboard:node:create',\n 'docx:document:create',\n 'docx:document:readonly',\n 'docx:document:write_only',\n ],\n 'feishu_sheet.info': ['sheets:spreadsheet.meta:read', 'sheets:spreadsheet:read'],\n 'feishu_sheet.read': ['sheets:spreadsheet.meta:read', 'sheets:spreadsheet:read'],\n 'feishu_sheet.write': [\n 'sheets:spreadsheet.meta:read',\n 'sheets:spreadsheet:read',\n 'sheets:spreadsheet:create',\n 'sheets:spreadsheet:write_only',\n ],\n 'feishu_sheet.append': [\n 'sheets:spreadsheet.meta:read',\n 'sheets:spreadsheet:read',\n 'sheets:spreadsheet:create',\n 'sheets:spreadsheet:write_only',\n ],\n 'feishu_sheet.find': ['sheets:spreadsheet.meta:read', 'sheets:spreadsheet:read'],\n 'feishu_sheet.create': [\n 'sheets:spreadsheet.meta:read',\n 'sheets:spreadsheet:read',\n 'sheets:spreadsheet:create',\n 'sheets:spreadsheet:write_only',\n ],\n 'feishu_sheet.export': ['docs:document:export'],\n} as const;\n\n// ===== \u5FC5\u9700\u7684\u5E94\u7528\u8EAB\u4EFD\u6743\u9650 =====\n\n/**\n * \u98DE\u4E66\u63D2\u4EF6\u8FD0\u884C\u5FC5\u987B\u5F00\u901A\u7684\u5E94\u7528\u8EAB\u4EFD\u6743\u9650\u6E05\u5355\n *\n * \u8FD9\u4E9B\u6743\u9650\u662F\u63D2\u4EF6\u57FA\u7840\u529F\u80FD\uFF08\u6D88\u606F\u63A5\u6536\u3001\u5361\u7247\u4EA4\u4E92\u3001\u57FA\u672C\u4FE1\u606F\u67E5\u8BE2\u7B49\uFF09\u6240\u5FC5\u9700\u7684\uFF0C\n * \u5982\u679C\u7F3A\u5931\u8FD9\u4E9B\u6743\u9650\uFF0C\u63D2\u4EF6\u5C06\u65E0\u6CD5\u6B63\u5E38\u5DE5\u4F5C\u3002\n *\n * \u6743\u9650\u5206\u7C7B\uFF1A\n * - im:message.* - \u6D88\u606F\u63A5\u6536\u548C\u53D1\u9001\n * - im:chat.* - \u7FA4\u804A\u7BA1\u7406\n * - im:resource - \u6D88\u606F\u8D44\u6E90\uFF08\u56FE\u7247\u3001\u6587\u4EF6\u7B49\uFF09\n * - cardkit:card.* - \u5361\u7247\u4EA4\u4E92\n * - application:application:self_manage - \u5E94\u7528\u81EA\u8EAB\u6743\u9650\u67E5\u8BE2\uFF08\u6743\u9650\u68C0\u67E5\u57FA\u7840\uFF09\n * - contact:contact.base:readonly - \u901A\u8BAF\u5F55\u57FA\u7840\u4FE1\u606F\n * - docx:document:readonly - \u6587\u6863\u57FA\u7840\u53EA\u8BFB\uFF08\u6587\u6863\u94FE\u63A5\u9884\u89C8\u7B49\uFF09\n *\n * \u6700\u540E\u66F4\u65B0: 2026-03-03\n */\nexport const REQUIRED_APP_SCOPES = [\n 'contact:contact.base:readonly',\n 'docx:document:readonly',\n 'im:chat:read',\n 'im:chat:update',\n 'im:message.group_at_msg:readonly',\n 'im:message.p2p_msg:readonly',\n 'im:message.pins:read',\n 'im:message.pins:write_only',\n 'im:message.reactions:read',\n 'im:message.reactions:write_only',\n 'im:message:readonly',\n 'im:message:recall',\n 'im:message:send_as_bot',\n 'im:message:send_multi_users',\n 'im:message:send_sys_msg',\n 'im:message:update',\n 'im:resource',\n 'application:application:self_manage',\n 'cardkit:card:write',\n 'cardkit:card:read',\n] as const;\n\n/**\n * \u5FC5\u9700\u5E94\u7528\u6743\u9650\u7C7B\u578B\n */\nexport type RequiredAppScope = (typeof REQUIRED_APP_SCOPES)[number];\n\n/**\n * \u5FC5\u9700\u6743\u9650\u7528\u9014\u8BF4\u660E\n *\n * \u63CF\u8FF0\u6BCF\u4E2A\u5FC5\u9700\u6743\u9650\u7684\u5177\u4F53\u7528\u9014\uFF0C\u5E2E\u52A9\u7BA1\u7406\u5458\u7406\u89E3\u4E3A\u4EC0\u4E48\u9700\u8981\u5F00\u901A\u8BE5\u6743\u9650\u3002\n */\nexport const REQUIRED_SCOPE_DESCRIPTIONS: Record<RequiredAppScope, string> = {\n 'contact:contact.base:readonly': '\u83B7\u53D6\u7528\u6237\u57FA\u672C\u4FE1\u606F\uFF08\u59D3\u540D\u3001\u5934\u50CF\uFF09',\n 'docx:document:readonly': '\u8BFB\u53D6\u6587\u6863\u5185\u5BB9\u3001\u9884\u89C8\u6587\u6863\u94FE\u63A5',\n 'im:chat:read': '\u8BFB\u53D6\u7FA4\u804A\u4FE1\u606F\u3001\u83B7\u53D6\u7FA4\u6210\u5458\u5217\u8868',\n 'im:chat:update': '\u4FEE\u6539\u7FA4\u804A\u8BBE\u7F6E\uFF08\u7FA4\u540D\u79F0\u3001\u7FA4\u516C\u544A\u7B49\uFF09',\n 'im:message.group_at_msg:readonly': '\u63A5\u6536\u7FA4\u804A\u4E2D @ \u673A\u5668\u4EBA\u7684\u6D88\u606F',\n 'im:message.p2p_msg:readonly': '\u63A5\u6536\u79C1\u804A\u6D88\u606F',\n 'im:message.pins:read': '\u8BFB\u53D6\u6D88\u606F\u7F6E\u9876\u72B6\u6001',\n 'im:message.pins:write_only': '\u7F6E\u9876/\u53D6\u6D88\u7F6E\u9876\u6D88\u606F',\n 'im:message.reactions:read': '\u8BFB\u53D6\u6D88\u606F\u8868\u60C5\u56DE\u590D',\n 'im:message.reactions:write_only': '\u6DFB\u52A0/\u5220\u9664\u6D88\u606F\u8868\u60C5\u56DE\u590D',\n 'im:message:readonly': '\u8BFB\u53D6\u6D88\u606F\u5185\u5BB9\u3001\u5386\u53F2\u6D88\u606F',\n 'im:message:recall': '\u21A9\u64A4\u56DE\u673A\u5668\u4EBA\u53D1\u9001\u7684\u6D88\u606F',\n 'im:message:send_as_bot': '\u4EE5\u673A\u5668\u4EBA\u8EAB\u4EFD\u53D1\u9001\u6D88\u606F',\n 'im:message:send_multi_users': '\u6279\u91CF\u53D1\u9001\u79C1\u804A\u6D88\u606F',\n 'im:message:send_sys_msg': '\u53D1\u9001\u7CFB\u7EDF\u901A\u77E5\u6D88\u606F',\n 'im:message:update': '\u66F4\u65B0/\u7F16\u8F91\u5DF2\u53D1\u9001\u7684\u6D88\u606F',\n 'im:resource': '\u4E0A\u4F20/\u4E0B\u8F7D\u6D88\u606F\u8D44\u6E90\uFF08\u56FE\u7247\u3001\u6587\u4EF6\u7B49\uFF09',\n 'application:application:self_manage': '\u67E5\u8BE2\u5E94\u7528\u81EA\u8EAB\u6743\u9650\u72B6\u6001\uFF08\u8BCA\u65AD\u57FA\u7840\uFF09',\n 'cardkit:card:write': '\u521B\u5EFA\u548C\u66F4\u65B0\u6D88\u606F\u5361\u7247',\n 'cardkit:card:read': '\u8BFB\u53D6\u6D88\u606F\u5361\u7247\u72B6\u6001',\n};\n\n// ===== \u9AD8\u654F\u611F\u6743\u9650 =====\n\n/**\n * \u9AD8\u654F\u611F\u6743\u9650\u6E05\u5355\n *\n * \u8FD9\u4E9B\u6743\u9650\u5177\u6709\u8F83\u9AD8\u7684\u654F\u611F\u5EA6\uFF0C\u4E0D\u5E94\u5728\u6279\u91CF\u6388\u6743\u65F6\u81EA\u52A8\u7533\u8BF7\u3002\n * \u7528\u6237\u9700\u8981\u660E\u786E\u77E5\u6653\u8FD9\u4E9B\u6743\u9650\u7684\u5F71\u54CD\u540E\uFF0C\u624D\u80FD\u624B\u52A8\u6388\u6743\u3002\n *\n * \u6743\u9650\u8BF4\u660E\uFF1A\n * - im:message:send_as_user - \u4EE5\u7528\u6237\u8EAB\u4EFD\u53D1\u9001\u6D88\u606F\uFF08\u9AD8\u98CE\u9669\uFF0C\u53EF\u80FD\u88AB\u6EE5\u7528\u53D1\u9001\u9493\u9C7C\u6216\u5783\u573E\u6D88\u606F\uFF09\n *\n * \u4F7F\u7528\u573A\u666F\uFF1A\n * - \u6279\u91CF\u6388\u6743\u65F6\u4F1A\u81EA\u52A8\u8FC7\u6EE4\u6389\u8FD9\u4E9B\u6743\u9650\n * - \u9700\u8981\u8FD9\u4E9B\u6743\u9650\u7684\u529F\u80FD\u4F1A\u5355\u72EC\u63D0\u793A\u7528\u6237\u6388\u6743\n *\n * \u6700\u540E\u66F4\u65B0: 2026-03-03\n */\nexport const SENSITIVE_SCOPES = ['im:message.send_as_user'] as const;\n\n/**\n * \u9AD8\u654F\u611F\u6743\u9650\u7C7B\u578B\n */\nexport type SensitiveScope = (typeof SENSITIVE_SCOPES)[number];\n\n/**\n * \u8FC7\u6EE4\u6389\u9AD8\u654F\u611F\u6743\u9650\n *\n * \u7528\u4E8E\u6279\u91CF\u6388\u6743\u65F6\u6392\u9664\u9AD8\u654F\u611F\u6743\u9650\uFF0C\u8FD9\u4E9B\u6743\u9650\u9700\u8981\u7528\u6237\u660E\u786E\u6388\u6743\u3002\n *\n * @param scopes - \u539F\u59CB\u6743\u9650\u5217\u8868\n * @returns \u8FC7\u6EE4\u540E\u7684\u6743\u9650\u5217\u8868\uFF08\u4E0D\u5305\u542B\u9AD8\u654F\u611F\u6743\u9650\uFF09\n *\n * @example\n * ```typescript\n * const allScopes = [\"im:message\", \"im:message:send_as_user\", \"calendar:calendar:read\"];\n * const safeScopes = filterSensitiveScopes(allScopes);\n * // \u8FD4\u56DE: [\"im:message\", \"calendar:calendar:read\"]\n * ```\n */\nexport function filterSensitiveScopes(scopes: string[]): string[] {\n const sensitiveSet = new Set<string>(SENSITIVE_SCOPES);\n return scopes.filter((scope) => !sensitiveSet.has(scope));\n}\n\n// ===== \u7EDF\u8BA1\u4FE1\u606F =====\n\n/**\n * \u5DE5\u5177\u52A8\u4F5C\u603B\u6570: 98\n * \u552F\u4E00 scope \u603B\u6570: 66\n * \u5FC5\u9700\u5E94\u7528\u6743\u9650\u603B\u6570: 20\n * \u9AD8\u654F\u611F\u6743\u9650\u603B\u6570: 1\n */\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
|
+
"names": []
|
|
7
|
+
}
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
const DEFAULT_TOOLS_CONFIG = {
|
|
2
|
+
doc: true,
|
|
3
|
+
wiki: true,
|
|
4
|
+
drive: true,
|
|
5
|
+
scopes: true,
|
|
6
|
+
perm: false,
|
|
7
|
+
mail: true,
|
|
8
|
+
sheets: true,
|
|
9
|
+
okr: false,
|
|
10
|
+
project: true
|
|
11
|
+
};
|
|
12
|
+
function resolveToolsConfig(cfg) {
|
|
13
|
+
if (!cfg) return { ...DEFAULT_TOOLS_CONFIG };
|
|
14
|
+
return {
|
|
15
|
+
doc: cfg.doc ?? DEFAULT_TOOLS_CONFIG.doc,
|
|
16
|
+
wiki: cfg.wiki ?? DEFAULT_TOOLS_CONFIG.wiki,
|
|
17
|
+
drive: cfg.drive ?? DEFAULT_TOOLS_CONFIG.drive,
|
|
18
|
+
perm: cfg.perm ?? DEFAULT_TOOLS_CONFIG.perm,
|
|
19
|
+
scopes: cfg.scopes ?? DEFAULT_TOOLS_CONFIG.scopes,
|
|
20
|
+
mail: cfg.mail ?? DEFAULT_TOOLS_CONFIG.mail,
|
|
21
|
+
sheets: cfg.sheets ?? DEFAULT_TOOLS_CONFIG.sheets,
|
|
22
|
+
okr: cfg.okr ?? DEFAULT_TOOLS_CONFIG.okr,
|
|
23
|
+
project: cfg.project ?? DEFAULT_TOOLS_CONFIG.project
|
|
24
|
+
};
|
|
25
|
+
}
|
|
26
|
+
function resolveAnyEnabledToolsConfig(accounts) {
|
|
27
|
+
const merged = {
|
|
28
|
+
doc: false,
|
|
29
|
+
wiki: false,
|
|
30
|
+
drive: false,
|
|
31
|
+
perm: false,
|
|
32
|
+
scopes: false,
|
|
33
|
+
mail: false,
|
|
34
|
+
sheets: false,
|
|
35
|
+
okr: false,
|
|
36
|
+
project: false
|
|
37
|
+
};
|
|
38
|
+
for (const account of accounts) {
|
|
39
|
+
const cfg = resolveToolsConfig(account.config.tools);
|
|
40
|
+
merged.doc = merged.doc || cfg.doc;
|
|
41
|
+
merged.wiki = merged.wiki || cfg.wiki;
|
|
42
|
+
merged.drive = merged.drive || cfg.drive;
|
|
43
|
+
merged.perm = merged.perm || cfg.perm;
|
|
44
|
+
merged.scopes = merged.scopes || cfg.scopes;
|
|
45
|
+
merged.mail = merged.mail || cfg.mail;
|
|
46
|
+
merged.sheets = merged.sheets || cfg.sheets;
|
|
47
|
+
merged.okr = merged.okr || cfg.okr;
|
|
48
|
+
merged.project = merged.project || cfg.project;
|
|
49
|
+
}
|
|
50
|
+
return merged;
|
|
51
|
+
}
|
|
52
|
+
export {
|
|
53
|
+
DEFAULT_TOOLS_CONFIG,
|
|
54
|
+
resolveAnyEnabledToolsConfig,
|
|
55
|
+
resolveToolsConfig
|
|
56
|
+
};
|
|
57
|
+
//# sourceMappingURL=tools-config.js.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../../src/core/tools-config.ts"],
|
|
4
|
+
"sourcesContent": ["/**\n * Copyright (c) 2026 ByteDance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n *\n * Default values and resolution logic for the Feishu tools configuration.\n *\n * Each boolean flag controls whether a particular category of Feishu-specific\n * agent tools (document access, wiki queries, drive operations, etc.) is\n * enabled for a given account.\n */\n\nimport type { FeishuToolsConfig, LarkAccount } from './types';\n\n// ---------------------------------------------------------------------------\n// Defaults\n// ---------------------------------------------------------------------------\n\n/**\n * The default tools configuration.\n *\n * By default every non-destructive capability is enabled. The `perm` flag\n * (permission management) defaults to `false` because granting / revoking\n * permissions is a privileged operation that admins should opt into\n * explicitly.\n */\nexport const DEFAULT_TOOLS_CONFIG: Required<FeishuToolsConfig> = {\n doc: true,\n wiki: true,\n drive: true,\n scopes: true,\n perm: false,\n mail: true,\n sheets: true,\n okr: false,\n project: true,\n};\n\n// ---------------------------------------------------------------------------\n// Resolver\n// ---------------------------------------------------------------------------\n\n/**\n * Merge a partial tools configuration with `DEFAULT_TOOLS_CONFIG`.\n *\n * Fields present in the input take precedence; anything absent falls back\n * to the default value.\n */\nexport function resolveToolsConfig(cfg?: FeishuToolsConfig): Required<FeishuToolsConfig> {\n if (!cfg) return { ...DEFAULT_TOOLS_CONFIG };\n\n return {\n doc: cfg.doc ?? DEFAULT_TOOLS_CONFIG.doc,\n wiki: cfg.wiki ?? DEFAULT_TOOLS_CONFIG.wiki,\n drive: cfg.drive ?? DEFAULT_TOOLS_CONFIG.drive,\n perm: cfg.perm ?? DEFAULT_TOOLS_CONFIG.perm,\n scopes: cfg.scopes ?? DEFAULT_TOOLS_CONFIG.scopes,\n mail: cfg.mail ?? DEFAULT_TOOLS_CONFIG.mail,\n sheets: cfg.sheets ?? DEFAULT_TOOLS_CONFIG.sheets,\n okr: cfg.okr ?? DEFAULT_TOOLS_CONFIG.okr,\n project: cfg.project ?? DEFAULT_TOOLS_CONFIG.project,\n };\n}\n\n// ---------------------------------------------------------------------------\n// Multi-account aggregation\n// ---------------------------------------------------------------------------\n\n/**\n * \u5408\u5E76\u591A\u4E2A\u8D26\u6237\u7684\u5DE5\u5177\u914D\u7F6E\uFF08\u53D6\u5E76\u96C6\uFF09\u3002\n *\n * \u5DE5\u5177\u6CE8\u518C\u662F\u5168\u5C40\u7684\uFF08\u542F\u52A8\u65F6\u6CE8\u518C\u4E00\u6B21\uFF09\uFF0C\u53EA\u8981\u4EFB\u610F\u4E00\u4E2A\u8D26\u6237\u542F\u7528\u4E86\u67D0\u5DE5\u5177\uFF0C\n * \u8BE5\u5DE5\u5177\u5C31\u5E94\u88AB\u6CE8\u518C\u3002\u6267\u884C\u65F6\u7531 LarkTicket \u8DEF\u7531\u5230\u5177\u4F53\u8D26\u6237\u3002\n */\nexport function resolveAnyEnabledToolsConfig(accounts: LarkAccount[]): Required<FeishuToolsConfig> {\n const merged: Required<FeishuToolsConfig> = {\n doc: false,\n wiki: false,\n drive: false,\n perm: false,\n scopes: false,\n mail: false,\n sheets: false,\n okr: false,\n project: false,\n };\n for (const account of accounts) {\n const cfg = resolveToolsConfig((account.config as { tools?: FeishuToolsConfig }).tools);\n merged.doc = merged.doc || cfg.doc;\n merged.wiki = merged.wiki || cfg.wiki;\n merged.drive = merged.drive || cfg.drive;\n merged.perm = merged.perm || cfg.perm;\n merged.scopes = merged.scopes || cfg.scopes;\n merged.mail = merged.mail || cfg.mail;\n merged.sheets = merged.sheets || cfg.sheets;\n merged.okr = merged.okr || cfg.okr;\n merged.project = merged.project || cfg.project;\n }\n return merged;\n}\n"],
|
|
5
|
+
"mappings": "AAyBO,MAAM,uBAAoD;AAAA,EAC/D,KAAK;AAAA,EACL,MAAM;AAAA,EACN,OAAO;AAAA,EACP,QAAQ;AAAA,EACR,MAAM;AAAA,EACN,MAAM;AAAA,EACN,QAAQ;AAAA,EACR,KAAK;AAAA,EACL,SAAS;AACX;AAYO,SAAS,mBAAmB,KAAsD;AACvF,MAAI,CAAC,IAAK,QAAO,EAAE,GAAG,qBAAqB;AAE3C,SAAO;AAAA,IACL,KAAK,IAAI,OAAO,qBAAqB;AAAA,IACrC,MAAM,IAAI,QAAQ,qBAAqB;AAAA,IACvC,OAAO,IAAI,SAAS,qBAAqB;AAAA,IACzC,MAAM,IAAI,QAAQ,qBAAqB;AAAA,IACvC,QAAQ,IAAI,UAAU,qBAAqB;AAAA,IAC3C,MAAM,IAAI,QAAQ,qBAAqB;AAAA,IACvC,QAAQ,IAAI,UAAU,qBAAqB;AAAA,IAC3C,KAAK,IAAI,OAAO,qBAAqB;AAAA,IACrC,SAAS,IAAI,WAAW,qBAAqB;AAAA,EAC/C;AACF;AAYO,SAAS,6BAA6B,UAAsD;AACjG,QAAM,SAAsC;AAAA,IAC1C,KAAK;AAAA,IACL,MAAM;AAAA,IACN,OAAO;AAAA,IACP,MAAM;AAAA,IACN,QAAQ;AAAA,IACR,MAAM;AAAA,IACN,QAAQ;AAAA,IACR,KAAK;AAAA,IACL,SAAS;AAAA,EACX;AACA,aAAW,WAAW,UAAU;AAC9B,UAAM,MAAM,mBAAoB,QAAQ,OAAyC,KAAK;AACtF,WAAO,MAAM,OAAO,OAAO,IAAI;AAC/B,WAAO,OAAO,OAAO,QAAQ,IAAI;AACjC,WAAO,QAAQ,OAAO,SAAS,IAAI;AACnC,WAAO,OAAO,OAAO,QAAQ,IAAI;AACjC,WAAO,SAAS,OAAO,UAAU,IAAI;AACrC,WAAO,OAAO,OAAO,QAAQ,IAAI;AACjC,WAAO,SAAS,OAAO,UAAU,IAAI;AACrC,WAAO,MAAM,OAAO,OAAO,IAAI;AAC/B,WAAO,UAAU,OAAO,WAAW,IAAI;AAAA,EACzC;AACA,SAAO;AACT;",
|
|
6
|
+
"names": []
|
|
7
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
//# sourceMappingURL=types.js.map
|
|
@@ -0,0 +1,124 @@
|
|
|
1
|
+
import {
|
|
2
|
+
getStoredToken,
|
|
3
|
+
setStoredToken,
|
|
4
|
+
removeStoredToken,
|
|
5
|
+
tokenStatus,
|
|
6
|
+
maskToken
|
|
7
|
+
} from "./token-store";
|
|
8
|
+
import { resolveOAuthEndpoints } from "./device-flow";
|
|
9
|
+
import { larkLogger } from "./lark-logger";
|
|
10
|
+
const log = larkLogger("core/uat-client");
|
|
11
|
+
import { feishuFetch } from "./feishu-fetch";
|
|
12
|
+
import { REFRESH_TOKEN_IRRECOVERABLE, TOKEN_RETRY_CODES, NeedAuthorizationError } from "./auth-errors";
|
|
13
|
+
const refreshLocks = /* @__PURE__ */ new Map();
|
|
14
|
+
async function doRefreshToken(opts, stored) {
|
|
15
|
+
if (Date.now() >= stored.refreshExpiresAt) {
|
|
16
|
+
log.info(`refresh_token expired for ${opts.userOpenId}, clearing`);
|
|
17
|
+
await removeStoredToken(opts.appId, opts.userOpenId);
|
|
18
|
+
return null;
|
|
19
|
+
}
|
|
20
|
+
const endpoints = resolveOAuthEndpoints(opts.domain);
|
|
21
|
+
const resp = await feishuFetch(endpoints.token, {
|
|
22
|
+
method: "POST",
|
|
23
|
+
headers: { "Content-Type": "application/x-www-form-urlencoded" },
|
|
24
|
+
body: new URLSearchParams({
|
|
25
|
+
grant_type: "refresh_token",
|
|
26
|
+
refresh_token: stored.refreshToken,
|
|
27
|
+
client_id: opts.appId,
|
|
28
|
+
client_secret: opts.appSecret
|
|
29
|
+
}).toString()
|
|
30
|
+
});
|
|
31
|
+
const data = await resp.json();
|
|
32
|
+
const code = data.code;
|
|
33
|
+
const error = data.error;
|
|
34
|
+
if (code !== void 0 && code !== 0 || error) {
|
|
35
|
+
const errCode = code ?? error;
|
|
36
|
+
const errMsg = data.error_description ?? data.msg ?? "unknown";
|
|
37
|
+
if (REFRESH_TOKEN_IRRECOVERABLE.has(code)) {
|
|
38
|
+
log.warn(`refresh failed (code=${errCode}), clearing token for ${opts.userOpenId}`);
|
|
39
|
+
await removeStoredToken(opts.appId, opts.userOpenId);
|
|
40
|
+
return null;
|
|
41
|
+
}
|
|
42
|
+
throw new Error(`Token refresh failed (code=${errCode}): ${errMsg}`);
|
|
43
|
+
}
|
|
44
|
+
if (!data.access_token) {
|
|
45
|
+
throw new Error("Token refresh returned no access_token");
|
|
46
|
+
}
|
|
47
|
+
const now = Date.now();
|
|
48
|
+
const updated = {
|
|
49
|
+
userOpenId: stored.userOpenId,
|
|
50
|
+
appId: opts.appId,
|
|
51
|
+
accessToken: data.access_token,
|
|
52
|
+
// refresh_token is rotated – always use the new one.
|
|
53
|
+
refreshToken: data.refresh_token ?? stored.refreshToken,
|
|
54
|
+
expiresAt: now + (data.expires_in ?? 7200) * 1e3,
|
|
55
|
+
refreshExpiresAt: data.refresh_token_expires_in ? now + data.refresh_token_expires_in * 1e3 : stored.refreshExpiresAt,
|
|
56
|
+
scope: data.scope ?? stored.scope,
|
|
57
|
+
grantedAt: stored.grantedAt
|
|
58
|
+
};
|
|
59
|
+
await setStoredToken(updated);
|
|
60
|
+
log.info(`refreshed UAT for ${opts.userOpenId} (at:${maskToken(updated.accessToken)})`);
|
|
61
|
+
return updated;
|
|
62
|
+
}
|
|
63
|
+
async function refreshWithLock(opts, stored) {
|
|
64
|
+
const key = `${opts.appId}:${opts.userOpenId}`;
|
|
65
|
+
const existing = refreshLocks.get(key);
|
|
66
|
+
if (existing) {
|
|
67
|
+
await existing;
|
|
68
|
+
return getStoredToken(opts.appId, opts.userOpenId);
|
|
69
|
+
}
|
|
70
|
+
const promise = doRefreshToken(opts, stored);
|
|
71
|
+
refreshLocks.set(key, promise);
|
|
72
|
+
try {
|
|
73
|
+
return await promise;
|
|
74
|
+
} finally {
|
|
75
|
+
refreshLocks.delete(key);
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
async function getValidAccessToken(opts) {
|
|
79
|
+
const stored = await getStoredToken(opts.appId, opts.userOpenId);
|
|
80
|
+
if (!stored) {
|
|
81
|
+
throw new NeedAuthorizationError(opts.userOpenId);
|
|
82
|
+
}
|
|
83
|
+
const status = tokenStatus(stored);
|
|
84
|
+
if (status === "valid") {
|
|
85
|
+
return stored.accessToken;
|
|
86
|
+
}
|
|
87
|
+
if (status === "needs_refresh") {
|
|
88
|
+
const refreshed = await refreshWithLock(opts, stored);
|
|
89
|
+
if (!refreshed) {
|
|
90
|
+
throw new NeedAuthorizationError(opts.userOpenId);
|
|
91
|
+
}
|
|
92
|
+
return refreshed.accessToken;
|
|
93
|
+
}
|
|
94
|
+
await removeStoredToken(opts.appId, opts.userOpenId);
|
|
95
|
+
throw new NeedAuthorizationError(opts.userOpenId);
|
|
96
|
+
}
|
|
97
|
+
async function callWithUAT(opts, apiCall) {
|
|
98
|
+
const accessToken = await getValidAccessToken(opts);
|
|
99
|
+
try {
|
|
100
|
+
return await apiCall(accessToken);
|
|
101
|
+
} catch (err) {
|
|
102
|
+
const code = err?.code ?? err?.response?.data?.code;
|
|
103
|
+
if (TOKEN_RETRY_CODES.has(code)) {
|
|
104
|
+
log.warn(`API call failed (code=${code}), refreshing and retrying`);
|
|
105
|
+
const stored = await getStoredToken(opts.appId, opts.userOpenId);
|
|
106
|
+
if (!stored) throw new NeedAuthorizationError(opts.userOpenId);
|
|
107
|
+
const refreshed = await refreshWithLock(opts, stored);
|
|
108
|
+
if (!refreshed) throw new NeedAuthorizationError(opts.userOpenId);
|
|
109
|
+
return await apiCall(refreshed.accessToken);
|
|
110
|
+
}
|
|
111
|
+
throw err;
|
|
112
|
+
}
|
|
113
|
+
}
|
|
114
|
+
async function revokeUAT(appId, userOpenId) {
|
|
115
|
+
await removeStoredToken(appId, userOpenId);
|
|
116
|
+
log.info(`revoked UAT for ${userOpenId}`);
|
|
117
|
+
}
|
|
118
|
+
export {
|
|
119
|
+
NeedAuthorizationError,
|
|
120
|
+
callWithUAT,
|
|
121
|
+
getValidAccessToken,
|
|
122
|
+
revokeUAT
|
|
123
|
+
};
|
|
124
|
+
//# sourceMappingURL=uat-client.js.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../../src/core/uat-client.ts"],
|
|
4
|
+
"sourcesContent": ["/**\n * Copyright (c) 2026 ByteDance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n *\n * UAT (User Access Token) API call wrapper.\n *\n * Provides a safe, auto-refreshing interface for making Feishu API calls on\n * behalf of a user. Tokens are read from the OS Keychain, refreshed\n * transparently, and **never** exposed to the AI layer.\n */\n\nimport type { LarkBrand } from './types';\nimport {\n getStoredToken,\n setStoredToken,\n removeStoredToken,\n tokenStatus,\n maskToken,\n type StoredUAToken,\n} from './token-store';\nimport { resolveOAuthEndpoints } from './device-flow';\nimport { larkLogger } from './lark-logger';\n\nconst log = larkLogger('core/uat-client');\nimport { feishuFetch } from './feishu-fetch';\nimport { REFRESH_TOKEN_IRRECOVERABLE, TOKEN_RETRY_CODES, NeedAuthorizationError } from './auth-errors';\n\n// Re-export for backward compatibility\nexport { NeedAuthorizationError };\n\n// ---------------------------------------------------------------------------\n// Types\n// ---------------------------------------------------------------------------\n\nexport interface UATCallOptions {\n userOpenId: string;\n appId: string;\n appSecret: string;\n domain: LarkBrand;\n}\n\nexport interface UATStatus {\n authorized: boolean;\n userOpenId: string;\n scope?: string;\n expiresAt?: number;\n refreshExpiresAt?: number;\n grantedAt?: number;\n tokenStatus?: 'valid' | 'needs_refresh' | 'expired';\n}\n\n// ---------------------------------------------------------------------------\n// Per-user refresh lock\n// ---------------------------------------------------------------------------\n\n/**\n * Guards against concurrent refresh operations for the same user.\n *\n * refresh_token is single-use: if two requests trigger a refresh\n * simultaneously, the second one would use an already-consumed token and\n * fail. The lock ensures only one refresh runs at a time per user.\n */\nconst refreshLocks = new Map<string, Promise<StoredUAToken | null>>();\n\n// ---------------------------------------------------------------------------\n// Refresh implementation\n// ---------------------------------------------------------------------------\n\nasync function doRefreshToken(opts: UATCallOptions, stored: StoredUAToken): Promise<StoredUAToken | null> {\n // refresh_token already expired \u2192 can't refresh, need re-auth.\n if (Date.now() >= stored.refreshExpiresAt) {\n log.info(`refresh_token expired for ${opts.userOpenId}, clearing`);\n await removeStoredToken(opts.appId, opts.userOpenId);\n return null;\n }\n\n const endpoints = resolveOAuthEndpoints(opts.domain);\n\n const resp = await feishuFetch(endpoints.token, {\n method: 'POST',\n headers: { 'Content-Type': 'application/x-www-form-urlencoded' },\n body: new URLSearchParams({\n grant_type: 'refresh_token',\n refresh_token: stored.refreshToken,\n client_id: opts.appId,\n client_secret: opts.appSecret,\n }).toString(),\n });\n\n const data = (await resp.json()) as Record<string, unknown>;\n\n // Feishu v2 token endpoint returns `code: 0` on success.\n // Some responses use `error` field instead (standard OAuth).\n const code = data.code as number | undefined;\n const error = data.error as string | undefined;\n\n if ((code !== undefined && code !== 0) || error) {\n const errCode = code ?? error;\n const errMsg = (data.error_description as string) ?? (data.msg as string) ?? 'unknown';\n\n // Known irrecoverable codes: invalid/expired/missing refresh_token\n if (REFRESH_TOKEN_IRRECOVERABLE.has(code as number)) {\n log.warn(`refresh failed (code=${errCode}), clearing token for ${opts.userOpenId}`);\n await removeStoredToken(opts.appId, opts.userOpenId);\n return null;\n }\n\n throw new Error(`Token refresh failed (code=${errCode}): ${errMsg}`);\n }\n\n if (!data.access_token) {\n throw new Error('Token refresh returned no access_token');\n }\n\n const now = Date.now();\n const updated: StoredUAToken = {\n userOpenId: stored.userOpenId,\n appId: opts.appId,\n accessToken: data.access_token as string,\n // refresh_token is rotated \u2013 always use the new one.\n refreshToken: (data.refresh_token as string) ?? stored.refreshToken,\n expiresAt: now + ((data.expires_in as number) ?? 7200) * 1000,\n refreshExpiresAt: data.refresh_token_expires_in\n ? now + (data.refresh_token_expires_in as number) * 1000\n : stored.refreshExpiresAt,\n scope: (data.scope as string) ?? stored.scope,\n grantedAt: stored.grantedAt,\n };\n\n await setStoredToken(updated);\n log.info(`refreshed UAT for ${opts.userOpenId} (at:${maskToken(updated.accessToken)})`);\n return updated;\n}\n\n/**\n * Refresh with per-user locking.\n */\nasync function refreshWithLock(opts: UATCallOptions, stored: StoredUAToken): Promise<StoredUAToken | null> {\n const key = `${opts.appId}:${opts.userOpenId}`;\n\n // Another refresh is already in-flight \u2013 wait for it and re-read.\n const existing = refreshLocks.get(key);\n if (existing) {\n await existing;\n return getStoredToken(opts.appId, opts.userOpenId);\n }\n\n const promise = doRefreshToken(opts, stored);\n refreshLocks.set(key, promise);\n try {\n return await promise;\n } finally {\n refreshLocks.delete(key);\n }\n}\n\n// ---------------------------------------------------------------------------\n// Public API\n// ---------------------------------------------------------------------------\n\n/**\n * Obtain a valid access_token for the given user.\n *\n * - Reads from Keychain.\n * - Refreshes proactively if the token is about to expire.\n * - Throws when no token exists or refresh fails irrecoverably.\n *\n * **The returned token must never be exposed to the AI layer.**\n */\nexport async function getValidAccessToken(opts: UATCallOptions): Promise<string> {\n // Owner \u68C0\u67E5\u5DF2\u8FC1\u79FB\u5230 owner-policy.ts\uFF08\u7531 tool-client.ts \u7684 invokeAsUser \u8C03\u7528\uFF09\n const stored = await getStoredToken(opts.appId, opts.userOpenId);\n if (!stored) {\n throw new NeedAuthorizationError(opts.userOpenId);\n }\n\n const status = tokenStatus(stored);\n\n if (status === 'valid') {\n return stored.accessToken;\n }\n\n if (status === 'needs_refresh') {\n const refreshed = await refreshWithLock(opts, stored);\n if (!refreshed) {\n throw new NeedAuthorizationError(opts.userOpenId);\n }\n return refreshed.accessToken;\n }\n\n // expired\n await removeStoredToken(opts.appId, opts.userOpenId);\n throw new NeedAuthorizationError(opts.userOpenId);\n}\n\n/**\n * Execute an API call with a valid UAT, retrying once on token-expiry errors.\n */\nexport async function callWithUAT<T>(opts: UATCallOptions, apiCall: (accessToken: string) => Promise<T>): Promise<T> {\n const accessToken = await getValidAccessToken(opts);\n try {\n return await apiCall(accessToken);\n } catch (err: unknown) {\n // Retry once if the server reports token invalid/expired.\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const code = (err as any)?.code ?? (err as any)?.response?.data?.code;\n if (TOKEN_RETRY_CODES.has(code as number)) {\n log.warn(`API call failed (code=${code}), refreshing and retrying`);\n const stored = await getStoredToken(opts.appId, opts.userOpenId);\n if (!stored) throw new NeedAuthorizationError(opts.userOpenId);\n const refreshed = await refreshWithLock(opts, stored);\n if (!refreshed) throw new NeedAuthorizationError(opts.userOpenId);\n return await apiCall(refreshed.accessToken);\n }\n throw err;\n }\n}\n\n/**\n * Revoke a user's UAT by removing it from the Keychain.\n */\nexport async function revokeUAT(appId: string, userOpenId: string): Promise<void> {\n await removeStoredToken(appId, userOpenId);\n log.info(`revoked UAT for ${userOpenId}`);\n}\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
|
+
"names": []
|
|
7
|
+
}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import { fileURLToPath } from "node:url";
|
|
2
|
+
import { dirname, join } from "node:path";
|
|
3
|
+
import { readFileSync } from "node:fs";
|
|
4
|
+
let cachedVersion;
|
|
5
|
+
function getPluginVersion() {
|
|
6
|
+
if (cachedVersion) return cachedVersion;
|
|
7
|
+
try {
|
|
8
|
+
const __filename = fileURLToPath(import.meta.url);
|
|
9
|
+
const __dirname = dirname(__filename);
|
|
10
|
+
const packageJsonPath = join(__dirname, "..", "..", "package.json");
|
|
11
|
+
const raw = readFileSync(packageJsonPath, "utf8");
|
|
12
|
+
const pkg = JSON.parse(raw);
|
|
13
|
+
cachedVersion = pkg.version ?? "unknown";
|
|
14
|
+
return cachedVersion;
|
|
15
|
+
} catch {
|
|
16
|
+
cachedVersion = "unknown";
|
|
17
|
+
return cachedVersion;
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
function getUserAgent() {
|
|
21
|
+
return `feishu-openclaw-plugin/${getPluginVersion()}`;
|
|
22
|
+
}
|
|
23
|
+
export {
|
|
24
|
+
getPluginVersion,
|
|
25
|
+
getUserAgent
|
|
26
|
+
};
|
|
27
|
+
//# sourceMappingURL=version.js.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../../src/core/version.ts"],
|
|
4
|
+
"sourcesContent": ["/**\n * Copyright (c) 2026 ByteDance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n *\n * \u63D2\u4EF6\u7248\u672C\u53F7\u7BA1\u7406\n *\n * \u4ECE package.json \u8BFB\u53D6\u7248\u672C\u53F7\u5E76\u751F\u6210 User-Agent \u5B57\u7B26\u4E32\u3002\n */\n\nimport { fileURLToPath } from 'node:url';\nimport { dirname, join } from 'node:path';\nimport { readFileSync } from 'node:fs';\n\n/** \u7F13\u5B58\u7684\u7248\u672C\u53F7 */\nlet cachedVersion: string | undefined;\n\n/**\n * \u83B7\u53D6\u63D2\u4EF6\u7248\u672C\u53F7\uFF08\u4ECE package.json \u8BFB\u53D6\uFF09\n *\n * @returns \u7248\u672C\u53F7\u5B57\u7B26\u4E32\uFF0C\u5982 \"2026.2.28.5\"\uFF1B\u8BFB\u53D6\u5931\u8D25\u8FD4\u56DE \"unknown\"\n */\nexport function getPluginVersion(): string {\n if (cachedVersion) return cachedVersion;\n\n try {\n // \u5F53\u524D\u6587\u4EF6: src/core/version.ts \u2192 \u5411\u4E0A\u4E24\u7EA7\u5230\u8FBE\u9879\u76EE\u6839\u76EE\u5F55\n const __filename = fileURLToPath(import.meta.url);\n const __dirname = dirname(__filename);\n const packageJsonPath = join(__dirname, '..', '..', 'package.json');\n\n const raw = readFileSync(packageJsonPath, 'utf8');\n const pkg = JSON.parse(raw) as { version?: string };\n cachedVersion = pkg.version ?? 'unknown';\n return cachedVersion;\n } catch {\n cachedVersion = 'unknown';\n return cachedVersion;\n }\n}\n\n/**\n * \u751F\u6210 User-Agent \u5B57\u7B26\u4E32\n *\n * @returns User-Agent \u5B57\u7B26\u4E32\uFF0C\u683C\u5F0F\uFF1A`feishu-openclaw-plugin/{version}`\n *\n * @example\n * ```typescript\n * getUserAgent() // => \"feishu-openclaw-plugin/2026.2.28.5\"\n * ```\n */\nexport function getUserAgent(): string {\n return `feishu-openclaw-plugin/${getPluginVersion()}`;\n}\n"],
|
|
5
|
+
"mappings": "AASA,SAAS,qBAAqB;AAC9B,SAAS,SAAS,YAAY;AAC9B,SAAS,oBAAoB;AAG7B,IAAI;AAOG,SAAS,mBAA2B;AACzC,MAAI,cAAe,QAAO;AAE1B,MAAI;AAEF,UAAM,aAAa,cAAc,YAAY,GAAG;AAChD,UAAM,YAAY,QAAQ,UAAU;AACpC,UAAM,kBAAkB,KAAK,WAAW,MAAM,MAAM,cAAc;AAElE,UAAM,MAAM,aAAa,iBAAiB,MAAM;AAChD,UAAM,MAAM,KAAK,MAAM,GAAG;AAC1B,oBAAgB,IAAI,WAAW;AAC/B,WAAO;AAAA,EACT,QAAQ;AACN,oBAAgB;AAChB,WAAO;AAAA,EACT;AACF;AAYO,SAAS,eAAuB;AACrC,SAAO,0BAA0B,iBAAiB,CAAC;AACrD;",
|
|
6
|
+
"names": []
|
|
7
|
+
}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import { safeParse } from "./utils";
|
|
2
|
+
import { formatDuration } from "./utils";
|
|
3
|
+
const convertAudio = (raw) => {
|
|
4
|
+
const parsed = safeParse(raw);
|
|
5
|
+
const fileKey = parsed?.file_key;
|
|
6
|
+
if (!fileKey) {
|
|
7
|
+
return { content: "[audio]", resources: [] };
|
|
8
|
+
}
|
|
9
|
+
const duration = parsed?.duration;
|
|
10
|
+
const durationAttr = duration != null ? ` duration="${formatDuration(duration)}"` : "";
|
|
11
|
+
return {
|
|
12
|
+
content: `<audio key="${fileKey}"${durationAttr}/>`,
|
|
13
|
+
resources: [{ type: "audio", fileKey, duration: duration ?? void 0 }]
|
|
14
|
+
};
|
|
15
|
+
};
|
|
16
|
+
export {
|
|
17
|
+
convertAudio
|
|
18
|
+
};
|
|
19
|
+
//# sourceMappingURL=audio.js.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../../../../src/messaging/converters/audio.ts"],
|
|
4
|
+
"sourcesContent": ["/**\n * Copyright (c) 2026 ByteDance Ltd. and/or its affiliates\n * SPDX-License-Identifier: MIT\n *\n * Converter for \"audio\" message type.\n */\n\nimport type { ContentConverterFn } from './types';\nimport { safeParse } from './utils';\nimport { formatDuration } from './utils';\n\nexport const convertAudio: ContentConverterFn = (raw) => {\n const parsed = safeParse(raw) as\n | {\n file_key?: string;\n duration?: number;\n }\n | undefined;\n\n const fileKey = parsed?.file_key;\n if (!fileKey) {\n return { content: '[audio]', resources: [] };\n }\n\n const duration = parsed?.duration;\n const durationAttr = duration != null ? ` duration=\"${formatDuration(duration)}\"` : '';\n\n return {\n content: `<audio key=\"${fileKey}\"${durationAttr}/>`,\n resources: [{ type: 'audio', fileKey, duration: duration ?? undefined }],\n };\n};\n"],
|
|
5
|
+
"mappings": "AAQA,SAAS,iBAAiB;AAC1B,SAAS,sBAAsB;AAExB,MAAM,eAAmC,CAAC,QAAQ;AACvD,QAAM,SAAS,UAAU,GAAG;AAO5B,QAAM,UAAU,QAAQ;AACxB,MAAI,CAAC,SAAS;AACZ,WAAO,EAAE,SAAS,WAAW,WAAW,CAAC,EAAE;AAAA,EAC7C;AAEA,QAAM,WAAW,QAAQ;AACzB,QAAM,eAAe,YAAY,OAAO,cAAc,eAAe,QAAQ,CAAC,MAAM;AAEpF,SAAO;AAAA,IACL,SAAS,eAAe,OAAO,IAAI,YAAY;AAAA,IAC/C,WAAW,CAAC,EAAE,MAAM,SAAS,SAAS,UAAU,YAAY,OAAU,CAAC;AAAA,EACzE;AACF;",
|
|
6
|
+
"names": []
|
|
7
|
+
}
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
import { safeParse, millisToDatetime } from "./utils";
|
|
2
|
+
function formatCalendarContent(parsed) {
|
|
3
|
+
const summary = parsed?.summary ?? "";
|
|
4
|
+
const parts = [];
|
|
5
|
+
if (summary) {
|
|
6
|
+
parts.push(`\u{1F4C5} ${summary}`);
|
|
7
|
+
}
|
|
8
|
+
const start = parsed?.start_time ? millisToDatetime(parsed.start_time) : "";
|
|
9
|
+
const end = parsed?.end_time ? millisToDatetime(parsed.end_time) : "";
|
|
10
|
+
if (start && end) {
|
|
11
|
+
parts.push(`\u{1F559} ${start} ~ ${end}`);
|
|
12
|
+
} else if (start) {
|
|
13
|
+
parts.push(`\u{1F559} ${start}`);
|
|
14
|
+
}
|
|
15
|
+
return parts.join("\n") || "[calendar event]";
|
|
16
|
+
}
|
|
17
|
+
const convertShareCalendarEvent = (raw) => {
|
|
18
|
+
const parsed = safeParse(raw);
|
|
19
|
+
const inner = formatCalendarContent(parsed);
|
|
20
|
+
return {
|
|
21
|
+
content: `<calendar_share>${inner}</calendar_share>`,
|
|
22
|
+
resources: []
|
|
23
|
+
};
|
|
24
|
+
};
|
|
25
|
+
const convertCalendar = (raw) => {
|
|
26
|
+
const parsed = safeParse(raw);
|
|
27
|
+
const inner = formatCalendarContent(parsed);
|
|
28
|
+
return {
|
|
29
|
+
content: `<calendar_invite>${inner}</calendar_invite>`,
|
|
30
|
+
resources: []
|
|
31
|
+
};
|
|
32
|
+
};
|
|
33
|
+
const convertGeneralCalendar = (raw) => {
|
|
34
|
+
const parsed = safeParse(raw);
|
|
35
|
+
const inner = formatCalendarContent(parsed);
|
|
36
|
+
return {
|
|
37
|
+
content: `<calendar>${inner}</calendar>`,
|
|
38
|
+
resources: []
|
|
39
|
+
};
|
|
40
|
+
};
|
|
41
|
+
export {
|
|
42
|
+
convertCalendar,
|
|
43
|
+
convertGeneralCalendar,
|
|
44
|
+
convertShareCalendarEvent
|
|
45
|
+
};
|
|
46
|
+
//# sourceMappingURL=calendar.js.map
|