Add heredoc support for cURL JSON body (#3790)

This commit is contained in:
Nolann B.
2025-11-10 11:20:53 +01:00
committed by GitHub
parent 1d92dc1350
commit b4a021a192
2 changed files with 49 additions and 4 deletions
+5
View File
@@ -0,0 +1,5 @@
---
'@gitbook/react-openapi': patch
---
Add heredoc support for cURL JSON body
+44 -4
View File
@@ -81,8 +81,6 @@ ${headerString}${bodyString}`;
label: 'cURL',
syntax: 'bash',
generate: ({ method, url: { origin, path }, headers, body }) => {
const separator = ' \\\n';
const lines: string[] = ['curl -L'];
if (method.toUpperCase() !== 'GET') {
@@ -114,7 +112,7 @@ ${headerString}${bodyString}`;
}
}
return lines.map((line, index) => (index > 0 ? indent(line, 2) : line)).join(separator);
return buildHeredoc(lines);
},
},
{
@@ -262,7 +260,15 @@ const BodyGenerators = {
} else if (isYAML(contentType)) {
body = `--data-binary $'${yaml.dump(body).replace(/'/g, '').replace(/\\n/g, '\n')}'`;
} else {
body = `--data '${stringifyOpenAPI(body, null, 2).replace(/\\n/g, '\n')}'`;
// For JSON, check if it contains single quotes, if so, use heredoc to avoid single quote issues
const jsonString = stringifyOpenAPI(body, null, 2).replace(/\\n/g, '\n');
if (jsonString.includes("'")) {
// Use heredoc format: return array with --data @- <<'EOF', JSON lines, and EOF
const jsonLines = jsonString.split('\n');
body = ["--data @- <<'EOF'", ...jsonLines, 'EOF'];
} else {
body = `--data '${jsonString}'`;
}
}
return {
@@ -447,3 +453,37 @@ function convertBodyToXML(body: any): string {
return json2xml(body).replace(/"/g, '').replace(/\\n/g, '\n').replace(/\\t/g, '\t');
}
/**
* Builds a heredoc string from an array of lines
*/
function buildHeredoc(lines: string[]): string {
const separator = ' \\\n';
let result = '';
let inHeredoc = false;
for (let i = 0; i < lines.length; i++) {
const line = lines[i];
if (!line) continue;
const isHeredocStart = line.includes("<<'EOF'");
const isHeredocEnd = inHeredoc && line === 'EOF';
if (isHeredocStart) {
inHeredoc = true;
// Heredoc start: indent with backslash continuation from previous line, then newline
result += `${i > 0 ? indent(line, 2) : line}\n`;
} else if (isHeredocEnd) {
inHeredoc = false;
// EOF: no indent, no backslash, no separator
result += line;
} else if (inHeredoc) {
// Inside heredoc: indent JSON lines, no backslash, newline
result += `${indent(line, 2)}\n`;
} else {
// Normal line: indent and add separator (backslash) if not last line
result += `${i > 0 ? indent(line, 2) : line}${i < lines.length - 1 ? separator : ''}`;
}
}
return result;
}