3

I am performing Nodejs development in emacs, but my environment seems incorrect. For example, when I run ac-js2-jump-to-definition, I get "no jump location found" in the minibuffer. Also when I run 'tern-find-definition`, I get "No definition found.".

How can I correctly jump to a Javascript definition in emacs?

Here is a sample of code, where I am using the "jump-to-definition":

In auth.js, I have this:

module.exports = function (options) {
  options = options || {}
  auth = {}

  auth.someFunction = function () {
    return "someFunction has been called"
  }

  return auth

}

Then I call auth from here:

var auth = require('auth')()
auth.someFunction()

But it does not work when I put the point over someFunction() above and run M-x ac-js2-jump-to-definition or tern-find-definition. Also, when I run js2-next-error, the require function in require('auth')() above is selected and gives the message "Undeclared variable or function 'require'".

I suspect that my Javascript environment is incorrect, but I don't know what it is. Any suggestions would be appreciated.

Here is my relevant configuration from my init script:

;; JAVASCRIPT-MODE

;; js2-mode provides 4 level of syntax highlighting. They are * 0 or a negative value means none. * 1 adds basic syntax highlighting. * 2 adds highlighting of some Ecma built-in properties. * 3 adds highlighting of many Ecma built-in functions.
(setq js2-highlight-level 3)

(add-hook 'js2-mode-hook
          (lambda ()

            ;; allow window resizing via M-l and M-h
            (local-unset-key (kbd "M-l"))
            (local-unset-key (kbd "M-h"))
            (local-unset-key (kbd "M-j"))

            (local-set-key (kbd "C-j") 'ac-js2-jump-to-definition)
            (local-set-key (kbd "C-c C-n") 'js2-next-error)
            (define-key js2-mode-map (kbd "C-j") 'ac-js2-jump-to-definition)
            (linum-mode)
            (js2-reparse t)
            (ac-js2-mode)))

(add-to-list 'interpreter-mode-alist '("node" . js2-mode))

(add-to-list 'auto-mode-alist
      '("\\.js$" . js2-mode))

(require 'js2-refactor)
(js2r-add-keybindings-with-prefix "C-c C-m")
(add-hook 'js2-mode-hook #'js2-refactor-mode)

(add-to-list 'load-path "~/.emacs.d/tern/emacs/")
(autoload 'tern-mode "tern.el" nil t)
(add-hook 'js-mode-hook (lambda () (tern-mode t)))
modulitos
  • 2,432
  • 1
  • 18
  • 36
  • With Tern, I believe you need to use its CommonJS plugin (http://ternjs.net/doc/manual.html#plugin_commonjs). Check out the Tern docs for my details, I don't know those myself. – Dmitry Oct 10 '15 at 08:33

1 Answers1

5

Thanks to @Dmitry's comment above, I was able to resolve this issue by configuring the default plugins for Tern.

In the tern file from the repo under bin/tern, I edited the default plugins here:

var defaultConfig = {
  libs: [],
  loadEagerly: false,
  plugins: {"commonjs":{}, "node":{}, "requirejs":{}, "node_resolve":{}},
  ecmaScript: true,
  ecmaVersion: 6,
  dependencyBudget: tern.defaultOptions.dependencyBudget
};

Where I changed the plugins property from plugins: {}, to plugins: {"commonjs":{}, "node":{}, "requirejs":{}, "node_resolve":{}},.

Now tern-find-definition is working well!


Furthermore, for the false-positive require statement error, I was able to correct this by running M-x customize group RET js2-mode and enabling Js2 Include Node Externs.

modulitos
  • 2,432
  • 1
  • 18
  • 36