@intellectif/lk-core 1.3.0 → 1.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +59 -0
- package/README.md +2 -0
- package/dist/{ai-B222dtHH.d.ts → ai-BYryFkF9.d.cts} +462 -5
- package/dist/ai-BYryFkF9.d.cts.map +1 -0
- package/dist/{ai-B222dtHH.d.cts → ai-BYryFkF9.d.ts} +462 -5
- package/dist/ai-BYryFkF9.d.ts.map +1 -0
- package/dist/ai-check.cjs +274 -23
- package/dist/ai-check.cjs.map +1 -1
- package/dist/ai-check.d.cts +13 -5
- package/dist/ai-check.d.cts.map +1 -1
- package/dist/ai-check.d.ts +13 -5
- package/dist/ai-check.d.ts.map +1 -1
- package/dist/ai-check.js +274 -23
- package/dist/ai-check.js.map +1 -1
- package/dist/{ai-writing-DCVkv4Zj.cjs → ai-writing-Cen7-3qs.cjs} +520 -58
- package/dist/ai-writing-Cen7-3qs.cjs.map +1 -0
- package/dist/{ai-writing-CCBjTOM3.js → ai-writing-D8PdhJJz.js} +513 -75
- package/dist/ai-writing-D8PdhJJz.js.map +1 -0
- package/dist/{index-Dyu66R4-.d.cts → index-Bg0aeWtM.d.cts} +327 -3
- package/dist/index-Bg0aeWtM.d.cts.map +1 -0
- package/dist/{index-BWPRPIXL.d.ts → index-CxpiWedW.d.ts} +7 -217
- package/dist/index-CxpiWedW.d.ts.map +1 -0
- package/dist/{index-CXyOV8sm.d.cts → index-D7R3Ll8R.d.cts} +2 -2
- package/dist/{index-CXyOV8sm.d.cts.map → index-D7R3Ll8R.d.cts.map} +1 -1
- package/dist/{index-UGxRSopE.d.ts → index-DUaW1Tj5.d.ts} +327 -3
- package/dist/index-DUaW1Tj5.d.ts.map +1 -0
- package/dist/{index-O4_ExlAD.d.cts → index-qMbxed1B.d.cts} +7 -217
- package/dist/index-qMbxed1B.d.cts.map +1 -0
- package/dist/{index-CegM8o15.d.ts → index-wMc1E_aM.d.ts} +2 -2
- package/dist/{index-CegM8o15.d.ts.map → index-wMc1E_aM.d.ts.map} +1 -1
- package/dist/index.cjs +32 -130
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +115 -97
- package/dist/index.d.cts.map +1 -1
- package/dist/index.d.ts +115 -97
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +9 -117
- package/dist/index.js.map +1 -1
- package/dist/{item-group-DroFXgLb.cjs → item-group-DEB7nLID.cjs} +2 -2
- package/dist/{item-group-DroFXgLb.cjs.map → item-group-DEB7nLID.cjs.map} +1 -1
- package/dist/{item-group-DXiR8nOr.js → item-group-DdSUCUjM.js} +2 -2
- package/dist/{item-group-DXiR8nOr.js.map → item-group-DdSUCUjM.js.map} +1 -1
- package/dist/{registry-DVi0LR_i.cjs → registry-Ce00A_OW.cjs} +184 -4
- package/dist/registry-Ce00A_OW.cjs.map +1 -0
- package/dist/{registry-Dsx9mNsS.js → registry-DaZRpqjW.js} +155 -5
- package/dist/registry-DaZRpqjW.js.map +1 -0
- package/dist/{schemas-Bdw0nGPo.js → schemas-BioKFf3F.js} +3 -3
- package/dist/{schemas-Bdw0nGPo.js.map → schemas-BioKFf3F.js.map} +1 -1
- package/dist/{schemas-DVbAOrtd.cjs → schemas-DksueYsu.cjs} +3 -3
- package/dist/{schemas-DVbAOrtd.cjs.map → schemas-DksueYsu.cjs.map} +1 -1
- package/dist/schemas.cjs +2 -2
- package/dist/schemas.d.cts +1 -1
- package/dist/schemas.d.ts +1 -1
- package/dist/schemas.js +2 -2
- package/dist/{scoring-BZqUkuDF.js → scoring-BKNNTz-s.js} +657 -3
- package/dist/scoring-BKNNTz-s.js.map +1 -0
- package/dist/{scoring-B2_HEhMT.cjs → scoring-lKQVYsxy.cjs} +722 -2
- package/dist/scoring-lKQVYsxy.cjs.map +1 -0
- package/dist/scoring.cjs +8 -2
- package/dist/scoring.d.cts +3 -3
- package/dist/scoring.d.ts +3 -3
- package/dist/scoring.js +3 -3
- package/dist/{xapi-DNzkSJ0S.cjs → xapi-NYrTlpID.cjs} +2 -2
- package/dist/{xapi-DNzkSJ0S.cjs.map → xapi-NYrTlpID.cjs.map} +1 -1
- package/dist/{xapi-CMTph7wG.js → xapi-wR6gu4qS.js} +2 -2
- package/dist/{xapi-CMTph7wG.js.map → xapi-wR6gu4qS.js.map} +1 -1
- package/dist/xapi.cjs +1 -1
- package/dist/xapi.d.cts +1 -1
- package/dist/xapi.d.ts +1 -1
- package/dist/xapi.js +1 -2
- package/package.json +2 -2
- package/vectors/README.md +24 -1
- package/vectors/scoring.json +18182 -1
- package/dist/ai-B222dtHH.d.cts.map +0 -1
- package/dist/ai-B222dtHH.d.ts.map +0 -1
- package/dist/ai-writing-CCBjTOM3.js.map +0 -1
- package/dist/ai-writing-DCVkv4Zj.cjs.map +0 -1
- package/dist/index-BWPRPIXL.d.ts.map +0 -1
- package/dist/index-Dyu66R4-.d.cts.map +0 -1
- package/dist/index-O4_ExlAD.d.cts.map +0 -1
- package/dist/index-UGxRSopE.d.ts.map +0 -1
- package/dist/registry-DVi0LR_i.cjs.map +0 -1
- package/dist/registry-Dsx9mNsS.js.map +0 -1
- package/dist/scoring-B2_HEhMT.cjs.map +0 -1
- package/dist/scoring-BZqUkuDF.js.map +0 -1
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,64 @@
|
|
|
1
1
|
# @intellectif/lk-core
|
|
2
2
|
|
|
3
|
+
## 1.5.0
|
|
4
|
+
|
|
5
|
+
### Minor Changes
|
|
6
|
+
|
|
7
|
+
- [#112](https://github.com/intellectif/learning-kit/pull/112) [`3fc1049`](https://github.com/intellectif/learning-kit/commit/3fc1049d67e14f6f4a12c235f19952a988472978) Thanks [@diego28e](https://github.com/diego28e)! - **Assisted grading**: a model grades a written response for the record, and in an exam no model's grade counts until it has been measured against your teachers.
|
|
8
|
+
|
|
9
|
+
**Action required:** none. Nothing grades until you call it. Four union members are new: `DeferredReason` gains `awaiting_human_review`, `AiRefusal` gains `misses-criteria` and `out-of-scale`, and `AiCheckCase['feature']` gains `grading`. A `switch` over one of them without a `default` branch needs them.
|
|
10
|
+
|
|
11
|
+
- **Levels on a rubric:** a criterion can carry `levels`, lowest first, from 2 to 10, each a `label` and an optional `description`. A level scores `index / (levels − 1)`.
|
|
12
|
+
- `validateActivity` does not check them in 1.x, so a field of that name you already use stays valid.
|
|
13
|
+
- The critic warns `wr_levels_unreadable` when it cannot read them.
|
|
14
|
+
- `redact()` passes readable levels to the learner, `label` and `description` only.
|
|
15
|
+
- **The request and its check:**
|
|
16
|
+
- `aiGradingRequest` builds what a model is told: the response verbatim, the rubric with its levels, and a group's material.
|
|
17
|
+
- `checkAiGrading` accepts a grade whole or not at all. It needs every criterion once (`misses-criteria`), each on its own scale (`out-of-scale`), with corrections that quote the response (`misquotes-answer`).
|
|
18
|
+
- **The grade:** `gradeFromJudgement` computes the total as `gradeFromRubric` does, with the item's weights and pass line. It records the model and the prompt revision on `grader`.
|
|
19
|
+
- **Calibration:** `calibrationReport` measures one grader configuration (a model, a prompt revision, a rubric and a target) against people's grades of the same responses. It reports:
|
|
20
|
+
|
|
21
|
+
- exact and adjacent agreement, quadratic kappa and a confusion matrix, on levels;
|
|
22
|
+
- Pearson's r, mean absolute error and the standardised mean difference, everywhere;
|
|
23
|
+
- calibration error and the Brier score, where grades carry level probabilities;
|
|
24
|
+
- the degradation from two people's agreement.
|
|
25
|
+
|
|
26
|
+
It ships no thresholds.
|
|
27
|
+
|
|
28
|
+
- **Routing:** `routeGrade` decides whether a grade counts or goes to a person, and gives every reason, in a fixed order:
|
|
29
|
+
|
|
30
|
+
- no matching calibration, in an exam;
|
|
31
|
+
- a report below your thresholds;
|
|
32
|
+
- a model unsure of a level, or one that asked for review;
|
|
33
|
+
- low confidence;
|
|
34
|
+
- the audit sample, chosen by `inAuditSample`.
|
|
35
|
+
|
|
36
|
+
`outcomeFromRoutedGrade` holds a grade for a person as `deferred` / `awaiting_human_review`, with the grade kept on `pendingGrade`, so `composeAssessmentScore` keeps the attempt provisional.
|
|
37
|
+
|
|
38
|
+
- **New optional fields:**
|
|
39
|
+
- `levels` on a rubric criterion, its redacted form included;
|
|
40
|
+
- `levelProbabilities` on `CriterionScore`;
|
|
41
|
+
- `routing` on `GradeRecord`;
|
|
42
|
+
- `pendingGrade` on a deferred `ItemOutcome`.
|
|
43
|
+
- **`@intellectif/lk-core/ai-check`** has five grading cases, for a `grading` port.
|
|
44
|
+
- **The grade-stability corpus** gains 123 vectors for the new functions. The 635 before them are unchanged.
|
|
45
|
+
|
|
46
|
+
Guide: https://github.com/intellectif/learning-kit/blob/main/docs/grading.md
|
|
47
|
+
|
|
48
|
+
## 1.4.0
|
|
49
|
+
|
|
50
|
+
### Minor Changes
|
|
51
|
+
|
|
52
|
+
- [#107](https://github.com/intellectif/learning-kit/pull/107) [`8bf7d6e`](https://github.com/intellectif/learning-kit/commit/8bf7d6edb76ff45ce32e425ef83663692127acc9) Thanks [@diego28e](https://github.com/diego28e)! - **AI help reads a question's group**: hints, explanations and feedback on writing now carry the passage, or the shared instructions, a grouped question is read beside.
|
|
53
|
+
|
|
54
|
+
**Action required:** none. Requests gain an optional `material`, which your prompt uses once you tell it to. A port that sends the whole request to its model sends the material too: up to 12,000 code points more per call on a question in a group.
|
|
55
|
+
|
|
56
|
+
- **lk-core:** `aiExplanationRequest`, `aiHintRequest` and `aiWritingFeedbackRequest` take an optional `group` (an `ItemGroup`, a redacted one, or your own `{ title, stimulus }`) and add `material`: the kind, the title, the text, the media type and its alt text, the attribution and the language. The text is cut past `AI_MATERIAL_MAX_LENGTH` (12,000 code points), at a word boundary, and marked `truncated`. The author's transcript and media addresses never go, so a whole group and a redacted one give the same material. The checks are unchanged: a hint that quotes the passage where it prints the answer is refused like any other.
|
|
57
|
+
- **lk-react:** inside `<ActivitySequence>` and `<InteractiveVideo>`, the SDK's own components, and a question you draw with `useAiHints`, `useAiExplanation` or `useAiWritingFeedback`, send their group's material by themselves. Outside a pager, pass `group` to the hooks. lk-react 23.2.0 peers on lk-core `^1.4.0`, so upgrade the two together. Coaching on a reading is unchanged.
|
|
58
|
+
- **`@intellectif/lk-core/ai-check`** has four more cases in item groups: a reading question explained, and hinted at, from a passage that prints its answer; a word-formation blank under its group's instructions; and a summary of the passage.
|
|
59
|
+
|
|
60
|
+
Guide: https://github.com/intellectif/learning-kit/blob/main/docs/ai.md#a-question-in-an-item-group-140
|
|
61
|
+
|
|
3
62
|
## 1.3.0
|
|
4
63
|
|
|
5
64
|
### Minor Changes
|
package/README.md
CHANGED
|
@@ -25,6 +25,7 @@ npm install @intellectif/lk-core
|
|
|
25
25
|
- **Dictation marking as data** — a dictation is graded by the character-level similarity of the typed text to the transcript, with one `ScoringDetail` per word carrying its own `score`. `alignDictation(data, text)` returns the same comparison the grade was made of (normalised strings, word pairings, which accepted transcript won), `diffDictationChars(reference, attempt)` the character-level edits for a marked display, and `dictationReferenceWords(data)` the ids and words a stored result can be checked against — so a review screen or an analytics job never re-implements the arithmetic. `score()` and `evaluate()` take an optional `{ rounding }` to compare the pass line as displayed.
|
|
26
26
|
- **`evaluate(data, response)` → `ItemOutcome`** — the resilient result: `scored`, `deferred` (graded later by an AI or a human), `graded` (the grade came back), or `unscorable`. "Not graded yet" is expressible in the type system and is never conflated with a zero.
|
|
27
27
|
- **Deferred grading, both directions** — `GradeRecord`, `gradeFromRubric()` (the weighted total as a pure function of the grader's judgements — never the model's arithmetic; declare `maxScore` per criterion if your grader works out of 100 or out of 9), `outcomeFromGrade()` (which refuses a record whose numbers cannot be a grade instead of mirroring them), `hasGrade()`.
|
|
28
|
+
- **Assisted grading, behind a calibration gate** — `aiGradingRequest` / `checkAiGrading` hold a model's grade of a written response to every criterion of the rubric, each on its own scale (levels the author writes, or a score); `gradeFromJudgement` computes the total. `calibrationReport` measures a model, prompt, rubric and target against your teachers' grades, and `routeGrade` sends a grade to a person, for reasons it names: in an exam, until a matching calibration is supplied. No thresholds ship: they are yours.
|
|
28
29
|
- **Assessment composition** — `composeAssessmentScore()` for weighted, sectioned totals, with a `provisional` status so an unmarked essay never deflates a grade — and a grade out of contract (`NaN`, 85 "out of 1") never finalises one — and `RoundingPolicy` / `roundGrade` / `gte` / `classifyBand` keeping grade rounding and band classification as the two distinct operations they are.
|
|
29
30
|
- **Item groups** — `Stimulus` + `ItemGroup` (one passage or recording serving several questions), `flattenSequence()` for seeded, shuffle-atomic presentation order with stable slot identity. Slot ids are positional by default (`"3"`, `"1.0"`); author a `slotKey` on an entry and its id survives an insert, so a stored response cannot slide onto a different question.
|
|
30
31
|
- **Delivery policies** — `DeliveryPolicy` says what a school lets a learner see around a question: feedback, solutions, hints and AI help. `resolveDeliveryPolicy` spells one out (an unreadable setting restricts, never allows), `validateDeliveryPolicy` checks one before it is stored, and `combineDeliveryPolicies` keeps a setting on only where every policy leaves it on.
|
|
@@ -161,6 +162,7 @@ Zod is the single runtime dependency, pinned to one exact version and private: n
|
|
|
161
162
|
- [Delivery policies](https://github.com/intellectif/learning-kit/blob/main/docs/delivery.md) — `DeliveryPolicy`, and recording it with an attempt.
|
|
162
163
|
- [Scoring policies](https://github.com/intellectif/learning-kit/blob/main/docs/scoring.md) — `ItemScoringPolicy`: tries, which counts, what hints cost, and scoring them on a server.
|
|
163
164
|
- [AI help for learners](https://github.com/intellectif/learning-kit/blob/main/docs/ai.md) — the AI contract, the checks, and the `ai-check` kit for your prompts.
|
|
165
|
+
- [Grading with a model](https://github.com/intellectif/learning-kit/blob/main/docs/grading.md) — a model's grade for the record: levels, calibration against your teachers, and where a grade goes.
|
|
164
166
|
- [Project README](https://github.com/intellectif/learning-kit#readme) — the full picture, including the React renderers.
|
|
165
167
|
- [Contributing](https://github.com/intellectif/learning-kit/blob/main/CONTRIBUTING.md) — adding a new activity type.
|
|
166
168
|
|
|
@@ -134,6 +134,57 @@ interface CriterionScore {
|
|
|
134
134
|
weight?: number;
|
|
135
135
|
/** Not applicable to this submission (e.g. interaction on a monologue task). */
|
|
136
136
|
notApplicable?: boolean;
|
|
137
|
+
/**
|
|
138
|
+
* How likely each of the criterion's levels was, lowest first, when the
|
|
139
|
+
* grader said: a distribution, whose likeliest level is `band`. Kept on the
|
|
140
|
+
* record as the evidence a routing rule read (`routeGrade`) and a
|
|
141
|
+
* calibration measures (`calibrationReport`).
|
|
142
|
+
*/
|
|
143
|
+
levelProbabilities?: number[];
|
|
144
|
+
}
|
|
145
|
+
/**
|
|
146
|
+
* What one calibration certifies: a model, a prompt revision, a rubric and a
|
|
147
|
+
* target language. A change to any of them is a different grader, measured
|
|
148
|
+
* afresh. Built by `graderConfiguration`.
|
|
149
|
+
*/
|
|
150
|
+
interface GraderConfiguration {
|
|
151
|
+
/** The model's identifier, from the grade's `grader.model`. */
|
|
152
|
+
model: string;
|
|
153
|
+
/** The prompt revision, from the grade's `grader.promptHash`. */
|
|
154
|
+
promptHash: string;
|
|
155
|
+
/** `contentHash` of the item's rubric, levels and descriptors included. */
|
|
156
|
+
rubricHash: string;
|
|
157
|
+
/** The item's `languageTarget`, or `null` when it has none. */
|
|
158
|
+
languageTarget: string | null;
|
|
159
|
+
}
|
|
160
|
+
/**
|
|
161
|
+
* Why `routeGrade` sent a grade to a person, in this order:
|
|
162
|
+
*
|
|
163
|
+
* - `no-calibration` — in `exam`, no calibration report for this grader's exact
|
|
164
|
+
* configuration was supplied: a model's grade counts on a paper of record
|
|
165
|
+
* only once it has been measured;
|
|
166
|
+
* - `calibration-below-policy` — the report misses one of the policy's
|
|
167
|
+
* thresholds, for a criterion or for the total;
|
|
168
|
+
* - `unsure` — a criterion's likeliest level is less likely than the policy's
|
|
169
|
+
* `minLevelProbability`;
|
|
170
|
+
* - `model-asked` — the grader set `requiresHumanReview`;
|
|
171
|
+
* - `low-confidence` — the grader's own `confidence` is `low`, and the policy
|
|
172
|
+
* routes on it;
|
|
173
|
+
* - `audit-sample` — the response is in the audit sample: a person marks it
|
|
174
|
+
* too, without the model's grade, to keep the calibration current.
|
|
175
|
+
*/
|
|
176
|
+
type GradeRoutingReason = 'no-calibration' | 'calibration-below-policy' | 'unsure' | 'model-asked' | 'low-confidence' | 'audit-sample';
|
|
177
|
+
/** Where a grade went, and why: the record an appeal reads. */
|
|
178
|
+
interface GradeRouting {
|
|
179
|
+
/** `model` when its grade counts; `person` when a person must mark it first. */
|
|
180
|
+
to: 'model' | 'person';
|
|
181
|
+
/** Every reason it went to a person, in {@link GradeRoutingReason}'s order; empty when it did not. */
|
|
182
|
+
reasons: GradeRoutingReason[];
|
|
183
|
+
/** The calibration report the decision read, by its hash and size, when one matched. */
|
|
184
|
+
calibration?: {
|
|
185
|
+
reportHash: string;
|
|
186
|
+
pairs: number;
|
|
187
|
+
};
|
|
137
188
|
}
|
|
138
189
|
/** A suggested correction anchored in the learner's own text. */
|
|
139
190
|
interface InlineCorrection {
|
|
@@ -189,6 +240,8 @@ interface GradeRecord {
|
|
|
189
240
|
usage?: GraderUsage;
|
|
190
241
|
/** ISO 8601 timestamp of when the grade was produced. */
|
|
191
242
|
gradedAt?: string;
|
|
243
|
+
/** Where `routeGrade` sent this grade, and why, when it was routed. */
|
|
244
|
+
routing?: GradeRouting;
|
|
192
245
|
}
|
|
193
246
|
//#endregion
|
|
194
247
|
//#region src/types/xapi.d.ts
|
|
@@ -770,6 +823,17 @@ interface FillInTheBlanksData {
|
|
|
770
823
|
/** What an author allows AI to do for this item: see {@link ActivityAiPermissions}. */
|
|
771
824
|
ai?: ActivityAiPermissions;
|
|
772
825
|
}
|
|
826
|
+
/**
|
|
827
|
+
* One level of a rubric criterion: what a response at this level does. Levels
|
|
828
|
+
* run from the lowest to the highest, and a grader judging against them names
|
|
829
|
+
* one.
|
|
830
|
+
*/
|
|
831
|
+
interface WrittenResponseRubricLevel {
|
|
832
|
+
/** A short name, unique within its criterion: "Developing", "B1". */
|
|
833
|
+
label: string;
|
|
834
|
+
/** What a response at this level does, for the grader and the learner. */
|
|
835
|
+
description?: string;
|
|
836
|
+
}
|
|
773
837
|
/** A single criterion within a written-response grading rubric. */
|
|
774
838
|
interface WrittenResponseRubricCriterion {
|
|
775
839
|
/** Criterion name (e.g. "Task achievement", "Grammar range"). */
|
|
@@ -778,6 +842,20 @@ interface WrittenResponseRubricCriterion {
|
|
|
778
842
|
description?: string;
|
|
779
843
|
/** Non-negative weight of this criterion in the overall grade. */
|
|
780
844
|
weight: number;
|
|
845
|
+
/**
|
|
846
|
+
* The criterion's levels, lowest first: 2 to 10, each with a label unique
|
|
847
|
+
* within the criterion once case and spacing are ignored. A grader judging
|
|
848
|
+
* against levels names one, and the criterion scores the level's place on
|
|
849
|
+
* the scale, `index / (levels.length - 1)`: 0 for the lowest, 1 for the
|
|
850
|
+
* highest.
|
|
851
|
+
*
|
|
852
|
+
* Read by the grading functions (`aiGradingRequest`, `gradeFromJudgement`,
|
|
853
|
+
* `calibrationReport`), which report levels they cannot use. In 1.x
|
|
854
|
+
* `validateActivity` does not check it: your own fields pass through it, and
|
|
855
|
+
* a field of yours named `levels` stays valid. The item critic warns about
|
|
856
|
+
* levels the grading functions cannot read.
|
|
857
|
+
*/
|
|
858
|
+
levels?: WrittenResponseRubricLevel[];
|
|
781
859
|
}
|
|
782
860
|
/** Grading rubric attached to a written-response activity. */
|
|
783
861
|
interface WrittenResponseRubric {
|
|
@@ -1232,8 +1310,12 @@ interface DeferredScoringPartial {
|
|
|
1232
1310
|
* a finite number, a `maxScore` of 0 or less, or a score outside 0 to
|
|
1233
1311
|
* `maxScore`). The record is kept on `rejectedGrade`. A real grade is still
|
|
1234
1312
|
* owed, so re-grade the slot: waiting will not bring one.
|
|
1313
|
+
* - `awaiting_human_review` — a model graded the response, and a routing rule
|
|
1314
|
+
* (`routeGrade`) sent it to a person: the grade does not count until a
|
|
1315
|
+
* person marks it. The model's grade is kept on `pendingGrade`, for the
|
|
1316
|
+
* person and for the next calibration.
|
|
1235
1317
|
*/
|
|
1236
|
-
type DeferredReason = 'requires_async_grading' | 'no_response_recorded' | 'grade_rejected';
|
|
1318
|
+
type DeferredReason = 'requires_async_grading' | 'no_response_recorded' | 'grade_rejected' | 'awaiting_human_review';
|
|
1237
1319
|
/**
|
|
1238
1320
|
* The outcome of evaluating a learner response against an activity — the
|
|
1239
1321
|
* union `evaluate()` returns. Unlike {@link ScoringResult}, it can express
|
|
@@ -1266,6 +1348,13 @@ type ItemOutcome = {
|
|
|
1266
1348
|
* is mirrored onto the outcome, and nothing reads it as a grade.
|
|
1267
1349
|
*/
|
|
1268
1350
|
rejectedGrade?: GradeRecord;
|
|
1351
|
+
/**
|
|
1352
|
+
* The model's grade a routing rule held for a person, when `reason` is
|
|
1353
|
+
* `awaiting_human_review`, with the decision on its `routing`. Kept for
|
|
1354
|
+
* the person and for the next calibration; nothing on it is mirrored
|
|
1355
|
+
* onto the outcome, and nothing reads it as a grade.
|
|
1356
|
+
*/
|
|
1357
|
+
pendingGrade?: GradeRecord;
|
|
1269
1358
|
} | {
|
|
1270
1359
|
status: 'graded';
|
|
1271
1360
|
/**
|
|
@@ -1491,6 +1580,220 @@ interface DraftContext {
|
|
|
1491
1580
|
newId: () => string;
|
|
1492
1581
|
}
|
|
1493
1582
|
//#endregion
|
|
1583
|
+
//#region src/types/item-group.d.ts
|
|
1584
|
+
/** What a stimulus primarily is. Drives validation and layout, never scoring. */
|
|
1585
|
+
type StimulusKind = 'text' | 'audio' | 'video' | 'image' | 'mixed';
|
|
1586
|
+
/**
|
|
1587
|
+
* Shared material that several items refer to: a reading passage, a
|
|
1588
|
+
* recording, a chart. Modelled as CONTENT — it lives inside the item group
|
|
1589
|
+
* that carries it — so it works in a lesson quiz, a sequence and an exam
|
|
1590
|
+
* section alike, and needs no blueprint to exist.
|
|
1591
|
+
*
|
|
1592
|
+
* Learner-visible by definition: the point of a stimulus is that the learner
|
|
1593
|
+
* reads or hears it. The one exception is `transcript`, an author asset that
|
|
1594
|
+
* `redactItemGroup` removes.
|
|
1595
|
+
*/
|
|
1596
|
+
interface Stimulus {
|
|
1597
|
+
id: string;
|
|
1598
|
+
kind: StimulusKind;
|
|
1599
|
+
/** Optional heading (a passage title). */
|
|
1600
|
+
title?: string;
|
|
1601
|
+
/**
|
|
1602
|
+
* Plain-text body: the passage itself, or short instructions above media.
|
|
1603
|
+
* Required for `text` and `mixed`.
|
|
1604
|
+
*/
|
|
1605
|
+
body?: string;
|
|
1606
|
+
/**
|
|
1607
|
+
* Optional sanitised rich-HTML sidecar of `body`. Requires `body`, which is
|
|
1608
|
+
* the accessible fallback rendered when no sanitiser is supplied.
|
|
1609
|
+
*/
|
|
1610
|
+
bodyHtml?: string;
|
|
1611
|
+
/** The recording, video or image. Required for `audio`, `video`, `image` and `mixed`. */
|
|
1612
|
+
media?: ActivityMedia;
|
|
1613
|
+
/**
|
|
1614
|
+
* Author-only transcript of `media` — for item generation and grading,
|
|
1615
|
+
* never shown to the learner. Removed by `redactItemGroup`.
|
|
1616
|
+
*/
|
|
1617
|
+
transcript?: string;
|
|
1618
|
+
/** BCP 47 language tag of the material, when it differs from the items'. */
|
|
1619
|
+
locale?: string;
|
|
1620
|
+
/** Source credit, shown to the learner after the material. */
|
|
1621
|
+
attribution?: string;
|
|
1622
|
+
}
|
|
1623
|
+
/**
|
|
1624
|
+
* A quiz inside an interactive video: one moment of the video, and the
|
|
1625
|
+
* questions shown there. The video pauses when playback reaches `at`, and the
|
|
1626
|
+
* questions are shown one at a time, in `itemIds` order.
|
|
1627
|
+
*/
|
|
1628
|
+
interface TimelineCue {
|
|
1629
|
+
/** Unique within the timeline. Names the quiz in events, the contents panel and drafts. */
|
|
1630
|
+
id: string;
|
|
1631
|
+
/**
|
|
1632
|
+
* Seconds from the start of the video: finite and 0 or more. The SDK never
|
|
1633
|
+
* reads the video, so it cannot check this against the duration: a quiz at
|
|
1634
|
+
* or past the end opens when the video ends.
|
|
1635
|
+
*/
|
|
1636
|
+
at: number;
|
|
1637
|
+
/**
|
|
1638
|
+
* `id`s of items in this group, in the order the quiz shows them. Non-empty.
|
|
1639
|
+
* Every item of the group belongs to exactly one quiz.
|
|
1640
|
+
*/
|
|
1641
|
+
itemIds: string[];
|
|
1642
|
+
/** Optional heading shown above the questions. At most 120 characters. */
|
|
1643
|
+
title?: string;
|
|
1644
|
+
/**
|
|
1645
|
+
* Every question must be answered (practice) or submitted (exam) before
|
|
1646
|
+
* playback may pass `at`. Default false.
|
|
1647
|
+
*/
|
|
1648
|
+
required?: boolean;
|
|
1649
|
+
}
|
|
1650
|
+
/** A titled section of the video. */
|
|
1651
|
+
interface TimelineChapter {
|
|
1652
|
+
/** Seconds from the start: finite, 0 or more, strictly increasing across the list. */
|
|
1653
|
+
at: number;
|
|
1654
|
+
/** Non-empty after trimming; at most 120 characters. */
|
|
1655
|
+
title: string;
|
|
1656
|
+
}
|
|
1657
|
+
/**
|
|
1658
|
+
* The arrangement that turns an item group with a video stimulus into an
|
|
1659
|
+
* interactive video: when each quiz opens, the video's chapters, and how far
|
|
1660
|
+
* ahead a learner may seek.
|
|
1661
|
+
*
|
|
1662
|
+
* It lives on the container rather than inside `stimulus` because it describes
|
|
1663
|
+
* how THESE questions are arranged over the material, not the material itself.
|
|
1664
|
+
*/
|
|
1665
|
+
interface MediaTimeline {
|
|
1666
|
+
cues: TimelineCue[];
|
|
1667
|
+
chapters?: TimelineChapter[];
|
|
1668
|
+
/**
|
|
1669
|
+
* `free` (default): seek anywhere. `no-skip-ahead`: rewind freely, never past
|
|
1670
|
+
* the furthest point reached. Either way, playback never passes a `required`
|
|
1671
|
+
* quiz that is not finished.
|
|
1672
|
+
*/
|
|
1673
|
+
navigation?: 'free' | 'no-skip-ahead';
|
|
1674
|
+
}
|
|
1675
|
+
/**
|
|
1676
|
+
* Where a learner stands in an interactive video, stored by the host so the
|
|
1677
|
+
* video can resume. Kept apart from `AttemptState`, which holds answers by slot
|
|
1678
|
+
* and drops fields it does not know. Read it back through
|
|
1679
|
+
* `readMediaProgress`, never directly.
|
|
1680
|
+
*/
|
|
1681
|
+
interface MediaProgress {
|
|
1682
|
+
progressVersion: '1.0';
|
|
1683
|
+
/** Seconds: where playback last stood. */
|
|
1684
|
+
at: number;
|
|
1685
|
+
/**
|
|
1686
|
+
* Seconds: the furthest point reached. Decides how far `no-skip-ahead` lets
|
|
1687
|
+
* the learner seek, and how much of the transcript it shows.
|
|
1688
|
+
*/
|
|
1689
|
+
furthest: number;
|
|
1690
|
+
}
|
|
1691
|
+
/**
|
|
1692
|
+
* One stimulus serving several items. Two rules, both taken from observed
|
|
1693
|
+
* failures: a group is SHUFFLE-ATOMIC (shuffling a sequence moves the group
|
|
1694
|
+
* as one block — interleaving two passages' questions is the defect), and its
|
|
1695
|
+
* stimulus is presented persistently alongside every item, never behind a
|
|
1696
|
+
* toggle the learner must reopen per question.
|
|
1697
|
+
*
|
|
1698
|
+
* Generic over the item type so one shape describes a group of full activity
|
|
1699
|
+
* data (authoring, server) and a group of `redact()` projections (client)
|
|
1700
|
+
* without a cast at every boundary.
|
|
1701
|
+
*/
|
|
1702
|
+
interface ItemGroup<TItem = ActivityData> {
|
|
1703
|
+
schemaVersion: '1.0';
|
|
1704
|
+
type: 'item-group';
|
|
1705
|
+
id: string;
|
|
1706
|
+
title?: string;
|
|
1707
|
+
/**
|
|
1708
|
+
* Stable identity for this entry's slots, independent of where it sits in
|
|
1709
|
+
* the array. See {@link SequenceSlot.slotId}: without one, inserting a
|
|
1710
|
+
* question above this group re-maps every slot id beneath it, and stored
|
|
1711
|
+
* grades quietly start naming different questions.
|
|
1712
|
+
*/
|
|
1713
|
+
slotKey?: string;
|
|
1714
|
+
stimulus: Stimulus;
|
|
1715
|
+
/**
|
|
1716
|
+
* The items, in authored order. Non-empty; ids unique within the group; no
|
|
1717
|
+
* nested groups.
|
|
1718
|
+
*
|
|
1719
|
+
* An item may declare its own `slotKey`, for the same reason an entry can:
|
|
1720
|
+
* it pins the item's identity within the group (`"reading.q1"` rather than
|
|
1721
|
+
* `"reading.0"`), so inserting a question into a published group does not
|
|
1722
|
+
* re-map the ones after it.
|
|
1723
|
+
*/
|
|
1724
|
+
items: (TItem & {
|
|
1725
|
+
slotKey?: string;
|
|
1726
|
+
})[];
|
|
1727
|
+
/**
|
|
1728
|
+
* `none` (default) keeps authored order; `within-group` shuffles the items
|
|
1729
|
+
* among themselves under the sequence seed. Either way the group stays one
|
|
1730
|
+
* contiguous block.
|
|
1731
|
+
*/
|
|
1732
|
+
shuffle?: 'none' | 'within-group';
|
|
1733
|
+
/**
|
|
1734
|
+
* Makes the group an interactive video: the stimulus must be a video, every
|
|
1735
|
+
* item must be one of `INTERACTIVE_VIDEO_ITEM_TYPES`, and every item belongs
|
|
1736
|
+
* to exactly one quiz. Items are then presented in quiz order, never
|
|
1737
|
+
* shuffled. An older lk-core that does not know this field presents the same
|
|
1738
|
+
* items as an ordinary video testlet, with the same slots and grades.
|
|
1739
|
+
*/
|
|
1740
|
+
timeline?: MediaTimeline;
|
|
1741
|
+
}
|
|
1742
|
+
/**
|
|
1743
|
+
* What a sequence is made of: loose activities and item groups, in authored
|
|
1744
|
+
* order.
|
|
1745
|
+
*
|
|
1746
|
+
* A plain activity may carry `slotKey` here even though no activity SCHEMA
|
|
1747
|
+
* declares one, because a slot key describes an item's PLACE in a paper, not
|
|
1748
|
+
* its content — the same question keeps its own id in every paper it appears
|
|
1749
|
+
* in. Putting it on the entry rather than on the activity is what lets it be
|
|
1750
|
+
* authored without every activity type having to know about assessment
|
|
1751
|
+
* assembly. See {@link SequenceSlot.slotId}.
|
|
1752
|
+
*/
|
|
1753
|
+
type SequenceEntry<TItem = ActivityData> = (TItem & {
|
|
1754
|
+
slotKey?: string;
|
|
1755
|
+
}) | ItemGroup<TItem>;
|
|
1756
|
+
/** The group a presented slot belongs to. */
|
|
1757
|
+
interface SequenceSlotGroup {
|
|
1758
|
+
id: string;
|
|
1759
|
+
title?: string;
|
|
1760
|
+
stimulus: Stimulus;
|
|
1761
|
+
/** 0-based position of this slot within the group's PRESENTED order. */
|
|
1762
|
+
position: number;
|
|
1763
|
+
/** Number of slots in the group. */
|
|
1764
|
+
size: number;
|
|
1765
|
+
/** The group's timeline, when the group is an interactive video. */
|
|
1766
|
+
timeline?: MediaTimeline;
|
|
1767
|
+
/** The quiz this slot's item sits in, when the group is an interactive video. */
|
|
1768
|
+
cue?: TimelineCue;
|
|
1769
|
+
}
|
|
1770
|
+
/** One presented position in a flattened sequence. */
|
|
1771
|
+
interface SequenceSlot<TItem = ActivityData> {
|
|
1772
|
+
/**
|
|
1773
|
+
* Identity of the slot within the sequence definition — unique, and stable
|
|
1774
|
+
* under shuffling. Feed it to `composeAssessmentScore` as `slotId`.
|
|
1775
|
+
*
|
|
1776
|
+
* By default it is derived from the AUTHORED position (`"2"` for the third
|
|
1777
|
+
* top-level entry; `"2.1"` for the second item of that entry when it is a
|
|
1778
|
+
* group), so the same activity can appear in two entries and still be two
|
|
1779
|
+
* slots.
|
|
1780
|
+
*
|
|
1781
|
+
* **A positional id is only valid against one version of the entries
|
|
1782
|
+
* array.** Insert a question at the top of a published paper and every id
|
|
1783
|
+
* below it shifts: rows stored as `"3"` now name what used to be entry 2,
|
|
1784
|
+
* and a re-grade or a review render pairs each response with the wrong
|
|
1785
|
+
* question — silently, because the ids still look valid. For any content
|
|
1786
|
+
* whose slot ids you persist, give the entries an explicit `slotKey`; it is
|
|
1787
|
+
* used verbatim here and survives insertion, deletion and re-ordering.
|
|
1788
|
+
*/
|
|
1789
|
+
slotId: string;
|
|
1790
|
+
/** 0-based PRESENTED position, after shuffling. */
|
|
1791
|
+
index: number;
|
|
1792
|
+
activity: TItem;
|
|
1793
|
+
/** Present when the slot comes from an item group. */
|
|
1794
|
+
group?: SequenceSlotGroup;
|
|
1795
|
+
}
|
|
1796
|
+
//#endregion
|
|
1494
1797
|
//#region src/types/ai.d.ts
|
|
1495
1798
|
/**
|
|
1496
1799
|
* What an author allows AI to do for one item. Absent, or a feature left out,
|
|
@@ -1629,6 +1932,46 @@ interface AiDictationFacts extends AiFactsBase {
|
|
|
1629
1932
|
* learner saw it, what they answered, and — part by part — the SDK's verdict.
|
|
1630
1933
|
*/
|
|
1631
1934
|
type AiItemFacts = AiMultipleChoiceFacts | AiFillInTheBlanksFacts | AiGapSelectFacts | AiDictationFacts;
|
|
1935
|
+
/**
|
|
1936
|
+
* The item group a question sits in, as a renderer holds it: an `ItemGroup`,
|
|
1937
|
+
* a redacted one, a sequence slot's `group`, or a host's own object with the
|
|
1938
|
+
* same two fields. Structural, and read defensively, like
|
|
1939
|
+
* {@link AiActivityInput}: a group whose material cannot be read gives none.
|
|
1940
|
+
*/
|
|
1941
|
+
interface AiGroupInput {
|
|
1942
|
+
readonly title?: unknown;
|
|
1943
|
+
readonly stimulus?: unknown;
|
|
1944
|
+
}
|
|
1945
|
+
/**
|
|
1946
|
+
* What a model is told about the material of the group a question sits in:
|
|
1947
|
+
* what the learner reads and sees beside the question — a passage, or the
|
|
1948
|
+
* instructions a run of questions shares. Never a media address, and never
|
|
1949
|
+
* the author-only transcript: the same facts whether the group is whole or
|
|
1950
|
+
* redacted.
|
|
1951
|
+
*/
|
|
1952
|
+
interface AiMaterialFacts {
|
|
1953
|
+
/** What the material primarily is. */
|
|
1954
|
+
kind: StimulusKind;
|
|
1955
|
+
/** The material's heading, or the group's title when it has none. */
|
|
1956
|
+
title?: string;
|
|
1957
|
+
/**
|
|
1958
|
+
* The text beside the questions, as plain text: the passage, or the
|
|
1959
|
+
* instructions above a recording or image. Cut past `AI_MATERIAL_MAX_LENGTH`
|
|
1960
|
+
* code points, at a word boundary where there is one.
|
|
1961
|
+
*/
|
|
1962
|
+
text?: string;
|
|
1963
|
+
/** Present when `text` was cut: the model is given only its start. */
|
|
1964
|
+
truncated?: true;
|
|
1965
|
+
/** The recording, video or image, without its address. An image's `alt` says what it shows. */
|
|
1966
|
+
media?: {
|
|
1967
|
+
type: ActivityMedia['type'];
|
|
1968
|
+
alt?: string;
|
|
1969
|
+
};
|
|
1970
|
+
/** The source credit the learner sees after the material. */
|
|
1971
|
+
attribution?: string;
|
|
1972
|
+
/** The language of the material, when the author gave one. */
|
|
1973
|
+
locale?: string;
|
|
1974
|
+
}
|
|
1632
1975
|
/**
|
|
1633
1976
|
* Asks for an explanation of a graded answer. Sent after the SDK has graded
|
|
1634
1977
|
* it, so `grade` is always present, and an explanation that contradicts
|
|
@@ -1638,6 +1981,8 @@ interface AiExplanationRequest {
|
|
|
1638
1981
|
feature: 'explanation';
|
|
1639
1982
|
facts: AiItemFacts;
|
|
1640
1983
|
grade: AiGrade;
|
|
1984
|
+
/** The material of the group the question sits in; absent outside a group. */
|
|
1985
|
+
material?: AiMaterialFacts;
|
|
1641
1986
|
/** The language to answer in: the learner's interface language, when known. */
|
|
1642
1987
|
learnerLocale?: string;
|
|
1643
1988
|
}
|
|
@@ -1653,6 +1998,8 @@ interface AiHintRequest {
|
|
|
1653
1998
|
hintNumber: number;
|
|
1654
1999
|
/** The hints already shown for this item, oldest first. */
|
|
1655
2000
|
previousHints: string[];
|
|
2001
|
+
/** The material of the group the question sits in; absent outside a group. */
|
|
2002
|
+
material?: AiMaterialFacts;
|
|
1656
2003
|
learnerLocale?: string;
|
|
1657
2004
|
}
|
|
1658
2005
|
/** What produced an AI text, for the record a host keeps. */
|
|
@@ -1693,8 +2040,15 @@ interface AiTextResult {
|
|
|
1693
2040
|
* a word the engine did not mark, or on a sound it did not report.
|
|
1694
2041
|
* `contradicts-item` is a critique of an item that points at a field the item
|
|
1695
2042
|
* does not have, or quotes words that field does not contain.
|
|
1696
|
-
|
|
1697
|
-
|
|
2043
|
+
* `misses-criteria` is a grade that leaves a rubric criterion out, renames
|
|
2044
|
+
* one, judges one twice, or calls one not applicable: judging fewer criteria
|
|
2045
|
+
* is judging a different task, and the total would be renormalised over the
|
|
2046
|
+
* rest. `out-of-scale` is a judgement off its criterion's scale: a level the
|
|
2047
|
+
* criterion does not have, a score outside 0 to 1, or level probabilities that
|
|
2048
|
+
* are not a distribution over its levels, or whose likeliest level is not the
|
|
2049
|
+
* one chosen.
|
|
2050
|
+
*/
|
|
2051
|
+
type AiRefusal = 'malformed' | 'empty' | 'too-long' | 'contradicts-grade' | 'reveals-answer' | 'misquotes-answer' | 'contradicts-marks' | 'contradicts-item' | 'misses-criteria' | 'out-of-scale';
|
|
1698
2052
|
/** One criterion of a written response's rubric, as the author wrote it. */
|
|
1699
2053
|
interface AiRubricCriterionFact {
|
|
1700
2054
|
name: string;
|
|
@@ -1735,6 +2089,11 @@ interface AiWritingFeedbackRequest {
|
|
|
1735
2089
|
draftNumber: number;
|
|
1736
2090
|
/** The text of the feedback already shown on earlier drafts, oldest first. */
|
|
1737
2091
|
previousFeedback: string[];
|
|
2092
|
+
/**
|
|
2093
|
+
* The material of the group the task sits in — the text a summary is of —
|
|
2094
|
+
* absent outside a group.
|
|
2095
|
+
*/
|
|
2096
|
+
material?: AiMaterialFacts;
|
|
1738
2097
|
/** The language to write in: the learner's interface language, when known. */
|
|
1739
2098
|
learnerLocale?: string;
|
|
1740
2099
|
}
|
|
@@ -1800,6 +2159,104 @@ interface AiWritingFeedback {
|
|
|
1800
2159
|
provenance?: AiProvenance;
|
|
1801
2160
|
usage?: GraderUsage;
|
|
1802
2161
|
}
|
|
2162
|
+
/** One criterion of the rubric a model grades against, as the author wrote it. */
|
|
2163
|
+
interface AiGradingCriterionFact {
|
|
2164
|
+
name: string;
|
|
2165
|
+
description?: string;
|
|
2166
|
+
weight: number;
|
|
2167
|
+
/**
|
|
2168
|
+
* The levels to choose from, lowest first, as the author wrote them; `null`
|
|
2169
|
+
* when the criterion is judged on a score from 0 to 1.
|
|
2170
|
+
*/
|
|
2171
|
+
levels: {
|
|
2172
|
+
label: string;
|
|
2173
|
+
description?: string;
|
|
2174
|
+
}[] | null;
|
|
2175
|
+
}
|
|
2176
|
+
/**
|
|
2177
|
+
* What a model is told about a submitted written response it grades: the task
|
|
2178
|
+
* as the learner saw it, the response verbatim, and the rubric with its levels.
|
|
2179
|
+
*/
|
|
2180
|
+
interface AiGradingFacts {
|
|
2181
|
+
activityType: 'written-response';
|
|
2182
|
+
activityId: string;
|
|
2183
|
+
title: string;
|
|
2184
|
+
/** The language the item is written in, when the author gave one. */
|
|
2185
|
+
locale?: string;
|
|
2186
|
+
prompt: string;
|
|
2187
|
+
/** The response, exactly as submitted. Every correction quotes it. */
|
|
2188
|
+
text: string;
|
|
2189
|
+
/** Recomputed with `countWords`, as the grader counts it. */
|
|
2190
|
+
wordCount: number;
|
|
2191
|
+
minWords: number;
|
|
2192
|
+
maxWords: number;
|
|
2193
|
+
withinWordBounds: boolean;
|
|
2194
|
+
/** Every criterion of the item's rubric, in its order. */
|
|
2195
|
+
rubric: AiGradingCriterionFact[];
|
|
2196
|
+
/** The target language and level, when the author gave one (e.g. `"en-B1"`). */
|
|
2197
|
+
languageTarget?: string;
|
|
2198
|
+
}
|
|
2199
|
+
/**
|
|
2200
|
+
* Asks a model to grade a submitted written response. Built on the server,
|
|
2201
|
+
* from the whole item: grading needs the rubric, never the learner's view.
|
|
2202
|
+
*/
|
|
2203
|
+
interface AiGradingRequest {
|
|
2204
|
+
feature: 'grading';
|
|
2205
|
+
facts: AiGradingFacts;
|
|
2206
|
+
/** The material of the group the task sits in; absent outside a group. */
|
|
2207
|
+
material?: AiMaterialFacts;
|
|
2208
|
+
/** The language to write comments and feedback in, when known. */
|
|
2209
|
+
learnerLocale?: string;
|
|
2210
|
+
}
|
|
2211
|
+
/**
|
|
2212
|
+
* Why `aiGradingRequest` built no request:
|
|
2213
|
+
*
|
|
2214
|
+
* - `not-written-response` — the item is another type;
|
|
2215
|
+
* - `redacted` — a `redact()` projection: grading is done on the server, from
|
|
2216
|
+
* the whole item;
|
|
2217
|
+
* - `no-rubric` — no rubric, or a criterion without a name and a weight: a
|
|
2218
|
+
* model has nothing to be held to;
|
|
2219
|
+
* - `duplicate-criteria` — two criteria with one name once case and spacing are
|
|
2220
|
+
* ignored: a model cannot judge them apart (`path` names the later one);
|
|
2221
|
+
* - `unreadable-levels` — a criterion's `levels` are there but cannot be used
|
|
2222
|
+
* (`path` names them; the item critic's `wr_levels_unreadable` says why);
|
|
2223
|
+
* - `empty-response` — nothing was written, so there is nothing to judge.
|
|
2224
|
+
*/
|
|
2225
|
+
type AiGradingRequestProblem = 'not-written-response' | 'redacted' | 'no-rubric' | 'duplicate-criteria' | 'unreadable-levels' | 'empty-response';
|
|
2226
|
+
/** A model's judgement of one criterion, as `checkAiGrading` accepted it. */
|
|
2227
|
+
interface AiGradedCriterion {
|
|
2228
|
+
/** The criterion's name, as the author wrote it. */
|
|
2229
|
+
name: string;
|
|
2230
|
+
/** The level chosen, as the author labelled it, on a criterion with levels. */
|
|
2231
|
+
level?: string;
|
|
2232
|
+
/**
|
|
2233
|
+
* From 0 to 1: the level's place on the scale, `index / (levels - 1)`, or the
|
|
2234
|
+
* model's score on a criterion without levels.
|
|
2235
|
+
*/
|
|
2236
|
+
score: number;
|
|
2237
|
+
/** How likely each level is, lowest first, when the model said: a distribution. */
|
|
2238
|
+
probabilities?: number[];
|
|
2239
|
+
comment?: string;
|
|
2240
|
+
}
|
|
2241
|
+
/**
|
|
2242
|
+
* A model's grade of a written response as `checkAiGrading` accepted it: every
|
|
2243
|
+
* criterion of the rubric judged, on its own scale. The total is not here —
|
|
2244
|
+
* `gradeFromJudgement` computes it.
|
|
2245
|
+
*/
|
|
2246
|
+
interface AiGradingJudgement {
|
|
2247
|
+
/** Every criterion of the rubric, once, in the rubric's order. */
|
|
2248
|
+
criteria: AiGradedCriterion[];
|
|
2249
|
+
/** Narrative feedback addressed to the learner. */
|
|
2250
|
+
feedback: string | null;
|
|
2251
|
+
/** Corrections, each anchored in the response, as on feedback on writing. */
|
|
2252
|
+
corrections: InlineCorrection[];
|
|
2253
|
+
/** How the model reached its verdict; for the record, never shown. */
|
|
2254
|
+
rationale?: string;
|
|
2255
|
+
/** The model asked for a person to mark this response. */
|
|
2256
|
+
requiresHumanReview: boolean;
|
|
2257
|
+
provenance?: AiProvenance;
|
|
2258
|
+
usage?: GraderUsage;
|
|
2259
|
+
}
|
|
1803
2260
|
/** One sound of a word, as the engine reported it. */
|
|
1804
2261
|
interface AiSoundFact {
|
|
1805
2262
|
/** The sound expected, in the assessment's phoneme alphabet. */
|
|
@@ -2150,5 +2607,5 @@ interface AiVideoDraft {
|
|
|
2150
2607
|
findings: ItemFinding[];
|
|
2151
2608
|
}
|
|
2152
2609
|
//#endregion
|
|
2153
|
-
export {
|
|
2154
|
-
//# sourceMappingURL=ai-
|
|
2610
|
+
export { AiVerdict as $, MultipleChoiceData as $t, AiGapSelectFacts as A, XAPIVerbObject as An, ActivityType as At, AiHintRequest as B, InlineCorrection as Bn, FillInTheBlanksLearnerResponse as Bt, AiDraftsCall as C, XAPIContext as Cn, ItemFinding as Ct, AiFeature as D, XAPIResult as Dn, ActivityFeedback as Dt, AiExplanationRequest as E, XAPIObject as En, ActivityDataMap as Et, AiGradingFacts as F, Grader as Fn, DictationEquivalence as Ft, AiProvenance as G, GapSelectLearnerResponse as Gt, AiMaterialFacts as H, TextMatchResult as Hn, GapSelectChoice as Ht, AiGradingJudgement as I, GraderConfiguration as In, DictationLearnerResponse as It, AiRefusal as J, ItemOutcome as Jt, AiReadingFacts as K, InteractionEvent as Kt, AiGradingRequest as L, GraderKind as Ln, DictationSlowMedia as Lt, AiGrade as M, GradeRecord as Mn, DeferredReason as Mt, AiGradedCriterion as N, GradeRouting as Nn, DeferredScoringPartial as Nt, AiFillInTheBlanksFacts as O, XAPIScore as On, ActivityMedia as Ot, AiGradingCriterionFact as P, GradeRoutingReason as Pn, DictationData as Pt, AiTextResult as Q, MediaTrack as Qt, AiGradingRequestProblem as R, GraderUsage as Rn, DictationTolerance as Rt, AiDrafts as S, XAPIConfig as Sn, DraftValidationResult as St, AiDraftsRun as T, XAPIError as Tn, ActivityData as Tt, AiMultipleChoiceFacts as U, levenshteinDistance as Un, GapSelectData as Ut, AiItemFacts as V, TextMatchPolicy as Vn, GapSelectBank as Vt, AiOptionFact as W, matchText as Wn, GapSelectGap as Wt, AiSoundFact as X, LearnerResponseMap as Xt, AiRubricCriterionFact as Y, LearnerResponse as Yt, AiSupportedActivityType as Z, MediaPlaybackPolicy as Zt, AiDraftCaption as _, WrittenResponseLearnerResponse as _n, DraftComplete as _t, AiCoachingRequest as a, ReadAloudDimension as an, AiWritingFeedbackRequest as at, AiDraftSource as b, WrittenResponseRubricLevel as bn, DraftNotComplete as bt, AiCriterionJudgement as c, ReadAloudSlowMedia as cn, MediaProgress as ct, AiCritiqueFinding as d, ScoringDetail as dn, SequenceSlot as dt, MultipleChoiceLearnerResponse as en, AiVideoDraft as et, AiCritiqueFindingResult as f, ScoringOutcome as fn, SequenceSlotGroup as ft, AiDictationFacts as g, WrittenResponseData as gn, TimelineCue as gt, AiCritiqueResult as h, ValidationResult as hn, TimelineChapter as ht, AiCoaching as i, ReadAloudData as in, AiWritingFeedback as it, AiGeneratedDraft as j, CriterionScore as jn, BlankConfig as jt, AiGapFact as k, XAPIStatement as kn, ActivityResult as kt, AiCritique as l, RecordingBounds as ln, MediaTimeline as lt, AiCritiqueRequest as m, ValidationError as mn, StimulusKind as mt, AiActivityInput as n, MultipleChoiceOptionMedia as nn, AiWritingCorrection as nt, AiCoachingResult as o, ReadAloudDimensionWeight as on, AiWritingFeedbackResult as ot, AiCritiqueKind as p, ScoringResult as pn, Stimulus as pt, AiReadingWordFact as q, InteractionKind as qt, AiBlankFact as r, NativeControlHint as rn, AiWritingFacts as rt, AiCoachingWord as s, ReadAloudLearnerResponse as sn, ItemGroup as st, ActivityAiPermissions as t, MultipleChoiceOption as tn, AiWordFact as tt, AiCritiqueField as u, RecordingRef as un, SequenceEntry as ut, AiDraftProblem as v, WrittenResponseRubric as vn, DraftContext as vt, AiDraftsRequest as w, XAPIContextActivities as wn, ItemFindingSeverity as wt, AiDraftType as x, XAPIActor as xn, DraftSeverity as xt, AiDraftSettings as y, WrittenResponseRubricCriterion as yn, DraftIssue as yt, AiGroupInput as z, GradingState as zn, FillInTheBlanksData as zt };
|
|
2611
|
+
//# sourceMappingURL=ai-BYryFkF9.d.cts.map
|