3 Commits
7 changed files with 96 additions and 9 deletions

No files matched your search

@@ -23,6 +23,7 @@ This file is the integrated default-branch snapshot. Feature tasks record progre
- Merge commit `b5f5847` integrating source commit `6f9fd0f` from task `20260902-agentbus-account-routing-b62f19e4` for employee-owned AgentBus channels, immutable task assignees, matching single-browser ERP workers, migration 018, and extension `0.5.164`.
- Merge commit `cc09506` integrating source commit `b1fe533` from task `20260902-dashboard-metrics-static-a91c` for display-only dashboard metric cards and explicit status filtering.
- Integration task `20260902-integrate-all-push-c93a7f21` for all-worktree reconciliation, semantic merge resolution, canonical promotion, full verification, and synchronization of `main` to `origin/main`.
- Merge commit `336ca6e` integrating source commit `b26001e` from task `20260902-account-permission-ui-6c9e21ad` for a scroll-safe account task-permission editor layout and focused regression coverage.
## Current Focus
@@ -46,6 +47,7 @@ Operate the repository's current `0.5.164` extension baseline and fixed-scope ac
- 2026-09-02: Restarted the standard `127.0.0.1:8786` control plane from current local `main` after the roster integration; liveness, database readiness, schema migration 017, and repeated listener stability checks passed. AgentBus remained enabled but disconnected, matching the pre-restart observation.
- 2026-09-02: Integrated migration 018 and extension `0.5.164` so each enabled AgentBus channel binds one non-admin employee, each task keeps an immutable execution assignee, administrators cannot execute another assignee's work, and only one fresh browser with the matching ERP account is execution-ready.
- 2026-09-02: Reworked leadership-dashboard reads into a bounded one-connection transaction with business SQL prefiltering, selective message hydration, page-only detail hydration, request/database deadlines, and 20-row pages; metric cards are now display-only and explicit filters default to all results.
- 2026-09-02: Corrected the account-management task-permission editor so opening it expands a dedicated five-row layout, keeps the account list below the editor, and allows vertical page scrolling on desktop and narrow screens without changing authorization semantics.
## In Progress
@@ -0,0 +1,54 @@
# Task: Integrate account permission UI fix
## Identity
- Task ID: 20260902-integrate-account-permission-ui-e4c8a17b
- Mode: Integration
- Branch: codex/20260902-integrate-account-permission-ui-e4c8a17b-integrate-account-permission-ui-e4c8a17b
- Worktree: /Users/inmanx/Documents/lwltAPI-integrate-account-permission-ui-e4c8a17b
- Base commit: a618d3dd9fd8aa4e6f9a22e81b9b65452185b86a
- Owner: codex
- Status: In progress
## Scope
- Integrate source commit `b26001e039eaee51a3588f06194e0db9d8c72457` from task `20260902-account-permission-ui-6c9e21ad` into the latest `origin/main` baseline.
- Keep the source task record intact on its source branch, merge the account-permission UI correction and regression coverage, and record the integrated commit in canonical current state.
- Run the required project-document and full repository verification, then advance `origin/main` with normal non-force pushes and verify its final commit.
## Intent And Constraints
- The user explicitly authorized merging the completed account-permission UI fix into `main` and pushing it to the repository.
- Preserve AUTH-001, all three roles, all 18 route-grant semantics, account ownership, APIs, and runtime behavior; this integration changes only the task-permission editor presentation, cache token, and regression coverage.
- Keep every operation inside the exclusively owned integration worktree because the main checkout remains owned and contains another task's record.
- Do not read `.env`, deploy, restart services, access ERP, or mutate real accounts, tasks, channels, database state, or other external runtime state.
- Use a normal non-force push only after confirming `origin/main` has not advanced beyond the recorded base.
## Outcome
- Verified that source commit `b26001e` is the sole commit above `origin/main` and that `origin/main` is its direct ancestor; the six-file source diff passed `git diff --check`.
- Merged the source branch without conflict through merge commit `336ca6e7de9aba1123451a066902a520a3963563`, keeping the source task record on its source branch as required by the Integration Gate.
- Added the source and merge facts to canonical current state without changing AUTH-001 or business rules because the source task has no promotion candidate and preserves authorization semantics.
- The fully merged tree passed repository hygiene, type checking, control-plane and legacy regressions, and production build; remote synchronization is in progress.
## Verification
- Source task verification: focused account authorization 11/11, control plane 159/159, legacy 265/265, repository/type/build checks, and desktop/narrow browser geometry and pointer-interaction checks passed.
- Integration source audit: `origin/main` was `a618d3dd9fd8aa4e6f9a22e81b9b65452185b86a`, source was `b26001e039eaee51a3588f06194e0db9d8c72457`, and `git merge-base --is-ancestor origin/main <source>` passed.
- `node --run check:repo`: 10 passed, 0 failed.
- `node --run check`: passed.
- `node --run test:control-plane`: 159 passed, 0 failed.
- `node --run test:legacy`: 265 passed, 0 failed.
- `node --run build`: passed.
- `check_project_docs.py`: passed.
- `check_doc_drift.py --task-id 20260902-integrate-account-permission-ui-e4c8a17b`: passed after retaining the source task record only on its source branch.
- `git diff --check` passed, and conflict-marker scanning returned no matches.
- Final remote-ref verification is pending.
## Follow-ups
- No runtime rollout is included; a service restart or deployment remains separately authorized work if needed.
## Promotion Candidates
- None recorded.
+3 -1
View File
@@ -1087,7 +1087,9 @@ function renderAccountAuthorizationPanel() {
const container = $('#accountAuthorizationTypes');
if (!panel || !container) return;
const account = accountList.find((item) => item.id === accountAuthorizationTargetId);
if (!account || account.role === 'admin') {
const isOpen = Boolean(account && account.role !== 'admin');
panel.closest('.account-panel')?.classList.toggle('is-authorizing', isOpen);
if (!isOpen) {
panel.hidden = true;
container.replaceChildren();
accountAuthorizationTargetId = '';
+2 -2
View File
@@ -5,7 +5,7 @@
<meta name="viewport" content="width=device-width, initial-scale=1, viewport-fit=cover">
<meta name="theme-color" content="#edf2f4">
<title>AI操作台 · LianSyn-platform</title>
<link rel="stylesheet" href="styles.css?v=20260902-agentbus-dashboard-metrics-filter-1">
<link rel="stylesheet" href="styles.css?v=20260902-account-authorization-layout-1">
</head>
<body>
<main class="app-shell">
@@ -407,6 +407,6 @@
</section>
</main>
<script src="app.js?v=20260902-agentbus-dashboard-metrics-filter-1"></script>
<script src="app.js?v=20260902-account-authorization-layout-1"></script>
</body>
</html>
+6 -4
View File
@@ -634,10 +634,6 @@ textarea {
font-size: 11px;
}
.account-panel {
grid-template-rows: auto auto auto minmax(0, 1fr) auto;
}
.account-authorization-summary {
color: var(--ink) !important;
}
@@ -3049,6 +3045,12 @@ textarea {
grid-template-rows: auto auto minmax(0, 1fr) auto;
}
.channels-page .channel-panel.account-panel.is-authorizing {
height: max-content;
grid-template-rows: auto auto auto auto auto;
overflow: visible;
}
.channels-page .channel-list {
max-height: none;
}
@@ -339,3 +339,30 @@ test('operator UI exposes role-aware accounts, executive drill-through, original
assert.doesNotMatch(retention, /DELETE FROM tasks/);
assert.doesNotMatch(retention, /DELETE FROM audit_events/);
});
test('account authorization editor uses a scroll-safe open layout without overriding the closed account list', async () => {
const [app, index, styles] = await Promise.all([
source('../../LianSyn-platform/app.js'),
source('../../LianSyn-platform/index.html'),
source('../../LianSyn-platform/styles.css')
]);
const renderStart = app.indexOf('function renderAccountAuthorizationPanel()');
const renderEnd = app.indexOf('function openAccountAuthorizationEditor(', renderStart);
const renderSource = app.slice(renderStart, renderEnd);
assert.match(renderSource, /const isOpen = Boolean\(account && account\.role !== 'admin'\)/);
assert.match(renderSource, /classList\.toggle\('is-authorizing', isOpen\)/);
assert.match(renderSource, /if \(!isOpen\)/);
const genericLayout = styles.indexOf('.channels-page .channel-panel {');
const openLayout = styles.indexOf('.channels-page .channel-panel.account-panel.is-authorizing {');
assert.ok(genericLayout >= 0, 'generic management-page layout is present');
assert.ok(openLayout > genericLayout, 'account open-state layout follows the generic layout in the cascade');
const openLayoutSource = styles.slice(openLayout, styles.indexOf('}', openLayout) + 1);
assert.match(openLayoutSource, /height:\s*max-content/);
assert.match(openLayoutSource, /grid-template-rows:\s*auto auto auto auto auto/);
assert.match(openLayoutSource, /overflow:\s*visible/);
assert.doesNotMatch(styles, /\.account-panel\s*\{\s*grid-template-rows:/);
assert.match(index, /styles\.css\?v=20260902-account-authorization-layout-1/);
assert.match(index, /app\.js\?v=20260902-account-authorization-layout-1/);
});
+2 -2
View File
@@ -1231,8 +1231,8 @@ test('operator page has a login gate and uses the durable task API', async () =>
const inpage = await readFile(new URL('../../chrome-extension/ltjt-order-assistant/inpage.js', import.meta.url), 'utf8');
assert.match(index, /id="loginPanel"/);
assert.match(index, /id="workbench"[^>]*hidden/);
assert.match(index, /styles\.css\?v=20260902-agentbus-dashboard-metrics-filter-1/);
assert.match(index, /app\.js\?v=20260902-agentbus-dashboard-metrics-filter-1/);
assert.match(index, /styles\.css\?v=20260902-account-authorization-layout-1/);
assert.match(index, /app\.js\?v=20260902-account-authorization-layout-1/);
assert.match(index, /id="statusDetailsPopover"/);
assert.match(index, /id="statusDetailsRefresh"/);
assert.match(app, /apiRequest\(`\/api\/tasks\?\$\{params\.toString\(\)\}`/);