Commit Graph
1191 Commits
Author SHA1 Message Date
DrSmoothl 2e2c1266ac test(core): cover WebUI auth password and TOTP restore 2026-08-14 10:57:17 +08:00
DrSmoothl 31bd8ea77b test(protocol): cover highway streaming hash and upload staging 2026-08-14 10:57:17 +08:00
DrSmoothl 4c994dbd20 test(onebot): cover group admin, message, media, and quick-operation paths 2026-08-14 10:57:17 +08:00
DrSmoothl 8004e9af9d test(sdk): cover API client, chain, emitter, guards, and segments 2026-08-14 10:57:16 +08:00
DrSmoothl 80f34ca720 test(bridge): cover injector lookup and QQ login port probe 2026-08-14 10:57:16 +08:00
DrSmoothl d46d8e4002 chore(release): v1.14.7 2026-08-13 19:47:25 +08:00
DrSmoothl 5a012fe0c8 fix(webui): allow empty OneBot tokens on loopback bind hosts
Empty inbound tokens were gated on the WebUI page hostname / client IP,
so a remote panel visit blocked clearing the token even when the
listener was 127.0.0.1. Trust the bind host as well: loopback listeners
are not reachable from outside, while 0.0.0.0 still requires a local
WebUI session.
2026-08-13 19:45:11 +08:00
DrSmoothl b8b9be83c3 feat(core): stream flash-transfer uploads from disk
create_flash_task loaded every fileset file through loadBinarySource
and kept the bytes through hash, commit, and sliceupload, so a single
file over 1 GiB could not be sent. Stage to disk like group files,
stream MD5/SHA1/Sha1StateV, then POST 1 MiB chunks from FileChunkSource.

Do not reuse video sha1Blocks as Sha1StateV: an exact N-MiB file would
ship an extra un-finalized last-slice state. Local/HTTP sources use the
4 GiB group-file ceiling; inline base64 stays at 1 GiB because stage
still decodes it in RAM. Protocol order, seconds-pass, and multi-file
commit are unchanged.

Fixes #359
2026-08-13 18:34:27 +08:00
DrSmoothl e7322e2e72 fix(protocol): decode current NT flash-transfer cards
Current clients put fileset identity on markdown extInfo and the
open_fileset scheme, not data.fileSetId. Empty message arrays were
the old scraper missing those fields.

Fixes #358
2026-08-13 18:18:56 +08:00
DrSmoothl 9e0dd5d75c chore(native): refresh bundled runtime files 2026-08-13 17:27:54 +08:00
DrSmoothl 7d5ca5523b refactor(protocol): own inbound UID-to-UIN resolution in Identity
Inbound person lookup used to be split across decoders, the packet
pipeline, and Bridge closures. Missing identities were filled from
unrelated packet headers, and "who is this person" was coupled to
roster refresh and pending-request enrichment.

Identity now owns both directions of resolution. The hot path stays
synchronous and emits unresolved events on a miss. Only the paths
that already waited before dispatch perform a network lookup, and
that lookup is a profile fetch by UID rather than a member-list
refresh. Pending-request comments and approval flags stay outside
Identity.

