From f9e67c403a4667372684ee8c3e82e1f0ba27031b Mon Sep 17 00:00:00 2001 From: Lee Byron Date: Thu, 30 Nov 2017 09:11:12 -0800 Subject: [PATCH] Improvements to printing block strings --- src/language/__tests__/printer-test.js | 33 +++++++++++++++++++++++++- src/language/printer.js | 13 +++++++++- 2 files changed, 44 insertions(+), 2 deletions(-) diff --git a/src/language/__tests__/printer-test.js b/src/language/__tests__/printer-test.js index bf30328879..a07bd0d96a 100644 --- a/src/language/__tests__/printer-test.js +++ b/src/language/__tests__/printer-test.js @@ -71,6 +71,37 @@ describe('Printer', () => { `); }); + it('correctly prints single-line block strings with leading space', () => { + const mutationAstWithArtifacts = parse( + '{ field(arg: """ space-led value""") }' + ); + expect(print(mutationAstWithArtifacts)).to.equal(dedent` + { + field(arg: """ space-led value""") + } + `); + }); + + it('correctly prints block strings with a first line indentation', () => { + const mutationAstWithArtifacts = parse(` + { + field(arg: """ + first + line + indentation + """) + } + `); + expect(print(mutationAstWithArtifacts)).to.equal(dedent` + { + field(arg: """ + first + line + indentation + """) + } + `); + }); const kitchenSink = readFileSync( join(__dirname, '/kitchen-sink.graphql'), @@ -128,7 +159,7 @@ describe('Printer', () => { fragment frag on Friend { foo(size: $size, bar: $b, obj: {key: "value", block: """ - block string uses \""" + block string uses \""" """}) } diff --git a/src/language/printer.js b/src/language/printer.js index a611b73c28..a16787bfd9 100644 --- a/src/language/printer.js +++ b/src/language/printer.js @@ -74,7 +74,7 @@ const printDocASTReducer = { FloatValue: ({ value }) => value, StringValue: ({ value, block: isBlockString }) => isBlockString ? - `"""\n${value.replace(/"""/g, '\\"""')}\n"""` : + printBlockString(value) : JSON.stringify(value), BooleanValue: ({ value }) => JSON.stringify(value), NullValue: () => 'null', @@ -204,3 +204,14 @@ function wrap(start, maybeString, end) { function indent(maybeString) { return maybeString && maybeString.replace(/\n/g, '\n '); } + +/** + * Print a block string in the indented block form by adding a leading and + * trailing blank line. However, if a block string starts with whitespace and is + * a single-line, adding a leading blank line would strip that whitespace. + */ +function printBlockString(value) { + return (value[0] === ' ' || value[0] === '\t') && value.indexOf('\n') === -1 ? + `"""${value.replace(/"""/g, '\\"""')}"""` : + indent('"""\n' + value.replace(/"""/g, '\\"""')) + '\n"""'; +}