GumTreeDiff / gumtree

An awesome code differencing tool
https://github.com/GumTreeDiff/gumtree/wiki
GNU Lesser General Public License v3.0
926 stars 173 forks source link

Meaning of numbers in diff #150

Closed elizabethdinella closed 5 years ago

elizabethdinella commented 5 years ago

What are the meaning of the numbers in the diff output? For example in the following output:

Match EXPR_VOID(95) to EXPR_VOID(95)
Match GETPROP(154) to GETPROP(154)
Match VAR(29) to VAR(29)
Match GETPROP(151) to GETPROP(151)
Match NAME: findByIdAndUpdate(191) to NAME: findByIdAndUpdate(191)
Match NAME: express(2) to NAME: express(2)
Match NAME: body(199) to NAME: body(199)
Match FUNCTION(220) to FUNCTION(220)
Match NAME: express(9) to NAME: express(9)
Match NAME: exports(224) to NAME: exports(224)
Match RETURN(52) to RETURN(52)
Match NAME: res(103) to NAME: res(103)
Match NAME: Project(190) to NAME: Project(190)
Match NAME: saved(204) to NAME: saved(204)
Match NAME: proj(159) to NAME: proj(159)
Match VAR(6) to VAR(6)
Match FUNCTION(97) to FUNCTION(97)
Match GETPROP(200) to GETPROP(200)
Match GETPROP(84) to GETPROP(84)
Match CALL(59) to CALL(59)
Match STRING: use strict(0) to STRING: use strict(0)
Match CALL(162) to CALL(162)
Match NAME: next(36) to NAME: next(36)
Match NAME: next(128) to NAME: next(128)
Match RETURN(171) to RETURN(171)
Match BLOCK(211) to BLOCK(211)
Match NAME: id(76) to NAME: id(76)
Match RETURN(122) to RETURN(122)
Match GETPROP(107) to GETPROP(107)
Match CALL(213) to CALL(213)
Match NAME: id(155) to NAME: id(155)
Match STRING: /(33) to STRING: /(33)
Match BLOCK(180) to BLOCK(180)
Match CALL(5) to CALL(5)
Match CALL(51) to CALL(51)
Match NAME: bodyParser(15) to NAME: bodyParser(15)
Match GETPROP(192) to GETPROP(192)
Match NAME: params(109) to NAME: params(109)
Match GETPROP(80) to GETPROP(80)
Match NAME: send(48) to NAME: send(48)
Match CALL(21) to CALL(21)
Match NAME: catch(56) to NAME: catch(56)
Match GETPROP(112) to GETPROP(112)
Match ASSIGN(157) to ASSIGN(157)
Match NAME: catch(126) to NAME: catch(126)
Match NAME: user(153) to NAME: user(153)
Match NAME: Router(10) to NAME: Router(10)
Match NAME: proj(141) to NAME: proj(141)
Match NAME: next(69) to NAME: next(69)
Match NAME: catch(91) to NAME: catch(91)
Match GETPROP(20) to GETPROP(20)
Match ASSIGN(227) to ASSIGN(227)
Match NAME: projects(50) to NAME: projects(50)
Match VAR(7) to VAR(7)
Match GETPROP(195) to GETPROP(195)
Match NAME: project(81) to NAME: project(81)
Match BLOCK(131) to BLOCK(131)
Match VAR(28) to VAR(28)
Match CALL(170) to CALL(170)
Match CALL(63) to CALL(63)
Match BLOCK(172) to BLOCK(172)
Match NAME: req(138) to NAME: req(138)
Match NAME: get(64) to NAME: get(64)
Match GETPROP(119) to GETPROP(119)
Match NAME: catch(175) to NAME: catch(175)
Match BLOCK(96) to BLOCK(96)
Match GETPROP(45) to GETPROP(45)
Match NAME: user(150) to NAME: userId(150)
Match NAME: next(216) to NAME: next(216)
Match GETPROP(225) to GETPROP(225)
Match NAME: post(134) to NAME: post(134)
Match NAME: res(139) to NAME: res(139)
Match NAME: Project(37) to NAME: Project(37)
Match NAME: catch(214) to NAME: catch(214)
Match GETPROP(11) to GETPROP(11)
Match GETPROP(65) to GETPROP(65)
Match CALL(78) to CALL(78)
Match NAME: res(205) to NAME: res(205)
Match NAME: Project(105) to NAME: Project(105)
Match NAME: req(152) to NAME: req(152)
Match NAME: req(102) to NAME: req(102)
Match GETPROP(197) to GETPROP(197)
Match CALL(133) to CALL(133)
Match GETPROP(57) to GETPROP(57)
Match FUNCTION(54) to FUNCTION(54)
Match GETPROP(110) to GETPROP(110)
Match NAME: params(194) to NAME: params(194)
Match NAME: saved(208) to NAME: saved(208)
Match NAME: next(140) to NAME: next(140)
Match CALL(178) to CALL(178)
Match SCRIPT(229) to SCRIPT(229)
Match NAME: delete(99) to NAME: delete(99)
Match STRING: body-parser(17) to STRING: body-parser(17)
Match NAME: next(58) to NAME: next(58)
Match GETPROP(156) to GETPROP(156)
Match CALL(55) to CALL(55)
Match VAR(13) to VAR(13)
Match GETPROP(164) to GETPROP(164)
Match FUNCTION(132) to FUNCTION(132)
Match RETURN(210) to RETURN(210)
Match EXPR_VOID(158) to EXPR_VOID(158)
Match GETPROP(77) to GETPROP(77)
Match CALL(98) to CALL(98)
Match NAME: req(143) to NAME: req(143)
Match NAME: find(38) to NAME: find(38)
Match GETPROP(207) to GETPROP(207)
Match GETPROP(75) to GETPROP(75)
Match NAME: req(34) to NAME: req(34)
Match NAME: Project(142) to NAME: Project(142)
Match NAME: router(8) to NAME: router(8)
Match NAME: require(25) to NAME: require(25)
Match NAME: json(19) to NAME: json(19)
Match CALL(217) to CALL(217)
Match VAR(147) to VAR(147)
Match NAME: then(163) to NAME: then(163)
Match NAME: id(111) to NAME: id(111)
Match NAME: req(193) to NAME: req(193)
Match NAME: req(198) to NAME: req(198)
Match GETPROP(176) to GETPROP(176)
Match GETPROP(168) to GETPROP(168)
Match BLOCK(88) to BLOCK(88)
Match CALL(113) to CALL(113)
Match EXPR_RESULT(222) to EXPR_RESULT(222)
Match NAME: Project(24) to NAME: Project(24)
Match VAR(23) to VAR(23)
Match NAME: next(177) to NAME: next(177)
Match NAME: send(206) to NAME: send(206)
Match NAME: res(68) to NAME: res(68)
Match BLOCK(123) to BLOCK(123)
Match EXPR_VOID(179) to EXPR_VOID(179)
Match NAME: body(144) to NAME: body(144)
Match NAME: res(47) to NAME: res(47)
Match NAME: require(16) to NAME: require(16)
Match CALL(90) to CALL(90)
Match GETPROP(92) to GETPROP(92)
Match NAME: module(223) to NAME: module(223)
Match NAME: id(196) to NAME: id(196)
Match EXPR_VOID(218) to EXPR_VOID(218)
Match GETPROP(127) to GETPROP(127)
Match NAME: send(83) to NAME: send(83)
Match NAME: put(183) to NAME: put(183)
Match CALL(125) to CALL(125)
Match EXPR_VOID(130) to EXPR_VOID(130)
Match NAME: req(67) to NAME: req(67)
Match NAME: res(188) to NAME: res(188)
Match NAME: next(104) to NAME: next(104)
Match NAME: req(187) to NAME: req(187)
Match CALL(86) to CALL(86)
Match BLOCK(61) to BLOCK(61)
Match GETPROP(184) to GETPROP(184)
Match GETPROP(135) to GETPROP(135)
Match NAME: save(160) to NAME: save(160)
Match NAME: next(93) to NAME: next(93)
Match NAME: findByIdAndRemove(106) to NAME: findByIdAndRemove(106)
Match NAME: then(79) to NAME: then(79)
Match CALL(209) to CALL(209)
Match GETPROP(115) to GETPROP(115)
Match CALL(201) to CALL(201)
Match GETPROP(203) to GETPROP(203)
Match CALL(27) to CALL(27)
Match CALL(18) to CALL(18)
Match NAME: then(44) to NAME: then(44)
Match NAME: params(74) to NAME: params(74)
Match GETPROP(145) to GETPROP(145)
Match CALL(174) to CALL(174)
Match VAR(14) to VAR(14)
Match NAME: project(85) to NAME: project(85)
Match STRING: /:id(185) to STRING: /:id(185)
Match VAR(148) to VAR(148)
Match CALL(182) to CALL(182)
Match GETPROP(42) to GETPROP(42)
Match NAME: bodyParser(186) to NAME: bodyParser(186)
Match GETPROP(215) to GETPROP(215)
Match NAME: saved(169) to NAME: saved(169)
Match NAME: then(202) to NAME: then(202)
Match NAME: then(114) to NAME: then(114)
Match CALL(121) to CALL(121)
Match NAME: require(3) to NAME: require(3)
Match STRING: /:id(66) to STRING: /:id(66)
Match EXPR_RESULT(1) to EXPR_RESULT(1)
Match CALL(12) to CALL(12)
Match FUNCTION(212) to FUNCTION(212)
Match NAME: deleted(120) to NAME: deleted(120)
Match GETPROP(161) to GETPROP(161)
Match NAME: projects(46) to NAME: projects(46)
Match STRING: ../models/project(26) to STRING: ../models/project(26)
Match GETPROP(72) to GETPROP(72)
Match STRING: /(136) to STRING: /(136)
Match NAME: router(226) to NAME: router(226)
Match FUNCTION(62) to FUNCTION(62)
Match EXPR_RESULT(228) to EXPR_RESULT(228)
Match VAR(22) to VAR(22)
Match FUNCTION(173) to FUNCTION(173)
Match NAME: lean(41) to NAME: lean(41)
Match NAME: send(118) to NAME: send(118)
Match NAME: req(108) to NAME: req(108)
Match BLOCK(219) to BLOCK(219)
Match STRING: express(4) to STRING: express(4)
Match GETPROP(32) to GETPROP(32)
Match NAME: bodyParser(137) to NAME: bodyParser(137)
Match NAME: deleted(116) to NAME: deleted(116)
Match NAME: send(167) to NAME: send(167)
Match FUNCTION(181) to FUNCTION(181)
Match NAME: res(117) to NAME: res(117)
Match CALL(40) to CALL(40)
Match CALL(129) to CALL(129)
Match NAME: res(82) to NAME: res(82)
Match NAME: res(35) to NAME: res(35)
Match FUNCTION(89) to FUNCTION(89)
Match RETURN(87) to RETURN(87)
Match CALL(221) to CALL(221)
Match GETPROP(100) to GETPROP(100)
Match NAME: router(30) to NAME: router(30)
Match CALL(94) to CALL(94)
Match NAME: res(166) to NAME: res(166)
Match BLOCK(53) to BLOCK(53)
Match NEW(146) to NEW(146)
Match CALL(43) to CALL(43)
Match NAME: proj(149) to NAME: proj(149)
Match NAME: findById(71) to NAME: findById(71)
Match FUNCTION(124) to FUNCTION(124)
Match NAME: req(73) to NAME: req(73)
Match NAME: saved(165) to NAME: saved(165)
Match GETPROP(49) to GETPROP(49)
Match NAME: get(31) to NAME: get(31)
Match EXPR_VOID(60) to EXPR_VOID(60)
Match NAME: Project(70) to NAME: Project(70)
Match STRING: /:id(101) to STRING: /:id(101)
Match NAME: next(189) to NAME: next(189)
Match GETPROP(39) to GETPROP(39)
Update NAME: user(150) to userId

