transform doesn't handle recursively transformed nodes (fix suggested)
- Dominant language
- TypeScript
- Stars
- 6.2k
- Forks
- 238
- Avg merge
- 2m
- Merged PRs (30d)
- 1
Description
So, I had this hair-brained idea to use ts-morph to wrap await around sub-expressions.
E.g. `fetch('http://example.com').json().data.x` -> `(await (await fetch('http://example.com')).json()).data.x`
**Describe the bug**
Version: 20.0.0
I get the following error attempting this
```
filePath: '/__temp___.ts',
oldText: "export default fetch('http://example.com').json().data.x",
newText: "export default (await fetch('http://example.com'))fetch('http://example.com')(await (await fetch('http://example.com')).json()).data.x"
```
**To Reproduce**
```ts
import { Project, ScriptTarget, ModuleKind, ts } from "ts-morph";
const project = new Project({
compilerOptions: {
allowJs: true,
target: ScriptTarget.ES2022,
module: ModuleKind.ES2022,
},
useInMemoryFileSystem: true,
});
const expr = `fetch('http://example.com').json().data.x`;
console.log(
project
.createSourceFile("__temp___.ts", `export default ${expr}`)
.getDefaultExportSymbol()
.getValueDeclaration()
.getChildAtIndex(2) // (BTW is there a cleaner way to make a file -> get an expression? I'm all ears.)
.transform(({ currentNode, factory, visitChildren }) => {
if (ts.isCallExpression(currentNode)) {
return factory.createParenthesizedExpression(factory.createAwaitExpression(visitChildren()));
}
return visitChildren();
})
.getFullText(),
);
```
**Expected behavior**
```
% node example.js
(await (await fetch('http://example.com')).json()).data.x
```
... as was produced after applying the following fix ... 😉
```diff
diff --git a/node_modules/ts-morph/dist/ts-morph.js b/node_modules/ts-morph/dist/ts-morph.js
index df176bd..918503f 100644
--- a/node_modules/ts-morph/dist/ts-morph.js
+++ b/node_modules/ts-morph/dist/ts-morph.js
@@ -3746,7 +3746,7 @@ class Node {
const start = oldNode.getStart(compilerSourceFile, true);
const end = oldNode.end;
let lastTransformation;
- while ((lastTransformation = transformations[transformations.length - 1]) && lastTransformation.start > start)
+ while ((lastTransformation = transformations[transformations.length - 1]) && lastTransformation.start >= start)
transformations.pop();
const wrappedNode = compilerFactory.getExistingNodeFromCompilerNode(oldNode);
transformations.push({
```
**See also**
Issue #852 / PR #853
Contributor guide
Assessment
This issue has not been assessed yet.