NodeAppender.spec.ts 9.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244
  1. import * as chai from 'chai';
  2. import * as ESTree from 'estree';
  3. import { TStatement } from '../../../src/types/TStatement';
  4. import { IStackTraceData } from '../../../src/interfaces/stack-trace-analyzer/IStackTraceData';
  5. import { readFileAsString } from '../../helpers/readFileAsString';
  6. import { NodeAppender } from '../../../src/node/NodeAppender';
  7. import { NodeMocks } from '../../mocks/NodeMocks';
  8. import { NodeUtils } from '../../../src/node/NodeUtils';
  9. import { StackTraceAnalyzer } from '../../../src/stack-trace-analyzer/StackTraceAnalyzer';
  10. const assert: any = chai.assert;
  11. describe('NodeAppender', () => {
  12. describe('appendNode (blockScopeNode: TNodeWithBlockStatement[], nodeBodyStatements: TStatement[]): void', () => {
  13. let astTree: ESTree.Program,
  14. expectedAstTree: ESTree.Program,
  15. node: TStatement[];
  16. beforeEach(() => {
  17. node = NodeUtils.convertCodeToStructure(`
  18. var test = 1;
  19. `);
  20. astTree = NodeMocks.getProgramNode(
  21. NodeUtils.convertCodeToStructure(
  22. readFileAsString('./test/fixtures/node-appender/append-node.js')
  23. )
  24. );
  25. expectedAstTree = NodeMocks.getProgramNode(
  26. NodeUtils.convertCodeToStructure(
  27. readFileAsString('./test/fixtures/node-appender/append-node-expected.js')
  28. )
  29. );
  30. NodeUtils.parentize(astTree);
  31. NodeUtils.parentize(expectedAstTree);
  32. NodeAppender.appendNode(astTree, node);
  33. });
  34. it('should append given node to a `BlockStatement` node body', () => {
  35. assert.deepEqual(astTree, expectedAstTree);
  36. });
  37. });
  38. describe('appendNodeToOptimalBlockScope (blockScopeStackTraceData: IStackTraceData[], blockScopeNode: TNodeWithBlockStatement, nodeBodyStatements: TStatement[], index: number = 0): void', () => {
  39. let astTree: ESTree.Program,
  40. expectedAstTree: ESTree.Program,
  41. node: TStatement[],
  42. stackTraceData: IStackTraceData[];
  43. beforeEach(() => {
  44. node = NodeUtils.convertCodeToStructure(`
  45. var test = 1;
  46. `);
  47. });
  48. it('should append node into first and deepest function call in calls trace - variant #1', () => {
  49. astTree = NodeMocks.getProgramNode(
  50. NodeUtils.convertCodeToStructure(
  51. readFileAsString('./test/fixtures/node-appender/append-node-to-optimal-block-scope/variant-1.js')
  52. )
  53. );
  54. expectedAstTree = NodeMocks.getProgramNode(
  55. NodeUtils.convertCodeToStructure(
  56. readFileAsString('./test/fixtures/node-appender/append-node-to-optimal-block-scope/variant-1-expected.js')
  57. )
  58. );
  59. stackTraceData = new StackTraceAnalyzer(astTree.body).analyze();
  60. NodeAppender.appendNodeToOptimalBlockScope(stackTraceData, astTree, node);
  61. assert.deepEqual(astTree, expectedAstTree);
  62. });
  63. it('should append node into first and deepest function call in calls trace - variant #2', () => {
  64. astTree = NodeMocks.getProgramNode(
  65. NodeUtils.convertCodeToStructure(
  66. readFileAsString('./test/fixtures/node-appender/append-node-to-optimal-block-scope/variant-2.js')
  67. )
  68. );
  69. expectedAstTree = NodeMocks.getProgramNode(
  70. NodeUtils.convertCodeToStructure(
  71. readFileAsString('./test/fixtures/node-appender/append-node-to-optimal-block-scope/variant-2-expected.js')
  72. )
  73. );
  74. stackTraceData = new StackTraceAnalyzer(astTree.body).analyze();
  75. NodeAppender.appendNodeToOptimalBlockScope(stackTraceData, astTree, node);
  76. assert.deepEqual(astTree, expectedAstTree);
  77. });
  78. describe('append by specific index', () => {
  79. let astTree: ESTree.Program;
  80. beforeEach(() => {
  81. astTree = NodeMocks.getProgramNode(
  82. NodeUtils.convertCodeToStructure(
  83. readFileAsString('./test/fixtures/node-appender/append-node-to-optimal-block-scope/by-index.js')
  84. )
  85. );
  86. });
  87. it('should append node into deepest function call by specified index in calls trace - variant #1', () => {
  88. expectedAstTree = NodeMocks.getProgramNode(
  89. NodeUtils.convertCodeToStructure(
  90. readFileAsString('./test/fixtures/node-appender/append-node-to-optimal-block-scope/by-index-variant-1-expected.js')
  91. )
  92. );
  93. stackTraceData = new StackTraceAnalyzer(astTree.body).analyze();
  94. NodeAppender.appendNodeToOptimalBlockScope(stackTraceData, astTree, node, 2);
  95. assert.deepEqual(astTree, expectedAstTree);
  96. });
  97. it('should append node into deepest function call by specified index in calls trace - variant #2', () => {
  98. expectedAstTree = NodeMocks.getProgramNode(
  99. NodeUtils.convertCodeToStructure(
  100. readFileAsString('./test/fixtures/node-appender/append-node-to-optimal-block-scope/by-index-variant-2-expected.js')
  101. )
  102. );
  103. stackTraceData = new StackTraceAnalyzer(astTree.body).analyze();
  104. NodeAppender.appendNodeToOptimalBlockScope(stackTraceData, astTree, node, 1);
  105. assert.deepEqual(astTree, expectedAstTree);
  106. });
  107. it('should append node into deepest function call by specified index in calls trace - variant #3', () => {
  108. astTree = NodeMocks.getProgramNode(
  109. NodeUtils.convertCodeToStructure(
  110. readFileAsString('./test/fixtures/node-appender/append-node-to-optimal-block-scope/by-index-variant-3.js')
  111. )
  112. );
  113. expectedAstTree = NodeMocks.getProgramNode(
  114. NodeUtils.convertCodeToStructure(
  115. readFileAsString('./test/fixtures/node-appender/append-node-to-optimal-block-scope/by-index-variant-3-expected.js')
  116. )
  117. );
  118. stackTraceData = new StackTraceAnalyzer(astTree.body).analyze();
  119. NodeAppender.appendNodeToOptimalBlockScope(
  120. stackTraceData,
  121. astTree,
  122. node,
  123. NodeAppender.getRandomStackTraceIndex(stackTraceData.length)
  124. );
  125. assert.deepEqual(astTree, expectedAstTree);
  126. });
  127. });
  128. });
  129. describe('getRandomStackTraceIndex (stackTraceRootLength: number): number', () => {
  130. it('should returns random index between 0 and stack trace data root length', () => {
  131. let index: number;
  132. for (let i: number = 0; i < 100; i++) {
  133. index = NodeAppender.getRandomStackTraceIndex(100);
  134. assert.isAtLeast(index, 0);
  135. assert.isAtMost(index, 100);
  136. }
  137. });
  138. });
  139. describe('insertNodeAtIndex (blockScopeNode: TNodeWithBlockStatement[], nodeBodyStatements: TStatement[], index: number): void', () => {
  140. let astTree: ESTree.Program,
  141. expectedAstTree: ESTree.Program,
  142. node: TStatement[];
  143. beforeEach(() => {
  144. node = NodeUtils.convertCodeToStructure(`
  145. var test = 1;
  146. `);
  147. astTree = NodeMocks.getProgramNode(
  148. NodeUtils.convertCodeToStructure(
  149. readFileAsString('./test/fixtures/node-appender/insert-node-at-index.js')
  150. )
  151. );
  152. expectedAstTree = NodeMocks.getProgramNode(
  153. NodeUtils.convertCodeToStructure(
  154. readFileAsString('./test/fixtures/node-appender/insert-node-at-index-expected.js')
  155. )
  156. );
  157. NodeUtils.parentize(astTree);
  158. NodeUtils.parentize(expectedAstTree);
  159. NodeAppender.insertNodeAtIndex(astTree, node, 2);
  160. });
  161. it('should insert given node in `BlockStatement` node body at index', () => {
  162. assert.deepEqual(astTree, expectedAstTree);
  163. });
  164. });
  165. describe('prependNode (blockScopeNode: TNodeWithBlockStatement[], nodeBodyStatements: TStatement[]): void', () => {
  166. let astTree: ESTree.Program,
  167. expectedAstTree: ESTree.Program,
  168. node: TStatement[];
  169. beforeEach(() => {
  170. node = NodeUtils.convertCodeToStructure(`
  171. var test = 1;
  172. `);
  173. astTree = NodeMocks.getProgramNode(
  174. NodeUtils.convertCodeToStructure(
  175. readFileAsString('./test/fixtures/node-appender/prepend-node.js')
  176. )
  177. );
  178. expectedAstTree = NodeMocks.getProgramNode(
  179. NodeUtils.convertCodeToStructure(
  180. readFileAsString('./test/fixtures/node-appender/prepend-node-expected.js')
  181. )
  182. );
  183. NodeUtils.parentize(astTree);
  184. NodeUtils.parentize(expectedAstTree);
  185. NodeAppender.prependNode(astTree, node);
  186. });
  187. it('should prepend given node to a `BlockStatement` node body', () => {
  188. assert.deepEqual(astTree, expectedAstTree);
  189. });
  190. });
  191. });