Reach tasks attached to topics, and read Etherpad pads
Testing against a local instance turned up four things the server was
getting wrong, all of them invisible against the live account because the
data that exposes them had never been produced there.
`GET /lessons/{id}/tasks` returns a bare array, not the `{data,total}`
envelope every sibling endpoint uses, so `.data` was undefined and a
topic's tasks silently vanished. Its items also carry no id at all —
`LessonLinkedTaskResponse` has no id property — which leaves a
topic-attached task unidentifiable: it is not a task element on the
course page, and once past due it is in neither task list. So its
submission, and its grade, could not be reached by any route. That is 18
of 60 tasks on the real account, now reachable: the ids come off the
legacy topic page, where each task is linked as `/homework/{id}`.
The types said `id: string` and `status: TaskStatus` on something that
has neither, which is what let this stay quiet; `LessonLinkedTask` and
`ResolvedTask` now say what is actually there.
Collaborative text editor elements come back with `content: {}`, and the
tool said their contents were unavailable. They are available: the
content-element endpoint returns the pad url *and* an Etherpad session
cookie, and the pad exports itself as text to whoever holds it. No API
key needed. Pads are now shown by get_board and indexed for search.
The store's file digest covered id and size on the grounds that file
records are immutable. `PATCH /file/rename/{id}` renames one in place,
so a rename was reported as nothing at all.
Finally, get_board reported an unpublished board as "no permission",
which sends the reader hunting for an access problem that is not there.
smoke gains checks for topic tasks and for pads, and no longer assumes a
populated index or a search term that happens to match. 39/39 live-only
and 41/41 index-backed, against both the live instance and a local one.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
36
docs/API.md
36
docs/API.md
@@ -173,6 +173,31 @@ clearest case in this API of live behaviour diverging from upstream source.
|
||||
instance configuration, including the session timeouts and feature flags. Handy
|
||||
for checking deployed settings without a token.
|
||||
|
||||
**`GET /lessons/{id}/tasks` returns a bare array, and its items have no id.**
|
||||
Every other list endpoint returns `{data, total}`; this one returns the array
|
||||
directly, so reading `.data` silently yields `undefined`. Worse, the items are
|
||||
`LessonLinkedTaskResponse`, which has no id property at all — name, description
|
||||
and dates only. A task attached to a topic is therefore unidentifiable from the
|
||||
API: it is not a task element on the course page (the topic reports only
|
||||
`numberOfPublishedTasks`), and once past due it is in neither `/tasks` nor
|
||||
`/tasks/finished`. On the account this server was built for that hid 18 of 60
|
||||
tasks, submissions and grades included. The ids are recoverable only from the
|
||||
legacy topic page, which links each task as `/homework/{id}` —
|
||||
`core/lesson-page.ts`.
|
||||
|
||||
**A student's task lists exclude past-due tasks.** `/tasks` drops a task once
|
||||
its due date passes; `/tasks/finished` holds only what the student ticked off.
|
||||
A submitted, graded, past-due task is in neither. Reach it through the course
|
||||
page, or through its topic.
|
||||
|
||||
**An unpublished board is listed but cannot be opened.** The course-board
|
||||
projection reports a draft board with its title, while `GET /boards/{id}`
|
||||
answers 403 for anyone who cannot edit it. Treat a 403 there as "probably not
|
||||
published yet", not as an access problem.
|
||||
|
||||
**`PATCH /file/rename/{fileRecordId}` mutates a file record in place.** The id
|
||||
and size stay the same, so any change detection keyed on those alone misses it.
|
||||
|
||||
**`Content-Disposition` on downloads is malformed.** It comes back as
|
||||
`attachment;; filename="…"` — note the doubled semicolon — and the filename is
|
||||
percent-encoded inside the quotes. Parse defensively.
|
||||
@@ -183,9 +208,14 @@ From `ContentElementType` in `schulcloud-server`, all seen live except where
|
||||
noted: `richText`, `file`, `fileFolder`, `link`, `drawing`,
|
||||
`collaborativeTextEditor`, `externalTool`, `videoConference`, `h5p`, `deleted`.
|
||||
|
||||
Collaborative text editor contents are **not** retrievable through the API —
|
||||
`GET /api/v3/collaborative-text-editor/{parentType}/{parentId}` returns a URL to
|
||||
the Etherpad-style editor, not the document text.
|
||||
Collaborative text editor elements come back with `content: {}` — no pad id, no
|
||||
url, nothing. `GET /api/v3/collaborative-text-editor/content-element/{elementId}`
|
||||
returns the pad url, and **also sets an Etherpad `sessionID` cookie** in its
|
||||
response. With that cookie, Etherpad's own `/etherpad/p/{padId}/export/txt`
|
||||
returns the document as plain text. So the contents *are* reachable, in two
|
||||
hops and without Etherpad's API key; `core/etherpad.ts` does this. The url is
|
||||
built from the server's `ETHERPAD__PAD_URI`, so it must be checked against the
|
||||
instance host before the session cookie is sent to it.
|
||||
|
||||
## Re-verifying after an upstream release
|
||||
|
||||
|
||||
Reference in New Issue
Block a user