Skip to content

Commit

Permalink
Modify question search to work by searching with only user
Browse files Browse the repository at this point in the history
  • Loading branch information
VirmasaloA committed Jan 29, 2024
1 parent bd4ecbf commit f1ddd04
Show file tree
Hide file tree
Showing 13 changed files with 212 additions and 88 deletions.
26 changes: 14 additions & 12 deletions app/controllers/CourseController.scala
Original file line number Diff line number Diff line change
Expand Up @@ -71,12 +71,11 @@ class CourseController @Inject() (
DB.find(classOf[Course]).where.isNotNull("name").orderBy("code").findList
}.map(_.asScala.toResult(OK))

private def getUserCourses(
user: User,
examIds: Option[List[Long]],
sectionIds: Option[List[Long]],
tagIds: Option[List[Long]]
): Result =
private def getUserCourses(user: User,
examIds: Option[List[Long]],
sectionIds: Option[List[Long]],
tagIds: Option[List[Long]],
ownerIds: Option[List[Long]]): Result =
var query = DB.find(classOf[Course]).where.isNotNull("name")
if !user.hasRole(Role.Name.ADMIN) then
query = query
Expand All @@ -87,6 +86,10 @@ class CourseController @Inject() (
if tagIds.getOrElse(Nil).nonEmpty then
query =
query.in("exams.examSections.sectionQuestions.question.parent.tags.id", tagIds.get.asJava)

if (ownerIds.getOrElse(Nil).nonEmpty)
query =
query.in("exams.examOwners.id", ownerIds.get.asJava)
query.orderBy("name desc").findList.asScala.toResult(OK)

// Actions ->
Expand All @@ -101,12 +104,11 @@ class CourseController @Inject() (
DB.find(classOf[Course], id).toResult(OK)
}

def listUsersCourses(
examIds: Option[List[Long]],
sectionIds: Option[List[Long]],
tagIds: Option[List[Long]]
): Action[AnyContent] =
def listUsersCourses(examIds: Option[List[Long]],
sectionIds: Option[List[Long]],
tagIds: Option[List[Long]],
ownerIds: Option[List[Long]]): Action[AnyContent] =
authenticated.andThen(authorized(Seq(Role.Name.TEACHER, Role.Name.ADMIN))) { request =>
val user = request.attrs(Auth.ATTR_USER)
getUserCourses(user, examIds, sectionIds, tagIds)
getUserCourses(user, examIds, sectionIds, tagIds, ownerIds)
}
5 changes: 5 additions & 0 deletions app/controllers/ExamController.java
Original file line number Diff line number Diff line change
Expand Up @@ -154,12 +154,14 @@ public Result listExams(
Optional<List<Long>> courseIds,
Optional<List<Long>> sectionIds,
Optional<List<Long>> tagIds,
Optional<List<Long>> ownerIds,
Http.Request request
) {
User user = request.attrs().get(Attrs.AUTHENTICATED_USER);
List<Long> courses = courseIds.orElse(Collections.emptyList());
List<Long> sections = sectionIds.orElse(Collections.emptyList());
List<Long> tags = tagIds.orElse(Collections.emptyList());
List<Long> owners = ownerIds.orElse(Collections.emptyList());
PathProperties pp = PathProperties.parse(
"(id, name, examActiveStartDate, examActiveEndDate, course(id, code), examSections(id, name))"
);
Expand All @@ -178,6 +180,9 @@ public Result listExams(
if (!tags.isEmpty()) {
el = el.in("examSections.sectionQuestions.question.parent.tags.id", tags);
}
if (!owners.isEmpty()) {
el = el.in("questionOwners.id", user);
}
return ok(el.findList(), pp);
}

Expand Down
4 changes: 4 additions & 0 deletions app/controllers/ExamSectionController.java
Original file line number Diff line number Diff line change
Expand Up @@ -624,6 +624,7 @@ public Result listSections(
Optional<List<Long>> courseIds,
Optional<List<Long>> examIds,
Optional<List<Long>> tagIds,
Optional<List<Long>> ownerIds,
Http.Request request
) {
User user = request.attrs().get(Attrs.AUTHENTICATED_USER);
Expand All @@ -644,6 +645,9 @@ public Result listSections(
if (tagIds.isPresent() && !tagIds.get().isEmpty()) {
query = query.in("examSectionQuestions.question.tags.id", tagIds.get());
}
if (ownerIds.isPresent() && !ownerIds.get().isEmpty()) {
query = query.in("questionOwners.id", ownerIds.get());
}
Set<ExamSection> sections = query.findSet();
return ok(sections, PathProperties.parse("(*, creator(id))"));
}
Expand Down
31 changes: 17 additions & 14 deletions app/controllers/QuestionController.java
Original file line number Diff line number Diff line change
Expand Up @@ -84,11 +84,12 @@ public Result getQuestions(
List<Long> courseIds,
List<Long> tagIds,
List<Long> sectionIds,
List<Long> ownerIds,
Http.Request request
) {
User user = request.attrs().get(Attrs.AUTHENTICATED_USER);
if (
user.hasRole(Role.Name.ADMIN) && Stream.of(examIds, courseIds, tagIds, sectionIds).allMatch(List::isEmpty)
user.hasRole(Role.Name.ADMIN) && Stream.of(examIds, courseIds, tagIds, sectionIds, ownerIds).allMatch(List::isEmpty)
) {
return ok(Collections.emptySet());
}
Expand All @@ -104,21 +105,23 @@ public Result getQuestions(
.endJunction()
.ne("state", QuestionState.DELETED.toString());
if (user.hasRole(Role.Name.TEACHER)) {
el = el.disjunction().eq("shared", true).eq("questionOwners", user).endJunction();
}
if (!examIds.isEmpty()) {
el = el.in("examSectionQuestions.examSection.exam.id", examIds);
}
if (!courseIds.isEmpty()) {
el = el.in("examSectionQuestions.examSection.exam.course.id", courseIds);
}
if (!tagIds.isEmpty()) {
el = el.in("tags.id", tagIds);
}
if (!sectionIds.isEmpty()) {
el = el.in("examSectionQuestions.examSection.id", sectionIds);
if (ownerIds.isEmpty()) {
el = el.eq("questionOwners", user);
} else {
el = el.in("questionOwners.id", ownerIds);
}
} else {
el = el.inOrEmpty("questionOwners.id", ownerIds);
}
el = el.inOrEmpty("examSectionQuestions.examSection.exam.id", examIds);
el = el.inOrEmpty("examSectionQuestions.examSection.exam.course.id", courseIds);
el = el.inOrEmpty("tags.id", tagIds);
el = el.inOrEmpty("examSectionQuestions.examSection.id", sectionIds);

Set<Question> questions = el.orderBy("created desc").findSet();
if (user.hasRole(Role.Name.TEACHER) && !ownerIds.isEmpty()) {
questions = questions.stream().filter(question -> question.getQuestionOwners().contains(user)).collect(Collectors.toSet());
}
return ok(questions, pp);
}

Expand Down
4 changes: 4 additions & 0 deletions app/controllers/TagController.java
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,7 @@ public Result listTags(
Optional<List<Long>> courseIds,
Optional<List<Long>> examIds,
Optional<List<Long>> sectionIds,
Optional<List<Long>> ownerIds,
Http.Request request
) {
User user = request.attrs().get(Attrs.AUTHENTICATED_USER);
Expand All @@ -64,6 +65,9 @@ public Result listTags(
if (sectionIds.isPresent() && !sectionIds.get().isEmpty()) {
query = query.in("questions.examSectionQuestions.examSection.id", sectionIds.get());
}
if (ownerIds.isPresent() && !ownerIds.get().isEmpty()) {
query = query.in("questions.questionOwners.id", ownerIds.get());
}
Set<Tag> tags = query.findSet();
return ok(tags, PathProperties.parse("(*, creator(id), questions(id))"));
}
Expand Down
12 changes: 7 additions & 5 deletions conf/routes
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,9 @@ GET / controlle
############### Session interface ############
GET /app/session controllers.SessionController.checkSession(request: Request)
PUT /app/session controllers.SessionController.extendSession(request: Request)
+nocsrf
POST /app/session controllers.SessionController.login(request: Request)
+nocsrf
DELETE /app/session controllers.SessionController.logout(request: Request)

############### User interface ###############
Expand Down Expand Up @@ -33,7 +35,7 @@ PUT /app/exams/:eid/course/:cid controlle
GET /app/exams/:id/preview controllers.ExamController.getExamPreview(id: Long, request: Request)
GET /app/reviewerexams controllers.ExamController.getTeachersExams(request: Request)

GET /app/examsearch controllers.ExamController.listExams(courseIds: java.util.Optional[LongList], sectionIds: java.util.Optional[LongList], tagIds: java.util.Optional[LongList], request: Request)
GET /app/examsearch controllers.ExamController.listExams(courseIds: java.util.Optional[LongList], sectionIds: java.util.Optional[LongList], tagIds: java.util.Optional[LongList], owner: java.util.Optional[LongList], request: Request)

PUT /app/exam/:eid/software/:sid controllers.ExamController.updateExamSoftware(eid: Long, sid: Long, request: Request)

Expand Down Expand Up @@ -121,7 +123,7 @@ DELETE /app/exams/:eid/sections/:sid/questions/:qid controlle
PUT /app/exams/:eid/sections/:sid/reorder controllers.ExamSectionController.reorderSectionQuestions(eid: Long, sid: Long, request: Request)
PUT /app/exams/:eid/reorder controllers.ExamSectionController.reorderSections(eid: Long, request: Request)
GET /app/exams/question/:id/distribution controllers.ExamSectionController.getQuestionDistribution(id: Long)
GET /app/sections controllers.ExamSectionController.listSections(filter: java.util.Optional[String], courseIds: java.util.Optional[LongList], examIds: java.util.Optional[LongList], tagIds: java.util.Optional[LongList], request: Request)
GET /app/sections controllers.ExamSectionController.listSections(filter: java.util.Optional[String], courseIds: java.util.Optional[LongList], examIds: java.util.Optional[LongList], tagIds: java.util.Optional[LongList], ownerIds: java.util.Optional[LongList], request: Request)

############### Section material interface ###############
GET /app/materials controllers.ExamMaterialController.listMaterials(request: Request)
Expand Down Expand Up @@ -181,12 +183,12 @@ DELETE /app/enrolments/configs/:eecid controlle

############### Courses interface ###############
GET /app/courses controllers.CourseController.getCourses(filter: Option[String], q: Option[String])
GET /app/courses/user controllers.CourseController.listUsersCourses(examIds: Option[List[Long]], sectionIds: Option[List[Long]], tagIds: Option[List[Long]])
GET /app/courses/user controllers.CourseController.listUsersCourses(examIds: Option[List[Long]], sectionIds: Option[List[Long]], tagIds: Option[List[Long]], ownerIds: Option[List[Long]])
GET /app/courses/:id controllers.CourseController.getCourse(id: Long)

############### Question interface ###############

GET /app/questions controllers.QuestionController.getQuestions(exam: java.util.List[java.lang.Long], course: java.util.List[java.lang.Long], tag: java.util.List[java.lang.Long], section: java.util.List[java.lang.Long], request: Request)
GET /app/questions controllers.QuestionController.getQuestions(exam: java.util.List[java.lang.Long], course: java.util.List[java.lang.Long], tag: java.util.List[java.lang.Long], section: java.util.List[java.lang.Long], owner: java.util.List[java.lang.Long], request: Request)
GET /app/questions/:id controllers.QuestionController.getQuestion(id: Long, request: Request)
PUT /app/questions/:id controllers.QuestionController.updateQuestion(id: Long, request: Request)

Expand Down Expand Up @@ -409,7 +411,7 @@ GET /app/availability/:roomId/:date controlle
GET /app/languages controllers.LanguageController.getSupportedLanguages

################# Tag interface ##################
GET /app/tags controllers.TagController.listTags(filter: java.util.Optional[String], courseIds: java.util.Optional[LongList], examIds: java.util.Optional[LongList], sectionIds: java.util.Optional[LongList], request: Request)
GET /app/tags controllers.TagController.listTags(filter: java.util.Optional[String], courseIds: java.util.Optional[LongList], examIds: java.util.Optional[LongList], sectionIds: java.util.Optional[LongList], owner: java.util.Optional[LongList], request: Request)
POST /app/tags/questions controllers.TagController.addTagToQuestions(request: Request)

################# General Settings interface ##################
Expand Down
30 changes: 19 additions & 11 deletions ui/src/app/question/library/library.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ import type { Observable } from 'rxjs';
import { map } from 'rxjs/operators';
import type { Course, Exam, ExamSection, ReverseQuestion, Tag } from '../../exam/exam.model';
import { QuestionService } from '../question.service';
import {User} from "../../session/session.service";

export interface LibraryQuestion extends ReverseQuestion {
icon: string;
Expand All @@ -36,20 +37,23 @@ export class LibraryService {
private Question: QuestionService,
) {}

listExams$ = (courseIds: number[], sectionIds: number[], tagIds: number[]): Observable<Exam[]> =>
this.http.get<Exam[]>('/app/examsearch', { params: this.getQueryParams(courseIds, [], sectionIds, tagIds) });
listExams$ = (courseIds: number[], sectionIds: number[], tagIds: number[], ownerIds: number[]): Observable<Exam[]> =>
this.http.get<Exam[]>('/app/examsearch', { params: this.getQueryParams(courseIds, [], sectionIds, tagIds, ownerIds) });

listCourses$ = (examIds: number[], sectionIds: number[], tagIds: number[]): Observable<Course[]> =>
this.http.get<Course[]>('/app/courses/user', { params: this.getQueryParams([], examIds, sectionIds, tagIds) });
listCourses$ = (examIds: number[], sectionIds: number[], tagIds: number[], ownerIds: number[]): Observable<Course[]> =>
this.http.get<Course[]>('/app/courses/user', { params: this.getQueryParams([], examIds, sectionIds, tagIds, ownerIds) });

listSections$ = (courseIds: number[], examIds: number[], tagIds: number[]): Observable<ExamSection[]> =>
this.http.get<ExamSection[]>('/app/sections', { params: this.getQueryParams(courseIds, examIds, [], tagIds) });
listSections$ = (courseIds: number[], examIds: number[], tagIds: number[], ownerIds: number[]): Observable<ExamSection[]> =>
this.http.get<ExamSection[]>('/app/sections', { params: this.getQueryParams(courseIds, examIds, [], tagIds, ownerIds) });

listTags$ = (courseIds: number[], examIds: number[], sectionIds: number[]): Observable<Tag[]> =>
this.http.get<Tag[]>('/app/tags', { params: this.getQueryParams(courseIds, sectionIds, examIds, []) });
listTags$ = (courseIds: number[], examIds: number[], sectionIds: number[], ownerIds: number[]): Observable<Tag[]> =>
this.http.get<Tag[]>('/app/tags', { params: this.getQueryParams(courseIds, sectionIds, examIds, [], ownerIds) });

listAllTags$ = (): Observable<Tag[]> => this.http.get<Tag[]>('/app/tags');

listAllOwners$ = (): Observable<User[]> =>
this.http.get<User[]>('/app/users');

addTagForQuestions$ = (tagId: number, questionIds: number[]) =>
this.http.post<void>('/app/tags/questions', { questionIds: questionIds, tagId: tagId });

Expand Down Expand Up @@ -93,7 +97,7 @@ export class LibraryService {
if (text) {
return questions.filter((question) => {
const re = new RegExp(text, 'i');
const owner = question.creator ? question.creator.firstName + ' ' + question.creator.lastName : '';
const owner = question.questionOwners.map((o)=> o.firstName + ' ' + o.lastName).toString();
return owner.match(re);
});
} else {
Expand All @@ -106,10 +110,11 @@ export class LibraryService {
examIds: number[],
sectionIds: number[],
tagIds: number[],
ownerIds: number[]
): Observable<LibraryQuestion[]> =>
this.http
.get<LibraryQuestion[]>('/app/questions', {
params: this.getQueryParams(courseIds, examIds, sectionIds, tagIds),
params: this.getQueryParams(courseIds, examIds, sectionIds, tagIds, ownerIds),
})
.pipe(
map((questions) => {
Expand Down Expand Up @@ -137,7 +142,7 @@ export class LibraryService {
}),
);

private getQueryParams = (courseIds: number[], examIds: number[], sectionIds: number[], tagIds: number[]) => {
private getQueryParams = (courseIds: number[], examIds: number[], sectionIds: number[], tagIds: number[], ownerIds: number[]) => {
let params = new HttpParams();

const append = (key: string, idArray: number[], paramsObj: HttpParams) => {
Expand All @@ -156,6 +161,9 @@ export class LibraryService {
if (examIds.length > 0) {
params = append('exam', examIds, params);
}
if (ownerIds.length > 0) {
params = append('owner', ownerIds, params);
}

return params;
};
Expand Down
15 changes: 15 additions & 0 deletions ui/src/app/question/library/results/library-results.component.html
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,16 @@
>
</xm-table-sort>
</th>
<th>
<xm-table-sort
by=""
text="i18n_creator"
[predicate]="questionsPredicate"
[reverse]="reverse"
(click)="setPredicate('creator')"
>
</xm-table-sort>
</th>
<th>
<xm-table-sort
by="modified"
Expand Down Expand Up @@ -135,6 +145,11 @@
</div>
</td>
<td>
<span class="">
<small>{{ question.creator?.firstName }} {{ question.creator?.lastName }}</small>
</span>
</td>
<td>
@if (question.modified) {
<span class="timestamp">
{{ question.modified | date: 'dd.MM.yyyy HH:mm' }}
Expand Down
Loading

0 comments on commit f1ddd04

Please sign in to comment.