UNPKG

2.99 kBJavaScriptView Raw
1"use strict";
2
3Object.defineProperty(exports, "__esModule", {
4 value: true
5});
6exports.dedentBlockStringValue = dedentBlockStringValue;
7exports.getBlockStringIndentation = getBlockStringIndentation;
8exports.printBlockString = printBlockString;
9
10/**
11 * Produces the value of a block string from its parsed raw value, similar to
12 * CoffeeScript's block string, Python's docstring trim or Ruby's strip_heredoc.
13 *
14 * This implements the GraphQL spec's BlockStringValue() static algorithm.
15 */
16function dedentBlockStringValue(rawString) {
17 // Expand a block string's raw value into independent lines.
18 var lines = rawString.split(/\r\n|[\n\r]/g); // Remove common indentation from all lines but first.
19
20 var commonIndent = getBlockStringIndentation(lines);
21
22 if (commonIndent !== 0) {
23 for (var i = 1; i < lines.length; i++) {
24 lines[i] = lines[i].slice(commonIndent);
25 }
26 } // Remove leading and trailing blank lines.
27
28
29 while (lines.length > 0 && isBlank(lines[0])) {
30 lines.shift();
31 }
32
33 while (lines.length > 0 && isBlank(lines[lines.length - 1])) {
34 lines.pop();
35 } // Return a string of the lines joined with U+000A.
36
37
38 return lines.join('\n');
39} // @internal
40
41
42function getBlockStringIndentation(lines) {
43 var commonIndent = null;
44
45 for (var i = 1; i < lines.length; i++) {
46 var line = lines[i];
47 var indent = leadingWhitespace(line);
48
49 if (indent === line.length) {
50 continue; // skip empty lines
51 }
52
53 if (commonIndent === null || indent < commonIndent) {
54 commonIndent = indent;
55
56 if (commonIndent === 0) {
57 break;
58 }
59 }
60 }
61
62 return commonIndent === null ? 0 : commonIndent;
63}
64
65function leadingWhitespace(str) {
66 var i = 0;
67
68 while (i < str.length && (str[i] === ' ' || str[i] === '\t')) {
69 i++;
70 }
71
72 return i;
73}
74
75function isBlank(str) {
76 return leadingWhitespace(str) === str.length;
77}
78/**
79 * Print a block string in the indented block form by adding a leading and
80 * trailing blank line. However, if a block string starts with whitespace and is
81 * a single-line, adding a leading blank line would strip that whitespace.
82 */
83
84
85function printBlockString(value) {
86 var indentation = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : '';
87 var preferMultipleLines = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : false;
88 var isSingleLine = value.indexOf('\n') === -1;
89 var hasLeadingSpace = value[0] === ' ' || value[0] === '\t';
90 var hasTrailingQuote = value[value.length - 1] === '"';
91 var printAsMultipleLines = !isSingleLine || hasTrailingQuote || preferMultipleLines;
92 var result = ''; // Format a multi-line block quote to account for leading space.
93
94 if (printAsMultipleLines && !(isSingleLine && hasLeadingSpace)) {
95 result += '\n' + indentation;
96 }
97
98 result += indentation ? value.replace(/\n/g, '\n' + indentation) : value;
99
100 if (printAsMultipleLines) {
101 result += '\n';
102 }
103
104 return '"""' + result.replace(/"""/g, '\\"""') + '"""';
105}