Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
50 changes: 44 additions & 6 deletions src/loader/babel.ts
Original file line number Diff line number Diff line change
Expand Up @@ -216,6 +216,10 @@ const babelPluginUntyped: PluginItem = function (

export default babelPluginUntyped;

function isExampleBlock(line = "") {
return line.startsWith("@example");
}

function containsIncompleteCodeblock(line = "") {
const codeDelimiters = line
.split("\n")
Expand All @@ -225,17 +229,51 @@ function containsIncompleteCodeblock(line = "") {

function clumpLines(lines: string[], delimiters = [" "], separator = " ") {
const clumps: string[] = [];

while (lines.length > 0) {
const line = lines.shift()!;
if (
(line && !delimiters.includes(line[0]) && clumps.at(-1)) ||
containsIncompleteCodeblock(clumps.at(-1))
) {
const line = lines.shift() as string;

// If there is no previous clump, create one
if (!clumps.at(-1)) {
clumps.push(line);
continue;
}

// If the line starts with a delimiter, create a new clump
if (delimiters.includes(line[0])) {
clumps.push(line);
continue;
}

// If the previous clump is an example block, append to it
if (isExampleBlock(clumps.at(-1))) {
clumps[clumps.length - 1] += separator + line;
continue;
}

// If the previous clump is an incomplete code block, append to it
if (containsIncompleteCodeblock(clumps.at(-1))) {
clumps[clumps.length - 1] += separator + line;
} else {
continue;
}

// If the line starts with a code block delimiter, create a new clump
// We need to check this after the previous check to avoid creating a new clump for an incomplete code block
if (line.startsWith("```")) {
clumps.push(line);
continue;
}

// Append to the previous clump
if (line) {
clumps[clumps.length - 1] += separator + line;
continue;
}

// If the line is empty, create a new clump
clumps.push(line);
}

return clumps.filter(Boolean);
}

Expand Down
56 changes: 56 additions & 0 deletions test/transform.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -326,6 +326,62 @@ describe("transform (jsdoc)", () => {
});
});

it("does not split example without codeblock", () => {
const result = transform(`
export default {
/**
* @note This is a note.
* @example
* export default secretNumber = 42
*
* export default nothing = null
* @type {'src' | 'root'}
*/
srcDir: 'src'
}
`);
expectCodeToMatch(result, /export default ([\S\s]*)$/, {
srcDir: {
$default: "src",
$schema: {
title: "",
tsType: "'src' | 'root'",
description: "",
tags: [
"@note This is a note.",
"@example\nexport default secretNumber = 42\n\nexport default nothing = null",
],
},
},
});
});

it("supports codeblock without `@example`", () => {
const result = transform(`
export default {
/**
* @note This is a note.
* \`\`\`js
* export default secret
* \`\`\`
* @type {'src' | 'root'}
*/
srcDir: 'src'
}
`);
expectCodeToMatch(result, /export default ([\S\s]*)$/, {
srcDir: {
$default: "src",
$schema: {
title: "",
tsType: "'src' | 'root'",
description: "",
tags: ["@note This is a note.", "```js\nexport default secret\n```"],
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shouldn't inline code go into the description?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's a good question. I don't know. What do you think? πŸ€·β€β™‚οΈ

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

But because there is the @, the title and description are the content above

see https://github.com/unjs/untyped/blob/main/src/loader/babel.ts#L253

},
},
});
});

it("correctly parses type assertion", () => {
const result = transform(`
import type { InputObject } from 'untyped'
Expand Down
Loading