hermes-transform 0.6.0 → 0.7.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -10,8 +10,9 @@
10
10
 
11
11
  'use strict';
12
12
 
13
- export type {TraversalContext, Visitor} from './traverse/traverse';
13
+ export type {TraversalContextBase, Visitor} from './traverse/traverse';
14
14
  export type {TransformVisitor} from './transform/transform';
15
+ export type {TransformContext} from './transform/TransformContext';
15
16
  export type {DetachedNode} from './detachedNode';
16
17
 
17
18
  export {SimpleTraverser} from './traverse/SimpleTraverser';
@@ -72,8 +72,8 @@ class MutationContext {
72
72
  }
73
73
  }
74
74
 
75
- appendCommentToSource(comment) {
76
- this.code = (0, _comments.appendCommentToSource)(this.code, comment);
75
+ appendCommentToSource(comment, placement) {
76
+ this.code = (0, _comments.appendCommentToSource)(this.code, comment, placement);
77
77
  }
78
78
 
79
79
  }
@@ -8,6 +8,7 @@
8
8
  * @format
9
9
  */
10
10
 
11
+ import type {CommentPlacement} from './comments/comments';
11
12
  import type {Comment, ESNode} from 'hermes-estree';
12
13
 
13
14
  import {NodeIsDeletedError, NodeIsMutatedError} from './Errors';
@@ -74,7 +75,7 @@ export class MutationContext {
74
75
  }
75
76
  }
76
77
 
77
- appendCommentToSource(comment: Comment): void {
78
- this.code = appendCommentToSource(this.code, comment);
78
+ appendCommentToSource(comment: Comment, placement: CommentPlacement): void {
79
+ this.code = appendCommentToSource(this.code, comment, placement);
79
80
  }
80
81
  }
@@ -5,15 +5,11 @@ Object.defineProperty(exports, "__esModule", {
5
5
  });
6
6
  exports.getTransformContext = getTransformContext;
7
7
 
8
- var _codeFrame = require("@babel/code-frame");
9
-
10
8
  var _detachedNode = require("../detachedNode");
11
9
 
12
10
  var _comments = require("./comments/comments");
13
11
 
14
- var _AddLeadingComments = require("./mutations/AddLeadingComments");
15
-
16
- var _AddTrailingComments = require("./mutations/AddTrailingComments");
12
+ var _AddComments = require("./mutations/AddComments");
17
13
 
18
14
  var _CloneCommentsTo = require("./mutations/CloneCommentsTo");
19
15
 
@@ -38,7 +34,7 @@ var _ReplaceStatementWithMany = require("./mutations/ReplaceStatementWithMany");
38
34
  *
39
35
  * @format
40
36
  */
