* feat(line): EBA LINE adapter skeleton (WO-LINE-01-SKELETON-1018)
- pkg/platform/adapters/line/ 9 files (LineAdapter hybrid inheritance +
Capability + event namespace + config env load, zero hardcoded secrets)
- LINE SDK calls all stub (NotImplementedError) pending WO-LINE-00/02/03
- Verified: compileall 7/7 + ruff 0 + import chain green against
v4.11.0-hotfixed SDK (container-extracted, read-only)
- Source: handoff box WO-LINE-01-SKELETON-1018 (sha256 9/9 matched)
Co-authored-by: multica-agent <[email protected]>
* feat(line): implement WO-LINE-02 message.received loop and converter
Co-authored-by: multica-agent <[email protected]>
* feat(line): implement WO-LINE-03 streaming and send API
Co-authored-by: multica-agent <[email protected]>
* feat(line): implement WO-LINE-04 group and user event extensions
Co-authored-by: multica-agent <[email protected]>
* feat(line): implement WO-LINE-05 group and user event extensions
Co-authored-by: multica-agent <[email protected]>
* docs(line): add EBA LINE adapter architecture guide and documentation
Co-authored-by: multica-agent <[email protected]>
* feat(line): resolve Ruff warnings and manifest spec update
Co-authored-by: multica-agent <[email protected]>
* feat(line): add webhook_url config and help_links to PR_DESCRIPTION.md
Co-authored-by: multica-agent <[email protected]>
* feat(line): add webhook_url config and help_links for PR #2736
Co-authored-by: multica-agent <[email protected]>
* fix(line): ruff format, update help_links, remove nested duplicate dir
Co-authored-by: multica-agent <[email protected]>
* fix(line): resolve 12 test failures, align types, and move architecture docs to dev-docs
Co-authored-by: multica-agent <[email protected]>
* fix(line): resolve ruff lint and formatting issues for CI
Co-authored-by: multica-agent <[email protected]>
* docs(line): sanitize internal orchestration notes and standardize documentation
Co-authored-by: multica-agent <[email protected]>
* clean(line): remove internal tracking ticket references from source code
Co-authored-by: multica-agent <[email protected]>
* fix(line): resolve MessageReceivedEvent and Friend entity mapping for 100% test pass
Co-authored-by: multica-agent <[email protected]>
* fix(line): resolve E402 import order in event_converter.py
Co-authored-by: multica-agent <[email protected]>
* feat(line): implement the LINE Omni adapter on the legacy messaging flow
Replace the placeholder skeleton with a working unified-webhook adapter:
- verify X-Line-Signature with WebhookParser and acknowledge before dispatch
- build real LINE messaging clients from channel_access_token and drop
the adapter's own messages using the account id from get_bot_info
- map message/image/voice events to message.received, unsend to
message.deleted, membership changes to group/bot events, and the
remaining LINE event types to platform.specific with chat identity
- send and reply through MessagingApi with LINE's five-message budget,
a reply-token to push fallback, and honest NotSupportedError paths
- expose get_user_info, get_group_info, leave_group and the get_bot_info,
get_profile, get_group_summary pass-through actions
- keep the legacy FriendMessage/GroupMessage listeners working
- move tests to tests/unit_tests/platform, add the adapter doc, and
register line in OMNI_ADAPTER_NAMES
Co-authored-by: multica-agent <[email protected]>
---------
Co-authored-by: multica-agent <[email protected]>
Co-authored-by: RockChinQ <[email protected]>
Drop intermediate stream frames that land inside the pacing window so a fast
runner cannot flood the WeCom wire. The first frame of a stream is released
immediately because there is no prior timestamp to compare against, and final
frames always bypass the throttle.
Frames carry complete snapshots since a2b7f6b7, so dropping an intermediate
frame loses no content: the next frame already carries everything.
- Deduplicate message and history resource URLs using stable catalog references
- Persist renewed URLs with concurrent refresh protection
- Refresh OneBot images via get_msg intervals or NapCat rkey TTL
- Migrate historical payloads and cover SQLite and PostgreSQL behavior
- Cache NapCat rkeys by type and refresh only when their TTL expires
- Renew image URLs through get_msg for other OneBot v11 implementations
- Refresh session views, Runner history, and each model request attempt
- Isolate caches by connection without downloading images or rewriting history
The platform adapters fetch URLs and open paths that come from inbound
messages, so both are attacker-influenced.
New guard module pkg/utils/outbound_url.py:
- assert_safe_outbound_url: checks the scheme, rejects literal private /
loopback / link-local / reserved / multicast addresses, and resolves the
hostname so a public-looking name pointing at an internal address is refused
too. Optional allowed_domains confines a fetch to a known prefix.
- assert_safe_local_media_path: resolves a caller-supplied path and requires it
to stay inside the media roots (data dir + temp dir), so symlinks and .. cannot
escape. Directories are refused.
Wired in:
- DingTalk send_message: session_webhook is taken from the inbound event and was
POSTed verbatim, so a forged event could redirect reply content (including LLM
output) to any host. Now restricted to dingtalk.com.
- DingTalk send_attachment: component.url was fetched with no destination check;
now goes through the SSRF guard, which also covers cloud metadata.
- DingTalk upload_image_media: caller-supplied file_path was opened directly; now
confined to the media roots.
- Slack attachment_bytes: component.path was opened directly and uploaded to the
channel (arbitrary file exfiltration); now confined to the media roots.
- Slack download_media: redirects were followed with no destination check. Every
hop is now validated, the hop count is bounded, and a redirect off the Slack
domain drops the bearer token.
Tests: 25 new cases for the guard (internal address forms, scheme rejection,
suffix impostor, traversal, symlink escape, directory). The Slack credential test
now stubs DNS because the guard resolves before fetching, and asserts
allow_redirects is False for every case since redirects are handled manually.
Co-authored-by: multica-agent <[email protected]>
* feat(onebot): support main-port reverse and forward WebSocket connections
* fix(onebot): keep protocol metadata out of business events
* test(onebot): validate WS events and APIs against independent protocol peer
---------
Co-authored-by: Hyu <[email protected]>