zesje issueshttps://gitlab.kwant-project.org/zesje/zesje/-/issues2023-04-14T09:15:46Zhttps://gitlab.kwant-project.org/zesje/zesje/-/issues/681Catch errors in uploaded csv2023-04-14T09:15:46ZAnton AkhmerovCatch errors in uploaded csvTrying to upload an invalid csv results in a 500 with this error.
```
Traceback (most recent call last):
File "/opt/conda/envs/zesje-dev/lib/python3.8/site-packages/flask/app.py", line 1516, in full_dispatch_request
rv = self.dispa...Trying to upload an invalid csv results in a 500 with this error.
```
Traceback (most recent call last):
File "/opt/conda/envs/zesje-dev/lib/python3.8/site-packages/flask/app.py", line 1516, in full_dispatch_request
rv = self.dispatch_request()
File "/opt/conda/envs/zesje-dev/lib/python3.8/site-packages/flask/app.py", line 1502, in dispatch_request
return self.ensure_sync(self.view_functions[rule.endpoint])(**req.view_args)
File "/opt/conda/envs/zesje-dev/lib/python3.8/site-packages/flask_restful/__init__.py", line 467, in wrapper
resp = resource(*args, **kwargs)
File "/opt/conda/envs/zesje-dev/lib/python3.8/site-packages/flask/views.py", line 84, in view
return current_app.ensure_sync(self.dispatch_request)(*args, **kwargs)
File "/opt/conda/envs/zesje-dev/lib/python3.8/site-packages/flask_restful/__init__.py", line 582, in dispatch_request
resp = meth(*args, **kwargs)
File "/app/zesje/api/students.py", line 136, in post
student = _row_to_student(row)
File "/app/zesje/api/students.py", line 175, in _row_to_student
first_name=row['First Name'],
File "/opt/conda/envs/zesje-dev/lib/python3.8/site-packages/pandas/core/series.py", line 981, in __getitem__
return self._get_value(key)
File "/opt/conda/envs/zesje-dev/lib/python3.8/site-packages/pandas/core/series.py", line 1089, in _get_value
loc = self.index.get_loc(label)
File "/opt/conda/envs/zesje-dev/lib/python3.8/site-packages/pandas/core/indexes/base.py", line 3805, in get_loc
raise KeyError(key) from err
KeyError: 'First Name'
```
we catch it and be more informativehttps://gitlab.kwant-project.org/zesje/zesje/-/issues/679Score of feedback options is nullable in the database2022-11-16T11:44:52ZHugo KerstensScore of feedback options is nullable in the databaseThe field `FeedbackOption.score` should not be nullable:
- A null value is not used anywhere in the code
- The front-end doesn't like it and throws errors.
- The root feedback option has score 0
- This originates from before SQLAlchemy
...The field `FeedbackOption.score` should not be nullable:
- A null value is not used anywhere in the code
- The front-end doesn't like it and throws errors.
- The root feedback option has score 0
- This originates from before SQLAlchemy
We should:
- Make it no longer nullable
- Add a migration that fills all null values with `0`.https://gitlab.kwant-project.org/zesje/zesje/-/issues/674More back-end checks for merging copies2022-10-27T13:15:51ZHugo KerstensMore back-end checks for merging copiesThe following discussion from !380 should be addressed:
- [ ] @Hugo started a [discussion](https://gitlab.kwant-project.org/zesje/zesje/-/merge_requests/380#note_56105):
> This MR exactly mimicks the old front-end checks. While wr...The following discussion from !380 should be addressed:
- [ ] @Hugo started a [discussion](https://gitlab.kwant-project.org/zesje/zesje/-/merge_requests/380#note_56105):
> This MR exactly mimicks the old front-end checks. While writing the tests, I realized we only warn the user whether we will modify the newly merged submission.
>
> However, when transferring a copy from submission A to B, submission A will be modified and thus ungraded, but it won't trigger any warning. IMO we should catch this as well and warn the user.
>
> We could either fix it in this MR, or make a new issue for it.https://gitlab.kwant-project.org/zesje/zesje/-/issues/671Searching students in grade view is broken2022-10-31T16:58:44ZHugo KerstensSearching students in grade view is brokenSearching student relies using the grade navigation in the grade view relies on the front-end having the full student data available for each submission. This data is requested from the `api/exams/<exam_id>/?only_metadata=true` endpoint ...Searching student relies using the grade navigation in the grade view relies on the front-end having the full student data available for each submission. This data is requested from the `api/exams/<exam_id>/?only_metadata=true` endpoint in the `Grade` component, but since commit a8e6e83708912687dfbf445c0f0b6e09547fb290, this no longer returns the full student data per submission, just the submission id and student id.
**_Note: this only applies to exams which have anonymous grading set to false._**
I see two options:
1. Add the student names back to the exam metadata endpoint. (How large is the performance impact?)
2. Add a separate API call in the grade navigation endpoint once it is focused, which loads the student names. Could add `only_metadata` option to the `api/submissions/<exam_id>` endpoint, which excludes solution data.https://gitlab.kwant-project.org/zesje/zesje/-/issues/662Show warning when looking at answer with multiple submissions assigned2022-10-31T11:05:25ZStefan HugtenburgShow warning when looking at answer with multiple submissions assignedIn some browsers the scrollbar only shows up when you hover over the image, meaning it is easy to miss that this exam has two (or more) submissions assigned. Especially for longer problems that can lead to incorrectly marking the answer ...In some browsers the scrollbar only shows up when you hover over the image, meaning it is easy to miss that this exam has two (or more) submissions assigned. Especially for longer problems that can lead to incorrectly marking the answer as blank.
Even with the scrollbar, noticing that this is actually 2 is not obvious :smile:
![image](/uploads/845fdab3843938b400b3f0365aca3487/image.png)https://gitlab.kwant-project.org/zesje/zesje/-/issues/657Change *all* MC labels when type changes2023-04-14T09:18:11ZAdrià LabayChange *all* MC labels when type changesBasically, if you start with a numeric label type and move to the alphabetical type, all new options will be added with the correct letter but any previously added option will still have numbers:
![Screenshot_from_2022-06-26_15-53-41](/...Basically, if you start with a numeric label type and move to the alphabetical type, all new options will be added with the correct letter but any previously added option will still have numbers:
![Screenshot_from_2022-06-26_15-53-41](/uploads/d20c4fd841c78c3822fe97e6faa4d66c/Screenshot_from_2022-06-26_15-53-41.png)
Solution: convert all labels to the new typehttps://gitlab.kwant-project.org/zesje/zesje/-/issues/656Automatically rebase MR2022-06-08T14:42:44ZAdrià LabayAutomatically rebase MRhttps://medium.com/ovrsea/how-to-automatically-rebase-all-your-merge-requests-on-gitlab-when-pushing-on-master-9b7c5119ac5fhttps://medium.com/ovrsea/how-to-automatically-rebase-all-your-merge-requests-on-gitlab-when-pushing-on-master-9b7c5119ac5fhttps://gitlab.kwant-project.org/zesje/zesje/-/issues/645Use dependabot to keep track of dependencies updates2022-03-16T10:55:48ZAdrià LabayUse dependabot to keep track of dependencies updatesThe number of packages that we are using for the `client` is quite big right now and it's difficult to maintain all of them. It would be great to implement a [dependabot](https://gitlab.com/dependabot-gitlab/dependabot) to keep track of ...The number of packages that we are using for the `client` is quite big right now and it's difficult to maintain all of them. It would be great to implement a [dependabot](https://gitlab.com/dependabot-gitlab/dependabot) to keep track of [patch and minor versions updates](https://docs.github.com/en/code-security/supply-chain-security/keeping-your-dependencies-updated-automatically/configuration-options-for-dependency-updates#specifying-dependencies-and-versions-to-ignore). It can also be used for the python packages.
Major version should still be done manually for safety.https://gitlab.kwant-project.org/zesje/zesje/-/issues/632Cover student number validation with tests2022-03-07T09:20:03ZAnton AkhmerovCover student number validation with tests#630 (fixed by !396) was not caught by tests, and therefore identifies a gap in our coverage.#630 (fixed by !396) was not caught by tests, and therefore identifies a gap in our coverage.https://gitlab.kwant-project.org/zesje/zesje/-/issues/628Drop SQLite migration support2022-03-06T16:07:10ZHugo KerstensDrop SQLite migration supportWe should remove all support for running migrations on/from SQLite. This significantly cleans up the migration environment.
- Almost 50% of the code in the migration environment consists of legacy SQLite backups code. This code will nev...We should remove all support for running migrations on/from SQLite. This significantly cleans up the migration environment.
- Almost 50% of the code in the migration environment consists of legacy SQLite backups code. This code will never be used again.
- The initial migration reads data from SQLite using the current db metadata. Will never be used again, and will break in the future if we ever add new tables.https://gitlab.kwant-project.org/zesje/zesje/-/issues/627Migration for naming database constraints2022-02-07T18:33:57ZHugo KerstensMigration for naming database constraintsThe following discussion from !385 should be addressed:
- [ ] @anton-akhmerov started a [discussion](https://gitlab.kwant-project.org/zesje/zesje/-/merge_requests/385#note_56290): (+1 comment)
> Adding naming conventions is releva...The following discussion from !385 should be addressed:
- [ ] @anton-akhmerov started a [discussion](https://gitlab.kwant-project.org/zesje/zesje/-/merge_requests/385#note_56290): (+1 comment)
> Adding naming conventions is relevant for migrations, is that correct?
Correct, otherwise MySQL uses the default naming convention for constraints, which depends on the order constraints were added. Also, the convention is not guaranteed to be the same for all MySQL servers. This means we do not have a reliable way to access the constraints in migrations.
Even after the current migration, there are tons of constraints which still have the default naming convention, shown by `%_ibfk_%` in the table below. (Apparently alembic only detects renaming unique constraints, not foreign key constraints). **Maybe it's better to solve this in a separate MR with its own migration.** This migration would drop *ALL* constraints and recreate them accordingly.
| TABLE | COLUMN | CONSTRAINT | REFERENCED_TABLE | REFERENCED_COLUMN |
|---|---|---|---|---|
| copy | number | uq_copy__exam_id | | |
| copy | _exam_id | uq_copy__exam_id | | |
| copy | submission_id | **copy_ibfk_1** | submission | id |
| copy | _exam_id | fk_copy__exam_id_exam | exam | id |
| exam | token | uq_exam_token | | |
| exam_widget | exam_id | exam_widget_ibfk_1 | exam | id |
| exam_widget | id | exam_widget_ibfk_2 | widget | id |
| feedback_option | problem_id | **feedback_option_ibfk_1** | problem | id |
| feedback_option | parent_id | fk_parent_feedback | feedback_option | id |
| grader | oauth_id | uq_grader_oauth_id | | |
| mc_option | feedback_id | **mc_option_ibfk_1** | feedback_option | id |
| mc_option | id | **mc_option_ibfk_2** | widget | id |
| page | copy_id | uq_page_copy_id | | |
| page | number | uq_page_copy_id | | |
| page | copy_id | **page_ibfk_1** | copy | id |
| problem | exam_id | **problem_ibfk_1** | exam | id |
| problem_widget | id | **problem_widget_ibfk_1** | widget | id |
| problem_widget | problem_id | **problem_widget_ibfk_2** | problem | id |
| scan | exam_id | **scan_ibfk_1** | exam | id |
| solution | grader_id | **solution_ibfk_1** | grader | id |
| solution | problem_id | **solution_ibfk_2** | problem | id |
| solution | submission_id | **solution_ibfk_3** | submission | id |
| solution_feedback | feedback_option_id | **solution_feedback_ibfk_1** | feedback_option | id |
| solution_feedback | solution_id | **solution_feedback_ibfk_2** | solution | id |
| student | email | uq_student_email | | |
| submission | exam_id | **submission_ibfk_1** | exam | id |
| submission | student_id | **submission_ibfk_2** | student | id |https://gitlab.kwant-project.org/zesje/zesje/-/issues/590auto Dockerfile is broken2023-10-20T21:08:29ZHugo Kerstensauto Dockerfile is brokenThere are 2 problems:
- Mysql cannot find shared libraries as the conda environment is not activated
- The mysql init file is not created in the data directory, but in the root dir, causing permission issues.There are 2 problems:
- Mysql cannot find shared libraries as the conda environment is not activated
- The mysql init file is not created in the data directory, but in the root dir, causing permission issues.https://gitlab.kwant-project.org/zesje/zesje/-/issues/587Race condition in Flask session data2022-10-07T09:32:40ZHugo KerstensRace condition in Flask session dataIt is possible for race conditions to occur in loading and saving the Flask session data, causing data loss.
A solution would be to use an extension to store the session data in a centralized place, instead of client side. The best opti...It is possible for race conditions to occur in loading and saving the Flask session data, causing data loss.
A solution would be to use an extension to store the session data in a centralized place, instead of client side. The best option IMO is `flasksession` with the Redis backend.
This also solves another issue that the session data is not accessible in Celery workers, as the `SECRET_KEY` that is issued to encrypt the session data is random for each instance of a Flask app (Celery workers have their own Flask app instance).
---
### Extra description from !362
After some investigation I found that there is a race condition. It happens more often with the mock server as the request is quicker.
As you open a page, the following happens:
- `GET url/to/view`
- `GET api/oauth/start?userurl=/url/to/view`
- `GET api/oauth/grader`
Both calls to `api/oauth/start` and `api/oauth/grader` are emitted at the same moment, originating from the `componentDidMount` of the `Login` and `NavBar` components respectively. Both requests load the same session data from the request at the same time, but the request that finishes last overwrites the session data from the other. This means that if `api/oauth/grader` finishes later, the session data gets overwritten with unaltered data, undoing the effects of `api/oauth/start`.https://gitlab.kwant-project.org/zesje/zesje/-/issues/584Upload issues when running Zesje as Docker container2021-10-01T09:52:27ZOtto VisserUpload issues when running Zesje as Docker containerZesje uses nginx for proxy, but the upload size limit is the default for nginx. For most uploads of scanned exams, this is not enough. I changed line 7 in auto.Dockerfile to:
`RUN echo "server { client_max_body_size 128M; listen 80; loc...Zesje uses nginx for proxy, but the upload size limit is the default for nginx. For most uploads of scanned exams, this is not enough. I changed line 7 in auto.Dockerfile to:
`RUN echo "server { client_max_body_size 128M; listen 80; location / { proxy_pass http://127.0.0.1:5000; } }" > /etc/nginx/sites-enabled/proxy.conf` to resolve this issue.https://gitlab.kwant-project.org/zesje/zesje/-/issues/583Zoom around cursor2021-09-30T13:49:24ZStefan HugtenburgZoom around cursorSome handwriting can be a challenge :grimacing:
Perhaps clicking on the pdf would have some old-school magnifying glass feature around the cursor to allow us to zoom in on tricky details ;)Some handwriting can be a challenge :grimacing:
Perhaps clicking on the pdf would have some old-school magnifying glass feature around the cursor to allow us to zoom in on tricky details ;)https://gitlab.kwant-project.org/zesje/zesje/-/issues/565Show index of current solution2022-03-30T07:49:45ZAlex MaatShow index of current solutionNear the text that shows how many submissions are matched with the applied filters (!345 ), it should indicate the position of the current submission you are viewing.Near the text that shows how many submissions are matched with the applied filters (!345 ), it should indicate the position of the current submission you are viewing.https://gitlab.kwant-project.org/zesje/zesje/-/issues/536Restructure project folder2020-11-08T17:56:25ZAdrià LabayRestructure project folderMove docker files into a single `docker` folder, configuration files into single `config` folder...Move docker files into a single `docker` folder, configuration files into single `config` folder...https://gitlab.kwant-project.org/zesje/zesje/-/issues/513Improve handling of missing pages in unstructured exams2020-06-28T16:27:24ZAnton AkhmerovImprove handling of missing pages in unstructured examsRight now a copy id is shown, but doesn't allow to easily determine where the problem occurred (one needs to go to /students and check which student got that copy).Right now a copy id is shown, but doesn't allow to easily determine where the problem occurred (one needs to go to /students and check which student got that copy).Unstructured examshttps://gitlab.kwant-project.org/zesje/zesje/-/issues/512Update signature view for unstructured exams2020-06-18T13:10:27ZAnton AkhmerovUpdate signature view for unstructured examsThe following discussion from !297 should be addressed:
- [ ] @Hugo started a [discussion](https://gitlab.kwant-project.org/zesje/zesje/-/merge_requests/297#note_44395): (+6 comments)
> The student verification view should be adju...The following discussion from !297 should be addressed:
- [ ] @Hugo started a [discussion](https://gitlab.kwant-project.org/zesje/zesje/-/merge_requests/297#note_44395): (+6 comments)
> The student verification view should be adjusted for unstructured exams.Unstructured examshttps://gitlab.kwant-project.org/zesje/zesje/-/issues/510Return total students for each course2020-06-18T12:57:58ZShashank AnandReturn total students for each courseAs part of the get request to the courses endpoint, the total number of students per course should also be returned.As part of the get request to the courses endpoint, the total number of students per course should also be returned.Multitenancy