Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Refactor Frontend Assignment Services #360

Merged
merged 15 commits into from
Sep 23, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
32 changes: 31 additions & 1 deletion frontend/src/app/assignment/assignment.module.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import {CommonModule} from '@angular/common';
import {HttpClientModule} from '@angular/common/http';
import {HTTP_INTERCEPTORS, HttpClientModule} from '@angular/common/http';
import {NgModule} from '@angular/core';
import {FormsModule} from '@angular/forms';

Expand All @@ -19,6 +19,19 @@ import {OverviewComponent} from './pages/overview/overview.component';
import {SettingsComponent} from './pages/settings/settings.component';
import {TokenModalComponent} from './pages/token-modal/token-modal.component';
import {ConfigService} from './services/config.service';
import {TokenInterceptor} from "./services/token.interceptor";
import {AssignmentService} from "./services/assignment.service";
import {TokenService} from "./services/token.service";
import {SolutionService} from "./services/solution.service";
import {TelemetryService} from "./services/telemetry.service";
import {CourseService} from "./services/course.service";
import {SelectionService} from "./services/selection.service";
import {SolutionContainerService} from "./services/solution-container.service";
import {TaskService} from "./services/task.service";
import {SubmitService} from "./modules/assignment/submit.service";
import {AssigneeService} from "./services/assignee.service";
import {EvaluationService} from "./services/evaluation.service";
import {EmbeddingService} from "./services/embedding.service";

