diff --git a/app/api/leantime/tasks/route.ts b/app/api/leantime/tasks/route.ts index 39a5374a..83b1caca 100644 --- a/app/api/leantime/tasks/route.ts +++ b/app/api/leantime/tasks/route.ts @@ -11,6 +11,9 @@ interface Task { dueDate: string | null; milestone: string | null; details: string | null; + createdOn: string; + editedOn: string | null; + assignedTo: number[]; } async function getLeantimeUserId(email: string): Promise { @@ -147,24 +150,30 @@ export async function GET(request: NextRequest) { throw new Error('Invalid response format from Leantime'); } - const tasks = data.result.map((task: any) => ({ - id: task.id.toString(), - headline: task.headline, - projectName: task.projectName, - projectId: task.projectId, - status: task.status, - dueDate: task.dateToFinish || null, - milestone: task.type || null, - details: task.description || null, - editTo: task.editTo || null, - dependingTicketId: task.dependingTicketId || null - })); + const tasks = data.result + .filter((task: any) => + // Only include tasks assigned to the user + Array.isArray(task.assignedTo) && task.assignedTo.includes(userId) + ) + .map((task: any) => ({ + id: task.id.toString(), + headline: task.headline, + projectName: task.projectName, + projectId: task.projectId, + status: task.status, + dueDate: task.dateToFinish || null, + milestone: task.type || null, + details: task.description || null, + createdOn: task.dateCreated, + editedOn: task.editedOn || null, + assignedTo: Array.isArray(task.assignedTo) ? task.assignedTo : [] + })); - // Sort tasks by due date - tasks.sort((a: any, b: any) => { - if (!a.dueDate) return 1; - if (!b.dueDate) return -1; - return new Date(a.dueDate).getTime() - new Date(b.dueDate).getTime(); + // Sort tasks by creation date (oldest first) + tasks.sort((a: Task, b: Task) => { + const dateA = new Date(a.createdOn).getTime(); + const dateB = new Date(b.createdOn).getTime(); + return dateA - dateB; }); return NextResponse.json({ tasks }); diff --git a/app/components/flow.tsx b/app/components/flow.tsx new file mode 100644 index 00000000..53b4ad46 --- /dev/null +++ b/app/components/flow.tsx @@ -0,0 +1,107 @@ +'use client'; + +import { useState, useEffect } from 'react'; + +interface Task { + id: string; + headline: string; + projectName: string; + projectId: number; + status: number; + dueDate: string | null; + milestone: string | null; + details: string | null; + createdOn: string; + editedOn: string | null; + assignedTo: number[]; +} + +export default function Flow() { + const [tasks, setTasks] = useState([]); + const [loading, setLoading] = useState(false); + const [error, setError] = useState(null); + + const getStatusLabel = (status: number): string => { + switch (status) { + case 1: + return 'New'; + case 2: + return 'In Progress'; + case 3: + return 'Done'; + default: + return 'Unknown'; + } + }; + + const getStatusColor = (status: number): string => { + switch (status) { + case 1: + return 'bg-blue-100 text-blue-800 dark:bg-blue-900 dark:text-blue-300'; + case 2: + return 'bg-yellow-100 text-yellow-800 dark:bg-yellow-900 dark:text-yellow-300'; + case 3: + return 'bg-green-100 text-green-800 dark:bg-green-900 dark:text-green-300'; + default: + return 'bg-gray-100 text-gray-800 dark:bg-gray-900 dark:text-gray-300'; + } + }; + + useEffect(() => { + const fetchTasks = async () => { + setLoading(true); + setError(null); + try { + const response = await fetch('/api/leantime/tasks'); + if (!response.ok) { + throw new Error('Failed to fetch tasks'); + } + const data = await response.json(); + setTasks(data); + } catch (err) { + setError(err instanceof Error ? err.message : 'An error occurred'); + } finally { + setLoading(false); + } + }; + + fetchTasks(); + }, []); + + if (loading) { + return
Loading...
; + } + + if (error) { + return
Error: {error}
; + } + + return ( +
+ {tasks.map((task) => ( +
+
+
+

+ {task.headline} +

+

+ {task.projectName} +

+
+ + {getStatusLabel(task.status)} + +
+
+ ))} +
+ ); +} \ No newline at end of file