tern icon indicating copy to clipboard operation
tern copied to clipboard

TypeError: Cannot read properties of undefined (reading 'fnType')

Open TrebledJ opened this issue 8 months ago • 0 comments

I've been testing tern on some minified files, but tern doesn't like the following code. I've been banging my head on this for a while to no avail.

curl localhost:52433 -d '{"files":[{"type":"full","name":"test.js","text":"function f(){};try{}catch{f=function(){}}"}]}'

Output:

Request: {
  "files": [
    {
      "type": "full",
      "name": "test.js",
      "text": "function f(){};try{}catch{f=function(){}}"
    }
  ]
}
Response: {}

/Users/idc/idk/node_modules/tern/lib/infer.js:1444
      var inner = node.scope, fn = inner.fnType;
                                         ^

TypeError: Cannot read properties of undefined (reading 'fnType')
    at /Users/idc/idk/node_modules/tern/lib/infer.js:1444:42
    at /Users/idc/idk/node_modules/tern/lib/infer.js:1384:15
    at infer (/Users/idc/idk/node_modules/tern/lib/infer.js:1653:22)
    at /Users/idc/idk/node_modules/tern/lib/infer.js:1501:15
    at /Users/idc/idk/node_modules/tern/lib/infer.js:1384:15
    at infer (/Users/idc/idk/node_modules/tern/lib/infer.js:1653:22)
    at Object.Expression (/Users/idc/idk/node_modules/tern/lib/infer.js:1662:7)
    at c (/Users/idc/idk/node_modules/acorn-walk/dist/walk.js:58:37)
    at base.ExpressionStatement.base.ParenthesizedExpression (/Users/idc/idk/node_modules/acorn-walk/dist/walk.js:204:37)
    at c (/Users/idc/idk/node_modules/acorn-walk/dist/walk.js:58:37)

I've tried the following snippets too:

function f(){};try{}catch{f=function(){}} // error

function f(){}try{f=function(){}}catch{} // ok
function f(){}if(1){f=function(){}} // ok
function f(){} {f=function(){}} // ok

I've also tried this:

// index.js
// run: node index.js
const fs = require('fs');
const tern = require('./node_modules/tern/lib/tern');
const defb = JSON.parse(fs.readFileSync('./node_modules/tern/defs/browser.json').toString());
const s = new tern.Server({defs: [defb]});
s.addFile('test.js', 'function f(){};try{}catch{f=function(){}}');
s.flush();

Same error.

For what it's worth, I'm trying to use tern to parse minified browser JS files, and have a programmatic interface for LSP-like behaviour (go-to-definition / go-to-reference). ~~I'm not sure if there are better suited tools out there, so this could just be me having xy problems.~~ (I guess I'm just looking for a scope analyser.)

I'm not sure if I'm supposed to load a plugin or configure tern differently? I've skimmed and tried a few of the bundled plugins and browsed plugins available on GitHub, but they seem to mostly be for local development.


Edit:

I realise this may be a syntax thing.

function f(){};try{}catch(){f=function(){}}

(parentheses after catch) works fine. Apparently, catch binding is optional is ES2019.

TrebledJ avatar Mar 02 '25 08:03 TrebledJ