Skip to content

Commit ed5a530

Browse files
committed
Added support for multiblock questions / answers in Markdown parser
See interpreter/Readme and unit tests for documentation.
1 parent 9039f59 commit ed5a530

File tree

6 files changed

+506
-239
lines changed

6 files changed

+506
-239
lines changed

packages/interpreter/Readme.md

Lines changed: 28 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,34 @@ For example, here's an excerpt of some notes I wrote as I was studying Service W
4646
>
4747
> A. Two.
4848
49-
The empty line between the question and answer is optional. The question and answer cannot currently span multiple paragraphs: the paragraph including `Q. ` or `A. ` is extracted as that field.
49+
The empty line between the question and answer is optional. So you can also write it like this, with a newline separating the question and answer.
50+
51+
> Q. How many dimensions are in a qubit's vector space? \
52+
> A. Two.
53+
54+
If you'd like to make the question or answer field span multiple Markdown blocks, add a newline after the `Q.` or `A.` prefix, like this:
55+
56+
```
57+
Q.
58+
What is this a picture of?
59+
60+
1. Apples
61+
2. Bananas
62+
3. Pears
63+
64+
A.
65+
Apples
66+
67+
68+
Q. How to do the hokey pokey?
69+
A.
70+
1. You put your right foot in
71+
2. You put your right foot out
72+
3. You put your right foot in
73+
4. And you shake it all about
74+
```
75+
76+
As shown above, you can mix and match the "multi-block" style with the "single-line" style. In "multi-block" mode, all the content after the prefix will be included in the field, until the next question, heading, or horizontal rule (`---`).
5077

5178
#### Creating cloze deletion prompts
5279

packages/interpreter/src/interpreters/markdown/MarkdownInterpreter.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@ import {
1111
IngestibleSource,
1212
IngestibleSourceIdentifier,
1313
} from "@withorbit/ingester";
14-
import mdast, * as Mdast from "mdast";
14+
import * as Mdast from "mdast";
1515
import { selectAll } from "unist-util-select";
1616
import { Hasher } from "../../hasher/hasher.js";
1717
import { InterpretableFile, Interpreter } from "../../interpreter.js";
@@ -78,13 +78,13 @@ function convertInterpreterPromptToIngestible(prompt: Prompt): TaskSpec {
7878
type: TaskContentType.QA,
7979
body: {
8080
text: processor
81-
.stringify(prompt.question as unknown as mdast.Root)
81+
.stringify({ type: "root", children: prompt.question })
8282
.trimEnd(),
8383
attachments: [],
8484
},
8585
answer: {
8686
text: processor
87-
.stringify(prompt.answer as unknown as mdast.Root)
87+
.stringify({ type: "root", children: prompt.answer })
8888
.trimEnd(),
8989
attachments: [],
9090
},

packages/interpreter/src/interpreters/markdown/markdown.test.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -68,12 +68,12 @@ test("cloze in backlink section", () => {
6868
expect(prompts).toHaveLength(0);
6969
});
7070

71-
test("QA prompt in blockquote", () => {
71+
test("QA prompts aren't recognized in blockquote", () => {
7272
const prompts = getPrompts(`# Heading
7373
7474
> Q. Test.
7575
> A. Answer.
7676
`);
7777

78-
expect(prompts).toHaveLength(1);
78+
expect(prompts).toHaveLength(0);
7979
});

packages/interpreter/src/interpreters/markdown/markdown.ts

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -26,10 +26,10 @@ export interface ClozePrompt extends JsonMap {
2626
}
2727

2828
export const qaPromptType = "qaPrompt";
29-
export interface QAPrompt extends JsonMap {
29+
export interface QAPrompt {
3030
type: typeof qaPromptType;
31-
question: mdast.RootContent & JsonMap;
32-
answer: mdast.RootContent & JsonMap;
31+
question: mdast.RootContent[];
32+
answer: mdast.RootContent[];
3333
}
3434

3535
export type Prompt = ClozePrompt | QAPrompt;
@@ -43,8 +43,8 @@ export interface ClozePromptNode extends unist.Node {
4343
export const qaPromptNodeType = "qaPrompt";
4444
export interface QAPromptNode extends unist.Node {
4545
type: typeof qaPromptNodeType;
46-
question: mdast.RootContent;
47-
answer: mdast.RootContent;
46+
question: mdast.RootContent[];
47+
answer: mdast.RootContent[];
4848
}
4949

5050
type NodeWithParent = mdast.Nodes & {
@@ -104,8 +104,8 @@ export function findAllPrompts(tree: mdast.Root): Prompt[] {
104104
const qaPromptNode = n as QAPromptNode;
105105
const qaPrompt: QAPrompt = {
106106
type: "qaPrompt",
107-
question: qaPromptNode.question as mdast.RootContent & JsonMap,
108-
answer: qaPromptNode.answer as mdast.RootContent & JsonMap,
107+
question: qaPromptNode.question,
108+
answer: qaPromptNode.answer,
109109
};
110110
return qaPrompt;
111111
});

0 commit comments

Comments
 (0)