diff --git a/src/components/KanbanBoard.tsx b/src/components/KanbanBoard.tsx
index bfe151c..9891702 100644
--- a/src/components/KanbanBoard.tsx
+++ b/src/components/KanbanBoard.tsx
@@ -49,21 +49,21 @@ export default function KanbanBoard({ projectId, projectSlug }: Props) {
loadTasks();
// Subscribe to WebSocket events for real-time updates
- const unsubscribeCreated = wsClient.on("task.created", (data: any) => {
+ const unsubscribeCreated = wsClient.on("task.created", (data: Task) => {
if (data.project_id === projectId) {
- setTasks((prev) => [...prev, data as Task]);
+ setTasks((prev) => prev.some((t) => t.id === data.id) ? prev : [...prev, data]);
}
});
- const unsubscribeUpdated = wsClient.on("task.updated", (data: any) => {
+ const unsubscribeUpdated = wsClient.on("task.updated", (data: Task) => {
if (data.project_id === projectId) {
- setTasks((prev) => prev.map((t) => t.id === data.id ? { ...t, ...data } : t));
+ setTasks((prev) => prev.map((t) => t.id === data.id ? data : t));
}
});
- const unsubscribeAssigned = wsClient.on("task.assigned", (data: any) => {
+ const unsubscribeAssigned = wsClient.on("task.assigned", (data: Task) => {
if (data.project_id === projectId) {
- setTasks((prev) => prev.map((t) => t.id === data.id ? { ...t, assignee_id: data.assignee_id, assignee: data.assignee, assigned_at: data.assigned_at } : t));
+ setTasks((prev) => prev.map((t) => t.id === data.id ? data : t));
}
});
diff --git a/src/components/TaskModal.tsx b/src/components/TaskModal.tsx
index 98b7c4d..1340ca4 100644
--- a/src/components/TaskModal.tsx
+++ b/src/components/TaskModal.tsx
@@ -251,7 +251,7 @@ export default function TaskModal({ task, projectId: _projectId, projectSlug: _p
{AUTHOR_ICON[msg.author_type] || "👤"}
- {msg.author?.slug || msg.author_id}
+ {msg.author_type === "system" ? "System" : (msg.author?.name || msg.author?.slug || "Unknown")}
·
{new Date(msg.created_at).toLocaleString("ru-RU", { hour: "2-digit", minute: "2-digit" })}
diff --git a/src/lib/api.ts b/src/lib/api.ts
index 1887666..8e0fc73 100644
--- a/src/lib/api.ts
+++ b/src/lib/api.ts
@@ -60,12 +60,6 @@ export interface AgentConfig {
model: string | null;
}
-export interface MemberBrief {
- id: string;
- slug: string;
- name: string;
-}
-
export interface Member {
id: string;
slug: string;
@@ -214,8 +208,8 @@ export async function deleteTask(taskId: string): Promise
{
await request(`/api/v1/tasks/${taskId}`, { method: "DELETE" });
}
-export async function takeTask(taskId: string, slug: string): Promise {
- return request(`/api/v1/tasks/${taskId}/take?slug=${slug}`, { method: "POST" });
+export async function takeTask(taskId: string): Promise {
+ return request(`/api/v1/tasks/${taskId}/take`, { method: "POST" });
}
export async function rejectTask(taskId: string, reason: string): Promise<{ok: boolean; reason: string; old_assignee: string}> {
@@ -232,12 +226,12 @@ export async function assignTask(taskId: string, assigneeId: string): Promise {
- return request(`/api/v1/tasks/${taskId}/watch?slug=${slug}`, { method: "POST" });
+export async function watchTask(taskId: string): Promise<{ok: boolean; watcher_ids: string[]}> {
+ return request(`/api/v1/tasks/${taskId}/watch`, { method: "POST" });
}
-export async function unwatchTask(taskId: string, slug: string): Promise<{ok: boolean; watchers: string[]}> {
- return request(`/api/v1/tasks/${taskId}/watch?slug=${slug}`, { method: "DELETE" });
+export async function unwatchTask(taskId: string): Promise<{ok: boolean; watcher_ids: string[]}> {
+ return request(`/api/v1/tasks/${taskId}/watch`, { method: "DELETE" });
}
// --- Steps ---