user(150) was updated. What does 150 mean? Does this correpond to something in the original AST? Thank you!

jrfaller commented 5 years ago

Hi, it's just a numeric identifier for the node's type (here 150 corresponds to NAME nodes). However, it will be gone in the next version, in which we will only rely on a ruby's symbol like implementation for defining a node type.

Regards!

elizabethdinella commented 5 years ago

Oh, thanks! So is there any way to identify which node in the original AST was updated?

jrfaller commented 5 years ago

If you are using Java code to generate this, you can retrieve the position of the node in the source file. In next version, node position will be included in the default output.

elizabethdinella commented 5 years ago

Hi, I am still not understanding how these numbers correspond to the type of node. For example, there are multiple name nodes with many different numbers (73, 165, 150, etc). Do these numbers somehow distinguish between different name nodes?

jrfaller commented 5 years ago

OK just to know what language are you analyzing?

elizabethdinella commented 5 years ago

Javascript

jrfaller commented 5 years ago

OK, since you are not using C where there is a regression, I recommend you to pull the latest version of the develop branch you will have a way better text output for the textual diff. I do not recall that much the old output since it was not used, so you're right that it does not seem to be the node's type id, so perhaps it is the node id, which is unique in its tree.

In the latest version, default text output is like that :

match
---
NAME: event [844,849]
NAME: event [844,849]
===
match
---
GETPROP [968,991]
GETPROP [968,991]
===
match
---
NAME: startsWith [763,773]
NAME: startsWith [763,773]

Where [763,773] corresponds to the starting and ending character index of the node in the source file.

elizabethdinella commented 5 years ago

Thanks! This is excatly what i'm looking for. However the same files produce different diffs in the new version.