@NgModule({
declarations: [
Expand All @@ -43,7 +56,24 @@ import {ConfigService} from './services/config.service';
ModalModule,
],
providers: [
{
provide: HTTP_INTERCEPTORS,
multi: true,
useClass: TokenInterceptor,
},
TokenService,
ConfigService,
AssignmentService,
SolutionService,
TelemetryService,
CourseService,
SelectionService,
SolutionContainerService,
TaskService,
SubmitService,
AssigneeService,
EvaluationService,
EmbeddingService,
],
})
export class AssignmentModule {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,8 @@ import {StatisticsBlockComponent} from './statistics-block/statistics-block.comp
import {StatisticsComponent} from './statistics/statistics.component';
import {SubmitModalComponent} from './submit-modal/submit-modal.component';
import {AssignmentTasksComponent} from './tasks/tasks.component';
import {StatisticsService} from "./statistics.service";
import {SubmitService} from "./submit.service";

@NgModule({
declarations: [
Expand Down Expand Up @@ -53,6 +55,10 @@ import {AssignmentTasksComponent} from './tasks/tasks.component';
RouteTabsModule,
ModalModule,
],
providers: [
StatisticsService,
SubmitService,
],
})
export class AssignmentModule {
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import {Component, OnInit, TrackByFunction} from '@angular/core';
import {ActivatedRoute, Router} from '@angular/router';
import {ToastService} from '@mean-stream/ngbx';
import {ClipboardService} from 'ngx-clipboard';
import {BehaviorSubject, combineLatest, firstValueFrom, forkJoin, Observable} from 'rxjs';
import {BehaviorSubject, combineLatest, forkJoin, Observable} from 'rxjs';
import {debounceTime, distinctUntilChanged, map, switchMap, tap} from 'rxjs/operators';
import {Assignee} from '../../../model/assignee';
import Assignment, {ReadAssignmentDto} from '../../../model/assignment';
Expand All @@ -15,6 +15,8 @@ import {TaskService} from '../../../services/task.service';
import {TelemetryService} from '../../../services/telemetry.service';
import {SubmitService} from "../submit.service";
import {UserService} from "../../../../user/user.service";
import {AssigneeService} from "../../../services/assignee.service";
import {EvaluationService} from "../../../services/evaluation.service";

type SearchKey = keyof AuthorInfo | 'assignee';
const searchKeys: readonly SearchKey[] = [
Expand Down Expand Up @@ -56,6 +58,8 @@ export class SolutionTableComponent implements OnInit {
constructor(
private assignmentService: AssignmentService,
private solutionService: SolutionService,
private assigneeService: AssigneeService,
private evaluationService: EvaluationService,
private solutionContainerService: SolutionContainerService,
private configService: ConfigService,
private router: Router,
Expand All @@ -78,7 +82,7 @@ export class SolutionTableComponent implements OnInit {
});

this.activatedRoute.params.pipe(
switchMap(({aid}) => this.solutionService.getAssignees(aid)),
switchMap(({aid}) => this.assigneeService.getAssignees(aid)),
).subscribe(assignees => {
this.assignees = {};
const names = new Set<string>();
Expand All @@ -91,8 +95,8 @@ export class SolutionTableComponent implements OnInit {

this.activatedRoute.params.pipe(
switchMap(({aid}) => forkJoin([
this.solutionService.getEvaluationValues<string>(aid, 'solution', {codeSearch: false}),
this.solutionService.getEvaluationValues<string>(aid, 'solution', {codeSearch: true}),
this.evaluationService.distinctValues<string>(aid, 'solution', {codeSearch: false}),
this.evaluationService.distinctValues<string>(aid, 'solution', {codeSearch: true}),
])),
).subscribe(([manual, codeSearch]) => {
this.evaluated = {};
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -51,9 +51,7 @@ export interface AssignmentStatistics {
tasks: TaskStatistics[];
}

@Injectable({
providedIn: 'root',
})
@Injectable()
export class StatisticsService {
constructor(
private http: HttpClient,
Expand Down
12 changes: 4 additions & 8 deletions frontend/src/app/assignment/modules/assignment/submit.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,14 +2,13 @@ import {HttpClient} from '@angular/common/http';
import {Injectable} from '@angular/core';
import {firstValueFrom} from 'rxjs';
import {environment} from '../../../../environments/environment';
import {UserService} from '../../../user/user.service';
import {ReadAssignmentDto} from '../../model/assignment';
import {Evaluation, Snippet} from '../../model/evaluation';
import Solution from '../../model/solution';
import Task from '../../model/task';
import {AssignmentService} from '../../services/assignment.service';
import {SolutionService} from '../../services/solution.service';
import {TaskService} from '../../services/task.service';
import {EvaluationService} from "../../services/evaluation.service";

export interface Issue {
number: number;
Expand All @@ -20,16 +19,13 @@ export interface Issue {

export type IssueDto = Omit<Issue, 'number'>;

@Injectable({
providedIn: 'root',
})
@Injectable()
export class SubmitService {

constructor(
private assignmentService: AssignmentService,
private evaluationService: EvaluationService,
private solutionService: SolutionService,
private taskService: TaskService,
private userService: UserService,
private http: HttpClient,
) {
}
Expand Down Expand Up @@ -73,7 +69,7 @@ export class SubmitService {
}

private async renderTasks(assignment: ReadAssignmentDto, solution: Solution) {
const evaluations = await firstValueFrom(this.solutionService.getEvaluations(assignment._id, solution._id!));
const evaluations = await firstValueFrom(this.evaluationService.findAll(assignment._id, solution._id!));
const evaluationRecord: Record<string, Evaluation> = {};
for (let evaluation of evaluations) {
evaluationRecord[evaluation.task] = evaluation;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ import {PreviewComponent} from './preview/preview.component';
import {SampleComponent} from './sample/sample.component';
import {TasksComponent} from './tasks/tasks.component';
import {TemplateComponent} from './template/template.component';
import {TaskMarkdownService} from "./task-markdown.service";


@NgModule({
Expand All @@ -42,6 +43,9 @@ import {TemplateComponent} from './template/template.component';
RouteTabsModule,
ModalModule,
],
providers: [
TaskMarkdownService,
],
})
export class EditAssignmentModule {
}
Original file line number Diff line number Diff line change
Expand Up @@ -3,9 +3,7 @@ import {extractTaskItem, TASK_ITEM_PATTERN} from '../../../../modes/task-list-co
import Task from '../../model/task';
import {TaskService} from '../../services/task.service';

@Injectable({
providedIn: 'root',
})
@Injectable()
export class TaskMarkdownService {
constructor(
private taskService: TaskService,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
import {Component, OnInit} from '@angular/core';
import {EstimatedCosts} from "../../../model/solution";
import {SolutionService} from "../../../services/solution.service";
import {ActivatedRoute} from "@angular/router";
import {tap} from "rxjs/operators";
import {switchMap, tap} from "rxjs/operators";
import {EmbeddingService} from "../../../services/embedding.service";

@Component({
selector: 'app-import-embeddings',
Expand All @@ -14,18 +14,20 @@ export class ImportEmbeddingsComponent implements OnInit {
finalCosts?: EstimatedCosts;

constructor(
private solutionService: SolutionService,
private embeddingService: EmbeddingService,
private route: ActivatedRoute,
) {
}

ngOnInit() {
this.solutionService.importEmbeddings(this.route.snapshot.params.aid, true).subscribe(costs => this.estimatedCosts = costs);
this.route.params.pipe(
switchMap(({aid}) => this.embeddingService.import(aid, true)),
).subscribe(costs => this.estimatedCosts = costs);
}

import() {
const assignmentId = this.route.snapshot.params.aid;
return this.solutionService.importEmbeddings(assignmentId).pipe(
return this.embeddingService.import(assignmentId).pipe(
tap(result => this.finalCosts = result),
);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import {ToastService} from '@mean-stream/ngbx';
import {Observable} from 'rxjs';
import {debounceTime, distinctUntilChanged, map} from 'rxjs/operators';
import {Assignee} from '../../../model/assignee';
import {SolutionService} from '../../../services/solution.service';
import {AssigneeService} from "../../../services/assignee.service";

@Component({
selector: 'app-assignee-input',
Expand All @@ -29,14 +29,14 @@ export class AssigneeInputComponent {
);

constructor(
private solutionService: SolutionService,
private assigneeService: AssigneeService,
private toastService: ToastService,
) {
}

save(): void {
this.saving = true;
this.solutionService.setAssignee(this.assignment, this.solution, this.assignee).subscribe(result => {
this.assigneeService.setAssignee(this.assignment, this.solution, this.assignee).subscribe(result => {
this.saving = false;
this.saved.next(result);
this.assigneeChange.next(result.assignee);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import Task from '../../../model/task';
import {ConfigService} from '../../../services/config.service';
import {SolutionService} from '../../../services/solution.service';
import {TelemetryService} from '../../../services/telemetry.service';
import {EvaluationService} from "../../../services/evaluation.service";

@Component({
selector: 'app-task-list',
Expand All @@ -21,6 +22,7 @@ export class TaskListComponent {
constructor(
private telemetryService: TelemetryService,
private solutionService: SolutionService,
private evaluationService: EvaluationService,
private configService: ConfigService,
private toastService: ToastService,
private route: ActivatedRoute,
Expand All @@ -38,10 +40,10 @@ export class TaskListComponent {

givePoints(task: Task, points: number) {
const {aid, sid} = this.route.snapshot.params;
this.solutionService.getEvaluationByTask(aid, sid, task._id).pipe(
this.evaluationService.findByTask(aid, sid, task._id).pipe(
switchMap(evaluation => evaluation ?
this.solutionService.updateEvaluation(aid, sid, evaluation._id, {points}) :
this.solutionService.createEvaluation(aid, sid, {
this.evaluationService.update(aid, sid, evaluation._id, {points}) :
this.evaluationService.create(aid, sid, {
task: task._id,
points,
author: this.configService.get('name'),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,12 @@ import {Component, OnDestroy, OnInit} from '@angular/core';
import {ActivatedRoute} from '@angular/router';
import {ToastService} from '@mean-stream/ngbx';
import {Subscription} from 'rxjs';
import {mapTo, switchMap, take, tap} from 'rxjs/operators';
import {mapTo, switchMap, tap} from 'rxjs/operators';
import {UserService} from '../../../../user/user.service';
import Comment from '../../../model/comment';
import {ConfigService} from '../../../services/config.service';
import {SolutionService} from '../../../services/solution.service';
import {CommentService} from "../comment.service";

@Component({
selector: 'app-comment-list',
Expand All @@ -27,6 +28,7 @@ export class CommentListComponent implements OnInit, OnDestroy {
constructor(
private userService: UserService,
private solutionService: SolutionService,
private commentService: CommentService,
private configService: ConfigService,
private toastService: ToastService,
private route: ActivatedRoute,
Expand All @@ -36,11 +38,11 @@ export class CommentListComponent implements OnInit, OnDestroy {
ngOnInit(): void {
const eventSub = this.route.params.pipe(
tap(({sid}) => this.loadCommentDraft(sid)),
switchMap(params => this.solutionService.getComments(params.aid, params.sid).pipe(
switchMap(params => this.commentService.findAll(params.aid, params.sid).pipe(
tap(comments => this.comments = comments),
mapTo(params),
)),
switchMap(({aid, sid}) => this.solutionService.streamComments(aid, sid)),
switchMap(({aid, sid}) => this.commentService.stream(aid, sid)),
).subscribe(({event, comment}) => {
this.safeApply(comment._id!, event === 'deleted' ? undefined : comment);
});
Expand Down Expand Up @@ -71,14 +73,14 @@ export class CommentListComponent implements OnInit, OnDestroy {
loadCommentDraft(solution: string): void {
this.commentName = this.configService.get('name');
this.commentEmail = this.configService.get('email');
this.commentBody = this.solutionService.getCommentDraft(solution) || '';
this.commentBody = this.commentService.getDraft(solution) || '';
}

saveCommentDraft(): void {
const solution = this.route.snapshot.params.sid;
this.configService.set('name', this.commentName);
this.configService.set('email', this.commentEmail);
this.solutionService.setCommentDraft(solution, this.commentBody);
this.commentService.setDraft(solution, this.commentBody);
}

submitComment(): void {
Expand All @@ -92,7 +94,7 @@ export class CommentListComponent implements OnInit, OnDestroy {
email: this.commentEmail,
body: this.commentBody,
};
this.solutionService.postComment(aid, sid, comment).subscribe(result => {
this.commentService.post(aid, sid, comment).subscribe(result => {
this.safeApply(result._id!, result);
this.commentBody = '';
this.saveCommentDraft();
Expand All @@ -109,7 +111,7 @@ export class CommentListComponent implements OnInit, OnDestroy {
}

const {sid, aid} = this.route.snapshot.params;
this.solutionService.deleteComment(aid, sid, comment._id!).subscribe(result => {
this.commentService.delete(aid, sid, comment._id!).subscribe(result => {
this.safeApply(result._id!, undefined);
this.toastService.warn('Comment', 'Successfully deleted comment');
}, error => {
Expand Down
Loading
Loading