Search code examples
javascriptdojowebstormjsdoc

JSDoc resolve unresolved variable


I use Dojo, and some page widgets are defined outside of code, in HTML template. How can I say to JSDoc that some this fields are really defined?

SomePage.js

define([ "dojo/dom", "dojo/on", "dojo/_base/lang" ],
   function(dom, on, lang) {

      return {        
            init: function(){    
                on(this._myButton, "click", lang.hitch(this, this._foo));
            },

            foo: function(){
                //some code here
            }
      }            
   }
});

SomePage.html

<div>
    <div class="Button" data-dojo-attach-point="_myButton">
        Click me!
    </div>
</div>

In this sample, JSDoc warns me that this._myButton is unresolved. It's really undefined in visible scope, but in fact it is guaranteed to be defined by Dojo via data-dojo-attach-point. How can I override JSDoc and say him that this._myButton is defined for current module? (Webstorm IDE is used)


Solution

  • I had the same problem, and currently it's "solved" not automatically, but through style/discipline. I don't have the code in front of me, but at work we're making widgets something like this:

    define([
            "dojo/declare", 
            "dojo/dom",
            "dojo/on",
            "dojo/_base/lang",
            "dijit/_WidgetBase",
            "dijit/_TemplatedMixin",
            "dijit/_WidgetsInTemplateMixin",
            "dojo/text!./templates/myTemplate.html"
            "dijit/form/Button" // Instantiated in template
    ], function(declare, dom, on, lang, _WidgetBase, _TemplatedMixin, _WidgetsInTemplateMixin, template) {         
            return declare([_WidgetBase, _TemplatedMixin, WidgetsInTemplateMixin],{        
                templateString:template,    
    
    
                // Attachpoints
                _myButtonWidget:null,
                _someThingyNode:null,
    
                init: function(){    
                    on(this._myButtonWidget, "click", lang.hitch(this, this._foo));
                },
                foo: function(){
                    //some code here
                }
            });            
    });
    

    With a myTemplate.html like:

    <div>
        <div data-dojo-type="dijit/form/Button" data-dojo-attach-point="_myButton">
            Click me!
        </div>
        <div data-dojo-attach-point="someThingyNode"><!-- Not a widget--></div>
    </div>
    

    The main takeaway should be that you're making the property without waiting for Dojo to make it at runtime. As a personal convention, attached dijits end in "Widget" and any "vanilla" attachpoints are named "Node".

    Benefits:

    1. It makes your IDE happy so it doesn't pop up unnecessary warnings
    2. It makes your IDE able to offer code-completion
    3. It notifies whomever is reading the .js file that the attachpoints exist
    4. Especially with a lot of attachpoints, you don't have to keep referring to the .html template to figure out whether you're dealing with a sub-widget versus a vanilla DOM node.