insert-node
---
String: "expression" [4484,4496]
to
FIELD [4484,63325]
at 0
===
insert-node
---
String: "callee" [4558,4566]
to
FIELD [4558,53880]
at 0
===
insert-node
---
String: "object" [4677,4685]
to
FIELD [4677,53721]
at 0
===
update-node
---
String: "user" [45784,45790]
replace "user" by "userId"
===
delete-node
---
String: "body" [57,63]
===
===
delete-node
---
String: "expression" [4484,4496]
===
===
delete-node
---
String: "callee" [4558,4566]
===
===
delete-node
---
String: "object" [4677,4685]
===

which was just a single update in the original version. Is there away to change matching parameters to get the matching output I was getting previously?

jrfaller commented 5 years ago

Can you attach your test files so that I can analyze them?

elizabethdinella commented 5 years ago

Yes, they're JSON representations fo JS es6 files that were generated using esprima.

{
  "type": "Program",
  "body": [
    {
      "type": "VariableDeclaration",
      "declarations": [
        {
          "type": "VariableDeclarator",
          "id": {
            "type": "Identifier",
            "name": "express"
          },
          "init": {
            "type": "CallExpression",
            "callee": {
              "type": "Identifier",
              "name": "require"
            },
            "arguments": [
              {
                "type": "Literal",
                "value": "express",
                "raw": "'express'"
              }
            ]
          }
        }
      ],
      "kind": "const"
    },
    {
      "type": "VariableDeclaration",
      "declarations": [
        {
          "type": "VariableDeclarator",
          "id": {
            "type": "Identifier",
            "name": "router"
          },
          "init": {
            "type": "CallExpression",
            "callee": {
              "type": "MemberExpression",
              "computed": false,
              "object": {
                "type": "Identifier",
                "name": "express"
              },
              "property": {
                "type": "Identifier",
                "name": "Router"
              }
            },
            "arguments": []
          }
        }
      ],
      "kind": "const"
    },
    {
      "type": "VariableDeclaration",
      "declarations": [
        {
          "type": "VariableDeclarator",
          "id": {
            "type": "Identifier",
            "name": "bodyParser"
          },
          "init": {
            "type": "CallExpression",
            "callee": {
              "type": "MemberExpression",
              "computed": false,
              "object": {
                "type": "CallExpression",
                "callee": {
                  "type": "Identifier",
                  "name": "require"
                },
                "arguments": [
                  {
                    "type": "Literal",
                    "value": "body-parser",
                    "raw": "'body-parser'"
                  }
                ]
              },
              "property": {
                "type": "Identifier",
                "name": "json"
              }
            },
            "arguments": []
          }
        }
      ],
      "kind": "const"
    },
    {
      "type": "VariableDeclaration",
      "declarations": [
        {
          "type": "VariableDeclarator",
          "id": {
            "type": "Identifier",
            "name": "Project"
          },
          "init": {
            "type": "CallExpression",
            "callee": {
              "type": "Identifier",
              "name": "require"
            },
            "arguments": [
              {
                "type": "Literal",
                "value": "../models/project",
                "raw": "'../models/project'"
              }
            ]
          }
        }
      ],
      "kind": "const"
    },
    {
      "type": "ExpressionStatement",
      "expression": {
        "type": "CallExpression",
        "callee": {
          "type": "MemberExpression",
          "computed": false,
          "object": {
            "type": "CallExpression",
            "callee": {
              "type": "MemberExpression",
              "computed": false,
              "object": {
                "type": "CallExpression",
                "callee": {
                  "type": "MemberExpression",
                  "computed": false,
                  "object": {
                    "type": "CallExpression",
                    "callee": {
                      "type": "MemberExpression",
                      "computed": false,
                      "object": {
                        "type": "CallExpression",
                        "callee": {
                          "type": "MemberExpression",
                          "computed": false,
                          "object": {
                            "type": "Identifier",
                            "name": "router"
                          },
                          "property": {
                            "type": "Identifier",
                            "name": "get"
                          }
                        },
                        "arguments": [
                          {
                            "type": "Literal",
                            "value": "/",
                            "raw": "'/'"
                          },
                          {
                            "type": "ArrowFunctionExpression",
                            "id": null,
                            "params": [
                              {
                                "type": "Identifier",
                                "name": "req"
                              },
                              {
                                "type": "Identifier",
                                "name": "res"
                              },
                              {
                                "type": "Identifier",
                                "name": "next"
                              }
                            ],
                            "body": {
                              "type": "BlockStatement",
                              "body": [
                                {
                                  "type": "ExpressionStatement",
                                  "expression": {
                                    "type": "CallExpression",
                                    "callee": {
                                      "type": "MemberExpression",
                                      "computed": false,
                                      "object": {
                                        "type": "CallExpression",
                                        "callee": {
                                          "type": "MemberExpression",
                                          "computed": false,
                                          "object": {
                                            "type": "CallExpression",
                                            "callee": {
                                              "type": "MemberExpression",
                                              "computed": false,
                                              "object": {
                                                "type": "CallExpression",
                                                "callee": {
                                                  "type": "MemberExpression",
                                                  "computed": false,
                                                  "object": {
                                                    "type": "Identifier",
                                                    "name": "Project"
                                                  },
                                                  "property": {
                                                    "type": "Identifier",
                                                    "name": "find"
                                                  }
                                                },
                                                "arguments": []
                                              },
                                              "property": {
                                                "type": "Identifier",
                                                "name": "lean"
                                              }
                                            },
                                            "arguments": []
                                          },
                                          "property": {
                                            "type": "Identifier",
                                            "name": "then"
                                          }
                                        },
                                        "arguments": [
                                          {
                                            "type": "ArrowFunctionExpression",
                                            "id": null,
                                            "params": [
                                              {
                                                "type": "Identifier",
                                                "name": "projects"
                                              }
                                            ],
                                            "body": {
                                              "type": "CallExpression",
                                              "callee": {
                                                "type": "MemberExpression",
                                                "computed": false,
                                                "object": {
                                                  "type": "Identifier",
                                                  "name": "res"
                                                },
                                                "property": {
                                                  "type": "Identifier",
                                                  "name": "send"
                                                }
                                              },
                                              "arguments": [
                                                {
                                                  "type": "Identifier",
                                                  "name": "projects"
                                                }
                                              ]
                                            },
                                            "generator": false,
                                            "expression": true,
                                            "async": false
                                          }
                                        ]
                                      },
                                      "property": {
                                        "type": "Identifier",
                                        "name": "catch"
                                      }
                                    },
                                    "arguments": [
                                      {
                                        "type": "Identifier",
                                        "name": "next"
                                      }
                                    ]
                                  }
                                }
                              ]
                            },
                            "generator": false,
                            "expression": false,
                            "async": false
                          }
                        ]
                      },
                      "property": {
                        "type": "Identifier",
                        "name": "get"
                      }
                    },
                    "arguments": [
                      {
                        "type": "Literal",
                        "value": "/:id",
                        "raw": "'/:id'"
                      },
                      {
                        "type": "ArrowFunctionExpression",
                        "id": null,
                        "params": [
                          {
                            "type": "Identifier",
                            "name": "req"
                          },
                          {
                            "type": "Identifier",
                            "name": "res"
                          },
                          {
                            "type": "Identifier",
                            "name": "next"
                          }
                        ],
                        "body": {
                          "type": "BlockStatement",
                          "body": [
                            {
                              "type": "ExpressionStatement",
                              "expression": {
                                "type": "CallExpression",
                                "callee": {
                                  "type": "MemberExpression",
                                  "computed": false,
                                  "object": {
                                    "type": "CallExpression",
                                    "callee": {
                                      "type": "MemberExpression",
                                      "computed": false,
                                      "object": {
                                        "type": "CallExpression",
                                        "callee": {
                                          "type": "MemberExpression",
                                          "computed": false,
                                          "object": {
                                            "type": "Identifier",
                                            "name": "Project"
                                          },
                                          "property": {
                                            "type": "Identifier",
                                            "name": "findById"
                                          }
                                        },
                                        "arguments": [
                                          {
                                            "type": "MemberExpression",
                                            "computed": false,
                                            "object": {
                                              "type": "MemberExpression",
                                              "computed": false,
                                              "object": {
                                                "type": "Identifier",
                                                "name": "req"
                                              },
                                              "property": {
                                                "type": "Identifier",
                                                "name": "params"
                                              }
                                            },
                                            "property": {
                                              "type": "Identifier",
                                              "name": "id"
                                            }
                                          }
                                        ]
                                      },
                                      "property": {
                                        "type": "Identifier",
                                        "name": "then"
                                      }
                                    },
                                    "arguments": [
                                      {
                                        "type": "ArrowFunctionExpression",
                                        "id": null,
                                        "params": [
                                          {
                                            "type": "Identifier",
                                            "name": "project"
                                          }
                                        ],
                                        "body": {
                                          "type": "CallExpression",
                                          "callee": {
                                            "type": "MemberExpression",
                                            "computed": false,
                                            "object": {
                                              "type": "Identifier",
                                              "name": "res"
                                            },
                                            "property": {
                                              "type": "Identifier",
                                              "name": "send"
                                            }
                                          },
                                          "arguments": [
                                            {
                                              "type": "Identifier",
                                              "name": "project"
                                            }
                                          ]
                                        },
                                        "generator": false,
                                        "expression": true,
                                        "async": false
                                      }
                                    ]
                                  },
                                  "property": {
                                    "type": "Identifier",
                                    "name": "catch"
                                  }
                                },
                                "arguments": [
                                  {
                                    "type": "Identifier",
                                    "name": "next"
                                  }
                                ]
                              }
                            }
                          ]
                        },
                        "generator": false,
                        "expression": false,
                        "async": false
                      }
                    ]
                  },
                  "property": {
                    "type": "Identifier",
                    "name": "delete"
                  }
                },
                "arguments": [
                  {
                    "type": "Literal",
                    "value": "/:id",
                    "raw": "'/:id'"
                  },
                  {
                    "type": "ArrowFunctionExpression",
                    "id": null,
                    "params": [
                      {
                        "type": "Identifier",
                        "name": "req"
                      },
                      {
                        "type": "Identifier",
                        "name": "res"
                      },
                      {
                        "type": "Identifier",
                        "name": "next"
                      }
                    ],
                    "body": {
                      "type": "BlockStatement",
                      "body": [
                        {
                          "type": "ExpressionStatement",
                          "expression": {
                            "type": "CallExpression",
                            "callee": {
                              "type": "MemberExpression",
                              "computed": false,
                              "object": {
                                "type": "CallExpression",
                                "callee": {
                                  "type": "MemberExpression",
                                  "computed": false,
                                  "object": {
                                    "type": "CallExpression",
                                    "callee": {
                                      "type": "MemberExpression",
                                      "computed": false,
                                      "object": {
                                        "type": "Identifier",
                                        "name": "Project"
                                      },
                                      "property": {
                                        "type": "Identifier",
                                        "name": "findByIdAndRemove"
                                      }
                                    },
                                    "arguments": [
                                      {
                                        "type": "MemberExpression",
                                        "computed": false,
                                        "object": {
                                          "type": "MemberExpression",
                                          "computed": false,
                                          "object": {
                                            "type": "Identifier",
                                            "name": "req"
                                          },
                                          "property": {
                                            "type": "Identifier",
                                            "name": "params"
                                          }
                                        },
                                        "property": {
                                          "type": "Identifier",
                                          "name": "id"
                                        }
                                      }
                                    ]
                                  },
                                  "property": {
                                    "type": "Identifier",
                                    "name": "then"
                                  }
                                },
                                "arguments": [
                                  {
                                    "type": "ArrowFunctionExpression",
                                    "id": null,
                                    "params": [
                                      {
                                        "type": "Identifier",
                                        "name": "deleted"
                                      }
                                    ],
                                    "body": {
                                      "type": "CallExpression",
                                      "callee": {
                                        "type": "MemberExpression",
                                        "computed": false,
                                        "object": {
                                          "type": "Identifier",
                                          "name": "res"
                                        },
                                        "property": {
                                          "type": "Identifier",
                                          "name": "send"
                                        }
                                      },
                                      "arguments": [
                                        {
                                          "type": "Identifier",
                                          "name": "deleted"
                                        }
                                      ]
                                    },
                                    "generator": false,
                                    "expression": true,
                                    "async": false
                                  }
                                ]
                              },
                              "property": {
                                "type": "Identifier",
                                "name": "catch"
                              }
                            },
                            "arguments": [
                              {
                                "type": "Identifier",
                                "name": "next"
                              }
                            ]
                          }
                        }
                      ]
                    },
                    "generator": false,
                    "expression": false,
                    "async": false
                  }
                ]
              },
              "property": {
                "type": "Identifier",
                "name": "post"
              }
            },
            "arguments": [
              {
                "type": "Literal",
                "value": "/",
                "raw": "'/'"
              },
              {
                "type": "Identifier",
                "name": "bodyParser"
              },
              {
                "type": "ArrowFunctionExpression",
                "id": null,
                "params": [
                  {
                    "type": "Identifier",
                    "name": "req"
                  },
                  {
                    "type": "Identifier",
                    "name": "res"
                  },
                  {
                    "type": "Identifier",
                    "name": "next"
                  }
                ],
                "body": {
                  "type": "BlockStatement",
                  "body": [
                    {
                      "type": "VariableDeclaration",
                      "declarations": [
                        {
                          "type": "VariableDeclarator",
                          "id": {
                            "type": "Identifier",
                            "name": "proj"
                          },
                          "init": {
                            "type": "NewExpression",
                            "callee": {
                              "type": "Identifier",
                              "name": "Project"
                            },
                            "arguments": [
                              {
                                "type": "MemberExpression",
                                "computed": false,
                                "object": {
                                  "type": "Identifier",
                                  "name": "req"
                                },
                                "property": {
                                  "type": "Identifier",
                                  "name": "body"
                                }
                              }
                            ]
                          }
                        }
                      ],
                      "kind": "let"
                    },
                    {
                      "type": "ExpressionStatement",
                      "expression": {
                        "type": "AssignmentExpression",
                        "operator": "=",
                        "left": {
                          "type": "MemberExpression",
                          "computed": false,
                          "object": {
                            "type": "Identifier",
                            "name": "proj"
                          },
                          "property": {
                            "type": "Identifier",
                            "name": "user"
                          }
                        },
                        "right": {
                          "type": "MemberExpression",
                          "computed": false,
                          "object": {
                            "type": "MemberExpression",
                            "computed": false,
                            "object": {
                              "type": "Identifier",
                              "name": "req"
                            },
                            "property": {
                              "type": "Identifier",
                              "name": "user"
                            }
                          },
                          "property": {
                            "type": "Identifier",
                            "name": "id"
                          }
                        }
                      }
                    },
                    {
                      "type": "ExpressionStatement",
                      "expression": {
                        "type": "CallExpression",
                        "callee": {
                          "type": "MemberExpression",
                          "computed": false,
                          "object": {
                            "type": "CallExpression",
                            "callee": {
                              "type": "MemberExpression",
                              "computed": false,
                              "object": {
                                "type": "CallExpression",
                                "callee": {
                                  "type": "MemberExpression",
                                  "computed": false,
                                  "object": {
                                    "type": "Identifier",
                                    "name": "proj"
                                  },
                                  "property": {
                                    "type": "Identifier",
                                    "name": "save"
                                  }
                                },
                                "arguments": []
                              },
                              "property": {
                                "type": "Identifier",
                                "name": "then"
                              }
                            },
                            "arguments": [
                              {
                                "type": "ArrowFunctionExpression",
                                "id": null,
                                "params": [
                                  {
                                    "type": "Identifier",
                                    "name": "saved"
                                  }
                                ],
                                "body": {
                                  "type": "CallExpression",
                                  "callee": {
                                    "type": "MemberExpression",
                                    "computed": false,
                                    "object": {
                                      "type": "Identifier",
                                      "name": "res"
                                    },
                                    "property": {
                                      "type": "Identifier",
                                      "name": "send"
                                    }
                                  },
                                  "arguments": [
                                    {
                                      "type": "Identifier",
                                      "name": "saved"
                                    }
                                  ]
                                },
                                "generator": false,
                                "expression": true,
                                "async": false
                              }
                            ]
                          },
                          "property": {
                            "type": "Identifier",
                            "name": "catch"
                          }
                        },
                        "arguments": [
                          {
                            "type": "Identifier",
                            "name": "next"
                          }
                        ]
                      }
                    }
                  ]
                },
                "generator": false,
                "expression": false,
                "async": false
              }
            ]
          },
          "property": {
            "type": "Identifier",
            "name": "put"
          }
        },
        "arguments": [
          {
            "type": "Literal",
            "value": "/:id",
            "raw": "'/:id'"
          },
          {
            "type": "Identifier",
            "name": "bodyParser"
          },
          {
            "type": "ArrowFunctionExpression",
            "id": null,
            "params": [
              {
                "type": "Identifier",
                "name": "req"
              },
              {
                "type": "Identifier",
                "name": "res"
              },
              {
                "type": "Identifier",
                "name": "next"
              }
            ],
            "body": {
              "type": "BlockStatement",
              "body": [
                {
                  "type": "ExpressionStatement",
                  "expression": {
                    "type": "CallExpression",
                    "callee": {
                      "type": "MemberExpression",
                      "computed": false,
                      "object": {
                        "type": "CallExpression",
                        "callee": {
                          "type": "MemberExpression",
                          "computed": false,
                          "object": {
                            "type": "CallExpression",
                            "callee": {
                              "type": "MemberExpression",
                              "computed": false,
                              "object": {
                                "type": "Identifier",
                                "name": "Project"
                              },
                              "property": {
                                "type": "Identifier",
                                "name": "findByIdAndUpdate"
                              }
                            },
                            "arguments": [
                              {
                                "type": "MemberExpression",
                                "computed": false,
                                "object": {
                                  "type": "MemberExpression",
                                  "computed": false,
                                  "object": {
                                    "type": "Identifier",
                                    "name": "req"
                                  },
                                  "property": {
                                    "type": "Identifier",
                                    "name": "params"
                                  }
                                },
                                "property": {
                                  "type": "Identifier",
                                  "name": "id"
                                }
                              },
                              {
                                "type": "MemberExpression",
                                "computed": false,
                                "object": {
                                  "type": "Identifier",
                                  "name": "req"
                                },
                                "property": {
                                  "type": "Identifier",
                                  "name": "body"
                                }
                              }
                            ]
                          },
                          "property": {
                            "type": "Identifier",
                            "name": "then"
                          }
                        },
                        "arguments": [
                          {
                            "type": "ArrowFunctionExpression",
                            "id": null,
                            "params": [
                              {
                                "type": "Identifier",
                                "name": "saved"
                              }
                            ],
                            "body": {
                              "type": "CallExpression",
                              "callee": {
                                "type": "MemberExpression",
                                "computed": false,
                                "object": {
                                  "type": "Identifier",
                                  "name": "res"
                                },
                                "property": {
                                  "type": "Identifier",
                                  "name": "send"
                                }
                              },
                              "arguments": [
                                {
                                  "type": "Identifier",
                                  "name": "saved"
                                }
                              ]
                            },
                            "generator": false,
                            "expression": true,
                            "async": false
                          }
                        ]
                      },
                      "property": {
                        "type": "Identifier",
                        "name": "catch"
                      }
                    },
                    "arguments": [
                      {
                        "type": "Identifier",
                        "name": "next"
                      }
                    ]
                  }
                }
              ]
            },
            "generator": false,
            "expression": false,
            "async": false
          }
        ]
      }
    },
    {
      "type": "ExpressionStatement",
      "expression": {
        "type": "AssignmentExpression",
        "operator": "=",
        "left": {
          "type": "MemberExpression",
          "computed": false,
          "object": {
            "type": "Identifier",
            "name": "module"
          },
          "property": {
            "type": "Identifier",
            "name": "exports"
          }
        },
        "right": {
          "type": "Identifier",
          "name": "router"
        }
      }
    }
  ],
  "sourceType": "script"
}

