diff --git a/automaton/dashboard/html/dashboard.js b/automaton/dashboard/html/dashboard.js
index e4f51dd..ae300b5 100644
--- a/automaton/dashboard/html/dashboard.js
+++ b/automaton/dashboard/html/dashboard.js
@@ -1,7 +1,7 @@
const state = {
scope: 'none', currentView: 'board', theme: 'default', selectedTask: null,
tasks: [], refreshCount: 0, autoRefresh: true, showWaves: true,
- filterPhase: 'all', filterReview: 'all', filterWave: 'all', searchQuery: '', filterVisible: false,
+ filterPhase: 'all', filterWave: 'all', searchQuery: '', filterVisible: false,
refreshInterval: null, projectName: null,
};
@@ -48,14 +48,8 @@ function getPhaseGroupForState(state) {
return group ? group.id : null;
}
-// Get display group for a task, accounting for review status.
-// Approved planning tasks advance to Design; rejected ones go to Blocked.
+// Get display group for a task based on its phase state.
function getTaskDisplayGroup(task) {
- const review = task.review ? task.review.status : 'pending';
- if ((task.state === 'research' || task.state === 'decomposition' || task.state === 'backlog')) {
- if (review === 'approved') return 'design';
- if (review === 'changes_requested') return 'blocked';
- }
return getPhaseGroupForState(task.state);
}
@@ -89,8 +83,7 @@ function renderHeader() {
wipTasks.textContent = filtered.filter(t => wipStates.includes(t.state)).length;
doneTasks.textContent = filtered.filter(t => t.state === 'done').length;
blockedTasks.textContent = filtered.filter(t => t.state === 'blocked').length;
- const pendingReview = document.getElementById('pending-review');
- if (pendingReview) pendingReview.textContent = filtered.filter(t => (t.state !== 'done' && t.state !== 'blocked') && (!t.review || t.review.status === 'pending')).length;
+
// Project name display
const projectName = state.projectName;
if (projectName) {
@@ -163,10 +156,6 @@ function renderTaskCard(task) {
const statusClass = task.state === 'done' ? 'done' : task.state === 'blocked' ? 'blocked' : 'in_progress';
const statusIcon = task.state === 'done' ? '✅' : task.state === 'blocked' ? '❌' : '🔄';
const subLabel = getSubLabel(task.state);
- const reviewStatus = task.review ? task.review.status : 'pending';
- const reviewBadge = reviewStatus === 'approved' ? '✅'
- : reviewStatus === 'changes_requested' ? '❌'
- : '🟡';
const progressHtml = task.sub_tasks.length > 0
? `${task.sub_tasks.filter(st => st.has_verdict && st.verdict_status === 'PASS').length}/${task.sub_tasks.length}`
: '';
@@ -177,14 +166,12 @@ function renderTaskCard(task) {
return `
${stIcon}${st.name}
`;
}).join('')}`
: '';
- const artifactsHtml = (reviewStatus === 'pending' || reviewStatus === 'changes_requested')
- ? `${COLUMNS.filter(col => task.artifacts[col.id]).map(col => {
+ const artifactsHtml = `
${COLUMNS.filter(col => task.artifacts[col.id]).map(col => {
const label = ARTIFACT_LABELS[col.id] || col.label;
return `${label}`;
- }).join('')}
`
- : '';
+ }).join('')}
`;
return `
-
+
${subLabel}
${task.status_reason ? `
${escapeHtml(task.status_reason)}
` : ''}
${artifactsHtml}
@@ -211,18 +198,6 @@ function renderDetail(task) {
return `
${icon}${col.label}`;
}).join('');
const phaseGroupHtml = phaseGroup ? `
${PHASE_GROUPS.find(g => g.id === phaseGroup).label}` : '';
- const reviewStatus = task.review ? task.review.status : 'pending';
- const reviewStatusText = reviewStatus === 'approved' ? '✅ Approved' : reviewStatus === 'changes_requested' ? '❌ Changes Requested' : '🟡 Pending Review';
- const reviewComment = task.review && task.review.comment ? `` : '';
- let reviewActionsHtml;
- if (reviewStatus === 'approved') {
- reviewActionsHtml = '
';
- } else if (reviewStatus === 'changes_requested') {
- reviewActionsHtml = '
';
- } else {
- reviewActionsHtml = '
' +
- '
';
- }
const approvePhaseBtn = task.is_approval_gated
? `
`
: '';
@@ -233,14 +208,6 @@ function renderDetail(task) {
${task.phase_guidance ? `
▶ What's Next
${escapeHtml(task.phase_guidance)}` : ''}
${task.state === 'blocked' && task.blocked_action_items && task.blocked_action_items.length > 0 ? `
📋 Action Items
${task.blocked_action_items.map(item => `- ${escapeHtml(item)}
`).join('')}
` : ''}
Artifacts
${artifactsHtml}
-
Review
-
${reviewStatusText}
- ${reviewComment}
-
-
- ${reviewActionsHtml}
-
-
${task.sub_tasks.length > 0 ? `
Sub-tasks (${task.sub_tasks.filter(st => st.has_verdict).length}/${task.sub_tasks.length})
${task.sub_tasks.map(st => {
const stStatus = st.has_verdict && st.verdict_status === 'PASS' ? 'pass' : st.has_verdict && st.verdict_status === 'FAIL' ? 'fail' : 'incomplete';
@@ -522,25 +489,6 @@ async function renderAgentTab() {
_startAgentPoller();
}
-async function submitReview(taskName, status) {
- const textarea = document.getElementById(`review-comment-${taskName}`);
- const comment = textarea ? textarea.value : '';
- try {
- const res = await fetch(`/api/task/${taskName}/review`, {
- method: 'POST',
- headers: { 'Content-Type': 'application/json' },
- body: JSON.stringify({ status, comment }),
- });
- const data = await res.json();
- if (data.success) {
- closeDetail();
- await refreshData();
- }
- } catch (err) {
- console.error('Review submission failed:', err);
- }
-}
-
async function approvePhase(taskName) {
try {
const res = await fetch(`/api/approve/${taskName}`, { method: 'POST' });
@@ -559,9 +507,6 @@ async function approvePhase(taskName) {
function getFilteredTasks() {
let filtered = [...state.tasks];
if (state.filterPhase !== 'all') filtered = filtered.filter(t => t.state === state.filterPhase);
- if (state.filterReview === 'pending') filtered = filtered.filter(t => !t.review || t.review.status === 'pending');
- else if (state.filterReview === 'approved') filtered = filtered.filter(t => t.review && t.review.status === 'approved');
- else if (state.filterReview === 'changes_requested') filtered = filtered.filter(t => t.review && t.review.status === 'changes_requested');
if (state.filterWave === 'has-waves') filtered = filtered.filter(t => t.sub_tasks.length > 0);
else if (state.filterWave === 'no-waves') filtered = filtered.filter(t => t.sub_tasks.length === 0);
if (state.searchQuery) {
@@ -640,16 +585,9 @@ function setupUI() {
document.getElementById('btn-close-detail').addEventListener('click', closeDetail);
document.getElementById('detail-overlay').addEventListener('click', (e) => { if (e.target === e.currentTarget) closeDetail(); });
document.getElementById('filter-phase').addEventListener('change', (e) => { state.filterPhase = e.target.value; renderCurrentView(); });
- document.getElementById('filter-review').addEventListener('change', (e) => { state.filterReview = e.target.value; renderCurrentView(); });
document.getElementById('filter-wave').addEventListener('change', (e) => { state.filterWave = e.target.value; renderCurrentView(); });
document.getElementById('search-input').addEventListener('input', (e) => { state.searchQuery = e.target.value; renderCurrentView(); });
document.addEventListener('click', (e) => {
- const btn = e.target.closest('.review-btn');
- if (btn) {
- const taskName = btn.dataset.task;
- const status = btn.dataset.status;
- if (taskName && status) submitReview(taskName, status);
- }
const approveBtn = e.target.closest('.approve-phase-btn');
if (approveBtn) {
const taskName = approveBtn.dataset.task;
diff --git a/automaton/dashboard/html/index.html b/automaton/dashboard/html/index.html
index 875dec8..4c9240e 100644
--- a/automaton/dashboard/html/index.html
+++ b/automaton/dashboard/html/index.html
@@ -26,7 +26,6 @@
WIP: 0
Done: 0
Blocked: 0
- Pending: 0
-
-
-
-