@openclaw/slack 2026.11.3 → 2026.11.5-beta.2
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/dist/.setup/{account-inspect-CmkKiSb9.mjs → account-inspect-BLVha-ov.mjs} +11 -8
- package/dist/.setup/{accounts-msihSF3-.mjs → accounts-CGJScKtk.mjs} +10 -1
- package/dist/.setup/{action-runtime-ChRfnnBu.mjs → action-runtime-D01wBhx5.mjs} +38 -45
- package/dist/.setup/action-runtime.runtime-VQGaR6g8.mjs +1 -0
- package/dist/.setup/{actions-By7tvpvv.mjs → actions-D5S6D_BU.mjs} +89 -76
- package/dist/.setup/{approval-handler.runtime-D8ArtDQt.mjs → approval-handler.runtime-Buw5jh2Y.mjs} +26 -30
- package/dist/.setup/{approval-message-updates-DT7XBPbV.mjs → approval-message-updates-pmXcve5E.mjs} +1 -1
- package/dist/.setup/{channel-DLFiMJm2.mjs → channel-C_R98Nbv.mjs} +569 -339
- package/dist/.setup/{channel-type-BEFP2ORi.mjs → channel-type-B5P3w9eA.mjs} +4 -8
- package/dist/.setup/{channel.setup-CzFw73mU.mjs → channel.setup-Lq2OxKkF.mjs} +13 -13
- package/dist/.setup/{config-schema-DNnh6bWU.mjs → config-schema-BWAaa5au.mjs} +3 -7
- package/dist/.setup/cursor-pages-CATAzbTT.mjs +313 -0
- package/dist/.setup/{directory-config-Cjj0N8R0.mjs → directory-config-D-hf9KGQ.mjs} +3 -3
- package/dist/.setup/{directory-live-BIKD-5B_.mjs → directory-live-onKAFI1E.mjs} +4 -4
- package/dist/.setup/{doctor-contract-Cd4-VzIM.mjs → doctor-contract-9-QJRCXk.mjs} +37 -45
- package/dist/.setup/{message-tool-api-BS5ekEA_.mjs → message-tool-api-LGIgVXJf.mjs} +4 -3
- package/dist/.setup/{monitor-CV6Z6FKP.mjs → monitor-Cm1TuqxN.mjs} +3424 -3703
- package/dist/.setup/{outbound-adapter-9dbnYtL1.mjs → outbound-adapter-C-95EWl2.mjs} +30 -36
- package/dist/.setup/paths-B1u59oLK.mjs +8 -0
- package/dist/.setup/{pipeline.runtime-DLIQf1Bo.mjs → pipeline.runtime-DGnV6akc.mjs} +416 -534
- package/dist/.setup/{policy-yhn48xf5.mjs → policy-DxhGRvc2.mjs} +1 -2
- package/dist/.setup/{session-status-Dv8wNBEt.mjs → probe-DANukR3O.mjs} +1206 -839
- package/dist/.setup/question-delivery-CWC7sRhH.mjs +39 -0
- package/dist/.setup/{relay-source-CxDcrn16.mjs → relay-source-DoyOlTbK.mjs} +5 -3
- package/dist/.setup/{replies-MRkrg3rC.mjs → replies-BcmUKord.mjs} +34 -19
- package/dist/.setup/{reply-blocks-Ca-raz2z.mjs → reply-blocks-BzsXUUUL.mjs} +201 -206
- package/dist/.setup/{resolve-channels-DRRhElwz.mjs → resolve-channels-XDPgnesf.mjs} +4 -7
- package/dist/.setup/{resolve-users-Cz8e17ky.mjs → resolve-users-aDAv24U2.mjs} +8 -16
- package/dist/.setup/runtime-setter-api-Cx_PV-xu.mjs +2 -0
- package/dist/.setup/{scopes-DfQVi8Jw.mjs → scopes-BocHwImV.mjs} +2 -1
- package/dist/.setup/secret-contract-api-BlLz88mj.mjs +2 -0
- package/dist/.setup/{secret-contract-vVRMoE1D.mjs → secret-contract-uiQtoNlu.mjs} +2 -2
- package/dist/.setup/{send-results-eeOu_HYm.mjs → send-results-BGxlroJ-.mjs} +3 -4
- package/dist/.setup/{send-C-8wY0lK.mjs → send-yK6_-px6.mjs} +297 -334
- package/dist/.setup/setup-plugin-api-Cfz58xoh.mjs +2 -0
- package/dist/.setup/{setup-surface--n8VsDvV.mjs → setup-surface-C0KRtyqa.mjs} +5 -6
- package/dist/.setup/{slash-dispatch.runtime-D3Wq45ER.mjs → slash-dispatch.runtime-CyVC3bYx.mjs} +2 -2
- package/dist/.setup/{target-parsing-FFE26kOV.mjs → target-parsing-Bx2UZniD.mjs} +1 -2
- package/dist/.setup/{targets-C6LZQL1Q.mjs → targets-D-ASeWHy.mjs} +1 -1
- package/dist/.source-module-urls/c5ffd0957b234c7c12090e7de4eca2482ef339b8561e078da55b734211b0ba58.json +1 -0
- package/dist/account-inspect-api.js +1 -1
- package/dist/api.js +16 -17
- package/dist/channel-config-api.js +1 -2
- package/dist/channel-plugin-api.js +1 -2
- package/dist/directory-contract-api.js +1 -2
- package/dist/doctor-contract-api.js +1 -2
- package/dist/index.js +0 -6
- package/dist/message-tool-api.js +1 -2
- package/dist/runtime-api.js +10 -12
- package/dist/runtime-setter-api.js +1 -2
- package/dist/secret-contract-api.js +1 -2
- package/dist/security-contract-api.js +1 -2
- package/dist/setup-entry.js +3 -3
- package/dist/setup-plugin-api.js +1 -2
- package/node_modules/@slack/bolt/node_modules/@types/node/README.md +1 -1
- package/node_modules/@slack/bolt/node_modules/@types/node/package.json +2 -2
- package/node_modules/@slack/bolt/node_modules/@types/node/util.d.ts +6 -3
- package/node_modules/@slack/bolt/node_modules/content-disposition/README.md +105 -35
- package/node_modules/@slack/bolt/node_modules/content-disposition/dist/index.d.ts +72 -0
- package/node_modules/@slack/bolt/node_modules/content-disposition/dist/index.js +388 -0
- package/node_modules/@slack/bolt/node_modules/content-disposition/dist/index.js.map +1 -0
- package/node_modules/@slack/bolt/node_modules/content-disposition/package.json +31 -19
- package/node_modules/@slack/bolt/node_modules/content-type/README.md +34 -57
- package/node_modules/@slack/bolt/node_modules/content-type/package.json +35 -25
- package/node_modules/@slack/bolt/node_modules/express/Readme.md +15 -9
- package/node_modules/@slack/bolt/node_modules/express/lib/application.js +2 -2
- package/node_modules/@slack/bolt/node_modules/express/lib/request.js +32 -19
- package/node_modules/@slack/bolt/node_modules/express/lib/response.js +27 -30
- package/node_modules/@slack/bolt/node_modules/express/package.json +10 -10
- package/node_modules/@slack/bolt/node_modules/qs/.github/THREAT_MODEL.md +4 -2
- package/node_modules/@slack/bolt/node_modules/qs/CHANGELOG.md +38 -14
- package/node_modules/@slack/bolt/node_modules/qs/README.md +31 -3
- package/node_modules/@slack/bolt/node_modules/qs/dist/qs.js +20 -20
- package/node_modules/@slack/bolt/node_modules/qs/lib/parse.js +94 -4
- package/node_modules/@slack/bolt/node_modules/qs/lib/stringify.js +4 -4
- package/node_modules/@slack/bolt/node_modules/qs/lib/utils.js +130 -6
- package/node_modules/@slack/bolt/node_modules/qs/package.json +4 -4
- package/node_modules/@slack/bolt/node_modules/qs/test/parse.js +174 -0
- package/node_modules/@slack/bolt/node_modules/qs/test/stringify.js +263 -33
- package/node_modules/@slack/bolt/node_modules/qs/test/utils.js +184 -0
- package/node_modules/@slack/web-api/node_modules/@types/node/README.md +1 -1
- package/node_modules/@slack/web-api/node_modules/@types/node/package.json +2 -2
- package/node_modules/@slack/web-api/node_modules/@types/node/util.d.ts +6 -3
- package/node_modules/typebox/build/format/duration.d.mts +2 -2
- package/node_modules/typebox/build/format/duration.mjs +2 -2
- package/node_modules/typebox/build/format/idn_email.d.mts +1 -0
- package/node_modules/typebox/build/format/idn_email.mjs +1 -0
- package/node_modules/typebox/build/format/idn_hostname.d.mts +1 -1
- package/node_modules/typebox/build/format/idn_hostname.mjs +1 -1
- package/node_modules/typebox/build/format/ipv4.d.mts +2 -2
- package/node_modules/typebox/build/format/ipv4.mjs +2 -2
- package/node_modules/typebox/build/format/ipv6.d.mts +1 -1
- package/node_modules/typebox/build/format/ipv6.mjs +1 -1
- package/node_modules/typebox/build/format/relative_json_pointer.d.mts +2 -2
- package/node_modules/typebox/build/format/relative_json_pointer.mjs +2 -2
- package/node_modules/typebox/build/schema/build.mjs +1 -0
- package/node_modules/typebox/build/schema/engine/_unique.d.mts +4 -2
- package/node_modules/typebox/build/schema/engine/_unique.mjs +7 -3
- package/node_modules/typebox/build/schema/engine/additionalItems.mjs +3 -3
- package/node_modules/typebox/build/schema/engine/additionalProperties.d.mts +0 -3
- package/node_modules/typebox/build/schema/engine/additionalProperties.mjs +15 -17
- package/node_modules/typebox/build/schema/engine/contains.mjs +3 -3
- package/node_modules/typebox/build/schema/engine/index.d.mts +1 -0
- package/node_modules/typebox/build/schema/engine/index.mjs +1 -0
- package/node_modules/typebox/build/schema/engine/items.mjs +7 -4
- package/node_modules/typebox/build/schema/engine/maxContains.mjs +2 -2
- package/node_modules/typebox/build/schema/engine/minContains.mjs +3 -3
- package/node_modules/typebox/build/schema/engine/oneOf.mjs +2 -2
- package/node_modules/typebox/build/schema/engine/patternProperties.mjs +2 -2
- package/node_modules/typebox/build/schema/engine/propertyNames.mjs +2 -2
- package/node_modules/typebox/build/schema/engine/unevaluatedItems.mjs +2 -2
- package/node_modules/typebox/build/schema/engine/unevaluatedProperties.mjs +2 -2
- package/node_modules/typebox/build/system/hashing/hash.mjs +63 -34
- package/node_modules/typebox/build/system/locale/en_US.mjs +2 -1
- package/node_modules/typebox/build/system/memory/assign.d.mts +2 -8
- package/node_modules/typebox/build/system/memory/assign.mjs +13 -6
- package/node_modules/typebox/build/system/memory/clone.d.mts +4 -5
- package/node_modules/typebox/build/system/memory/clone.mjs +8 -96
- package/node_modules/typebox/build/system/memory/create.d.mts +1 -5
- package/node_modules/typebox/build/system/memory/create.mjs +18 -13
- package/node_modules/typebox/build/system/memory/deep.d.mts +2 -0
- package/node_modules/typebox/build/system/memory/deep.mjs +108 -0
- package/node_modules/typebox/build/system/memory/discard.d.mts +1 -1
- package/node_modules/typebox/build/system/memory/discard.mjs +9 -8
- package/node_modules/typebox/build/system/memory/finalize.d.mts +4 -0
- package/node_modules/typebox/build/system/memory/finalize.mjs +30 -0
- package/node_modules/typebox/build/system/memory/keys.d.mts +2 -0
- package/node_modules/typebox/build/system/memory/keys.mjs +8 -0
- package/node_modules/typebox/build/system/memory/update.d.mts +1 -4
- package/node_modules/typebox/build/system/memory/update.mjs +43 -16
- package/node_modules/typebox/build/type/engine/call/index.d.mts +1 -0
- package/node_modules/typebox/build/type/engine/call/index.mjs +1 -0
- package/node_modules/typebox/build/type/engine/evaluate/composite.d.mts +2 -24
- package/node_modules/typebox/build/type/engine/evaluate/composite.mjs +2 -29
- package/node_modules/typebox/build/type/engine/evaluate/index.d.mts +1 -0
- package/node_modules/typebox/build/type/engine/evaluate/index.mjs +1 -0
- package/node_modules/typebox/build/type/engine/evaluate/narrow.d.mts +5 -1
- package/node_modules/typebox/build/type/engine/evaluate/narrow.mjs +6 -1
- package/node_modules/typebox/build/type/engine/evaluate/property.d.mts +30 -0
- package/node_modules/typebox/build/type/engine/evaluate/property.mjs +29 -0
- package/node_modules/typebox/build/type/engine/immutable/instantiate_add.d.mts +1 -3
- package/node_modules/typebox/build/type/engine/immutable/instantiate_add.mjs +1 -4
- package/node_modules/typebox/build/type/engine/object/from_intersect.d.mts +2 -2
- package/node_modules/typebox/build/type/engine/object/from_intersect.mjs +2 -2
- package/node_modules/typebox/build/type/engine/object/from_union.d.mts +2 -2
- package/node_modules/typebox/build/type/engine/object/from_union.mjs +2 -2
- package/node_modules/typebox/build/type/engine/optional/instantiate_add.d.mts +1 -3
- package/node_modules/typebox/build/type/engine/optional/instantiate_add.mjs +1 -4
- package/node_modules/typebox/build/type/engine/readonly/instantiate_add.d.mts +1 -3
- package/node_modules/typebox/build/type/engine/readonly/instantiate_add.mjs +1 -4
- package/node_modules/typebox/build/type/engine/this/index.d.mts +1 -0
- package/node_modules/typebox/build/type/engine/this/index.mjs +1 -0
- package/node_modules/typebox/build/value/clone/clone.d.mts +4 -3
- package/node_modules/typebox/build/value/clone/clone.mjs +5 -7
- package/node_modules/typebox/build/value/repair/from_cyclic.d.mts +2 -0
- package/node_modules/typebox/build/value/repair/from_cyclic.mjs +6 -0
- package/node_modules/typebox/build/value/shared/union_priority_sort.mjs +25 -14
- package/node_modules/typebox/package.json +1 -1
- package/node_modules/typebox/readme.md +1 -1
- package/node_modules/undici/docs/docs/api/Interceptors.md +15 -2
- package/node_modules/undici/lib/dispatcher/client-h2.js +78 -3
- package/node_modules/undici/lib/dispatcher/pool-base.js +20 -3
- package/node_modules/undici/package.json +3 -3
- package/node_modules/undici/types/api.d.ts +1 -1
- package/node_modules/undici/types/utility.d.ts +4 -4
- package/node_modules/zod/package.json +1 -1
- package/node_modules/zod/src/v4/classic/tests/array.test.ts +27 -0
- package/node_modules/zod/src/v4/classic/tests/map.test.ts +7 -0
- package/node_modules/zod/src/v4/classic/tests/set.test.ts +6 -0
- package/node_modules/zod/src/v4/core/compile.ts +9 -0
- package/node_modules/zod/src/v4/core/schemas.ts +35 -1
- package/node_modules/zod/src/v4/core/util.ts +13 -0
- package/node_modules/zod/src/v4/core/versions.ts +1 -1
- package/node_modules/zod/v4/core/compile.cjs +8 -0
- package/node_modules/zod/v4/core/compile.js +8 -0
- package/node_modules/zod/v4/core/schemas.cjs +30 -0
- package/node_modules/zod/v4/core/schemas.d.cts +3 -1
- package/node_modules/zod/v4/core/schemas.d.ts +3 -1
- package/node_modules/zod/v4/core/schemas.js +30 -0
- package/node_modules/zod/v4/core/util.cjs +15 -0
- package/node_modules/zod/v4/core/util.d.cts +2 -0
- package/node_modules/zod/v4/core/util.d.ts +2 -0
- package/node_modules/zod/v4/core/util.js +14 -0
- package/node_modules/zod/v4/core/versions.cjs +1 -1
- package/node_modules/zod/v4/core/versions.js +1 -1
- package/openclaw.plugin.json +6 -30
- package/package.json +7 -7
- package/dist/.setup/action-runtime.runtime-vLxx_7s2.mjs +0 -2
- package/dist/.setup/http-C9sM-FXe.mjs +0 -2
- package/dist/.setup/plugin-routes-D4qozHVn.mjs +0 -22
- package/dist/.setup/probe-IiHogLQN.mjs +0 -694
- package/dist/.setup/registry-DizWcnNp.mjs +0 -36
- package/dist/.setup/runtime-setter-api-CMFvhrAr.mjs +0 -3
- package/dist/.setup/secret-contract-api-DK9gZldc.mjs +0 -3
- package/dist/.setup/setup-plugin-api-BGD1TYnK.mjs +0 -3
- package/dist/.setup/shared-BhJHIZs1.mjs +0 -259
- package/dist/http-routes-api.js +0 -2
- package/node_modules/@slack/bolt/node_modules/body-parser/node_modules/content-type/LICENSE +0 -22
- package/node_modules/@slack/bolt/node_modules/body-parser/node_modules/content-type/README.md +0 -71
- package/node_modules/@slack/bolt/node_modules/body-parser/node_modules/content-type/package.json +0 -52
- package/node_modules/@slack/bolt/node_modules/content-disposition/index.js +0 -536
- package/node_modules/@slack/bolt/node_modules/content-type/HISTORY.md +0 -29
- package/node_modules/@slack/bolt/node_modules/content-type/index.js +0 -225
- package/node_modules/@slack/bolt/node_modules/negotiator/node_modules/content-type/LICENSE +0 -22
- package/node_modules/@slack/bolt/node_modules/negotiator/node_modules/content-type/README.md +0 -71
- package/node_modules/@slack/bolt/node_modules/negotiator/node_modules/content-type/dist/index.d.ts +0 -46
- package/node_modules/@slack/bolt/node_modules/negotiator/node_modules/content-type/dist/index.js +0 -176
- package/node_modules/@slack/bolt/node_modules/negotiator/node_modules/content-type/dist/index.js.map +0 -1
- package/node_modules/@slack/bolt/node_modules/negotiator/node_modules/content-type/package.json +0 -52
- package/node_modules/@slack/bolt/node_modules/type-is/node_modules/content-type/LICENSE +0 -22
- package/node_modules/@slack/bolt/node_modules/type-is/node_modules/content-type/README.md +0 -71
- package/node_modules/@slack/bolt/node_modules/type-is/node_modules/content-type/dist/index.d.ts +0 -46
- package/node_modules/@slack/bolt/node_modules/type-is/node_modules/content-type/dist/index.js +0 -176
- package/node_modules/@slack/bolt/node_modules/type-is/node_modules/content-type/dist/index.js.map +0 -1
- package/node_modules/@slack/bolt/node_modules/type-is/node_modules/content-type/package.json +0 -52
- package/node_modules/typebox/build/system/memory/freeze.d.mts +0 -4
- package/node_modules/typebox/build/system/memory/freeze.mjs +0 -6
- /package/node_modules/@slack/bolt/node_modules/{body-parser/node_modules/content-type → content-type}/dist/index.d.ts +0 -0
- /package/node_modules/@slack/bolt/node_modules/{body-parser/node_modules/content-type → content-type}/dist/index.js +0 -0
- /package/node_modules/@slack/bolt/node_modules/{body-parser/node_modules/content-type → content-type}/dist/index.js.map +0 -0
|
@@ -1,9 +1,36 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { Ct as markdownToSlackMrkdwnChunks, E as buildSlackNativeDataAccessibilityText, F as truncateSlackText, H as SLACK_SELECT_ACTION_IDS, L as SLACK_BUTTON_ACTION_IDS, O as hasSlackNativeDataBlock, St as chunkSlackMrkdwnText, Tt as escapeSlackMrkdwn, X as encodeSlackQuestionAction, at as buildSlackCompleteBlocksFallbackText, ct as hasSlackDataVisualizationBlock, dt as countSlackDataTableBlocksCellCharacters, et as encodeSlackApprovalAction, ft as countSlackDataTableCellCharacters, gt as renderSlackMessagePresentationChartFallbackText, ht as SLACK_SECTION_TEXT_MAX, it as buildSlackBlocksFallbackText, nt as parseSlackBlocksInput, ot as renderSlackBlockFallbackText, st as buildSlackDataVisualizationBlock, ut as buildSlackDataTableBlock, w as appendSlackNativeDataFallbackText } from "./probe-DANukR3O.mjs";
|
|
2
2
|
import { asOptionalRecord, normalizeOptionalString } from "openclaw/plugin-sdk/string-coerce-runtime";
|
|
3
3
|
import { chunkTextForOutbound } from "openclaw/plugin-sdk/text-chunking";
|
|
4
4
|
import { legacyInteractiveReplyToPresentation, normalizeMessagePresentation, renderMessagePresentationFallbackText, resolveMessagePresentationButtonAction, resolveMessagePresentationOptionAction } from "openclaw/plugin-sdk/interactive-runtime";
|
|
5
|
-
import { parseExecApprovalCommandText } from "openclaw/plugin-sdk/approval-reply-runtime";
|
|
6
5
|
import { resolveAskUserQuestionOptionIndex, resolveAskUserQuestionOptionIndices, resolveSendableOutboundReplyParts } from "openclaw/plugin-sdk/reply-payload";
|
|
6
|
+
import { parseExecApprovalCommandText } from "openclaw/plugin-sdk/approval-reply-runtime";
|
|
7
|
+
//#region extensions/slack/src/authored-text.ts
|
|
8
|
+
function isSlackAuthoredTextRepresentedInFragments(plan, fragments) {
|
|
9
|
+
if (plan.length === 0) return false;
|
|
10
|
+
if (fragments.some((_, start) => plan.every((text, index) => text === fragments[start + index]))) return true;
|
|
11
|
+
const [text] = plan;
|
|
12
|
+
if (plan.length !== 1 || !text || /[*_~`<]/u.test(text)) return false;
|
|
13
|
+
for (let start = 0; start < fragments.length; start += 1) {
|
|
14
|
+
let offset = 0;
|
|
15
|
+
for (let end = start; end < fragments.length; end += 1) {
|
|
16
|
+
const fragment = fragments[end];
|
|
17
|
+
if (typeof fragment !== "string" || !text.startsWith(fragment, offset)) break;
|
|
18
|
+
offset += fragment.length;
|
|
19
|
+
if (offset === text.length) return true;
|
|
20
|
+
if (!/\s/u.test(text[offset] ?? "")) break;
|
|
21
|
+
while (/\s/u.test(text[offset] ?? "")) offset += 1;
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
return false;
|
|
25
|
+
}
|
|
26
|
+
/** Resolve placement from producer facts, before accessibility text changes the payload text. */
|
|
27
|
+
function resolveSlackAuthoredTextPlacement(params) {
|
|
28
|
+
const text = normalizeOptionalString(params.text);
|
|
29
|
+
if (!text) return "none";
|
|
30
|
+
const fragments = (params.renderedTextFragments ?? params.interactive?.blocks.flatMap((block) => block.type === "text" ? [block.text] : []) ?? []).map((fragment) => fragment?.trim() ?? null).filter((fragment) => fragment !== "");
|
|
31
|
+
return isSlackAuthoredTextRepresentedInFragments((params.authoredChunks ?? [text]).map((fragment) => fragment.trim()).filter(Boolean), fragments) ? "blocks" : "outside-blocks";
|
|
32
|
+
}
|
|
33
|
+
//#endregion
|
|
7
34
|
//#region extensions/slack/src/blocks-render.ts
|
|
8
35
|
const SLACK_BUTTON_URL_MAX = 3e3;
|
|
9
36
|
function buildSlackPlainText(text, maxLength) {
|
|
@@ -13,10 +40,6 @@ function buildSlackPlainText(text, maxLength) {
|
|
|
13
40
|
emoji: true
|
|
14
41
|
};
|
|
15
42
|
}
|
|
16
|
-
function resolveSlackButtonStyle(style) {
|
|
17
|
-
if (style === "primary" || style === "danger") return style;
|
|
18
|
-
if (style === "success") return "primary";
|
|
19
|
-
}
|
|
20
43
|
function resolveSlackActionTarget(action, questionOptionIndices) {
|
|
21
44
|
if (!action) return;
|
|
22
45
|
if (action.type === "approval") return {
|
|
@@ -59,42 +82,10 @@ function resolveSlackActionTarget(action, questionOptionIndices) {
|
|
|
59
82
|
value: command
|
|
60
83
|
} : void 0;
|
|
61
84
|
}
|
|
62
|
-
function resolveSlackButtonTarget(button, questionOptionIndices) {
|
|
63
|
-
if (button.action !== void 0) {
|
|
64
|
-
const action = resolveMessagePresentationButtonAction(button);
|
|
65
|
-
return action ? resolveSlackActionTarget(action, questionOptionIndices) : void 0;
|
|
66
|
-
}
|
|
67
|
-
const legacyUrl = normalizeOptionalString(button.url ?? button.webApp?.url ?? button.web_app?.url);
|
|
68
|
-
if (legacyUrl && legacyUrl.length <= SLACK_BUTTON_URL_MAX) return {
|
|
69
|
-
kind: "link",
|
|
70
|
-
url: legacyUrl
|
|
71
|
-
};
|
|
72
|
-
const legacyValue = normalizeOptionalString(button.value);
|
|
73
|
-
if (legacyValue) return {
|
|
74
|
-
kind: "reply",
|
|
75
|
-
value: legacyValue
|
|
76
|
-
};
|
|
77
|
-
return legacyUrl ? {
|
|
78
|
-
kind: "link",
|
|
79
|
-
url: legacyUrl
|
|
80
|
-
} : void 0;
|
|
81
|
-
}
|
|
82
85
|
function isSlackTextFallbackButton(button) {
|
|
83
86
|
const action = resolveMessagePresentationButtonAction(button);
|
|
84
87
|
return action?.type === "question" && "intent" in action && action.intent === "custom-input";
|
|
85
88
|
}
|
|
86
|
-
function resolveSlackOptionTarget(option) {
|
|
87
|
-
if (option.action !== void 0) {
|
|
88
|
-
const action = resolveMessagePresentationOptionAction(option);
|
|
89
|
-
const target = action ? resolveSlackActionTarget(action) : void 0;
|
|
90
|
-
return target?.kind === "link" || target?.kind === "question" ? void 0 : target;
|
|
91
|
-
}
|
|
92
|
-
const value = normalizeOptionalString(option.value);
|
|
93
|
-
return value ? {
|
|
94
|
-
kind: "reply",
|
|
95
|
-
value
|
|
96
|
-
} : void 0;
|
|
97
|
-
}
|
|
98
89
|
function readSlackOpenClawBlockIndex(blockId, prefix) {
|
|
99
90
|
if (!blockId.startsWith(prefix)) return;
|
|
100
91
|
const value = Number.parseInt(blockId.slice(prefix.length), 10);
|
|
@@ -136,7 +127,18 @@ function buildSlackPresentationBlocksIfComplete(presentation, options = {}) {
|
|
|
136
127
|
function compileSlackPresentationBlocks(presentation, options, requireComplete) {
|
|
137
128
|
if (!presentation) return [];
|
|
138
129
|
if (requireComplete && presentation.title && presentation.title.trim().length > 150) return;
|
|
139
|
-
|
|
130
|
+
let tables = [];
|
|
131
|
+
let cellCharacterCount = options.dataTableCellCharacterCountOffset ?? 0;
|
|
132
|
+
for (const block of presentation.blocks) {
|
|
133
|
+
if (block.type !== "table") continue;
|
|
134
|
+
const table = buildSlackDataTableBlock(block, { cellCharacterCountOffset: cellCharacterCount });
|
|
135
|
+
if (!table) {
|
|
136
|
+
tables = void 0;
|
|
137
|
+
break;
|
|
138
|
+
}
|
|
139
|
+
cellCharacterCount += countSlackDataTableCellCharacters(table);
|
|
140
|
+
tables.push(table);
|
|
141
|
+
}
|
|
140
142
|
if (requireComplete && !tables) return;
|
|
141
143
|
const blocks = [];
|
|
142
144
|
if (presentation.title) blocks.push({
|
|
@@ -175,8 +177,79 @@ function compileSlackPresentationBlocks(presentation, options, requireComplete)
|
|
|
175
177
|
}
|
|
176
178
|
if (block.type === "buttons" || block.type === "select") {
|
|
177
179
|
const index = controlIndices[block.type] + 1;
|
|
178
|
-
|
|
179
|
-
if (
|
|
180
|
+
let elements;
|
|
181
|
+
if (block.type === "buttons") {
|
|
182
|
+
let complete = true;
|
|
183
|
+
const buttons = block.buttons.flatMap((button, choiceIndex) => {
|
|
184
|
+
const questionOptionIndices = options.questionOptionIndices;
|
|
185
|
+
let target;
|
|
186
|
+
if (button.action !== void 0) {
|
|
187
|
+
const action = resolveMessagePresentationButtonAction(button);
|
|
188
|
+
target = action ? resolveSlackActionTarget(action, questionOptionIndices) : void 0;
|
|
189
|
+
} else {
|
|
190
|
+
const legacyUrl = normalizeOptionalString(button.url ?? button.webApp?.url ?? button.web_app?.url);
|
|
191
|
+
if (legacyUrl && legacyUrl.length <= SLACK_BUTTON_URL_MAX) target = {
|
|
192
|
+
kind: "link",
|
|
193
|
+
url: legacyUrl
|
|
194
|
+
};
|
|
195
|
+
else {
|
|
196
|
+
const legacyValue = normalizeOptionalString(button.value);
|
|
197
|
+
target = legacyValue ? {
|
|
198
|
+
kind: "reply",
|
|
199
|
+
value: legacyValue
|
|
200
|
+
} : legacyUrl ? {
|
|
201
|
+
kind: "link",
|
|
202
|
+
url: legacyUrl
|
|
203
|
+
} : void 0;
|
|
204
|
+
}
|
|
205
|
+
}
|
|
206
|
+
if (!target || (target.kind === "link" ? target.url.length > SLACK_BUTTON_URL_MAX : target.value.length > 2e3)) {
|
|
207
|
+
if (requireComplete && !isSlackTextFallbackButton(button)) complete = false;
|
|
208
|
+
return [];
|
|
209
|
+
}
|
|
210
|
+
if (button.label.length > 75) complete = false;
|
|
211
|
+
const style = button.style === "success" ? "primary" : button.style === "primary" || button.style === "danger" ? button.style : void 0;
|
|
212
|
+
return [{
|
|
213
|
+
type: "button",
|
|
214
|
+
action_id: `${SLACK_BUTTON_ACTION_IDS[target.kind]}:${index}:${choiceIndex + 1}`,
|
|
215
|
+
text: buildSlackPlainText(button.label, 75),
|
|
216
|
+
...target.kind === "link" ? { url: target.url } : { value: target.value },
|
|
217
|
+
...style ? { style } : {}
|
|
218
|
+
}];
|
|
219
|
+
});
|
|
220
|
+
if (requireComplete && (!complete || buttons.length > 25)) return;
|
|
221
|
+
elements = buttons.slice(0, 25);
|
|
222
|
+
} else {
|
|
223
|
+
const placeholder = normalizeOptionalString(block.placeholder) ?? "Choose an option";
|
|
224
|
+
const candidates = block.options.map((option) => {
|
|
225
|
+
if (option.action !== void 0) {
|
|
226
|
+
const action = resolveMessagePresentationOptionAction(option);
|
|
227
|
+
const target = action ? resolveSlackActionTarget(action) : void 0;
|
|
228
|
+
return target && target.kind !== "link" && target.kind !== "question" ? {
|
|
229
|
+
label: option.label,
|
|
230
|
+
...target
|
|
231
|
+
} : void 0;
|
|
232
|
+
}
|
|
233
|
+
const value = normalizeOptionalString(option.value);
|
|
234
|
+
return value ? {
|
|
235
|
+
label: option.label,
|
|
236
|
+
kind: "reply",
|
|
237
|
+
value
|
|
238
|
+
} : void 0;
|
|
239
|
+
});
|
|
240
|
+
if (requireComplete && (placeholder.length > 75 || block.options.length > 100 || block.placeholder && block.placeholder.length > 75 || !candidates.every((option) => option && option.label.length <= 75 && option.value.length <= 150) || new Set(candidates.map((option) => option?.kind)).size !== 1)) return;
|
|
241
|
+
const selectOptions = candidates.flatMap((option) => option && option.value.length <= 150 ? [option] : []).slice(0, 100);
|
|
242
|
+
const optionKinds = new Set(selectOptions.map((option) => option.kind));
|
|
243
|
+
elements = selectOptions.length > 0 && optionKinds.size === 1 ? [{
|
|
244
|
+
type: "static_select",
|
|
245
|
+
action_id: `${SLACK_SELECT_ACTION_IDS[selectOptions[0].kind]}:${index}`,
|
|
246
|
+
placeholder: buildSlackPlainText(placeholder, 75),
|
|
247
|
+
options: selectOptions.map((option) => ({
|
|
248
|
+
text: buildSlackPlainText(option.label, 75),
|
|
249
|
+
value: option.value
|
|
250
|
+
}))
|
|
251
|
+
}] : [];
|
|
252
|
+
}
|
|
180
253
|
if (elements.length > 0) {
|
|
181
254
|
controlIndices[block.type] = index;
|
|
182
255
|
blocks.push({
|
|
@@ -212,92 +285,6 @@ function compileSlackPresentationBlocks(presentation, options, requireComplete)
|
|
|
212
285
|
}
|
|
213
286
|
return blocks;
|
|
214
287
|
}
|
|
215
|
-
function buildSlackPresentationButtonElements(block, buttonIndex, questionOptionIndices, requireComplete) {
|
|
216
|
-
let complete = true;
|
|
217
|
-
const elements = block.buttons.flatMap((button, choiceIndex) => {
|
|
218
|
-
const target = resolveSlackButtonTarget(button, questionOptionIndices);
|
|
219
|
-
if (!target || (target.kind === "link" ? target.url.length > SLACK_BUTTON_URL_MAX : target.value.length > 2e3)) {
|
|
220
|
-
if (requireComplete && !isSlackTextFallbackButton(button)) complete = false;
|
|
221
|
-
return [];
|
|
222
|
-
}
|
|
223
|
-
if (button.label.length > 75) complete = false;
|
|
224
|
-
const style = resolveSlackButtonStyle(button.style);
|
|
225
|
-
return [{
|
|
226
|
-
type: "button",
|
|
227
|
-
action_id: `${SLACK_BUTTON_ACTION_IDS[target.kind]}:${buttonIndex}:${choiceIndex + 1}`,
|
|
228
|
-
text: buildSlackPlainText(button.label, 75),
|
|
229
|
-
...target.kind === "link" ? { url: target.url } : { value: target.value },
|
|
230
|
-
...style ? { style } : {}
|
|
231
|
-
}];
|
|
232
|
-
});
|
|
233
|
-
if (requireComplete && (!complete || elements.length > 25)) return;
|
|
234
|
-
return elements.slice(0, 25);
|
|
235
|
-
}
|
|
236
|
-
/** Admit tables together: one invalid or over-budget table keeps every table on the text path. */
|
|
237
|
-
function buildSlackPresentationTables(presentation, options = {}) {
|
|
238
|
-
const tables = [];
|
|
239
|
-
let cellCharacterCount = options.dataTableCellCharacterCountOffset ?? 0;
|
|
240
|
-
for (const block of presentation.blocks) {
|
|
241
|
-
if (block.type !== "table") continue;
|
|
242
|
-
const table = buildSlackDataTableBlock(block, { cellCharacterCountOffset: cellCharacterCount });
|
|
243
|
-
if (!table) return;
|
|
244
|
-
cellCharacterCount += countSlackDataTableCellCharacters(table);
|
|
245
|
-
tables.push(table);
|
|
246
|
-
}
|
|
247
|
-
return tables;
|
|
248
|
-
}
|
|
249
|
-
function buildSlackPresentationSelectElements(block, selectIndex, requireComplete) {
|
|
250
|
-
const placeholder = normalizeOptionalString(block.placeholder) ?? "Choose an option";
|
|
251
|
-
const candidates = block.options.map((option) => {
|
|
252
|
-
const target = resolveSlackOptionTarget(option);
|
|
253
|
-
return target ? {
|
|
254
|
-
label: option.label,
|
|
255
|
-
...target
|
|
256
|
-
} : void 0;
|
|
257
|
-
});
|
|
258
|
-
if (requireComplete && (placeholder.length > 75 || block.options.length > 100 || block.placeholder && block.placeholder.length > 75 || !candidates.every((option) => option && option.label.length <= 75 && option.value.length <= 150) || new Set(candidates.map((option) => option?.kind)).size !== 1)) return;
|
|
259
|
-
const options = candidates.flatMap((option) => option && option.value.length <= 150 ? [option] : []).slice(0, 100);
|
|
260
|
-
const optionKinds = new Set(options.map((option) => option.kind));
|
|
261
|
-
return options.length > 0 && optionKinds.size === 1 ? [{
|
|
262
|
-
type: "static_select",
|
|
263
|
-
action_id: `${SLACK_SELECT_ACTION_IDS[options[0].kind]}:${selectIndex}`,
|
|
264
|
-
placeholder: buildSlackPlainText(placeholder, 75),
|
|
265
|
-
options: options.map((option) => ({
|
|
266
|
-
text: buildSlackPlainText(option.label, 75),
|
|
267
|
-
value: option.value
|
|
268
|
-
}))
|
|
269
|
-
}] : [];
|
|
270
|
-
}
|
|
271
|
-
//#endregion
|
|
272
|
-
//#region extensions/slack/src/authored-text.ts
|
|
273
|
-
function normalizeComparableSlackText(text) {
|
|
274
|
-
return text.trim().replace(/\s+/g, " ");
|
|
275
|
-
}
|
|
276
|
-
function isSlackAuthoredTextRepresentedInFragments(text, rawFragments) {
|
|
277
|
-
const target = normalizeComparableSlackText(text);
|
|
278
|
-
const fragments = rawFragments.map(normalizeComparableSlackText).filter(Boolean);
|
|
279
|
-
let remainingLength = fragments.reduce((length, fragment) => length + fragment.length + 1, -1);
|
|
280
|
-
for (const [start, firstFragment] of fragments.entries()) {
|
|
281
|
-
if (remainingLength < target.length) break;
|
|
282
|
-
remainingLength -= firstFragment.length + 1;
|
|
283
|
-
let offset = 0;
|
|
284
|
-
for (let end = start;; end += 1) {
|
|
285
|
-
const fragment = fragments[end];
|
|
286
|
-
if (fragment === void 0 || !target.startsWith(fragment, offset)) break;
|
|
287
|
-
offset += fragment.length;
|
|
288
|
-
if (offset === target.length) return true;
|
|
289
|
-
if (target[offset] !== " ") break;
|
|
290
|
-
offset += 1;
|
|
291
|
-
}
|
|
292
|
-
}
|
|
293
|
-
return false;
|
|
294
|
-
}
|
|
295
|
-
/** Resolve placement from producer facts, before accessibility text changes the payload text. */
|
|
296
|
-
function resolveSlackAuthoredTextPlacement(params) {
|
|
297
|
-
const text = normalizeOptionalString(params.text);
|
|
298
|
-
if (!text) return "none";
|
|
299
|
-
return params.renderedInBlocks || isSlackAuthoredTextRepresentedInFragments(text, params.renderedTextFragments ?? []) || isSlackAuthoredTextRepresentedInFragments(text, params.interactive?.blocks.flatMap((block) => block.type === "text" ? [block.text] : []) ?? []) ? "blocks" : "outside-blocks";
|
|
300
|
-
}
|
|
301
288
|
//#endregion
|
|
302
289
|
//#region extensions/slack/src/reply-blocks.ts
|
|
303
290
|
function normalizeSlackReplyPayload(payload) {
|
|
@@ -321,27 +308,6 @@ function normalizeSlackReplyPayload(payload) {
|
|
|
321
308
|
}
|
|
322
309
|
};
|
|
323
310
|
}
|
|
324
|
-
function parseSlackReplyBlockSegments(value) {
|
|
325
|
-
if (value === void 0) return;
|
|
326
|
-
if (!Array.isArray(value)) throw new Error("Slack rendered presentation segments must be an array");
|
|
327
|
-
return value.map((raw) => {
|
|
328
|
-
if (!raw || typeof raw !== "object" || Array.isArray(raw)) throw new Error("Slack rendered presentation segment must be an object");
|
|
329
|
-
const segment = raw;
|
|
330
|
-
if (segment.kind === "text" && typeof segment.text === "string" && segment.mrkdwn === false) return {
|
|
331
|
-
kind: "text",
|
|
332
|
-
text: segment.text,
|
|
333
|
-
mrkdwn: false
|
|
334
|
-
};
|
|
335
|
-
if (segment.kind === "blocks") {
|
|
336
|
-
const blocks = parseSlackBlocksInput(segment.blocks);
|
|
337
|
-
if (blocks?.length) return {
|
|
338
|
-
kind: "blocks",
|
|
339
|
-
blocks
|
|
340
|
-
};
|
|
341
|
-
}
|
|
342
|
-
throw new Error("Slack rendered presentation segment is invalid");
|
|
343
|
-
});
|
|
344
|
-
}
|
|
345
311
|
/** Project each segment only when the caller is ready to deliver it. */
|
|
346
312
|
function* iterateSlackReplyDeliveryMessages(params) {
|
|
347
313
|
let outsideText = params.authoredTextPlacement === "outside-blocks" ? params.text?.trim() ?? "" : "";
|
|
@@ -374,35 +340,35 @@ function* iterateSlackReplyDeliveryMessages(params) {
|
|
|
374
340
|
function resolveSlackReplyDeliveryMessages(params) {
|
|
375
341
|
return Array.from(iterateSlackReplyDeliveryMessages(params));
|
|
376
342
|
}
|
|
377
|
-
function resolveSlackReplyRenderPlan(payload, text = payload.text) {
|
|
378
|
-
return prepareSlackReply(payload).resolvePreview(text);
|
|
343
|
+
function resolveSlackReplyRenderPlan(payload, text = payload.text, options = {}) {
|
|
344
|
+
return prepareSlackReply(payload, options).resolvePreview(text);
|
|
379
345
|
}
|
|
380
346
|
/** One attempt owns its authored compilation; media captions retain a separate delivery policy. */
|
|
381
|
-
function prepareSlackReply(payload) {
|
|
347
|
+
function prepareSlackReply(payload, options = {}) {
|
|
382
348
|
const text = payload.text;
|
|
383
|
-
const source = {
|
|
384
|
-
...payload,
|
|
385
|
-
text
|
|
386
|
-
};
|
|
387
349
|
let authoredChunks;
|
|
388
350
|
let structuredContent;
|
|
389
351
|
let materialized;
|
|
390
352
|
let unmaterialized;
|
|
391
353
|
let preview;
|
|
392
|
-
const resolveAuthoredTextChunks = () => authoredChunks ??= markdownToSlackMrkdwnChunks(text?.trim() ?? "", SLACK_SECTION_TEXT_MAX);
|
|
393
|
-
const hasStructuredContent = () => structuredContent ??= hasSlackReplyStructuredContent(
|
|
394
|
-
const resolve = (materializeAuthoredText) => materializeAuthoredText ? materialized ??= resolveSlackReplyBlockResolution(
|
|
354
|
+
const resolveAuthoredTextChunks = () => authoredChunks ??= markdownToSlackMrkdwnChunks(text?.trim() ?? "", SLACK_SECTION_TEXT_MAX, options);
|
|
355
|
+
const hasStructuredContent = () => structuredContent ??= hasSlackReplyStructuredContent(payload);
|
|
356
|
+
const resolve = (materializeAuthoredText) => materializeAuthoredText ? materialized ??= resolveSlackReplyBlockResolution(payload, {
|
|
357
|
+
...options,
|
|
395
358
|
materializeAuthoredText: true,
|
|
396
359
|
resolveAuthoredTextChunks
|
|
397
|
-
}) : unmaterialized ??= resolveSlackReplyBlockResolution(
|
|
360
|
+
}) : unmaterialized ??= resolveSlackReplyBlockResolution(payload, {
|
|
361
|
+
...options,
|
|
362
|
+
resolveAuthoredTextChunks
|
|
363
|
+
});
|
|
398
364
|
return {
|
|
399
365
|
payload,
|
|
400
|
-
resolveDelivery: () => resolve(!resolveSendableOutboundReplyParts(
|
|
366
|
+
resolveDelivery: () => resolve(!resolveSendableOutboundReplyParts(payload).hasMedia && hasStructuredContent()),
|
|
401
367
|
resolvePreview: (override = text) => {
|
|
402
368
|
if (override !== text) return prepareSlackReply({
|
|
403
|
-
...
|
|
369
|
+
...payload,
|
|
404
370
|
text: override
|
|
405
|
-
}).resolvePreview();
|
|
371
|
+
}, options).resolvePreview();
|
|
406
372
|
return preview ??= projectSlackReplyRenderPlan(text, resolve(hasStructuredContent()), resolveAuthoredTextChunks);
|
|
407
373
|
}
|
|
408
374
|
};
|
|
@@ -452,11 +418,52 @@ function readSlackChannelBlocks(payload) {
|
|
|
452
418
|
function hasSlackReplyStructuredContent(payload) {
|
|
453
419
|
return Boolean(readSlackChannelBlocks(payload).length || normalizeMessagePresentation(payload.presentation) || payload.interactive?.blocks.length);
|
|
454
420
|
}
|
|
421
|
+
function literalSlackComparisonText(text) {
|
|
422
|
+
return /[*_~`]/u.test(text) ? null : escapeSlackMrkdwn(text);
|
|
423
|
+
}
|
|
424
|
+
function renderSlackRichTextComparisonFragments(value) {
|
|
425
|
+
if (!Array.isArray(value)) return [null];
|
|
426
|
+
return value.map((raw) => {
|
|
427
|
+
const section = asOptionalRecord(raw);
|
|
428
|
+
if (section?.type !== "rich_text_section" && section?.type !== "rich_text_preformatted" || !Array.isArray(section.elements)) return null;
|
|
429
|
+
let text = "";
|
|
430
|
+
let style;
|
|
431
|
+
for (const rawElement of section.elements) {
|
|
432
|
+
const element = asOptionalRecord(rawElement);
|
|
433
|
+
if (element?.type !== "text" || typeof element.text !== "string") return null;
|
|
434
|
+
const styles = Object.entries(asOptionalRecord(element.style) ?? {}).filter(([, enabled]) => enabled !== false);
|
|
435
|
+
const nextStyle = styles[0]?.[0] ?? "";
|
|
436
|
+
if (styles.length > 1 || styles.some(([key, enabled]) => enabled !== true || ![
|
|
437
|
+
"bold",
|
|
438
|
+
"italic",
|
|
439
|
+
"strike",
|
|
440
|
+
"code"
|
|
441
|
+
].includes(key)) || style !== void 0 && nextStyle !== style) return null;
|
|
442
|
+
style = nextStyle;
|
|
443
|
+
text += element.text;
|
|
444
|
+
}
|
|
445
|
+
if (section.type === "rich_text_preformatted") return style || text.includes("```") ? null : "```\n" + escapeSlackMrkdwn(text) + (text.endsWith("\n") ? "" : "\n") + "```";
|
|
446
|
+
if (style === "code") return /[`\r\n]/u.test(text) ? null : "`" + escapeSlackMrkdwn(text) + "`";
|
|
447
|
+
const literal = literalSlackComparisonText(text);
|
|
448
|
+
if (!style || literal === null) return literal;
|
|
449
|
+
if (text.trim() !== text) return null;
|
|
450
|
+
const marker = style === "bold" ? "*" : style === "italic" ? "_" : "~";
|
|
451
|
+
return marker + literal + marker;
|
|
452
|
+
});
|
|
453
|
+
}
|
|
455
454
|
function renderSlackAuthoredTextFragments(blocks) {
|
|
455
|
+
const readTextObject = (value) => {
|
|
456
|
+
const record = asOptionalRecord(value);
|
|
457
|
+
const text = normalizeOptionalString(record?.text);
|
|
458
|
+
return text === void 0 ? void 0 : record?.type === "mrkdwn" ? text : literalSlackComparisonText(text);
|
|
459
|
+
};
|
|
456
460
|
return blocks.flatMap((block) => {
|
|
457
|
-
|
|
458
|
-
|
|
459
|
-
return
|
|
461
|
+
const record = asOptionalRecord(block);
|
|
462
|
+
if (block.type === "actions" || block.type === "divider") return [];
|
|
463
|
+
if (block.type === "section" || block.type === "context" || block.type === "header") return (block.type === "context" ? Array.isArray(record?.elements) ? record.elements : [] : [record?.text, ...Array.isArray(record?.fields) ? record.fields : []]).map(readTextObject).filter((text) => text !== void 0);
|
|
464
|
+
if (block.type === "rich_text") return renderSlackRichTextComparisonFragments(record?.elements);
|
|
465
|
+
const text = renderSlackBlockFallbackText(block);
|
|
466
|
+
return text ? [/[*_~`]/u.test(text) ? null : text] : [];
|
|
460
467
|
});
|
|
461
468
|
}
|
|
462
469
|
function buildSlackAuthoredTextBlocks(chunks) {
|
|
@@ -501,8 +508,7 @@ function appendTextSegment(segments, text) {
|
|
|
501
508
|
}
|
|
502
509
|
segments.push({
|
|
503
510
|
kind: "text",
|
|
504
|
-
text: trimmed
|
|
505
|
-
mrkdwn: false
|
|
511
|
+
text: trimmed
|
|
506
512
|
});
|
|
507
513
|
}
|
|
508
514
|
function appendBlockSegment(segments, blocks, startNew = false) {
|
|
@@ -570,37 +576,10 @@ function subtractMirroredSlackControlRows(params) {
|
|
|
570
576
|
return false;
|
|
571
577
|
});
|
|
572
578
|
}
|
|
573
|
-
|
|
574
|
-
* Resolve reply content into transport-order segments. Each blocks segment is
|
|
575
|
-
* one Slack message; text segments carry complete fallback content between it.
|
|
576
|
-
*/
|
|
577
|
-
function resolveSlackReplyBlockResolution(payload, options = {}) {
|
|
579
|
+
function compileSlackReplyBlockSegments(payload, channelBlocks, presentation) {
|
|
578
580
|
const segments = [];
|
|
579
|
-
const presentation = normalizeMessagePresentation(payload.presentation);
|
|
580
581
|
const textIsFallback = presentation && payload.presentationTextMode === "fallback";
|
|
581
|
-
|
|
582
|
-
const channelBlocks = readSlackChannelBlocks(payload);
|
|
583
|
-
let compiledChannelBlocks = channelBlocks;
|
|
584
|
-
let authoredTextKnownInBlocks = false;
|
|
585
|
-
if (options.materializeAuthoredText) {
|
|
586
|
-
const rawTextFragments = renderSlackAuthoredTextFragments(channelBlocks);
|
|
587
|
-
const initialPlacement = resolveSlackAuthoredTextPlacement({
|
|
588
|
-
text: authoredText,
|
|
589
|
-
interactive: payload.interactive,
|
|
590
|
-
renderedTextFragments: rawTextFragments
|
|
591
|
-
});
|
|
592
|
-
authoredTextKnownInBlocks = initialPlacement === "blocks";
|
|
593
|
-
const text = normalizeOptionalString(authoredText);
|
|
594
|
-
if (text && initialPlacement === "outside-blocks") {
|
|
595
|
-
const textBlocks = buildSlackAuthoredTextBlocks(options.resolveAuthoredTextChunks?.() ?? markdownToSlackMrkdwnChunks(text, 3e3));
|
|
596
|
-
if (resolveSlackAuthoredTextPlacement({
|
|
597
|
-
text: renderSlackAuthoredTextFragments(textBlocks).join(" "),
|
|
598
|
-
renderedTextFragments: rawTextFragments
|
|
599
|
-
}) !== "blocks") compiledChannelBlocks = [...channelBlocks, ...textBlocks];
|
|
600
|
-
authoredTextKnownInBlocks = true;
|
|
601
|
-
}
|
|
602
|
-
}
|
|
603
|
-
if (compiledChannelBlocks.length > 0) appendBlockSegment(segments, compiledChannelBlocks);
|
|
582
|
+
if (channelBlocks.length > 0) appendBlockSegment(segments, channelBlocks);
|
|
604
583
|
const questionOptionIndices = resolveAskUserQuestionOptionIndices(payload);
|
|
605
584
|
const presentationBlockOffset = readAllNativeBlocks(segments).length;
|
|
606
585
|
if (presentation?.title) appendPresentationPart(segments, {
|
|
@@ -621,31 +600,47 @@ function resolveSlackReplyBlockResolution(payload, options = {}) {
|
|
|
621
600
|
"rich_text"
|
|
622
601
|
].includes(block.type) && !("accessory" in block && block.accessory))) {
|
|
623
602
|
segments.length = 0;
|
|
624
|
-
appendBlockSegment(segments,
|
|
603
|
+
appendBlockSegment(segments, channelBlocks);
|
|
625
604
|
appendTextSegment(segments, payload.text);
|
|
626
605
|
}
|
|
627
606
|
appendBlockSegment(segments, subtractMirroredSlackControlRows({
|
|
628
607
|
interactiveBlocks,
|
|
629
608
|
presentationBlocks: renderedPresentationBlocks
|
|
630
609
|
}));
|
|
631
|
-
|
|
632
|
-
|
|
633
|
-
|
|
610
|
+
return segments;
|
|
611
|
+
}
|
|
612
|
+
/**
|
|
613
|
+
* Resolve reply content into transport-order segments. Each blocks segment is
|
|
614
|
+
* one Slack message; text segments carry complete fallback content between it.
|
|
615
|
+
*/
|
|
616
|
+
function resolveSlackReplyBlockResolution(payload, options = {}) {
|
|
617
|
+
const presentation = normalizeMessagePresentation(payload.presentation);
|
|
618
|
+
const authoredText = presentation && payload.presentationTextMode === "fallback" ? void 0 : normalizeOptionalString(payload.text);
|
|
619
|
+
const channelBlocks = readSlackChannelBlocks(payload);
|
|
620
|
+
let segments = compileSlackReplyBlockSegments(payload, channelBlocks, presentation);
|
|
621
|
+
const chunks = authoredText && (segments.length > 0 || options.materializeAuthoredText) ? options.resolveAuthoredTextChunks?.() ?? markdownToSlackMrkdwnChunks(authoredText, 3e3, options) : [];
|
|
622
|
+
let authoredTextPlacement = resolveSlackAuthoredTextPlacement({
|
|
623
|
+
text: authoredText,
|
|
624
|
+
authoredChunks: chunks,
|
|
625
|
+
renderedTextFragments: segments.flatMap((segment) => segment.kind === "text" ? [literalSlackComparisonText(segment.text)] : renderSlackAuthoredTextFragments(segment.blocks))
|
|
634
626
|
});
|
|
635
|
-
|
|
627
|
+
if (authoredTextPlacement === "outside-blocks" && !/[*_~`<[\]\\#>|]/u.test(authoredText ?? "")) authoredTextPlacement = resolveSlackAuthoredTextPlacement({
|
|
636
628
|
text: authoredText,
|
|
637
|
-
|
|
638
|
-
renderedTextFragments
|
|
629
|
+
renderedTextFragments: segments.flatMap((segment) => segment.kind === "text" ? [segment.text] : segment.blocks.map((block) => hasSlackNativeDataBlock([block]) ? renderSlackBlockFallbackText(block, { nativeDataFormat: "plain" }) ?? null : null))
|
|
639
630
|
});
|
|
631
|
+
if (options.materializeAuthoredText && authoredTextPlacement === "outside-blocks") {
|
|
632
|
+
segments = compileSlackReplyBlockSegments(payload, [...channelBlocks, ...buildSlackAuthoredTextBlocks(chunks)], presentation);
|
|
633
|
+
authoredTextPlacement = "blocks";
|
|
634
|
+
}
|
|
640
635
|
return {
|
|
641
|
-
authoredTextPlacement
|
|
636
|
+
authoredTextPlacement,
|
|
642
637
|
segments
|
|
643
638
|
};
|
|
644
639
|
}
|
|
645
640
|
/** Return the single-message native shape when no ordered text fallback is required. */
|
|
646
641
|
function resolveSlackReplyBlocks(payload) {
|
|
647
|
-
const
|
|
642
|
+
const segments = compileSlackReplyBlockSegments(payload, readSlackChannelBlocks(payload), normalizeMessagePresentation(payload.presentation));
|
|
648
643
|
return segments.length === 1 && segments[0]?.kind === "blocks" ? segments[0].blocks : void 0;
|
|
649
644
|
}
|
|
650
645
|
//#endregion
|
|
651
|
-
export {
|
|
646
|
+
export { resolveSlackReplyBlockResolution as a, resolveSlackReplyRenderPlan as c, resolveSlackAuthoredTextPlacement as d, prepareSlackReply as i, buildSlackInteractiveBlocks as l, iterateSlackReplyDeliveryMessages as n, resolveSlackReplyBlocks as o, normalizeSlackReplyPayload as r, resolveSlackReplyDeliveryMessages as s, hasSlackReplyStructuredContent as t, buildSlackPresentationBlocks as u };
|
|
@@ -1,12 +1,11 @@
|
|
|
1
1
|
import { t as __exportAll } from "./rolldown-runtime-B4FMCO8f.mjs";
|
|
2
|
-
import { s as resolveWorkspaceQualifiedSlackTarget } from "./target-parsing-
|
|
3
|
-
import {
|
|
2
|
+
import { s as resolveWorkspaceQualifiedSlackTarget } from "./target-parsing-Bx2UZniD.mjs";
|
|
3
|
+
import { n as fetchSlackChannelListPage, r as createSlackLookupClient, t as collectSlackCursorPages } from "./cursor-pages-CATAzbTT.mjs";
|
|
4
4
|
import { normalizeLowercaseStringOrEmpty } from "openclaw/plugin-sdk/string-coerce-runtime";
|
|
5
5
|
//#region extensions/slack/src/resolve-channels.ts
|
|
6
6
|
var resolve_channels_exports = /* @__PURE__ */ __exportAll({ resolveSlackChannelAllowlist: () => resolveSlackChannelAllowlist });
|
|
7
7
|
function parseSlackChannelMention(raw) {
|
|
8
8
|
const trimmed = raw.trim();
|
|
9
|
-
if (!trimmed) return {};
|
|
10
9
|
const mention = trimmed.match(/^<#([A-Z0-9]+)(?:\|([^>]+))?>$/i);
|
|
11
10
|
if (mention) return {
|
|
12
11
|
id: mention[1]?.toUpperCase(),
|
|
@@ -14,7 +13,7 @@ function parseSlackChannelMention(raw) {
|
|
|
14
13
|
};
|
|
15
14
|
const prefixed = trimmed.replace(/^(slack:|channel:)/i, "");
|
|
16
15
|
if (/^[CG][A-Z0-9]{8,}$/i.test(prefixed)) return { id: prefixed.toUpperCase() };
|
|
17
|
-
const name = prefixed.replace(/^#/, "")
|
|
16
|
+
const name = normalizeLowercaseStringOrEmpty(prefixed.replace(/^#/, ""));
|
|
18
17
|
return name ? { name } : {};
|
|
19
18
|
}
|
|
20
19
|
async function listSlackChannels(client) {
|
|
@@ -34,9 +33,7 @@ async function listSlackChannels(client) {
|
|
|
34
33
|
});
|
|
35
34
|
}
|
|
36
35
|
function resolveByName(name, channels) {
|
|
37
|
-
const
|
|
38
|
-
if (!target) return;
|
|
39
|
-
const matches = channels.filter((channel) => normalizeLowercaseStringOrEmpty(channel.name) === target);
|
|
36
|
+
const matches = channels.filter((channel) => normalizeLowercaseStringOrEmpty(channel.name) === name);
|
|
40
37
|
return matches.find((channel) => !channel.archived) ?? matches[0];
|
|
41
38
|
}
|
|
42
39
|
async function resolveSlackChannelAllowlist(params) {
|
|
@@ -1,18 +1,17 @@
|
|
|
1
1
|
import { t as __exportAll } from "./rolldown-runtime-B4FMCO8f.mjs";
|
|
2
|
-
import { s as resolveWorkspaceQualifiedSlackTarget } from "./target-parsing-
|
|
3
|
-
import {
|
|
2
|
+
import { s as resolveWorkspaceQualifiedSlackTarget } from "./target-parsing-Bx2UZniD.mjs";
|
|
3
|
+
import { r as createSlackLookupClient, t as collectSlackCursorPages } from "./cursor-pages-CATAzbTT.mjs";
|
|
4
4
|
import { normalizeLowercaseStringOrEmpty, normalizeOptionalLowercaseString, normalizeOptionalString } from "openclaw/plugin-sdk/string-coerce-runtime";
|
|
5
5
|
//#region extensions/slack/src/resolve-users.ts
|
|
6
6
|
var resolve_users_exports = /* @__PURE__ */ __exportAll({ resolveSlackUserAllowlist: () => resolveSlackUserAllowlist });
|
|
7
7
|
function parseSlackUserInput(raw) {
|
|
8
8
|
const trimmed = raw.trim();
|
|
9
|
-
if (!trimmed) return {};
|
|
10
9
|
const mention = trimmed.match(/^<@([A-Z0-9]+)>$/i);
|
|
11
10
|
if (mention) return { id: mention[1]?.toUpperCase() };
|
|
12
11
|
const prefixed = trimmed.replace(/^(slack:|user:)/i, "");
|
|
13
12
|
if (/^[A-Z][A-Z0-9]+$/i.test(prefixed)) return { id: prefixed.toUpperCase() };
|
|
14
13
|
if (trimmed.includes("@") && !trimmed.startsWith("@")) return { email: normalizeLowercaseStringOrEmpty(trimmed) };
|
|
15
|
-
const name = trimmed.replace(/^@/, "")
|
|
14
|
+
const name = normalizeLowercaseStringOrEmpty(trimmed.replace(/^@/, ""));
|
|
16
15
|
return name ? { name } : {};
|
|
17
16
|
}
|
|
18
17
|
async function listSlackUsers(client) {
|
|
@@ -39,17 +38,6 @@ async function listSlackUsers(client) {
|
|
|
39
38
|
}).filter((user) => user !== null)
|
|
40
39
|
});
|
|
41
40
|
}
|
|
42
|
-
function matchesSlackUserName(user, name) {
|
|
43
|
-
const target = normalizeLowercaseStringOrEmpty(name);
|
|
44
|
-
return [
|
|
45
|
-
user.name,
|
|
46
|
-
user.displayName,
|
|
47
|
-
user.realName
|
|
48
|
-
].some((value) => {
|
|
49
|
-
const candidate = normalizeLowercaseStringOrEmpty(value);
|
|
50
|
-
return Boolean(candidate) && candidate === target;
|
|
51
|
-
});
|
|
52
|
-
}
|
|
53
41
|
function scoreSlackUser(user) {
|
|
54
42
|
return (user.deleted ? 0 : 3) + (user.isBot || user.isAppUser ? 0 : 2);
|
|
55
43
|
}
|
|
@@ -62,7 +50,11 @@ async function resolveSlackUserAllowlist(params) {
|
|
|
62
50
|
const users = entries.some(({ workspace }) => !workspace) ? await listSlackUsers(params.client ?? createSlackLookupClient(params.token)) : [];
|
|
63
51
|
return entries.map(({ input, workspace, parsed }) => {
|
|
64
52
|
if (workspace) return workspace;
|
|
65
|
-
const matches = users.filter((user) => parsed.id ? user.id === parsed.id : parsed.email ? user.email === parsed.email : parsed.name ?
|
|
53
|
+
const matches = users.filter((user) => parsed.id ? user.id === parsed.id : parsed.email ? user.email === parsed.email : parsed.name ? [
|
|
54
|
+
user.name,
|
|
55
|
+
user.displayName,
|
|
56
|
+
user.realName
|
|
57
|
+
].some((value) => normalizeLowercaseStringOrEmpty(value) === parsed.name) : false);
|
|
66
58
|
const match = parsed.id ? matches[0] : matches.toSorted((a, b) => scoreSlackUser(b) - scoreSlackUser(a))[0];
|
|
67
59
|
if (!parsed.id && !match) return {
|
|
68
60
|
input,
|
|
@@ -1,4 +1,5 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { m as formatSlackError } from "./probe-DANukR3O.mjs";
|
|
2
|
+
import { i as createSlackReadClient } from "./cursor-pages-CATAzbTT.mjs";
|
|
2
3
|
import { isRecord, normalizeOptionalString, normalizeTrimmedStringList, sortUniqueStrings } from "openclaw/plugin-sdk/string-coerce-runtime";
|
|
3
4
|
//#region extensions/slack/src/scopes.ts
|
|
4
5
|
function collectScopes(value, into) {
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { n as hasSlackAccountCredentialsFromConfig } from "./account-configured-zcR9TJJN.mjs";
|
|
2
|
-
import { collectConditionalChannelFieldAssignments, collectNestedChannelFieldAssignments, collectSimpleChannelFieldAssignments, createChannelSecretContract, hasOwnProperty } from "openclaw/plugin-sdk/channel-secret-basic-runtime";
|
|
2
|
+
import { collectConditionalChannelFieldAssignments, collectNestedChannelFieldAssignments, collectSimpleChannelFieldAssignments, createChannelSecretContract, hasOwnProperty, isRecord } from "openclaw/plugin-sdk/channel-secret-basic-runtime";
|
|
3
3
|
//#region extensions/slack/src/secret-contract.ts
|
|
4
4
|
const channelSecrets = createChannelSecretContract({
|
|
5
5
|
channelKey: "slack",
|
|
@@ -31,7 +31,7 @@ const channelSecrets = createChannelSecretContract({
|
|
|
31
31
|
const resolveAccountMode = (account) => resolveMode(account.mode) ?? baseMode;
|
|
32
32
|
const hasNestedAuthTokenOverride = (account) => {
|
|
33
33
|
const relay = account.relay;
|
|
34
|
-
return
|
|
34
|
+
return isRecord(relay) && hasOwnProperty(relay, "authToken");
|
|
35
35
|
};
|
|
36
36
|
for (const [field, mode, label] of [[
|
|
37
37
|
"appToken",
|