41
- function getTransformContext(code) {
37
+ function getTransformContext() {
42
38
  /**
43
39
  * The mutations in order of collection.
44
40
  */
@@ -51,7 +47,6 @@ function getTransformContext(code) {
51
47
  }
52
48
 
53
49
  const cloneAPIs = {
54
- // $FlowExpectedError[incompatible-exact]
55
50
  shallowCloneNode: node => {
56
51
  if (node == null) {
57
52
  return null;
@@ -74,7 +69,6 @@ function getTransformContext(code) {
74
69
 
75
70
  return nodes.map(node => (0, _detachedNode.shallowCloneNode)(node));
76
71
  },
77
- // $FlowExpectedError[incompatible-exact]
78
72
  deepCloneNode: node => {
79
73
  if (node == null) {
80
74
  return null;
@@ -105,10 +99,28 @@ function getTransformContext(code) {
105
99
  pushMutation((0, _CloneCommentsTo.createCloneCommentsToMutation)(target, destination));
106
100
  },
107
101
  addLeadingComments: (node, comments) => {
108
- pushMutation((0, _AddLeadingComments.createAddLeadingCommentsMutation)(node, toArray(comments)));
102
+ pushMutation((0, _AddComments.createAddCommentsMutation)(node, toArray(comments).map(comment => ({
103
+ comment,
104
+ placement: _comments.CommentPlacement.LEADING_OWN_LINE
105
+ }))));
106
+ },
107
+ addLeadingInlineComments: (node, comments) => {
108
+ pushMutation((0, _AddComments.createAddCommentsMutation)(node, toArray(comments).map(comment => ({
109
+ comment,
110
+ placement: _comments.CommentPlacement.LEADING_INLINE
111
+ }))));
109
112
  },
110
113
  addTrailingComments: (node, comments) => {
111
- pushMutation((0, _AddTrailingComments.createAddTrailingCommentsMutation)(node, toArray(comments)));
114
+ pushMutation((0, _AddComments.createAddCommentsMutation)(node, toArray(comments).map(comment => ({
115
+ comment,
116
+ placement: _comments.CommentPlacement.TRAILING_OWN_LINE
117
+ }))));
118
+ },
119
+ addTrailingInlineComments: (node, comments) => {
120
+ pushMutation((0, _AddComments.createAddCommentsMutation)(node, toArray(comments).map(comment => ({
121
+ comment,
122
+ placement: _comments.CommentPlacement.TRAILING_INLINE
123
+ }))));
112
124
  },
113
125
  removeComments: comments => {
114
126
  toArray(comments).forEach(comment => {
@@ -148,28 +160,6 @@ function getTransformContext(code) {
148
160
  return mutations.length > 0;
149
161
  },
150
162
 
151
- buildCodeFrame: (node, message) => {
152
- // babel uses 1-indexed columns
153
- const locForBabel = {
154
- start: {
155
- line: node.loc.start.line,
156
- column: node.loc.start.column + 1
157
- },
158
- end: {
159
- line: node.loc.end.line,
160
- column: node.loc.end.column + 1
161
- }
162
- };
163
- return (0, _codeFrame.codeFrameColumns)(code, locForBabel, {
164
- linesAbove: 0,
165
- linesBelow: 0,
166
- highlightCode: process.env.NODE_ENV !== 'test',
167
- message: message
168
- });
169
- },
170
- buildSimpleCodeFrame: (node, message) => {
171
- return `[${node.type}:${node.loc.start.line}:${node.loc.start.column}] ${message}`;
172
- },
173
163
  ...cloneAPIs,
174
164
  ...commentAPIs,
175
165
  ...insertAPIs,
@@ -21,8 +21,8 @@ import type {
21
21
  import type {DetachedNode} from '../detachedNode';
22
22
  import type {TransformCloneSignatures} from '../generated/TransformCloneSignatures';
23
23
  import type {TransformReplaceSignatures} from '../generated/TransformReplaceSignatures';
24
- import type {AddLeadingCommentsMutation} from './mutations/AddLeadingComments';
25
- import type {AddTrailingCommentsMutation} from './mutations/AddTrailingComments';
24
+ import type {TraversalContext} from '../traverse/traverse';
25
+ import type {AddCommentsMutation} from './mutations/AddComments';
26
26
  import type {CloneCommentsToMutation} from './mutations/CloneCommentsTo';
27
27
  import type {InsertStatementMutation} from './mutations/InsertStatement';
28
28
  import type {RemoveCommentMutation} from './mutations/RemoveComment';
@@ -31,15 +31,14 @@ import type {RemoveStatementMutation} from './mutations/RemoveStatement';
31
31
  import type {ReplaceNodeMutation} from './mutations/ReplaceNode';
32
32
  import type {ReplaceStatementWithManyMutation} from './mutations/ReplaceStatementWithMany';
33
33
 
34
- import {codeFrameColumns} from '@babel/code-frame';
35
34
  import {deepCloneNode, shallowCloneNode} from '../detachedNode';
36
35
  import {
36
+ CommentPlacement,
37
37
  getCommentsForNode,
38
38
  isLeadingComment,
39
39
  isTrailingComment,
40
40
  } from './comments/comments';
41
- import {createAddLeadingCommentsMutation} from './mutations/AddLeadingComments';
42
- import {createAddTrailingCommentsMutation} from './mutations/AddTrailingComments';
41
+ import {createAddCommentsMutation} from './mutations/AddComments';
43
42
  import {createCloneCommentsToMutation} from './mutations/CloneCommentsTo';
44
43
  import {createInsertStatementMutation} from './mutations/InsertStatement';
45
44
  import {createRemoveCommentMutation} from './mutations/RemoveComment';
@@ -49,8 +48,7 @@ import {createReplaceNodeMutation} from './mutations/ReplaceNode';
49
48
  import {createReplaceStatementWithManyMutation} from './mutations/ReplaceStatementWithMany';
50
49
 
51
50
  type Mutation = $ReadOnly<
52
- | AddLeadingCommentsMutation
53
- | AddTrailingCommentsMutation
51
+ | AddCommentsMutation
54
52
  | CloneCommentsToMutation
55
53
  | InsertStatementMutation
56
54
  | RemoveCommentMutation
@@ -154,7 +152,7 @@ type TransformCommentAPIs = $ReadOnly<{
154
152
  ) => void,
155
153
 
156
154
  /**
157
- * Add leading comments to the specified node.
155
+ * Add comments on the line before a specified node.
158
156
  */
159
157
  addLeadingComments: (
160
158
  node: ESNode | DetachedNode<ESNode>,
@@ -162,13 +160,29 @@ type TransformCommentAPIs = $ReadOnly<{
162
160
  ) => void,
163
161
 
164
162
  /**
165
- * Add trailing comments to the specified node.
163
+ * Add comments inline before a specified node.
164
+ */
165
+ addLeadingInlineComments: (
166
+ node: ESNode | DetachedNode<ESNode>,
167
+ comments: SingleOrArray<Comment>,
168
+ ) => void,
169
+
170
+ /**
171
+ * Add comments on the line after a specified node.
166
172
  */
167
173
  addTrailingComments: (
168
174
  node: ESNode | DetachedNode<ESNode>,
169
175
  comments: SingleOrArray<Comment>,
170
176
  ) => void,
171
177
 
178
+ /**
179
+ * Add comments inline after a specified node.
180
+ */
181
+ addTrailingInlineComments: (
182
+ node: ESNode | DetachedNode<ESNode>,
183
+ comments: SingleOrArray<Comment>,
184
+ ) => void,
185
+
172
186
  /**
173
187
  * Removes the specified comments
174
188
  */
@@ -275,43 +289,19 @@ type TransformReplaceAPIs = $ReadOnly<{
275
289
  ) => void,
276
290
  }>;
277
291
 
278
- export type TransformContext = $ReadOnly<{
292
+ export type TransformContextAdditions = $ReadOnly<{
279
293
  mutations: $ReadOnlyArray<Mutation>,
280
294
  astWasMutated: boolean,
281
295
 
282
- /**
283
- * Creates a full code frame for the node along with the message.
284
- *
285
- * i.e. `context.buildCodeFrame(node, 'foo')` will create a string like:
286
- * ```
287
- * 56 | function () {
288
- * | ^^^^^^^^^^^^^
289
- * 57 | }.bind(this)
290
- * | ^^ foo
291
- * ```
292
- */
293
- buildCodeFrame: (node: ESNode, message: string) => string,
294
-
295
- /**
296
- * Creates a simple code frame for the node along with the message.
297
- * Use this if you want a condensed marker for your message.
298
- *
299
- * i.e. `context.logWithNode(node, 'foo')` will create a string like:
300
- * ```
301
- * [FunctionExpression:56:44] foo
302
- * ```
303
- * (where 56:44 represents L56, Col44)
304
- */
305
- buildSimpleCodeFrame: (node: ESNode, message: string) => string,
306
-
307
296
  ...TransformCommentAPIs,
308
297
  ...TransformCloneAPIs,
309
298
  ...TransformInsertAPIs,
310
299
  ...TransformRemoveAPIs,
311
300
  ...TransformReplaceAPIs,
312
301
  }>;
302
+ export type TransformContext = TraversalContext<TransformContextAdditions>;
313
303
 
314
- export function getTransformContext(code: string): TransformContext {
304
+ export function getTransformContext(): TransformContextAdditions {
315
305
  /**
316
306
  * The mutations in order of collection.
317
307
  */
@@ -323,7 +313,6 @@ export function getTransformContext(code: string): TransformContext {
323
313
  }
324
314
 
325
315
  const cloneAPIs: TransformCloneAPIs = {
326
- // $FlowExpectedError[incompatible-exact]
327
316
  shallowCloneNode: ((
328
317
  node: ?ESNode,
329
318
  ): // $FlowExpectedError[incompatible-cast]
@@ -339,8 +328,7 @@ export function getTransformContext(code: string): TransformContext {
339
328
  shallowCloneNodeWithOverrides: ((
340
329
  node: ?ESNode,
341
330
  newProps?: $ReadOnly<{...}>,
342
- ): // $FlowExpectedError[incompatible-cast]
343
- ?DetachedNode<ESNode> => {
331
+ ): ?DetachedNode<ESNode> => {
344
332
  if (node == null) {
345
333
  return null;
346
334
  }
@@ -359,7 +347,6 @@ export function getTransformContext(code: string): TransformContext {
359
347
  return nodes.map(node => shallowCloneNode<T>(node));
360
348
  }: TransformCloneAPIs['shallowCloneArray']),
361
349
 
362
- // $FlowExpectedError[incompatible-exact]
363
350
  deepCloneNode: ((
364
351
  node: ?ESNode,
365
352
  ): // $FlowExpectedError[incompatible-cast]
@@ -375,8 +362,7 @@ export function getTransformContext(code: string): TransformContext {
375
362
  deepCloneNodeWithOverrides: ((
376
363
  node: ?ESNode,
377
364
  newProps?: $ReadOnly<{...}>,
378
- ): // $FlowExpectedError[incompatible-cast]
379
- ?DetachedNode<ESNode> => {
365
+ ): ?DetachedNode<ESNode> => {
380
366
  if (node == null) {
381
367
  return null;
382
368
  }
@@ -402,13 +388,53 @@ export function getTransformContext(code: string): TransformContext {
402
388
  }: TransformCommentAPIs['cloneCommentsTo']),
403
389
 
404
390
  addLeadingComments: ((node, comments): void => {
405
- pushMutation(createAddLeadingCommentsMutation(node, toArray(comments)));
391
+ pushMutation(
392
+ createAddCommentsMutation(
393
+ node,
394
+ toArray(comments).map(comment => ({
395
+ comment,
396
+ placement: CommentPlacement.LEADING_OWN_LINE,
397
+ })),
398
+ ),
399
+ );
406
400
  }: TransformCommentAPIs['addLeadingComments']),
407
401
 
402
+ addLeadingInlineComments: ((node, comments): void => {
403
+ pushMutation(
404
+ createAddCommentsMutation(
405
+ node,
406
+ toArray(comments).map(comment => ({
407
+ comment,
408
+ placement: CommentPlacement.LEADING_INLINE,
409
+ })),
410
+ ),
411
+ );
412
+ }: TransformCommentAPIs['addLeadingInlineComments']),
413
+
408
414
  addTrailingComments: ((node, comments): void => {
409
- pushMutation(createAddTrailingCommentsMutation(node, toArray(comments)));
415
+ pushMutation(
416
+ createAddCommentsMutation(
417
+ node,
418
+ toArray(comments).map(comment => ({
419
+ comment,
420
+ placement: CommentPlacement.TRAILING_OWN_LINE,
421
+ })),
422
+ ),
423
+ );
410
424
  }: TransformCommentAPIs['addTrailingComments']),
411
425
 
426
+ addTrailingInlineComments: ((node, comments): void => {
427
+ pushMutation(
428
+ createAddCommentsMutation(
429
+ node,
430
+ toArray(comments).map(comment => ({
431
+ comment,
432
+ placement: CommentPlacement.TRAILING_INLINE,
433
+ })),
434
+ ),
435
+ );
436
+ }: TransformCommentAPIs['addTrailingInlineComments']),
437
+
412
438
  removeComments: ((comments): void => {
413
439
  toArray(comments).forEach(comment => {
414
440
  pushMutation(createRemoveCommentMutation(comment));
@@ -441,7 +467,7 @@ export function getTransformContext(code: string): TransformContext {
441
467
  replaceNode: ((
442
468
  target: ESNode,
443
469
  nodeToReplaceWith: DetachedNode<ESNode>,
444
- options?: $ReadOnly<{keepComments?: boolean}>,
470
+ options?: ReplaceNodeOptions,
445
471
  ): void => {
446
472
  pushMutation(
447
473
  createReplaceNodeMutation(target, nodeToReplaceWith, options),
@@ -451,7 +477,7 @@ export function getTransformContext(code: string): TransformContext {
451
477
  replaceStatementWithMany: ((
452
478
  target,
453
479
  nodesToReplaceWith,
454
- options?: $ReadOnly<{keepComments?: boolean}>,
480
+ options?: ReplaceNodeOptions,
455
481
  ): void => {
456
482
  pushMutation(
457
483
  createReplaceStatementWithManyMutation(
@@ -471,30 +497,6 @@ export function getTransformContext(code: string): TransformContext {
471
497
  return mutations.length > 0;
472
498
  },
473
499
 
474
- buildCodeFrame: (node: ESNode, message: string): string => {
475
- // babel uses 1-indexed columns
476
- const locForBabel = {
477
- start: {
478
- line: node.loc.start.line,
479
- column: node.loc.start.column + 1,
480
- },
481
- end: {
482
- line: node.loc.end.line,
483
- column: node.loc.end.column + 1,
484
- },
485
- };
486
- return codeFrameColumns(code, locForBabel, {
487
- linesAbove: 0,
488
- linesBelow: 0,
489
- highlightCode: process.env.NODE_ENV !== 'test',
490
- message: message,
491
- });
492
- },
493
-
494
- buildSimpleCodeFrame: (node: ESNode, message: string): string => {
495
- return `[${node.type}:${node.loc.start.line}:${node.loc.start.column}] ${message}`;
496
- },
497
-
498
500
  ...cloneAPIs,
499
501
  ...commentAPIs,
500
502
  ...insertAPIs,
@@ -3,9 +3,9 @@
3
3
  Object.defineProperty(exports, "__esModule", {
4
4
  value: true
5
5
  });
6
+ exports.CommentPlacement = void 0;
7
+ exports.addComment = addComment;
6
8
  exports.addCommentsToNode = addCommentsToNode;
7
- exports.addLeadingComment = addLeadingComment;
8
- exports.addTrailingComment = addTrailingComment;
9
9
  exports.appendCommentToSource = appendCommentToSource;
10
10
  exports.attachComments = attachComments;
11
11
  exports.cloneComment = cloneComment;
@@ -24,6 +24,8 @@ var _printerEstree = _interopRequireDefault(require("./prettier/language-js/prin
24
24
 
25
25
  var _util = require("./prettier/common/util");
26
26
 
27
+ var _os = require("os");
28
+
27
29
  function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
28
30
 
29
31
  /**
@@ -38,6 +40,10 @@ function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { de
38
40
  // $FlowExpectedError[untyped-import]
39
41
  // $FlowExpectedError[untyped-import]
40
42
  // $FlowExpectedError[untyped-import]
43
+ const CommentPlacement = require("flow-enums-runtime").Mirrored(["LEADING_OWN_LINE", "LEADING_INLINE", "TRAILING_OWN_LINE", "TRAILING_INLINE"]);
44
+
45
+ exports.CommentPlacement = CommentPlacement;
46
+
41
47
  function attachComments(comments, ast, text) {
42
48
  (0, _comments.attach)(comments, ast, text, {
43
49
  locStart: _loc.locStart,
@@ -82,12 +88,22 @@ function isTrailingComment(comment) {
82
88
  return comment.trailing === true;
83
89
  }
84
90
 
85
- function addLeadingComment(node, comment) {
86
- (0, _util.addLeadingComment)(node, comment);
87
- }
88
-
89
- function addTrailingComment(node, comment) {
90
- (0, _util.addTrailingComment)(node, comment);
91
+ function addComment(node, comment, placement) {
92
+ switch (placement) {
93
+ case CommentPlacement.LEADING_OWN_LINE:
94
+ case CommentPlacement.LEADING_INLINE:
95
+ {
96
+ (0, _util.addLeadingComment)(node, comment);
97
+ break;
98
+ }
99
+
100
+ case CommentPlacement.TRAILING_OWN_LINE:
101
+ case CommentPlacement.TRAILING_INLINE:
102
+ {
103
+ (0, _util.addTrailingComment)(node, comment);
104
+ break;
105
+ }
106
+ }
91
107
  }
92
108
 
93
109
  function cloneComment(comment) {
@@ -112,29 +128,100 @@ function cloneCommentWithMarkers(comment) {
112
128
  };
113
129
  }
114
130
 
115
- function appendCommentToSource(code, comment) {
116
- // prettier slices comments directly from the source code when printing
117
- // https://github.com/prettier/prettier/blob/5f0ee39fa03532c85bd1c35291450fe7ac3667b3/src/language-js/print/comment.js#L15-L20
118
- // this means that we need to have any appended comments directly in the
119
- // source code or else prettier will slice nothing and bork up the transform
120
- let commentText = comment.value;
131
+ function getFirstNewlineIndex(code) {
132
+ return code.search(/\r\n|\n|\r/);
133
+ }
134
+
135
+ function getFirstNonWhitespaceIndex(code) {
136
+ return code.search(/\S/);
137
+ }
138
+
139
+ function appendCommentToSource(code, comment, placement) {
140
+ let newCode = code;
121
141
 
122
142
  switch (comment.type) {
123
143
  case 'Block':
124
- commentText = `/*${commentText}*/`;
125
- break;
144
+ {
145
+ // Prettier decides if a newline is necessary between the comment and its node by looking
146
+ // to see if a newline seperates them in the source text. We can trick prettier into
147
+ // formatting how we want for new comments by placing the range such that a newline
148
+ // will (OWN_LINE) or will not (INLINE) be found when searching from the specified range
149
+ // position.
150
+ switch (placement) {
151
+ case CommentPlacement.LEADING_OWN_LINE:
152
+ case CommentPlacement.TRAILING_OWN_LINE:
153
+ {
154
+ // Since we always want a line break we need to ensure a newline is found when
155
+ // searching out from either side of the comment range.
156
+ let firstNewline = getFirstNewlineIndex(code);
157
+
158
+ if (firstNewline === -1) {
159
+ // No newline in file, lets add one.
160
+ newCode += _os.EOL;
161
+ firstNewline = newCode.length;
162
+ } // Prettier only uses these ranges for detecting whitespace, so this nonsensical
163
+ // range is safe.
164
+ // $FlowExpectedError[cannot-write]
165
+
166
+
167
+ comment.range = [firstNewline + 1, firstNewline];
168
+ break;
169
+ }
170
+
171
+ case CommentPlacement.LEADING_INLINE:
172
+ case CommentPlacement.TRAILING_INLINE:
173
+ {
174
+ // Since we don't want a line break we need to ensure a non whitespace char is
175
+ // always found before a newline when searching out from either side of the
176
+ // comment range.
177
+ let firstNonWhitespace = getFirstNonWhitespaceIndex(code);
178
+
179
+ if (firstNonWhitespace === -1) {
180
+ // No non whitespace chars in file, lets add an identifiable statement for prettier to find.
181
+ newCode += '$FORCE_INLINE_ON_EMPTY_FILE_TOKEN$;';
182
+ firstNonWhitespace = newCode.length;
183
+ break;
184
+ } // $FlowExpectedError[cannot-write]
185
+
186
+
187
+ comment.range = [firstNonWhitespace + 1, firstNonWhitespace];
188
+ break;
189
+ }
190
+ }
191
+
192
+ break;
193
+ }
126
194
 
127
195
  case 'Line':
128
- commentText = `//${commentText}`;
129
- break;
196
+ {
197
+ // For `Line` comments prettier slices comments directly from the source code when printing
198
+ // https://github.com/prettier/prettier/blob/5f0ee39fa03532c85bd1c35291450fe7ac3667b3/src/language-js/print/comment.js#L15-L20
199
+ // this means that we need to have any appended comments directly in the
200
+ // source code or else prettier will slice nothing and bork up the transform
201
+ const commentText = `//${comment.value}`;
202
+ const lastChar = newCode[newCode.length - 1];
203
+
204
+ if (lastChar !== '\n' && lastChar !== '\r') {
205
+ newCode += _os.EOL;
206
+ } // Line comments cannot be inline before a node so we only place trailing Line comments inline.
207
+
208
+
209
+ if (placement === CommentPlacement.TRAILING_INLINE) {
210
+ // Prettier determines an "end of line" comment by walking backwards from
211
+ // the comment start range through the source code to see if it finds a non
212
+ // newline token. In order to trick prettier for new comments we need to
213
+ // insert fake source code for it to find.
214
+ newCode += '$FORCE_END_OF_LINE_COMMENT_TOKEN$;';
215
+ }
216
+
217
+ const start = newCode.length;
218
+ newCode += commentText;
219
+ const end = newCode.length; // $FlowExpectedError[cannot-write]
220
+
221
+ comment.range = [start, end];
222
+ break;
223
+ }
130
224
  }
131
225
 
132
- let newCode = code;
133
- newCode += '\n';
134
- const start = newCode.length;
135
- newCode += commentText;
136
- const end = newCode.length; // $FlowExpectedError[cannot-write]
137
-
138
- comment.range = [start, end];
139
226
  return newCode;
140
227
  }