and

{
  "type": "Program",
  "body": [
    {
      "type": "VariableDeclaration",
      "declarations": [
        {
          "type": "VariableDeclarator",
          "id": {
            "type": "Identifier",
            "name": "express"
          },
          "init": {
            "type": "CallExpression",
            "callee": {
              "type": "Identifier",
              "name": "require"
            },
            "arguments": [
              {
                "type": "Literal",
                "value": "express",
                "raw": "'express'"
              }
            ]
          }
        }
      ],
      "kind": "const"
    },
    {
      "type": "VariableDeclaration",
      "declarations": [
        {
          "type": "VariableDeclarator",
          "id": {
            "type": "Identifier",
            "name": "router"
          },
          "init": {
            "type": "CallExpression",
            "callee": {
              "type": "MemberExpression",
              "computed": false,
              "object": {
                "type": "Identifier",
                "name": "express"
              },
              "property": {
                "type": "Identifier",
                "name": "Router"
              }
            },
            "arguments": []
          }
        }
      ],
      "kind": "const"
    },
    {
      "type": "VariableDeclaration",
      "declarations": [
        {
          "type": "VariableDeclarator",
          "id": {
            "type": "Identifier",
            "name": "bodyParser"
          },
          "init": {
            "type": "CallExpression",
            "callee": {
              "type": "MemberExpression",
              "computed": false,
              "object": {
                "type": "CallExpression",
                "callee": {
                  "type": "Identifier",
                  "name": "require"
                },
                "arguments": [
                  {
                    "type": "Literal",
                    "value": "body-parser",
                    "raw": "'body-parser'"
                  }
                ]
              },
              "property": {
                "type": "Identifier",
                "name": "json"
              }
            },
            "arguments": []
          }
        }
      ],
      "kind": "const"
    },
    {
      "type": "VariableDeclaration",
      "declarations": [
        {
          "type": "VariableDeclarator",
          "id": {
            "type": "Identifier",
            "name": "Project"
          },
          "init": {
            "type": "CallExpression",
            "callee": {
              "type": "Identifier",
              "name": "require"
            },
            "arguments": [
              {
                "type": "Literal",
                "value": "../models/project",
                "raw": "'../models/project'"
              }
            ]
          }
        }
      ],
      "kind": "const"
    },
    {
      "type": "ExpressionStatement",
      "expression": {
        "type": "CallExpression",
        "callee": {
          "type": "MemberExpression",
          "computed": false,
          "object": {
            "type": "CallExpression",
            "callee": {
              "type": "MemberExpression",
              "computed": false,
              "object": {
                "type": "CallExpression",
                "callee": {
                  "type": "MemberExpression",
                  "computed": false,
                  "object": {
                    "type": "CallExpression",
                    "callee": {
                      "type": "MemberExpression",
                      "computed": false,
                      "object": {
                        "type": "CallExpression",
                        "callee": {
                          "type": "MemberExpression",
                          "computed": false,
                          "object": {
                            "type": "Identifier",
                            "name": "router"
                          },
                          "property": {
                            "type": "Identifier",
                            "name": "get"
                          }
                        },
                        "arguments": [
                          {
                            "type": "Literal",
                            "value": "/",
                            "raw": "'/'"
                          },
                          {
                            "type": "ArrowFunctionExpression",
                            "id": null,
                            "params": [
                              {
                                "type": "Identifier",
                                "name": "req"
                              },
                              {
                                "type": "Identifier",
                                "name": "res"
                              },
                              {
                                "type": "Identifier",
                                "name": "next"
                              }
                            ],
                            "body": {
                              "type": "BlockStatement",
                              "body": [
                                {
                                  "type": "ExpressionStatement",
                                  "expression": {
                                    "type": "CallExpression",
                                    "callee": {
                                      "type": "MemberExpression",
                                      "computed": false,
                                      "object": {
                                        "type": "CallExpression",
                                        "callee": {
                                          "type": "MemberExpression",
                                          "computed": false,
                                          "object": {
                                            "type": "CallExpression",
                                            "callee": {
                                              "type": "MemberExpression",
                                              "computed": false,
                                              "object": {
                                                "type": "CallExpression",
                                                "callee": {
                                                  "type": "MemberExpression",
                                                  "computed": false,
                                                  "object": {
                                                    "type": "Identifier",
                                                    "name": "Project"
                                                  },
                                                  "property": {
                                                    "type": "Identifier",
                                                    "name": "find"
                                                  }
                                                },
                                                "arguments": []
                                              },
                                              "property": {
                                                "type": "Identifier",
                                                "name": "lean"
                                              }
                                            },
                                            "arguments": []
                                          },
                                          "property": {
                                            "type": "Identifier",
                                            "name": "then"
                                          }
                                        },
                                        "arguments": [
                                          {
                                            "type": "ArrowFunctionExpression",
                                            "id": null,
                                            "params": [
                                              {
                                                "type": "Identifier",
                                                "name": "projects"
                                              }
                                            ],
                                            "body": {
                                              "type": "CallExpression",
                                              "callee": {
                                                "type": "MemberExpression",
                                                "computed": false,
                                                "object": {
                                                  "type": "Identifier",
                                                  "name": "res"
                                                },
                                                "property": {
                                                  "type": "Identifier",
                                                  "name": "send"
                                                }
                                              },
                                              "arguments": [
                                                {
                                                  "type": "Identifier",
                                                  "name": "projects"
                                                }
                                              ]
                                            },
                                            "generator": false,
                                            "expression": true,
                                            "async": false
                                          }
                                        ]
                                      },
                                      "property": {
                                        "type": "Identifier",
                                        "name": "catch"
                                      }
                                    },
                                    "arguments": [
                                      {
                                        "type": "Identifier",
                                        "name": "next"
                                      }
                                    ]
                                  }
                                }
                              ]
                            },
                            "generator": false,
                            "expression": false,
                            "async": false
                          }
                        ]
                      },
                      "property": {
                        "type": "Identifier",
                        "name": "get"
                      }
                    },
                    "arguments": [
                      {
                        "type": "Literal",
                        "value": "/:id",
                        "raw": "'/:id'"
                      },
                      {
                        "type": "ArrowFunctionExpression",
                        "id": null,
                        "params": [
                          {
                            "type": "Identifier",
                            "name": "req"
                          },
                          {
                            "type": "Identifier",
                            "name": "res"
                          },
                          {
                            "type": "Identifier",
                            "name": "next"
                          }
                        ],
                        "body": {
                          "type": "BlockStatement",
                          "body": [
                            {
                              "type": "ExpressionStatement",
                              "expression": {
                                "type": "CallExpression",
                                "callee": {
                                  "type": "MemberExpression",
                                  "computed": false,
                                  "object": {
                                    "type": "CallExpression",
                                    "callee": {
                                      "type": "MemberExpression",
                                      "computed": false,
                                      "object": {
                                        "type": "CallExpression",
                                        "callee": {
                                          "type": "MemberExpression",
                                          "computed": false,
                                          "object": {
                                            "type": "Identifier",
                                            "name": "Project"
                                          },
                                          "property": {
                                            "type": "Identifier",
                                            "name": "findById"
                                          }
                                        },
                                        "arguments": [
                                          {
                                            "type": "MemberExpression",
                                            "computed": false,
                                            "object": {
                                              "type": "MemberExpression",
                                              "computed": false,
                                              "object": {
                                                "type": "Identifier",
                                                "name": "req"
                                              },
                                              "property": {
                                                "type": "Identifier",
                                                "name": "params"
                                              }
                                            },
                                            "property": {
                                              "type": "Identifier",
                                              "name": "id"
                                            }
                                          }
                                        ]
                                      },
                                      "property": {
                                        "type": "Identifier",
                                        "name": "then"
                                      }
                                    },
                                    "arguments": [
                                      {
                                        "type": "ArrowFunctionExpression",
                                        "id": null,
                                        "params": [
                                          {
                                            "type": "Identifier",
                                            "name": "project"
                                          }
                                        ],
                                        "body": {
                                          "type": "CallExpression",
                                          "callee": {
                                            "type": "MemberExpression",
                                            "computed": false,
                                            "object": {
                                              "type": "Identifier",
                                              "name": "res"
                                            },
                                            "property": {
                                              "type": "Identifier",
                                              "name": "send"
                                            }
                                          },
                                          "arguments": [
                                            {
                                              "type": "Identifier",
                                              "name": "project"
                                            }
                                          ]
                                        },
                                        "generator": false,
                                        "expression": true,
                                        "async": false
                                      }
                                    ]
                                  },
                                  "property": {
                                    "type": "Identifier",
                                    "name": "catch"
                                  }
                                },
                                "arguments": [
                                  {
                                    "type": "Identifier",
                                    "name": "next"
                                  }
                                ]
                              }
                            }
                          ]
                        },
                        "generator": false,
                        "expression": false,
                        "async": false
                      }
                    ]
                  },
                  "property": {
                    "type": "Identifier",
                    "name": "delete"
                  }
                },
                "arguments": [
                  {
                    "type": "Literal",
                    "value": "/:id",
                    "raw": "'/:id'"
                  },
                  {
                    "type": "ArrowFunctionExpression",
                    "id": null,
                    "params": [
                      {
                        "type": "Identifier",
                        "name": "req"
                      },
                      {
                        "type": "Identifier",
                        "name": "res"
                      },
                      {
                        "type": "Identifier",
                        "name": "next"
                      }
                    ],
                    "body": {
                      "type": "BlockStatement",
                      "body": [
                        {
                          "type": "ExpressionStatement",
                          "expression": {
                            "type": "CallExpression",
                            "callee": {
                              "type": "MemberExpression",
                              "computed": false,
                              "object": {
                                "type": "CallExpression",
                                "callee": {
                                  "type": "MemberExpression",
                                  "computed": false,
                                  "object": {
                                    "type": "CallExpression",
                                    "callee": {
                                      "type": "MemberExpression",
                                      "computed": false,
                                      "object": {
                                        "type": "Identifier",
                                        "name": "Project"
                                      },
                                      "property": {
                                        "type": "Identifier",
                                        "name": "findByIdAndRemove"
                                      }
                                    },
                                    "arguments": [
                                      {
                                        "type": "MemberExpression",
                                        "computed": false,
                                        "object": {
                                          "type": "MemberExpression",
                                          "computed": false,
                                          "object": {
                                            "type": "Identifier",
                                            "name": "req"
                                          },
                                          "property": {
                                            "type": "Identifier",
                                            "name": "params"
                                          }
                                        },
                                        "property": {
                                          "type": "Identifier",
                                          "name": "id"
                                        }
                                      }
                                    ]
                                  },
                                  "property": {
                                    "type": "Identifier",
                                    "name": "then"
                                  }
                                },
                                "arguments": [
                                  {
                                    "type": "ArrowFunctionExpression",
                                    "id": null,
                                    "params": [
                                      {
                                        "type": "Identifier",
                                        "name": "deleted"
                                      }
                                    ],
                                    "body": {
                                      "type": "CallExpression",
                                      "callee": {
                                        "type": "MemberExpression",
                                        "computed": false,
                                        "object": {
                                          "type": "Identifier",
                                          "name": "res"
                                        },
                                        "property": {
                                          "type": "Identifier",
                                          "name": "send"
                                        }
                                      },
                                      "arguments": [
                                        {
                                          "type": "Identifier",
                                          "name": "deleted"
                                        }
                                      ]
                                    },
                                    "generator": false,
                                    "expression": true,
                                    "async": false
                                  }
                                ]
                              },
                              "property": {
                                "type": "Identifier",
                                "name": "catch"
                              }
                            },
                            "arguments": [
                              {
                                "type": "Identifier",
                                "name": "next"
                              }
                            ]
                          }
                        }
                      ]
                    },
                    "generator": false,
                    "expression": false,
                    "async": false
                  }
                ]
              },
              "property": {
                "type": "Identifier",
                "name": "post"
              }
            },
            "arguments": [
              {
                "type": "Literal",
                "value": "/",
                "raw": "'/'"
              },
              {
                "type": "Identifier",
                "name": "bodyParser"
              },
              {
                "type": "ArrowFunctionExpression",
                "id": null,
                "params": [
                  {
                    "type": "Identifier",
                    "name": "req"
                  },
                  {
                    "type": "Identifier",
                    "name": "res"
                  },
                  {
                    "type": "Identifier",
                    "name": "next"
                  }
                ],
                "body": {
                  "type": "BlockStatement",
                  "body": [
                    {
                      "type": "VariableDeclaration",
                      "declarations": [
                        {
                          "type": "VariableDeclarator",
                          "id": {
                            "type": "Identifier",
                            "name": "proj"
                          },
                          "init": {
                            "type": "NewExpression",
                            "callee": {
                              "type": "Identifier",
                              "name": "Project"
                            },
                            "arguments": [
                              {
                                "type": "MemberExpression",
                                "computed": false,
                                "object": {
                                  "type": "Identifier",
                                  "name": "req"
                                },
                                "property": {
                                  "type": "Identifier",
                                  "name": "body"
                                }
                              }
                            ]
                          }
                        }
                      ],
                      "kind": "let"
                    },
                    {
                      "type": "ExpressionStatement",
                      "expression": {
                        "type": "AssignmentExpression",
                        "operator": "=",
                        "left": {
                          "type": "MemberExpression",
                          "computed": false,
                          "object": {
                            "type": "Identifier",
                            "name": "proj"
                          },
                          "property": {
                            "type": "Identifier",
                            "name": "userId"
                          }
                        },
                        "right": {
                          "type": "MemberExpression",
                          "computed": false,
                          "object": {
                            "type": "MemberExpression",
                            "computed": false,
                            "object": {
                              "type": "Identifier",
                              "name": "req"
                            },
                            "property": {
                              "type": "Identifier",
                              "name": "user"
                            }
                          },
                          "property": {
                            "type": "Identifier",
                            "name": "id"
                          }
                        }
                      }
                    },
                    {
                      "type": "ExpressionStatement",
                      "expression": {
                        "type": "CallExpression",
                        "callee": {
                          "type": "MemberExpression",
                          "computed": false,
                          "object": {
                            "type": "CallExpression",
                            "callee": {
                              "type": "MemberExpression",
                              "computed": false,
                              "object": {
                                "type": "CallExpression",
                                "callee": {
                                  "type": "MemberExpression",
                                  "computed": false,
                                  "object": {
                                    "type": "Identifier",
                                    "name": "proj"
                                  },
                                  "property": {
                                    "type": "Identifier",
                                    "name": "save"
                                  }
                                },
                                "arguments": []
                              },
                              "property": {
                                "type": "Identifier",
                                "name": "then"
                              }
                            },
                            "arguments": [
                              {
                                "type": "ArrowFunctionExpression",
                                "id": null,
                                "params": [
                                  {
                                    "type": "Identifier",
                                    "name": "saved"
                                  }
                                ],
                                "body": {
                                  "type": "CallExpression",
                                  "callee": {
                                    "type": "MemberExpression",
                                    "computed": false,
                                    "object": {
                                      "type": "Identifier",
                                      "name": "res"
                                    },
                                    "property": {
                                      "type": "Identifier",
                                      "name": "send"
                                    }
                                  },
                                  "arguments": [
                                    {
                                      "type": "Identifier",
                                      "name": "saved"
                                    }
                                  ]
                                },
                                "generator": false,
                                "expression": true,
                                "async": false
                              }
                            ]
                          },
                          "property": {
                            "type": "Identifier",
                            "name": "catch"
                          }
                        },
                        "arguments": [
                          {
                            "type": "Identifier",
                            "name": "next"
                          }
                        ]
                      }
                    }
                  ]
                },
                "generator": false,
                "expression": false,
                "async": false
              }
            ]
          },
          "property": {
            "type": "Identifier",
            "name": "put"
          }
        },
        "arguments": [
          {
            "type": "Literal",
            "value": "/:id",
            "raw": "'/:id'"
          },
          {
            "type": "Identifier",
            "name": "bodyParser"
          },
          {
            "type": "ArrowFunctionExpression",
            "id": null,
            "params": [
              {
                "type": "Identifier",
                "name": "req"
              },
              {
                "type": "Identifier",
                "name": "res"
              },
              {
                "type": "Identifier",
                "name": "next"
              }
            ],
            "body": {
              "type": "BlockStatement",
              "body": [
                {
                  "type": "ExpressionStatement",
                  "expression": {
                    "type": "CallExpression",
                    "callee": {
                      "type": "MemberExpression",
                      "computed": false,
                      "object": {
                        "type": "CallExpression",
                        "callee": {
                          "type": "MemberExpression",
                          "computed": false,
                          "object": {
                            "type": "CallExpression",
                            "callee": {
                              "type": "MemberExpression",
                              "computed": false,
                              "object": {
                                "type": "Identifier",
                                "name": "Project"
                              },
                              "property": {
                                "type": "Identifier",
                                "name": "findByIdAndUpdate"
                              }
                            },
                            "arguments": [
                              {
                                "type": "MemberExpression",
                                "computed": false,
                                "object": {
                                  "type": "MemberExpression",
                                  "computed": false,
                                  "object": {
                                    "type": "Identifier",
                                    "name": "req"
                                  },
                                  "property": {
                                    "type": "Identifier",
                                    "name": "params"
                                  }
                                },
                                "property": {
                                  "type": "Identifier",
                                  "name": "id"
                                }
                              },
                              {
                                "type": "MemberExpression",
                                "computed": false,
                                "object": {
                                  "type": "Identifier",
                                  "name": "req"
                                },
                                "property": {
                                  "type": "Identifier",
                                  "name": "body"
                                }
                              }
                            ]
                          },
                          "property": {
                            "type": "Identifier",
                            "name": "then"
                          }
                        },
                        "arguments": [
                          {
                            "type": "ArrowFunctionExpression",
                            "id": null,
                            "params": [
                              {
                                "type": "Identifier",
                                "name": "saved"
                              }
                            ],
                            "body": {
                              "type": "CallExpression",
                              "callee": {
                                "type": "MemberExpression",
                                "computed": false,
                                "object": {
                                  "type": "Identifier",
                                  "name": "res"
                                },
                                "property": {
                                  "type": "Identifier",
                                  "name": "send"
                                }
                              },
                              "arguments": [
                                {
                                  "type": "Identifier",
                                  "name": "saved"
                                }
                              ]
                            },
                            "generator": false,
                            "expression": true,
                            "async": false
                          }
                        ]
                      },
                      "property": {
                        "type": "Identifier",
                        "name": "catch"
                      }
                    },
                    "arguments": [
                      {
                        "type": "Identifier",
                        "name": "next"
                      }
                    ]
                  }
                }
              ]
            },
            "generator": false,
            "expression": false,
            "async": false
          }
        ]
      }
    },
    {
      "type": "ExpressionStatement",
      "expression": {
        "type": "AssignmentExpression",
        "operator": "=",
        "left": {
          "type": "MemberExpression",
          "computed": false,
          "object": {
            "type": "Identifier",
            "name": "module"
          },
          "property": {
            "type": "Identifier",
            "name": "exports"
          }
        },
        "right": {
          "type": "Identifier",
          "name": "router"
        }
      }
    }
  ],
  "sourceType": "script"
}
elizabethdinella commented 5 years ago

