Skip to content
This repository was archived by the owner on Oct 22, 2025. It is now read-only.

Commit 6fe0417

Browse files
committed
fix: submissions view
1 parent 7cdd8fb commit 6fe0417

File tree

9 files changed

+121
-41
lines changed

9 files changed

+121
-41
lines changed

messages/en.json

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,7 @@
6969
"submissions_status_label": "Status",
7070
"submissions_passed_label": "Passed",
7171
"submissions_user_link_label": "User link",
72+
"submissions_see_all_button_text": "See all submissions",
7273

7374
"group_form_title": "Add a new group",
7475
"group_form_name_label": "Group name",
@@ -113,6 +114,9 @@
113114
"error_invalid_task_id_error_message": "Invalid task ID",
114115
"error_invalid_group_id_error_message": "Invalid group ID",
115116
"error_invalid_user_id_error_message": "Invalid user ID",
117+
"error_not_allowed_to_view_page_error_message": "You are not allowed to view this page",
118+
"error_status_code_label": "Status code",
119+
"error_message_label": "Message",
116120

117121
"toaster_edit_user_success_message": "User has been successfully edited",
118122
"toaster_edit_password_success_message": "Password has been successfully changed",
@@ -123,5 +127,5 @@
123127
"toaster_group_create_success_message": "Group has been successfully created",
124128
"toaster_task_edit_success_message": "Task has been successfully edited",
125129
"toaster_task_create_success_message": "Task has been successfully created",
126-
"task_form_submit_success": "Task has been successfully submitted"
130+
"toaster_task_form_submit_success": "Task has been successfully submitted"
127131
}

messages/pl.json

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,7 @@
6969
"submissions_status_label": "Status",
7070
"submissions_passed_label": "Zaliczone",
7171
"submissions_user_link_label": "Link do użytkownika",
72+
"submissions_see_all_button_text": "Zobacz wszystkie zgłoszenia",
7273

7374
"group_form_title": "Dodaj nową grupę",
7475
"group_form_name_label": "Nazwa grupy",
@@ -113,6 +114,9 @@
113114
"error_invalid_task_id_error_message": "Nieprawidłowe ID zadania",
114115
"error_invalid_group_id_error_message": "Nieprawidłowe ID grupy",
115116
"error_invalid_user_id_error_message": "Nieprawidłowe ID użytkownika",
117+
"error_not_allowed_to_view_page_error_message": "Nie masz uprawnień do przeglądania tej strony",
118+
"error_status_code_label": "Kod statusu",
119+
"error_message_label": "Wiadomość o błędzie",
116120

117121
"toaster_edit_user_success_message": "Użytkownik został pomyślnie edytowany",
118122
"toaster_edit_password_success_message": "Hasło zostało pomyślnie zmienione",
@@ -123,5 +127,5 @@
123127
"toaster_group_create_success_message": "Grupa została pomyślnie utworzona",
124128
"toaster_task_edit_success_message": "Zadanie zostało pomyślnie edytowane",
125129
"toaster_task_create_success_message": "Zadanie zostało pomyślnie utworzone",
126-
"task_form_submit_success": "Zadanie zostało pomyślnie przesłane"
130+
"toaster_task_form_submit_success": "Zadanie zostało pomyślnie przesłane"
127131
}

src/lib/components/tasks/TaskView.svelte