Decoders no longer invent a UIN from a group routing header. Private
chat routing still uses a hop's own wire UIN when the hop is named
that way. Inbound misses stay availability-first: they do not throw
and do not mark Identity degraded.
2026-08-13 14:37:56 +08:00
DrSmoothl d26aef86d8 chore(release): v1.14.6 2026-08-13 12:52:21 +08:00
DrSmoothl f100faaeb6 fix(protocol): read group mute expire from official proto tags (#356)
get_group_info / get_group_list mapped FE5 tag 31 and 88D tag 59 as
shutUpAllTimestamp, then treated any >0 value as muted. Official
wrapper.node maps those tags to internal 60259; the real expire
(60027 / groupShutupExpireTime) is FE5 tag 10 and 88D tag 45
(request mask 45). After a group had been muted, 60259 often stayed
nonzero so group_all_shut stuck at -1. Read the 60027 tags and treat
all-mute as expire > now (0xFFFFFFFF is permanent).

Fixes #356
2026-08-13 12:44:56 +08:00
DrSmoothl 2f5065545a fix(onebot): percent-decode file URL basenames on upload (#354)
send_group_msg / send_private_msg with a file segment that only has
file:// (no name/filename) used url.split('/').pop() as the upload
name, so percent-encoded CJK paths uploaded as
%E6%B5%8B%E8%AF%95%E6%96%87%E4%BB%B6.xlsx. Derive the fallback through
guessFileNameFromUrl, which decodeURIComponent's the path basename
(invalid encodings are left as-is). An explicit name still wins.

Fixes #354
2026-08-13 11:02:02 +08:00
DrSmoothl 5c2f620c54 feat(webui): add optional TOTP 2FA for operator login (#351)
WebUI access was a single shared password. This adds optional
Authenticator TOTP as a second factor, with one-time recovery codes
and SSH as the last-resort disable path.

Login stays two HTTP posts with no pending token: a correct password
and enabled 2FA without a second factor returns { needsTotp: true };
the client then resubmits { password, totp } or { password, recoveryCode }.
The TOTP secret is wrapped with a password-derived AES-256-GCM key.
Eight XXXX-XXXX recovery codes are stored as SHA-256 hashes and each
code is consumed once. Enabling or disabling 2FA invalidates other
sessions; disabling still requires password plus TOTP or a recovery
code. SNOWLUMA_DEV_MODE hides the feature.

The login page uses a dedicated second-factor screen (Interior OTP
cells for the 6-digit code; the same cell UI for recovery codes,
grouped as XXXX-XXXX). Settings expose enroll/confirm/disable and
one-time recovery-code display.

Fixes #351
2026-08-13 01:33:57 +08:00
DrSmoothl 679f3b5b9f fix(highway): delay-retry 102902 instead of aborting the upload (#352)
upload_group_file of ~2 GiB files failed after a highway idle timeout
because the next decoded error_code=102902 was treated as a fatal
server reject. QQ's own BDH client (multi_uploader.cc NeedDelayRetry)
treats 102902 / 302902 as backpressure: wait, switch sender, and
re-PUT the same offset. Mirror that — drop the socket, wait 250 ms,
increment retryTimes, and retry the chunk up to 8 times. Definitive
codes such as 921 still fail immediately.

Fixes #352
2026-08-13 00:20:40 +08:00
DrSmoothl 8ded1065d4 fix(onebot): return profile like user details
Restore the interaction user lists returned by get_profile_like and keep self and other-user lookups consistent with the current client behavior.

Resolve missing account identities when needed, surface lookup failures, and update the public action catalog with the completed response shape. Add regression coverage for request selection, response decoding, identity enrichment, and malformed results.

Fixes #349
2026-08-11 23:46:46 +08:00
DrSmoothl b38db6715f chore(native): refresh bundled runtime files 2026-08-11 23:23:08 +08:00
DrSmoothl 58f1a1fc50 fix(release): make main synchronization deterministic
Fetch and fast-forward the remote main branch without inheriting user pull settings. Verify both refs match before tagging and keep manual recovery instructions aligned with the automated flow.
2026-08-11 18:38:07 +08:00
DrSmoothl 0357d136d8 chore(release): v1.14.5 2026-08-11 18:20:17 +08:00
DrSmoothl 190f156fca fix(onebot): preserve group requests with unknown senders
Deliver actionable invitations even when the sender account is unavailable instead of failing the full polling batch.

Isolate malformed records, keep sibling requests flowing, and distinguish multiple anonymous invitations by their request handles.

Add regression coverage for repeated polls, batch isolation, and anonymous-request deduplication.
2026-08-10 13:12:18 +08:00
DrSmoothl da3821ced4 feat(sdk): expose group request query options
Add typed group, pending-state, and per-inbox limit options to group-system message queries while preserving existing call sites.

Regenerate the shared action catalog so SDK and MCP consumers receive consistent validation rules and updated request-flag guidance.
2026-08-10 00:26:29 +08:00
DrSmoothl 1996192a5e feat(onebot): report web-originated group requests
Report pending group invitations through the standard OneBot request event even when their origin does not provide a live notification.

Prevent duplicate delivery when the same invitation is observed more than once, stop outstanding work with the account lifecycle, and preserve previously supported invitation behavior.

Expand group-system message queries and surface incomplete lookups instead of reporting misleading empty or not-found results.
2026-08-10 00:26:16 +08:00
DrSmoothl fe44a2f5bc fix(group-requests): normalize request retrieval and handling
Correct group-request retrieval so requester identities and action metadata remain usable across client and web-originated invitations.

Keep existing live-event behavior compatible, ensure returned requests carry the correct information for approval or rejection, and reject malformed request identifiers instead of emitting unusable flags.

Add regression coverage for both request inboxes and the supported invitation categories.
2026-08-10 00:26:01 +08:00
DrSmoothl 870e9a5fbc fix(bridge): recover stale outbound sessions
Recover invalidated native send bindings from same-account receive evidence. Track outbound connection loss in status health and refresh the six public native artifacts from native build 94f2b63.

Closes #342
2026-08-09 21:40:09 +08:00
DrSmoothl 129b091081 fix(onebot): skip unusable reply segments
Keep delivering valid message content when a reply target cannot be resolved, while retaining strict validation for all other segments.

Fixes #339
2026-08-09 17:25:48 +08:00
DrSmoothl dbf654ad57 chore(release): v1.14.4 2026-08-09 16:53:10 +08:00
DrSmoothl c08150fc0c feat(onebot): query group todo messages
Fixes #332
2026-08-09 13:36:41 +08:00
DrSmoothl 4aba81ec6b feat(onebot): decode bot markdown and keyboards
Fixes #337
2026-08-09 13:06:35 +08:00
DrSmoothl 1e0c91e74d feat(onebot): configure group member permissions
Fixes #335
2026-08-09 12:56:05 +08:00
DrSmoothl e08613062e feat(onebot): configure group history visibility
Fixes #336
2026-08-09 12:53:45 +08:00
DrSmoothl cd6fcadea4 feat(onebot): configure group invite policy
Add validated group member invite policy updates with post-write verification.

Fixes #334
2026-08-09 11:46:04 +08:00
DrSmoothl 597a4c05f3 feat(onebot): fetch custom face details
Add packet-backed custom face detail retrieval and expose the result through the OneBot action.

Fixes #333
2026-08-09 11:45:43 +08:00
DrSmoothl 49439370e1 fix(onebot): decode user status property list (#330) 2026-08-09 11:28:14 +08:00
DrSmoothl 7eea8059cc chore(release): v1.14.3 2026-08-08 19:44:58 +08:00
DrSmoothl c404974e75 fix(protocol): support cross-pack system face overlaps (#324) 2026-08-08 19:26:09 +08:00
DrSmoothl 4c385bf640 fix(release): refresh generated action catalog 2026-08-08 17:52:52 +08:00
DrSmoothl f968687a25 chore(release): v1.14.2 2026-08-08 17:46:31 +08:00
DrSmoothl 39d5a50d5f fix(protocol): accept Unicode system face identifiers (#324) 2026-08-08 17:42:14 +08:00
DrSmoothl 65683bb44d fix(onebot): accept compatible JSON card payloads (#325) 2026-08-08 10:14:39 +08:00
DrSmoothl 751217c13d perf(webui): reduce initial loading delays 2026-08-08 00:04:51 +08:00
DrSmoothl c53c6651a5 docs(readme): streamline project overview 2026-08-07 21:58:44 +08:00
DrSmoothl 005154077f fix(onebot): accept id-less custom music cards (#319) 2026-08-07 21:50:28 +08:00
DrSmoothl 1646f265ec fix(protocol): skip non-addressable system face entries 2026-08-07 21:24:05 +08:00
DrSmoothl 4d958eb984 chore(release): v1.14.1 2026-08-07 20:29:00 +08:00
DrSmoothl 810509ef58 fix: restore message sending after restart 2026-08-07 19:24:24 +08:00
DrSmoothl f1ae0736c6 build(release): enforce neutral runtime layout
Keep release files at the archive root and reject product-named directory components before CI packages artifacts.

Use neutral directories for media staging, WebUI uploads, stream storage, and MCP downloads so packaged and runtime layouts remain consistent.
2026-08-06 23:08:19 +08:00
DrSmoothl c0e73cd738 fix(protocol): handle empty group essence lists
Return an empty result when a successful, completed group essence response omits its message list instead of reporting a malformed response.

Keep upstream errors and incomplete pagination responses explicit, and cover omitted and null list variants with regression tests.

Fixes #320.
2026-08-06 22:36:05 +08:00
DrSmoothl 27c527976b fix(onebot): reject ambiguous video message combinations
Prevent ordinary messages and forwarded nodes from combining video content with visible sibling segments or additional videos. Invalid combinations now fail before parsing side effects, media work, or bridge sends, while exact empty text placeholders remain compatible with a single video.

Cover group, private, temporary-session, CQ string, nested forward, cached forward, and protocol-builder paths. Preserve the existing standalone window-shake behavior and keep valid single-video messages unchanged.
2026-08-05 23:55:55 +08:00
DrSmoothl 2ac0b92859 fix(onebot): support standard forward WebSocket routes
Accept the standard action, event, and universal paths when a forward WebSocket server listens at the root endpoint.

Keep authentication, custom endpoints, embedded listeners, and rejected-path reporting compatible while assigning each accepted connection the correct role.

Add real-listener regression coverage for standard paths, trailing slashes, query authentication, invalid paths, and existing lifecycle behavior.

Fixes #317
2026-08-05 19:39:30 +08:00