The same issue occurs with the following files (fed to gumtree as js): https://github.com/nohyoungjin/ensi/blob/2aaa1079575559f6aa8b554a83fed3f8bc565bd0/js/common.js https://github.com/nohyoungjin/ensi/blob/1600e248bfea723f11d5c5332d4ed8292cbce347/js/common.js

In gumtree 2.1.2 the only update is the number on line 47. In gumtree 2.1.3 the diff includes many inserts and delete

jrfaller commented 5 years ago

I see, I could reproduce. Strange thing when I cut down the json files to contain only the first body element, I have no longer the detected useless insertion / deletion. I think there might be a bug inside one of the two phases of matching. I will investigate but files are huge to debug ;)

jrfaller commented 5 years ago

OK I found the problem. TLDR the problem is caused by trees exceeding the size for which the optimal matching algorithm of Zhang and Shasha is launched. Previously the trees were pruned of already matched nodes, and now it's no longer the case (because it was deleting potential anchors, but we are looking for a solution that preserves anchors and reduce search space). Therefore the behavior has changed. I am working on a good tradeof algorithm that seems to work in your case but I have to try it on a big benchmark before releasing it. I will commit it so that you can try.

jrfaller commented 5 years ago

Okay, you can try with the gumtree-simple matcher (-m gumtree-simple argument).