Render publish_type=draft tasks with the warn tone and 已存草稿 label, swap
the management link copy to 打开草稿箱 for weixin_gzh, and expand the task
summary to mention the publish_authorization_required reason. In the admin
drawer, stop falling back to external_manage_url for missing public links
and instead show a hint pointing operators back to the desktop client for
weixin_gzh / zol records.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Replace the masssend HTTP path with a Playwright-driven editor flow that
clicks "群发" and resolves the publish response, then polls appmsgpublish
for the public mp.weixin.qq.com/s URL. When the dialog asks for admin
verification / scan-code authorization, swallow it as a successful draft
save and surface fallback_reason=publish_authorization_required so the
operator can finish from the console. Also broaden token extraction in
account-binder and treat the draft list URL (cgi-bin/appmsg) as the
console landing page.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
"内容由AI生成" tripped Wangyihao's AIGC review and parked drafts under
manual screening. Switch to "个人观点,仅供参考" so legitimate posts move
through normal moderation.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Drafts previously stopped at the草稿箱 step, leaving the operator to publish
manually. Chain a /cgi-bin/masssend call, then poll the appmsgpublish list
(by title and by latest) to extract the mp.weixin.qq.com/s public link
and a publish_id. Surface dedicated failures for publish and link-missing
states, and switch the result payload to publish_type="publish" with the
appmsgpublish manage URL.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Replace the generic 重新校验 action with state-aware copy and an arrow
icon when authState is expired, and route the click through the bind flow
so users land directly on the platform login page. AiPlatformsView gains
the same shortcut and an inline alert explaining tasks are paused until
re-auth completes.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Move the per-platform translation map out of HomeView/TasksView and the
titleCaseToken fallback out of PublishManagementView into shared helpers
on media-catalog. Single source of truth keeps renderer views consistent
with the binding catalog when new platforms ship.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Bind callbacks now stamp the runtime account as health=live with a fresh
verified_at and seed the health record via markTrackedAccountBound, so the
UI doesn't show a just-bound account as 尚未校验 while waiting for the next
probe. Also let force probes bypass the cached-result short-circuit so the
manual 重新校验 button always re-runs the probe.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Naked /cgi-bin/home redirects to the login page even with a live cookie,
which made probe/refresh/verify mis-classify accounts as expired. Resolve
the tokenized console URL via mp.weixin.qq.com first, then read the page
state to detect 登录超时/未登录 banners and reuse detectWeixinGzh to confirm
identity. Open-console also now lands on the tokenized URL.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
The MP draft API sometimes returns appMsgId as a number or under the
appmsgid alias; coerce both shapes before treating the response as a
success. Also extend the platform auth adapter to recognize 登录超时/
请重新登录 wording so the runtime drives the account back to re-auth.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
These ByteDance asset CDNs ship images and static docs that are not real
citations, so they pollute the monitoring source list. Filter them at both
buildSourceItem and dedupe stages, and add unit coverage via an exported
test-only helper bag.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Add a CRUD page for site_domain_mappings with search, pagination, create/
edit/enable/disable/delete actions, and register it in the AppShell nav.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Persistent logins land in localStorage, ephemeral ones in sessionStorage,
and we recall the last username + remember preference on the login form.
Also propagate the indigo brand color through the antd ConfigProvider
theme token so the side nav and avatar match the redesigned login.
Why: avoid showing accounts as not-live during stale-window probes; keep publish gating consistent with runtime view.
- collapse FIRST_PROBE window so initial probe runs immediately
- skip due-probe selection when a probe is already queued/in-flight
- mirror auth-state→health projection on both client report and tenant ingest paths
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Replace the previous split-screen with a brand panel that hosts an
animated mascot (eyeballs whose pupils track the focused form field and
hide while the password is typed) and decorative grid/circles, plus a
mobile brand mark and footer links. Swap Ant Design form controls for
native inputs styled to match. The mascot is composed from new
AnimatedCharacters / EyeBall / Pupil components.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Add an IPRegionResolver wrapping the ip2region xdb library and attach it
to AuditService so each appended event records both the raw IP and a
resolved region in a new ops.audit_logs.ip_region column. Loopback and
private addresses short-circuit to local labels; missing xdb data or
lookup errors degrade silently so auditing keeps working without it.
The ops console audit view shows the region beneath the IP. Bundle the
v4/v6 xdb data under internal/ops/app/ipregiondata so the resolver works
out of the box, with config paths/env overrides for swapping in updated
data sets.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Adds /admin-users CRUD on the ops backend, covering listing, plan/role/KOL
toggles, subscription expiry, status flips and password resets, with a
configurable default plan code. The ops console exposes a new top-level
"用户管理" view and reorganises the sidebar so 操作员管理 and 审计日志
move under a "系统设置" group; AccountsView is renamed accordingly.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Login form takes a phone-or-email identifier; user info now exposes phone
so the shell can fall back through name → phone → email. When membership
expires, the app stays on the current route but renders a minimal blocked
state in the shell instead of redirecting to a dedicated page; an Axios
interceptor flips the local session into the blocked state when the API
returns trial/subscription errors.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Server callback now rejects succeeded submissions without a non-empty answer,
or whose answer contains [citation:N] markers without any sources. Desktop
adapters mirror this client-side: kimi returns unknown when sources arrive
without a final answer, and yuanbao returns unknown when the answer has
unresolved citation markers. Yuanbao also unwraps redirect URLs, harvests
citations from more DOM attributes and document URL fields, drops links
pointing back at yuanbao itself, and dedupes overlapping streaming
fragments. Runtime controller forwards only an explicit "succeeded" status
as success; anything else becomes failed.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Surfaces the new AI point quota in the workspace shell and adds a
Personal Center → AI Point Usage page that shows balance, base-char
rule, and the paginated reservation/refund history. Updates shared
types for the QuotaSummary and ledger payloads.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Vue 3 + Ant Design Vue SPA scaffold for the internal ops console. Ships
the auth, account list, and audit log views that consume the new ops-api
endpoints, plus the nginx/vite/typecheck plumbing.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
The transport/lease-manager/vault JSON dump was a debug artifact and
duplicated information already surfaced in the network and accounts
panels. Remove the panel and its styles.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
The deepseek adapter pulls in electron/main when registering ipc listeners,
which made the test fail at import time outside the electron runtime. Stub
ipcMain with vi.mock so the unit test can load the module under vitest.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Use the account session for imagex apply/upload/commit so the requests carry
the same cookies/UA the bind console saw, instead of falling out of the
session via a bare Node fetch — bytedance imagex was rejecting these as
unauthenticated under the bound session. Also align the binding console URL
with the v2 publish article path.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Surface the new runtime_health/runtime_checked_at fields through a tiny
desktop-account-runtime helper so PublishArticleModal, MediaView, and
TrackingView fall back to the desktop client's last live signal instead of
the slower DB column. This keeps the publishable card and tracking
breakdown in sync with the desktop probe loop.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Replace serial probe-on-lock with a bounded probe queue (concurrency 3) that
adds a "queued" probe state, manual cooldown, and retry backoff. After each
probe the runtime debounces a batched POST to the new
/desktop/accounts/health-reports endpoint so the server learns about live,
expired, and risk transitions without waiting for a re-bind. Adds an
account-scoped IPC (probeRuntimeAccount + runtimeAccountSnapshot) so the
renderer can refresh a single row instead of replaying the full snapshot,
and exposes the resulting "重新校验" action in AccountsView/AiPlatformsView.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
The login shell sets -webkit-app-region: drag on its frameless header,
which captured clicks on the "记住密码" checkbox before v-model could
update. Mark .options-row and its descendants as no-drag, and bind the
checkbox via :checked + @change so the click reliably reaches the
toggle handler.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Switch the publish management page to the hero-card + stats-strip layout
shared with AccountsView for visual consistency: bigger title, stats
row, modern table styling, and a content-section wrapper. Add a
buildSohuArticleUrl helper that reconstructs the sohu article URL from
the task result and the bound account's platform uid when the adapter
result didn't include external_article_url, so older finished tasks
also resolve a viewable link.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
The v3 manage URL has been retired and now redirects through a login
gate, breaking the post-publish "管理" deeplink and login detection.
Switch the binding console URL and the adapter SOHU_MANAGE_URL to the
v4 contentManagement endpoints, and synthesize external_article_url for
publish (not draft) results from the article id and account uid so the
publish list can offer a "查看文章" link without an extra fetch.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Generate the desktop client_id deterministically from OS machine identifiers
(IOPlatformUUID / MachineGuid / /etc/machine-id) scoped per
tenant+workspace+user, with a persisted UUID fallback when the OS lookup
fails. The renderer now requests the id over a new IPC bridge instead of
keeping a localStorage UUID, so reinstalls and storage clears no longer
fork into duplicate clients. Server enforces the id as required and
rejects empty/malformed UUIDs. Also harden bootstrap reveal flow and
single-instance exit so a second launch focuses the existing window.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Collapse the hero card into a compact header with inline metrics, and rework the table with denser rows, fixed action column, and tooltip-backed time/title cells so more tasks fit on screen without losing the error popover and platform context.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Periodically polls runtime snapshot for accounts in expired/revoked/challenge_required states and reflects the count via tray badge, macOS dock badge, and Windows overlay icon so users see authentication problems without opening the app.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
- Switch retry/copy/console feedback from inline banners to antd
notifications so the table layout stops jumping on each action.
- Truncate the error message in the table cell and move full text +
copy button into a hover popover, preventing very long adapter
errors from blowing out the row width.
- Pin column widths and force fixed table layout so the meta column
no longer expands the table off-screen on long error strings.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Replace the raw external URL link with an in-app shortcut that opens the
bound account's platform console window, and add a one-click copy button
for failure error messages (with truncation + tooltip preview) so long
adapter errors stay readable in the task table.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
- Detect zol login redirects via passport/service hostnames and verify
console access by re-detecting the bound account so a different logged
in user is treated as expired instead of active.
- Skip networkPic upload for local/private URLs and fall back to file
upload (with siteType retry) so desktop-hosted assets no longer reach
ZOL as unreachable links and produce blank images.
- Surface zol_content_image_upload_failed and challenge errors instead
of silently substituting empty image URLs.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
When a public asset URL fails (e.g. stale signed token), retry via the
new /api/desktop/content/assets endpoint with the desktop Bearer token
so editor images keep rendering across token rotations.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
- Detect qiehao's real-name auth blocking response (code/message) in the
desktop adapter, surface a Chinese-friendly summary, and propagate the
detail through the failure result.
- Extract a shared publisher-errors module so the renderer can normalize
these messages for the publish task table without duplicating regex.
- Pre-process article HTML for qiehao before upload via a new
packages/publisher-platforms/src/qiehao.ts entry point.
- Update the manual self-test notes for jianshu and qiehao with the
latest results.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Jianshu's HTML editor strips uploaded <img> tags during save, so previously
uploaded images vanished from the rendered article. After image upload,
convert each <img> (and surrounding <p> wrappers) to a markdown image block
in both the desktop and extension publish paths so the references survive.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Import individual Crepe common stylesheets instead of the aggregate, which
transitively pulled in latex.css and emitted ~59 KaTeX font files even
though CrepeFeature.Latex is disabled.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Platforms like Bilibili refuse to serve avatar images when the
Referer points at our admin origin, so the article publish status
panel and the media account cards now request avatars with a
no-referrer policy to stop the placeholder from showing instead of
the user's real avatar.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Replace the hard-coded platform name map with a lookup against the
shared desktop publish media catalog so the task table renders the
real platform logo (or a colored short-name fallback) next to the
account name and stays in sync as new platforms are added.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Switch the account picker from a vertical list to an auto-fill grid of
bento-style cards so a creator can compare more accounts at a glance.
Each card stacks identity + check above a dashed divider with the
status tags below, hovers lift with a soft shadow, and the avatar
loads with a no-referrer policy to keep cross-origin platform CDNs
happy.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Wire sohuhao, wangyihao, juejin, smzdm, weixin-gzh, zol, and dongchedi
into the publish runtime: each ships its own publish protocol and
auth-failure classifier (login/token/challenge codes) plus registry
entries in selectPublishAdapter and the auth adapter map. Smzdm bind
detection now triple-falls-back across page-context fetch, session
fetch, cookie fetch, and a final cookie-derived account so the
nickname-less guest profile still resolves to a stable platform UID.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Introduce a reusable helper that produces upload-ready blobs for
adapters that share the same image-asset semantics (dongchedi,
sohuhao, wangyihao, weixin-gzh, zol). Centralizes URL candidate
expansion and passthrough mime detection so each adapter focuses on
its own publish protocol.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Upgrade admin-web and desktop-client onto Vite 7 / Vitest 4 with the
matching @vitejs/plugin-vue 6 and electron-vite 5, and introduce
manualChunks plus gzip/brotli compression so the admin bundle ships
in smaller, route-aware pieces. ANALYZE=true emits a treemap via
rollup-plugin-visualizer; the generated stats.html is gitignored.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>