Commit Graph

1137 Commits

Author SHA1 Message Date
Peter Steinberger
6bd14d9129 test(channels): extend bundled artifact parity and add plugin-shape contract suite (#104618) 2026-07-11 11:44:34 -07:00
NIO
473df17bd7 fix(feishu): add 30 s request timeout to streaming-card API calls (#102948)
* fix(feishu): bound streaming-card API requests with a 30s timeout

* fix(feishu): honor configured streaming timeout

Signed-off-by: sallyom <somalley@redhat.com>

* test(feishu): declare streaming mock credentials

Signed-off-by: sallyom <somalley@redhat.com>

---------

Signed-off-by: sallyom <somalley@redhat.com>
Co-authored-by: NIO <nocodet@mail.com>
Co-authored-by: sallyom <somalley@redhat.com>
2026-07-11 14:35:42 -04:00
Peter Steinberger
96f0983a85 fix(onboarding): skip setup for configured gateways and require inference first (#102883)
* fix(crestodian): keep onboarding RPCs restart-safe

* fix(profiles): isolate approval state migrations

* fix(crestodian): bypass configured gateway setup

* test(crestodian): type onboarding mocks

* fix(onboarding): require inference before Crestodian

* fix(onboarding): enforce verified inference handoff

* fix(macos): reset setup on gateway endpoint edits

* chore(i18n): refresh native source inventory

* fix(gateway): keep socket on request cancellation

* test(packaging): require workspace templates

* fix(onboarding): bind setup to verified inference

* fix(onboarding): align inference gate contracts

* fix(crestodian): classify concurrent policy rejection

* test(crestodian): expect registry restoration

* fix(onboarding): bind setup to configured gateways

* fix(codex): preserve startup phase deadlines

* test(crestodian): match fail-closed policy ordering

* test(onboarding): assert bound gateway handoff

* fix(codex): bind runtime resolution to spawn cwd

* test(crestodian): assert policy rejection order

* fix(cli): preserve gateway routing across restarts

* fix(macos): fail closed during gateway edits

* test(macos): cover gateway route generation races

* chore: keep release notes out of onboarding PR

* fix(ci): refresh onboarding generated checks

* style(swift): align gateway channel formatting

* fix(ci): refresh plugin SDK surface budgets

* fix(ci): resync native string inventory

* refactor(swift): split gateway channel support

* test(doctor): isolate plugin compatibility registry

* test(macos): isolate gateway onboarding fixtures

* test(macos): assert gateway lease health ordering

* fix(codex): reconcile computer-use startup changes
2026-07-11 10:25:14 -07:00
Peter Steinberger
ba826be268 test(channels): delivery trace harness with feishu and mattermost goldens (#104478) 2026-07-11 06:49:27 -07:00
Peter Steinberger
3902adf9f6 refactor(channels): adopt core retryAsync for hand-rolled retry loops (#104431) 2026-07-11 04:30:21 -07:00
Peter Steinberger
a8e2da7d5e refactor(feishu): adopt core claimable dedupe for inbound events (#104384) 2026-07-11 03:27:14 -07:00
Peter Steinberger
7bf80dc2c6 chore(tooling): enforce formatting and refresh TypeScript checks (#104239)
* chore(tooling): enforce current formatter and refresh checks

* chore(tooling): keep release changelog formatter-owned

* chore(tooling): retain compatible Node type surface

* ci: enforce formatting for docs-only changes

* ci: isolate docs formatter check

* chore(tooling): apply updated lint and format rules

* chore(tooling): satisfy updated switch lint

* style(ui): apply Linux formatter layout

* test(doctor): match quiet local audio contribution

* test(doctor): assert quiet output only

* test(doctor): follow restored information contract
2026-07-11 01:09:51 -07:00
Peter Steinberger
f94a7dc183 feat(codex): supervise native Codex sessions (#104045)
* feat(codex): add native session supervision

* fix(codex): harden supervision integration

* fix(codex): preserve locked harness ownership

* fix(codex): fence native session archive

* fix(codex): revalidate archive binding ownership

* feat(codex): integrate supervision runtime

* feat(sessions): preserve harness-owned execution

* feat(sessions): persist harness ownership invariants

* feat(gateway): enforce harness-owned sessions

* feat(setup): enable detected Codex supervision

* feat(mac): expose supervised Codex sessions

* feat(ui): make Codex sessions actionable

* docs(codex): document session supervision

* test(codex): cover integration ownership

* chore(i18n): refresh supervision inventories

* fix(setup): finalize Codex activation atomically

* test(codex): narrow binding store update

* fix(sessions): preserve legacy model locks

* test(macos): serialize Codex catalog fixtures

* fix(sessions): preserve legacy lock admission

* chore(i18n): reconcile supervision metadata

* test(sessions): mark legacy lock fixture

* fix(macos): drain final Codex catalog frame

* docs: leave supervision note to release

* style(macos): satisfy Codex catalog type length

* chore: record session accessor seam owners

* fix(macos): honor configured Codex supervision

* fix(codex): preserve harness-owned model locks

* fix(codex): satisfy supervision lint gates

* chore(i18n): refresh native supervision inventory

* fix(codex): align supervision validation contracts

* fix(codex): close supervision boundary gaps

* fix(codex): preserve supervision activation contracts

* fix(codex): dispose standalone supervision runtime

* fix(codex): pin supervised source connection

* fix(plugins): bind delegated runs to exact session target

* fix(codex): scope supervised sessions to configured agents

* fix(codex): fingerprint effective supervision home

* fix(codex): normalize supervision plugin policy

* fix(codex): keep supervised bindings stable across upgrades

* fix(codex): guard all supervised binding connections

* fix(codex): preserve catalog filters and pending CAS identity

* fix(codex): preserve supervision identity for diagnostics

* fix(codex): bind uncertain commits to supervision connection

* fix(codex): satisfy supervision type boundaries

* fix(macos): reconcile current main validation

* fix(codex): handle absent runtime config in supervision

* fix(doctor): own local audio acceleration check

* fix(codex): satisfy integration lint gates

* fix(codex): satisfy lifecycle safety guards
2026-07-11 00:12:08 -07:00
Peter Steinberger
81a201df26 feat: add portable table presentation blocks (#103583)
* feat(presentation): add portable table blocks

* chore(presentation): refresh generated contracts

* fix(slack): preserve table fallback payloads

* docs(changelog): note portable message tables

* fix(presentation): preserve cross-channel fallback delivery

* chore(plugin-sdk): refresh rebased contracts

* test(slack): align accessibility expectations

* fix(presentation): harden cross-channel fallback delivery

* chore(plugin-sdk): refresh rebased contracts

* docs(changelog): defer portable table release note

* fix(presentation): satisfy extension lint

* chore(plugin-sdk): refresh surface budgets

* fix(telegram): preserve reactions after progress replies

* fix(slack): preserve rendered preview fallback text

* fix(feishu): preserve oversized presentation fallbacks

* docs(changelog): note portable message tables

* docs(changelog): defer portable table release note

* chore(plugin-sdk): refresh rebased contracts

---------

Co-authored-by: Peter Steinberger <steipete@openai.com>
2026-07-10 22:29:13 -07:00
Josh Avant
fbd330b7aa fix(channels): honor configured read target policies (#99905)
* fix(channels): enforce configured read targets

* test(channels): align policy checks with boundaries

* fix: bind channel reads to trusted turn context

* test: satisfy gateway lint

* fix: narrow message action channel imports

* fix(feishu): authorize message reads before provider access

* fix(slack): await reaction clear authorization

* fix(channels): align provider action contracts

* fix(matrix): read direct-room account data before sync

* fix(channels): reject unsupported attachment actions early

* fix: restore trusted operator conversation reads

* fix(matrix): authorize pin actions before provider reads

* fix: preserve trusted channel read workflows

* fix(discord): resolve current channel ids consistently

* fix(agents): preserve message action turn capability

* fix(plugins): enforce host-owned read provenance

* fix(channels): harden Teams and Discord read policy

* fix(channels): preserve exact-current action compatibility

* fix(imessage): authorize trusted current chat aliases

* fix(channels): preserve normalized current aliases

* fix(channels): preserve external current target aliases

* fix: reconcile channel policy with current main

* fix(discord): isolate DM read policy

* fix(channels): enforce provider read gates

* fix(gateway): await serialized message action identity tokens

* fix(ci): refresh channel protocol contracts
2026-07-10 22:29:37 -05:00
Peter Steinberger
dba64d574f chore(release): set version to 2026.7.2 2026-07-11 04:00:49 +01:00
sunlit-deng
4d55b116c6 fix(feishu): keep native-card payloads in topic threads (#102804) 2026-07-10 19:33:18 -07:00
Peter Steinberger
1b1120a69d fix(feishu): prevent duplicate content in streaming cards (#103915)
* fix(feishu): keep streaming card snapshots authoritative

Co-authored-by: Jun Ma <hpumajunhappy@163.com>

* refactor(feishu): use current snapshot as retry source

* fix(feishu): validate CardKit response bodies

* fix(feishu): keep close summaries accepted

* test(feishu): simplify close rejection state proof

* test(feishu): match normalized close summary

---------

Co-authored-by: Jun Ma <hpumajunhappy@163.com>
2026-07-10 22:05:18 +01:00
Peter Steinberger
add2c586c2 feat(slack): support native chart presentations (#102635) 2026-07-10 04:05:23 +01:00
Vincent Koc
eb721b0b30 refactor(feishu): localize internal declarations (#101949) 2026-07-07 18:41:30 -07:00
Vincent Koc
b88f80940a refactor: localize internal implementation symbols (#101831) 2026-07-07 10:23:36 -07:00
Vincent Koc
fdc7892a6e refactor: localize internal implementation types (#101731) 2026-07-07 07:41:04 -07:00
Peter Steinberger
69b9932fae fix(feishu): support drive folder pagination (#101572)
Co-authored-by: 张贵萍0668001030 <zhang.guiping@xydigit.com>
2026-07-07 11:48:04 +01:00
Peter Steinberger
a2a68d154b fix(agent): preserve explicit recipient sessions (#101507)
* fix(agent): honor recipient session routing

Co-authored-by: vincentkoc <25068+vincentkoc@users.noreply.github.com>
Co-authored-by: pingfanfan <pingfan.work@gmail.com>

* fix(agent): preserve canonical recipient routes

* fix(agent): require exact recipient routes

Co-authored-by: vincentkoc <25068+vincentkoc@users.noreply.github.com>

Co-authored-by: pingfanfan <pingfan.work@gmail.com>

* fix(agent): harden recipient route resolution

* fix(imessage): require canonical recipient handles

* fix(agent): refine provider recipient exactness

* fix(agent): bound direct alias session routing

* fix(signal): preserve direct alias route type

* fix(agent): honor binding-scoped recipient sessions

* fix(routing): honor configured main session aliases

* fix(clickclack): align account-owned session routes

* fix(twitch): preserve canonical recipient sessions

* fix(routing): isolate stable outbound identities

* chore: defer recipient session changelog

* fix(sms): use dedicated channel SDK facade

---------

Co-authored-by: vincentkoc <25068+vincentkoc@users.noreply.github.com>
Co-authored-by: pingfanfan <pingfan.work@gmail.com>
2026-07-07 10:07:13 +01:00
Peter Steinberger
ac24461252 fix(feishu): keep operator logs UTF-16 safe (#101364)
Co-authored-by: Wynne668 <ceng.wen@xydigit.com>
2026-07-07 05:54:50 +01:00
xingzhou
f805bb4e02 fix(feishu): avoid mention forwarding when bot open id is unavailable (#100891)
* fix(feishu): avoid forwarding mentions without bot open id

* fix(feishu): require bot identity for mention forwarding

---------

Co-authored-by: Peter Steinberger <steipete@gmail.com>
2026-07-06 18:54:02 +01:00
Vincent Koc
25a7708f19 fix(feishu): send card JSON message params as cards (#100883)
* fix(feishu): send plain card JSON as interactive cards

Co-authored-by: martingarramon <263922628+martingarramon@users.noreply.github.com>

* fix(clownfish): address review for gitcrawl-21-autonomous-drip-20260706 (1)

Co-authored-by: martingarramon <263922628+martingarramon@users.noreply.github.com>

* fix(feishu): preserve native card compatibility

Reported-by: @ZenoRewn
Co-authored-by: martingarramon <263922628+martingarramon@users.noreply.github.com>

* fix(feishu): fix native card fallback precedence

* fix(feishu): fix native card fallback precedence

---------

Co-authored-by: openclaw-clownfish[bot] <280122609+openclaw-clownfish[bot]@users.noreply.github.com>
Co-authored-by: martingarramon <263922628+martingarramon@users.noreply.github.com>
2026-07-06 06:22:36 -07:00
Alix-007
bf5c9d1748 fix(feishu): bound Feishu API JSON response reads to prevent OOM (#97782)
* fix(feishu): bound Feishu API JSON response reads to prevent OOM

Replace the bare `response.json()` in `fetchFeishuJson`
(`extensions/feishu/src/app-registration.ts`) with a `readResponseWithLimit`
call capped at 16 MiB. A misconfigured or adversarial Feishu endpoint that
streams an unbounded body previously had no defence; the bounded reader now
cancels the stream at the cap and throws a labelled `feishu.api` error.

Tests: over-cap (32 MiB stream, no Content-Length — stream cancelled, error
matches feishu.api), under-cap (chunked valid JSON — parsed and returned),
and malformed-JSON (labelled feishu.api error). All five tests pass.

* fix(feishu): delegate JSON reads to provider helper

* test(feishu): add real node:http server proof for readProviderJsonResponse bound

* test(feishu): fix lint errors in real HTTP server proof (curly + no-promise-executor-return)

* test(feishu): prove bound reads through SSRF guard

* fix(feishu): satisfy overloaded LookupFn type in hermetic test lookup stub
2026-07-06 01:06:08 -07:00
Wynne668
6378d5efcc fix(feishu): strip internal tool-trace banners from outbound text (#98705)
Part of #90684

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-07-06 06:33:16 +00:00
Peter Steinberger
73fc0f5c5f fix(channels): expose inbound media download failures [AI-assisted] (#100119)
* fix(channels): expose inbound media download failures

* fix(msteams): correlate attachment references
2026-07-04 20:28:52 -04:00
TwinsLee
568237b3ab fix(feishu): emit non-empty value schema for bitable write tools (#94547) (#94990)
Type.Record(Type.String(), Type.Any()) serializes via TypeBox to an empty nested value schema (patternProperties: { "^.*$": {} }). AWS Bedrock's strict tool-schema validation rejects the empty sub-schema, breaking all agent turns for Bedrock-backed Anthropic users with Feishu bitable tools enabled.

Replace the three affected free-form field maps (create_record, update_record, create_field) with an explicit non-empty FlexibleFieldValue value schema that still accepts any JSON value. Type.Unknown() is avoided because it also serializes to an empty schema. Adds regression coverage asserting the emitted value schema is non-empty.

Co-authored-by: TwinsLee <1460694+TwinsLee@users.noreply.github.com>
2026-07-04 17:05:32 -07:00
Dallin Romney
bfffa950d7 refactor(plugin-sdk): consolidate tool result helpers (#99740)
* refactor(plugin-sdk): consolidate tool result helpers

* docs(plugin-sdk): tighten tool result guidance

* refactor(feishu): use tool results directly
2026-07-04 16:50:44 -07:00
Peter Steinberger
614e87cce1 chore: update dependencies (#100027) 2026-07-04 14:56:50 -04:00
xingzhou
741d9524be fix: outbound recovery can replay already sent replies (#99600)
* fix(outbound): avoid replaying sent recovery deliveries

* fix(outbound): persist recovery send state before ack

Co-authored-by: zhang-guiping <zhang.guiping@xydigit.com>

* fix(outbound): preserve partial send evidence across adapters

* test(line): cover multi-send delivery progress

* fix(outbound): preserve repeated receipt result multiplicity

* test(heartbeat): expect delivery progress callback

---------

Co-authored-by: Peter Steinberger <steipete@gmail.com>
2026-07-04 01:09:12 -07:00
Dallin Romney
c7aca4f029 refactor: consolidate async timing helpers (#99721) 2026-07-03 17:58:15 -07:00
LZY3538
e272da5c55 fix: keep always-on group fallback messages in dispatch (#99506)
* fix(auto-reply): honor always-on plugin fallback groups

* fix(channels): preserve mention policy across bindings

* test(discord): type mention policy dispatch context

* test(discord): type mention policy dispatch context

* fix(whatsapp): preserve effective mention policy

* fix(whatsapp): preserve effective mention policy

---------

Co-authored-by: Peter Steinberger <steipete@gmail.com>
Co-authored-by: Peter Steinberger <peter@steipete.me>
2026-07-03 07:26:45 -07:00
lwy-2
33c1e6224c fix(feishu): catch unhandled promise rejection in streaming card flush timer (#99301)
* fix(feishu): catch unhandled promise rejection in streaming card flush timer

## What Problem This Solves

The scheduled flush update in FeishuStreamingSession called
`this.update(pending)` without catching potential rejections, which
could cause unhandled promise rejections when card content updates
fail due to transient network errors.

## Why This Change Was Made

Add a `.catch()` with diagnostic logging to the scheduled flush
timer's `update()` call so transient card update failures are visible
without causing unhandled promise rejections.

## User Impact

Scheduled streaming-card updates that fail transiently will log a
diagnostic instead of producing an unhandled promise rejection.

## Evidence

node scripts/run-vitest.mjs extensions/feishu/src/media.test.ts

  Test Files  1 passed (1)
  Tests       44 passed (44)

pnpm exec oxfmt --check ...

  All matched files use the correct format.

node scripts/run-oxlint.mjs ...

  oxlint_exit=0

git diff --check

  exit=0

Co-Authored-By: Claude <noreply@anthropic.com>

* test(feishu): cover rejected scheduled card flush

---------

Co-authored-by: Claude <noreply@anthropic.com>
Co-authored-by: Peter Steinberger <steipete@gmail.com>
2026-07-03 02:20:43 -07:00
Dallin Romney
de34dfdbe8 refactor(plugins): consolidate record guards (#99361) 2026-07-02 22:12:53 -07:00
Dallin Romney
59b08b4693 refactor(shared): consolidate remaining channel lazy loaders (#99302) 2026-07-02 19:08:11 -07:00
Peter Lee
2d764dd8fe fix(feishu): preserve button command values in fallback text and add Feishu comment guidance with callback privacy (#94385)
* fix(interactive): preserve button command values in fallback text for degraded approval UX

* fix(interactive): keep callback values private in fallback text and narrow Feishu interactive detection

- P1: Skip rendering action.type === "callback" values in
  renderMessagePresentationFallbackText to avoid leaking opaque
  channel/plugin data into user-visible text. Command and legacy
  values are still rendered.
- P2: Replace hasMessagePresentationBlocks/hasInteractiveReplyBlocks
  with isMessagePresentationInteractiveBlock so Feishu comment
  guidance only appears when the presentation actually contains
  buttons or selects, not for text-only blocks.
- Update tests: callback button now shows label-only; all 137 tests pass.

* fix(interactive): only render typed command values in fallback text, keep legacy value private

* fix(feishu): gate document-comment command guidance on actual command action

* docs(message-presentation): document command/callback value fallback visibility

* fix(feishu): omit command guidance when URL overrides fallback command text

* docs: regenerate docs_map.md

* fix(interactive): exclude disabled buttons from fallback command rendering and guidance

* fix(interactive): extract hasRenderedCommandAction, exclude disabled buttons from command fallback

* fix(feishu): preserve command guidance marker through core presentation rendering

* fix(feishu): type-narrow channelData.feishu with isRecord before reading rendered-command marker

* fix(feishu): move hasRenderedCommandAction from public SDK into Feishu plugin as local helper

Keep the helper local to the only caller (Feishu outbound) instead of
adding a new public plugin SDK API contract. The shared fallback renderer
in renderMessagePresentationFallbackText already inlines the same
command-visibility logic; a local helper is sufficient for the Feishu
comment-thread guidance gate.

* refactor(feishu): tighten fallback command marker

---------

Co-authored-by: Peter Steinberger <steipete@gmail.com>
2026-07-02 12:42:31 -07:00
areslp
22d686d13e fix(feishu): include video upload duration (#98235) 2026-07-02 02:28:21 -07:00
Peter Lee
9fabdcf49d fix(feishu): send blocks as independent messages when blockStreaming is enabled (#94250)
* fix(feishu): send blocks as independent messages when blockStreaming is enabled

* fix(feishu): preserve mention targets on first independently sent block

* fix(feishu): route independent block sends through chunked text delivery

Route the independent block-send path through sendChunkedTextReply
instead of calling sendMessageFeishu directly, so the configured
Feishu textChunkLimit is honored for completed blocks. Preserve
mention targets only on the first emitted block chunk and keep
sentBlockText based on the original block text for duplicate-final
suppression.

Add regression test with a small textChunkLimit that verifies a
long block is split into chunked messages and mentions only appear
on the first chunk.

* fix(feishu): preserve block delivery target

---------

Co-authored-by: Vincent Koc <vincentkoc@ieee.org>
2026-07-01 08:12:13 -07:00
Peter Steinberger
60d55a1725 fix: restore main lint after timer repairs
Preserve the Tailscale timeout cleanup from #98134 and the Feishu TDZ fix from #98137 while satisfying the repository lint rules.

Credit: @zhangLei99586 authored both underlying fixes.

Co-authored-by: Peter Steinberger <58493+steipete@users.noreply.github.com>
Co-authored-by: zhangLei99586 <zhang.lei162@xydigit.com>
2026-07-01 04:43:24 -07:00
zhangLei99586
8b14321c11 fix(feishu): hoist abortable delay timer binding
The finish() closure referenced timer which was declared with const after
finish was defined. If finish(false) ran via the abort signal check at
line 99 or via the abort event listener before the const timer assignment,
accessing timer in the temporal dead zone would throw a ReferenceError.

Hoist timer as a let binding above finish so it is safely undefined when
finish fires early, and the  guard in finish handles it.
2026-07-01 04:06:33 -07:00
xydt-tanshanshan
5f80f12a95 [AI] fix(feishu): guard partial channelRuntime in monitor startup (#94013)
* [AI] fix(feishu): guard partial channelRuntime in monitor startup

When the gateway passes a partial channelRuntime (ChannelRuntimeSurface
with only runtimeContexts but no inbound/debounce), the ?? operator in
monitor.account.ts selects it over the full local runtime, causing
monitor startup to crash on channelRuntime.debounce access.

Mirror the same ?.inbound guard pattern from bot.ts:739 (PR #93466)
to monitor.account.ts:487. When the runtime lacks inbound, fall back
to getFeishuRuntime().channel which always has the full surface.

No test: the guard mirrors an already-merged pattern (#93466) and only
affects the partial-runtime edge case that requires a gateway context.

Related to #92595

* [AI] test(feishu): add channelRuntime guard tests for monitorSingleAccount

Three test cases for the channelRuntime guard at
monitor.account.ts:489:
1. Partial channelRuntime (no inbound) → falls back to local runtime
2. Full channelRuntime with inbound → uses provided runtime
3. No channelRuntime (undefined) → falls back to local runtime

Related to #92595
2026-07-01 01:58:58 -07:00
Vincent Koc
3e2646a786 fix(release): use workspace host deps in release lockfile
(cherry picked from commit d377c0f910)
2026-06-30 15:54:12 -07:00
Vincent Koc
66e676d29b chore(release): close out 2026.6.11 on main 2026-06-30 11:31:08 -07:00
Vincent Koc
c16bb8725a fix(channels): keep text previews UTF-16 safe 2026-06-30 11:04:32 -07:00
Ayaan Zaidi
f078962d17 fix(feishu): require explicit reply send target 2026-06-30 10:40:48 -07:00
xydigit-zt
62fa674a39 fix(feishu): route non-thread p2p DM replies to user:<open_id>
Add sendTarget param to createFeishuReplyDispatcher that overrides
the to: field for visible sends. Fix streaming card delivery target
by stripping routing prefixes (user:, chat:) before the Feishu
streaming API call. Route streaming card reply metadata through
suppressed sendReplyToMessageId.

Closes #83730
2026-06-30 10:40:48 -07:00
Acache
e7d6566b8f fix(feishu): publish transport health status (#90966)
Co-authored-by: Vincent Koc <vincentkoc@ieee.org>
Co-authored-by: Acache <acache@users.noreply.github.com>
2026-06-28 23:12:09 -07:00
llagy009
1841c4caf5 fix(feishu): truncate comment prompt text on UTF-16 boundary 2026-06-28 19:07:11 -07:00
zw-xysk
4e7992cc9b fix(feishu): keep top-level appSecret SecretRef active for the implicit default account (#96965)
When a Feishu channel has top-level appId/appSecret using SecretRef
format and sub-accounts with their own inline appSecret, the secrets
resolver marks the top-level SecretRef as inactive because
isBaseFieldActiveForChannelSurface only checks whether any explicit
account inherits the field.

Feishu account listing always creates an implicit default account from
top-level credentials.  The fix detects this implicit default account
and keeps the top-level appSecret active accordingly, without changing
the shared channel secret helper semantics for other channels.

Fixes #96929

Signed-off-by: 赵旺0668001248 <0668001248@duomai.com>
2026-06-28 18:40:41 -07:00
Harjoth Khara
31b531e791 fix(feishu): sanitize identity emoji in card headers (#96587)
* fix(feishu): sanitize identity emoji in card headers

* test(feishu): avoid env-key identity header fixture
2026-06-28 18:36:00 -07:00
ly-wang19
20645753a4 fix(feishu): truncate streaming-card summary on a code-point boundary (#97462)
truncateSummary used clean.slice(0, max - 3), which can cut between the
two UTF-16 halves of a surrogate pair (emoji / astral char) straddling
the limit. The serialized card summary then carries a lone high
surrogate that Feishu renders as the replacement char.

Slice with the surrogate-safe sliceUtf16Safe helper instead, matching
the pattern already used in extensions/slack/src/truncate.ts, so a
straddling code point is dropped whole.

Co-authored-by: ly-wang19 <ly-wang19@users.noreply.github.com>
Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-28 12:10:42 -07:00