-
Notifications
You must be signed in to change notification settings - Fork 2
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
refactor(frontend): Components for import tabs
- Loading branch information
Showing
19 changed files
with
307 additions
and
224 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
22 changes: 22 additions & 0 deletions
22
frontend/src/app/assignment/modules/assignment/import-consent/import-consent.component.html
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,22 @@ | ||
<p> | ||
Import consent flags by pasting tab-, space- or comma-separated values below. | ||
</p> | ||
<details> | ||
<summary>More Info</summary> | ||
<p> | ||
The first line should specify the column names (case insensitive), for example: | ||
</p> | ||
<p> | ||
<code>github,demonstration,scientific,3p</code> | ||
</p> | ||
<p> | ||
Instead of or in addition to <code>github</code>, | ||
you can also use <code>name</code>, <code>studentid</code> or <code>email</code>, | ||
but at least one of must be specified. | ||
</p> | ||
<p> | ||
The columns <code>demonstration</code>, <code>scientific</code> and <code>3p</code> are optional | ||
and accept boolean values like <code>true</code> or <code>false</code> (case-insensitive). | ||
</p> | ||
</details> | ||
<textarea class="form-control" rows="10" [(ngModel)]="consentText"></textarea> |
Empty file.
54 changes: 54 additions & 0 deletions
54
frontend/src/app/assignment/modules/assignment/import-consent/import-consent.component.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,54 @@ | ||
import {Component} from '@angular/core'; | ||
import {Observable} from "rxjs"; | ||
import Solution, { | ||
AuthorInfo, | ||
authorInfoProperties, | ||
Consent, | ||
consentKeys, | ||
ImportSolution | ||
} from "../../../model/solution"; | ||
import {map} from "rxjs/operators"; | ||
import {SolutionService} from "../../../services/solution.service"; | ||
import {ActivatedRoute} from "@angular/router"; | ||
|
||
@Component({ | ||
selector: 'app-import-consent', | ||
templateUrl: './import-consent.component.html', | ||
styleUrls: ['./import-consent.component.scss'] | ||
}) | ||
export class ImportConsentComponent { | ||
consentText = ''; | ||
|
||
constructor( | ||
private solutionService: SolutionService, | ||
private route: ActivatedRoute, | ||
) { | ||
} | ||
|
||
import(): Observable<ImportSolution[]> { | ||
const assignment = this.route.snapshot.params.aid; | ||
const lines = this.consentText.split('\n'); | ||
const splitter = /[\s,;]/; | ||
const columns = lines[0].split(splitter); | ||
const updates: Partial<Solution>[] = []; | ||
for (let i = 1; i < lines.length; i++) { | ||
const values = lines[i].split(splitter); | ||
const author: AuthorInfo = {}; | ||
const consent: Consent = {}; | ||
for (let j = 0; j < columns.length; j++) { | ||
const column = columns[j].toLowerCase(); | ||
const value = values[j]; | ||
if (authorInfoProperties.find(([, key]) => key === column)) { | ||
author[column as keyof AuthorInfo] = value; | ||
} | ||
if (consentKeys.includes(column as keyof Consent)) { | ||
consent[column] = Boolean(value.toLowerCase()); | ||
} | ||
} | ||
if (Object.keys(author).length) { | ||
updates.push({author, consent}); | ||
} | ||
} | ||
return this.solutionService.updateMany(assignment, updates).pipe(map(results => results.filter(s => s))); | ||
} | ||
} |
29 changes: 29 additions & 0 deletions
29
.../src/app/assignment/modules/assignment/import-embeddings/import-embeddings.component.html
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,29 @@ | ||
<p> | ||
After importing from GitHub or Files, you can import embeddings. | ||
</p> | ||
<p> | ||
Here is an estimate of the token costs. | ||
Actual costs may be <strong>lower</strong> if the embeddings are already cached, | ||
or <strong>slightly higher</strong> due to some tokens like filenames being added to improve results. | ||
Charges will be applied to your OpenAI account. | ||
</p> | ||
<p> | ||
Please review the results below and click <b>Import</b> to confirm. | ||
</p> | ||
<div class="row" *ngIf="estimatedCosts"> | ||
<app-statistic-value class="col" label="Solutions" [value]="estimatedCosts.solutions" [standalone]="true"></app-statistic-value> | ||
<app-statistic-value class="col" label="Files" [value]="estimatedCosts.files" [standalone]="true"></app-statistic-value> | ||
<app-statistic-value class="col" label="Tokens" [value]="estimatedCosts.tokens" [standalone]="true"></app-statistic-value> | ||
<app-statistic-value class="col" label="Estimated Cost" [value]="estimatedCosts.estimatedCost | currency:'USD':true:'0.7'" [standalone]="true"></app-statistic-value> | ||
</div> | ||
<ng-container *ngIf="finalCosts"> | ||
<hr/> | ||
<p> | ||
The import has been completed. | ||
The following costs have been applied to your OpenAI account. | ||
</p> | ||
<div class="row"> | ||
<app-statistic-value class="col" label="Tokens" [value]="finalCosts.tokens" [standalone]="true"></app-statistic-value> | ||
<app-statistic-value class="col" label="Cost" [value]="finalCosts.estimatedCost | currency:'USD':true:'0.7'" [standalone]="true"></app-statistic-value> | ||
</div> | ||
</ng-container> |
Empty file.
32 changes: 32 additions & 0 deletions
32
...nd/src/app/assignment/modules/assignment/import-embeddings/import-embeddings.component.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,32 @@ | ||
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"; | ||
|
||
@Component({ | ||
selector: 'app-import-embeddings', | ||
templateUrl: './import-embeddings.component.html', | ||
styleUrls: ['./import-embeddings.component.scss'] | ||
}) | ||
export class ImportEmbeddingsComponent implements OnInit { | ||
estimatedCosts?: EstimatedCosts; | ||
finalCosts?: EstimatedCosts; | ||
|
||
constructor( | ||
private solutionService: SolutionService, | ||
private route: ActivatedRoute, | ||
) { | ||
} | ||
|
||
ngOnInit() { | ||
this.solutionService.importEmbeddings(this.route.snapshot.params.aid, true).subscribe(costs => this.estimatedCosts = costs); | ||
} | ||
|
||
import() { | ||
const assignmentId = this.route.snapshot.params.aid; | ||
return this.solutionService.importEmbeddings(assignmentId).pipe( | ||
tap(result => this.finalCosts = result), | ||
); | ||
} | ||
} |
19 changes: 19 additions & 0 deletions
19
frontend/src/app/assignment/modules/assignment/import-files/import-files.component.html
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,19 @@ | ||
<p> | ||
Select multiple zip or jar files from your disk to upload. | ||
The file name may have any of the following formats: | ||
</p> | ||
<ul> | ||
<li> | ||
Digits, e.g. <code>12345678.zip</code>, interpreted as Student IDs. | ||
</li> | ||
<li> | ||
Prefixed with the same GitHub Classroom prefix as the assignment, | ||
e.g. <code>assignment-1-Student.zip</code>, | ||
which extracts the GitHub Username like <code>Student</code>. | ||
</li> | ||
<li> | ||
Anything else, with the file name without extension becoming the student name. | ||
</li> | ||
</ul> | ||
<input type="file" class="form-control" id="files" multiple accept="application/zip" #input | ||
(change)="setFiles(input.files!)"> |
Empty file.
27 changes: 27 additions & 0 deletions
27
frontend/src/app/assignment/modules/assignment/import-files/import-files.component.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,27 @@ | ||
import {Component} from '@angular/core'; | ||
import {SolutionService} from "../../../services/solution.service"; | ||
import {ActivatedRoute} from "@angular/router"; | ||
|
||
@Component({ | ||
selector: 'app-import-files', | ||
templateUrl: './import-files.component.html', | ||
styleUrls: ['./import-files.component.scss'] | ||
}) | ||
export class ImportFilesComponent { | ||
files: File[] = []; | ||
|
||
constructor( | ||
private solutionService: SolutionService, | ||
private route: ActivatedRoute, | ||
) { | ||
} | ||
|
||
setFiles(files: FileList) { | ||
this.files = Array.from(files); | ||
} | ||
|
||
import() { | ||
const assignmentId = this.route.snapshot.params.aid; | ||
return this.solutionService.import(assignmentId, this.files); | ||
} | ||
} |
18 changes: 18 additions & 0 deletions
18
frontend/src/app/assignment/modules/assignment/import-github/import-github.component.html
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,18 @@ | ||
<p> | ||
Imports solutions from GitHub using the organisation and prefix configured in the | ||
<a routerLink="../edit/classroom">assignment settings</a>. | ||
No further configuration is required. | ||
</p> | ||
<details #previewDetails (toggle)="previewDetails.open && previewGitHubImport()"> | ||
<summary>Select Students</summary> | ||
<ul class="list-unstyled"> | ||
<li *ngFor="let solution of previewSolutions" class="form-check"> | ||
<input class="form-check-input" type="checkbox" [id]="'check-' + solution.author.github" | ||
[(ngModel)]="checkedUsernames[solution.author.github!]"> | ||
<label class="form-check-label" [for]="'check-' + solution.author.github"> | ||
{{ solution.author.github }} | ||
<span class="text-muted"> • {{ solution.timestamp | date:'short' }}</span> | ||
</label> | ||
</li> | ||
</ul> | ||
</details> |
Empty file.
30 changes: 30 additions & 0 deletions
30
frontend/src/app/assignment/modules/assignment/import-github/import-github.component.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
import {Component} from '@angular/core'; | ||
import {ImportSolution} from "../../../model/solution"; | ||
import {SolutionService} from "../../../services/solution.service"; | ||
import {ActivatedRoute} from "@angular/router"; | ||
|
||
@Component({ | ||
selector: 'app-import-github', | ||
templateUrl: './import-github.component.html', | ||
styleUrls: ['./import-github.component.scss'] | ||
}) | ||
export class ImportGithubComponent { | ||
checkedUsernames: Partial<Record<string, boolean>> = {}; | ||
previewSolutions: ImportSolution[]; | ||
|
||
constructor( | ||
private solutionService: SolutionService, | ||
private route: ActivatedRoute, | ||
) { | ||
} | ||
|
||
previewGitHubImport() { | ||
this.solutionService.previewImport(this.route.snapshot.params.aid).subscribe(solutions => this.previewSolutions = solutions); | ||
} | ||
|
||
import() { | ||
const assignmentId = this.route.snapshot.params.aid; | ||
const usernames = Object.keys(this.checkedUsernames).filter(username => this.checkedUsernames[username]); | ||
return this.solutionService.import(assignmentId, undefined, usernames); | ||
} | ||
} |
Oops, something went wrong.