Lines changed: 12 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,8 @@
1212
} from '$lib/backendSchemas';
1313
import EditTaskDialog from './EditTaskDialog.svelte';
1414
import type { AssingTaskToGroupsSchema, EditTaskSchema } from './formSchemas';
15+
import Button from '$components/ui/button/button.svelte';
16+
import { page } from '$app/state';
1517
1618
let {
1719
localUser,
@@ -39,7 +41,9 @@
3941
availableLanguages: availableLanguages
4042
};
4143
42-
function isAllowedToEdit() {
44+
const { taskId } = page.params;
45+
46+
function isAllowed() {
4347
return (
4448
(localUser.role === UserRole.Teacher && task.created_by === localUser.id) ||
4549
localUser.role === UserRole.Admin
@@ -50,8 +54,13 @@
5054
<div class="container mb-12 flex flex-col flex-1">
5155
<div class="flex justify-between p-4 items-center">
5256
<h1 class="text-2xl font-bold my-4">{task.title}</h1>
53-
{#if isAllowedToEdit()}
54-
<EditTaskDialog taskData={task} {editTaskForm} {assingTaskToGroupsForm} {userGroups} />
57+
{#if isAllowed()}
58+
<div>
59+
<Button href="/dashboard/tasks/{taskId}/submissions" variant="outline" size="lg">
60+
{m.submissions_see_all_button_text()}
61+
</Button>
62+
<EditTaskDialog taskData={task} {editTaskForm} {assingTaskToGroupsForm} {userGroups} />
63+
</div>
5564
{/if}
5665
</div>
5766
<div class="flex-1 flex overflow-hidden">

src/lib/components/tasks/solutions/UploadSolution.svelte

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@
2424
validators: zodClient(uploadTaskSolutionSchema),
2525
onUpdate({ result }) {
2626
if (result.type === 'success') {
27-
toast.success(m.task_form_submit_success());
27+
toast.success(m.toaster_task_form_submit_success());
2828
} else if (result.type === 'failure') {
2929
toast.error(m.error_unexpected_request_error_message());
3030
}

src/routes/+error.svelte

Lines changed: 28 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,32 @@
11
<script lang="ts">
22
import { page } from '$app/state';
3+
import * as Card from '$components/ui/card/index.js';
4+
import * as m from '$lib/paraglide/messages.js';
5+
import Separator from '$components/ui/separator/separator.svelte';
36
</script>
47

5-
<h1>{page.status}: {page.error?.message}</h1>
8+
<div class="w-full p-8 flex-grow items-center justify-center flex">
9+
<Card.Root class="bg-red-200">
10+
<Card.Header class="text-center font-semibold">
11+
<h2>Error</h2>
12+
</Card.Header>
13+
<div class="mt-4 px-4">
14+
<Separator class="bg-black" />
15+
</div>
16+
<Card.Content class="flex flex-row">
17+
<div>
18+
<p>
19+
{m.error_status_code_label()}:
20+
</p>
21+
<p>
22+
{m.error_message_label()}:
23+
</p>
24+
</div>
25+
26+
<div class="ml-4">
27+
<p>{page.status}</p>
28+
<p>{page.error?.message}</p>
29+
</div>
30+
</Card.Content>
31+
</Card.Root>
32+
</div>

src/routes/+page.server.ts

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
import { redirect } from '@sveltejs/kit';
2+
import type { PageServerLoad } from './$types';
3+
4+
export const load: PageServerLoad = async ({ locals }) => {
5+
if (locals.user) {
6+
redirect(302, '/dashboard');
7+
}
8+
};
Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
import { error } from '@sveltejs/kit';
2+
import type { LayoutServerLoad } from './$types';
3+
import * as m from '$lib/paraglide/messages';
4+
import { parse_error_response } from '$lib/server/utils';
5+
import { env } from '$env/dynamic/private';
6+
import type { ApiErrorResponse, GetTaskResponse } from '$lib/backendSchemas';
7+
8+
export const load: LayoutServerLoad = async ({ params, locals }) => {
9+
const { taskId } = params;
10+
let taskIdInt: number;
11+
12+
try {
13+
taskIdInt = parseInt(taskId);
14+
} catch (e) {
15+
error(400, {
16+
message: m.error_invalid_task_id_error_message()
17+
});
18+
}
19+
20+
const taskDataResponse = await fetch(`${env.BACKEND_URL}/api/v1/task/${taskIdInt}`, {
21+
headers: {
22+
session: `${locals.sessionId}`
23+
}
24+
});
25+
26+
if (!taskDataResponse.ok) {
27+
const errorResponse: ApiErrorResponse = await parse_error_response(taskDataResponse);
28+
error(taskDataResponse.status, {
29+
code: errorResponse.data.code,
30+
message: errorResponse.data.message
31+
});
32+
}
33+
34+
const task: GetTaskResponse = await taskDataResponse.json();
35+
36+
return {
37+
task: task.data
38+
};
39+
};

src/routes/dashboard/tasks/[taskId]/+page.server.ts

Lines changed: 6 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -17,37 +17,11 @@ import { PARSE_ERROR, parse_error_response } from '$lib/server/utils';
1717
import { message } from 'sveltekit-superforms';
1818
import type { ErrorStatus } from 'sveltekit-superforms';
1919

20-
export const load: PageServerLoad = async ({ params, locals }) => {
21-
const { taskId } = params;
22-
let taskIdInt: number;
23-
24-
try {
25-
taskIdInt = parseInt(taskId);
26-
} catch (e) {
27-
error(400, {
28-
message: m.error_invalid_task_id_error_message()
29-
});
30-
}
31-
32-
const taskDataResponse = await fetch(`${env.BACKEND_URL}/api/v1/task/${taskIdInt}`, {
33-
headers: {
34-
session: `${locals.sessionId}`
35-
}
36-
});
37-
38-
if (!taskDataResponse.ok) {
39-
const errorResponse: ApiErrorResponse = await parse_error_response(taskDataResponse);
40-
error(taskDataResponse.status, {
41-
code: errorResponse.data.code,
42-
message: errorResponse.data.message
43-
});
44-
}
45-
46-
const task: GetTaskResponse = await taskDataResponse.json();
47-
20+
export const load: PageServerLoad = async ({ locals, parent }) => {
21+
const { task } = await parent();
4822
const taskDescriptionResponse = await fetch(
4923
`${env.FILESTORAGE_URL}/getTaskDescription?` +
50-
new URLSearchParams({ taskID: taskIdInt.toString() }).toString()
24+
new URLSearchParams({ taskID: task.id.toString() }).toString()
5125
);
5226

5327
if (!taskDescriptionResponse.ok) {
@@ -80,9 +54,9 @@ export const load: PageServerLoad = async ({ params, locals }) => {
8054
const taskData: Omit<TaskData, 'description_url'> & {
8155
description_file: Promise<ArrayBuffer>;
8256
} = {
83-
id: task.data.id,
84-
title: task.data.title,
85-
created_by: task.data.created_by,
57+
id: task.id,
58+
title: task.title,
59+
created_by: task.created_by,
8660
description_file: taskDescriptionResponse.arrayBuffer()
8761
};
8862

src/routes/dashboard/tasks/[taskId]/submissions/+page.server.ts

Lines changed: 17 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,25 @@
11
import { error } from '@sveltejs/kit';
22
import type { PageServerLoad } from './$types';
33
import { env } from '$env/dynamic/private';
4-
import type { ApiErrorResponse, GetAllSubmissionsResponse } from '$lib/backendSchemas';
4+
import {
5+
UserRole,
6+
type ApiErrorResponse,
7+
type GetAllSubmissionsResponse
8+
} from '$lib/backendSchemas';
59
import { parse_error_response } from '$lib/server/utils';
10+
import * as m from '$lib/paraglide/messages';
611

7-
export const load: PageServerLoad = async ({ params, locals }) => {
12+
export const load: PageServerLoad = async ({ parent, params, locals }) => {
13+
const { task } = await parent();
14+
const user = locals.user!;
15+
if (
16+
(user.role !== UserRole.Teacher || task.created_by !== user.id) &&
17+
user.role !== UserRole.Admin
18+
) {
19+
error(403, {
20+
message: m.error_not_allowed_to_view_page_error_message()
21+
});
22+
}
823
const { taskId } = params;
924
let taskIdInt: number;
1025

0 commit comments

Comments
 (0)