VarName is not defined, please fix or add /*global VarName*/ Cloud9 - javascript

Objective
Stop Cloud9 IDE from giving me the warning message.
Background
I am coding JavaScript using the Cloud9 IDE, and wherever I use a class from another file (in the same folder) I get the warning message:
VarName is not defined, please fix or add /*global VarName*/
Now this bugs me and I want to fix it.
The obvious solution would be to just add the comment /*global VarName*/ and be done with it, but I don't believe this is a good practice.
What I tried
After researching, I came across the JavaScript import functionality. In theory, this would allow me to do something like import "myOtherJsFile" and be done with it.
This would be a good standardized solution for the problem, as many other languages take the same approach.
Problem
However, even after adding the said line, I still get the warning. It wont go away.
Questions
Am I doing something wrong?
Is there a way to remove the warning without adding comments to my code?
Is there another way of achieving my objective?

After creating a thread on the official forums I am now confident enough to post here what I learned.
Summary
There were discussed four ways of solving the problem:
Disable the variable warnings withing the project
Creating an .eslintrc file with all the globals
Use of import and export
Adding the comment /*global varName*/ at the top of the file
Solution 1
To avoid the message one can simply turn off the "mark undefined variables" option in the project settings.
Although this solution will work, it will simply stop marking all undefined variables, even the ones you want it to mark. For this reason, I don't recommend this approach.
Solution 2
One can also create an .eslintrc think file with all the globals, like the following:
{
"globals": {
"var1": true,
"var2": false
}
}
More information on configuration: http://eslint.org/docs/user-guide/configuring
The problem with this approach is that every time you create, delete or change a global variable, you have to update the global variables file.
This can quickly become cumbersome and I am not even going to discuss the maintenance impacts on big projects, which would soon become a nightmare.
The way I see it, a techy solution, but not practical.
Solution 3
The preferred solution, as it relies solely on JavaScript and is very similar to the import and export functionalities on other languages.
The problem with this approach however, is that at the time of writing of the answer, no browser supports either the export nor the import keywords:
https://developer.mozilla.org/en/docs/web/javascript/reference/statements/import
https://developer.mozilla.org/en/docs/web/javascript/reference/statements/export
In the future this may change, but for now it is as it is, so we cannot use this solution either.
Solution 4
By exclusion of parts, since solutions one and two are either prone to huge side effects or either have huge scaling problems, this is the solution I will be using for the time being.
It has no side effects, scales very well due to its independence regarding other files and most importantly, once solution 3 becomes available to use, it will be very easy to simply replace the comments with a call to the import keyword.
Conclusion
For the time being, solution 4 is the best practice. However, once browsers add support for solution 3, that should be used instead of solution 4.
Credits
Special thanks to Harutyun Amirjanyan for his tenacity, patience and guidance in helping me solve this issue.

Another possible method, similar to Solution 1 is to go to the "Hints and Warnings" section in the project settings and under "Ignore messages matching Regex" type
.* is not defined; please fix or add /\*global
This regex will match those annoying messages but also allows the error-checker to catch other undefined variables that just don't have that particular message.
(Of course, this is only better than other proposed solutions if Cloud9 does have other warnings for undefined variables that aren't in that form.)

Related

Better practices for catching code mistakes with Ember.js (specifically, messed up variable names)

In Ember.js, we use Ember's own object variants which recommend/necessitate using this.get and this.set in order to access object attributes.
I (mostly) understand why this is done, and appreciate the consistency and flexibility it adds to the Ember programming experience, but I do feel that I lose out on my IDE's sanity checking.
With Jetbrain products (or any good IDE w/ deep analysis and completion) I can usually rely on symbol suggestions to make sure I'm choosing the correct variable name. Entering in strings with ember relies on me to get the name right, and I'm a fallible human.
I have a few thoughts regarding possible solutions.
Some IDE plugin which does static analysis to suggest the correct string to use
An ES6 or alternative transpired language which accesses members the ember way by default
Some way of automatically establishing string constants where I need them
Some ember debugging setting which at least throws warnings if I try to get a variable which hasn't been defined.
I would also find it useful to throw warnings if ember catches me trying to set an attribute to undefined.
Hopefully, someone will tell me that one of these solutions exists, something better has been thought of, or my problem isn't really a problem.
(An example to illustrate my problem:)
In the following snippet
const email = this.get('email');
const newInvitation = this.store.createRecord('invitation', {email: email});
I am trying to get the attribute email but the real attribute I meant to get was called emailAddress. When I create the record, I do so with an undefined email field which isn't caught until later in the code.
It wasn't terrible to debug, but if I have to manually sift through every line of code every time I misspell something, I'm going to waste a lot of time and be a sad debugging-boy. Help!
Currently we don't have a good solution for this. However the future looks bright!
Currently there is a lot of work going on in the ember-typings repository to build a typescript definition that will allow the typescript language server to give you that completion. This will give you completions for things like this.get('foo') but not for things like this.get('foo.bar') in near future.
Also I've build this, which will allow you to omit .get and .set on browsers that support the proxy object. However this is more a proof-of-concept then something you should use in production!
If you just want debug messages if you access a property thats null you can use unknownProperty:
unknownProperty(key) {
console.log('access to unknown property');
}
However I sometimes its required to access an unknown property for code like this:
if(!obj.get('foo')) {
obj.set('foo', 'bar');
}
So overall I would recommend you to try out typescript, because thats probably the solution that will give you a good developer experience soon and good support from the community as well. Interesting is also the ES classes RFC, that shows, that ember goes toward standard ES classes and at some point we won't .set and .get at all.
Also glimmer integration is going forward, and inside a glimmer component you won't need .set and .get.
Also I don't recommend you ember script. I tried it out, but there is basically no-one using it, and no support at all.

Validate JavaScript code without enforcing a specific style

I would like to validate some JavaScript code for syntactic correctness, but without enforcing a specific coding-style to the user.
My first approach was to use esvalidate that comes included with esprima. This does the job partially, as it detects unexpected tokens, such as:
constx foo = {};
What it does not detect is among other things usage of variables that have never been declared, such as:
const foox = {
bar() {}
};
foo.bar();
A tool such as eslint would detect this, but it's very difficult to configure ESLint in a way that no specific style is enforced to the user (I don't say it's not possible, I just say it's a huge amount of work since you need to check every single rule and decide whether to enable or disable it, and with hundreds of rules this is… yes, well, a huge amount of work).
What other options do I have? How could I validate the code without this effort?
By the way: What is it that I want to validate here? It's not the syntax (I mean, syntactically, everything is fine, it just does not make sense), but it's also not the semantics. What would be the correct term for this type of checks?
Years ago Linters were only there to check the style of your code. Nowadays they do more, a lot more. Even static analysis. ESLint is such a powerful tool and IMHO it is exactly what you're looking for.
You may think the initial configuration may be costly, but as the ESLint page says:
No rules are enabled by default.
Besides, having a consistent coding style across your time is very beneficial and if you and your team found a common basline you can share the .eslintrc between projects.
Enabling the no-undef rule and using a plugin for your IDE, like one of those should solve your issue -> static code analysis at development time :)
To answer your last question, I think that what you want is static analysis. This will be harder with JavaScript in general because of its dynamic nature and lack of types, and relative lack of maturity in tooling. Decades of work have gone into writing static analyzers for C, for example, and that work won't immediately carry over into others languages.
Something like jshint may be what you want because its goal is to help developers "write complex programs without worrying about typos and language gotchas".
Hope this helps!
ESLint Recommended set: Recommended rules have checkmark next to them do not include any stylistic rules. You can use that to verify validity of the script without enforcing any specific style. At the very least it's a good starting point, and you can always turn off the rules you don't like.

How to hide "Is this intentional?" warning in Ext JS 6?

I'm currently developing an Ext JS 6 application with some levels of inheritance on components, where some alias mappings get overridden. Ext JS debug is so friendly to let me know each time when I do this.
[W] Overriding existing mapping: 'controller.my-controller' From 'MyBase.app.Controller' to 'MySub.app.Controller'. Is this intentional?
In my case, it is intentional. The warnings are stacking up, and it is starting to get hard to see the forest for the trees.
Can I turn these statements off somehow just for those classes that are intentional?
Is renaming all my aliases a better solution?
I would recommend renaming your aliases.
Having two classes with the same alias might lead to problems when trying to instantiate one of them. There already is a great answer to this question for ExtJS 5 with a more detailed explanation. The core concepts are the same for ExtJs 6.
As an alias should always be unique (in it's namespace), it's probably a good idea to keep the warnings, just in case you ever miss something ... ;-)
If you really want to suppress these warnings anyway you could overwrite the Ext.log.warn function with an empty one. As you can see in ext/packages/core/src/class/Inventory.js there seems to be no other way around it.
Hope this answers your questions!
You can easily override the warning by forcing the "update" parameter to be set to true when addAlias calls addMapping.
Ext.Inventory.prototype.addAlias = function(className,alias, update) {
return this.addMapping(className, alias, this.aliasToName, this.nameToAliases, true);
};
https://fiddle.sencha.com/#fiddle/1dec

How can I prove that my JavaScript files are in the scope of a specific JS or ECMA version?

Let's say you would get a bunch of .js files and now it is your job to sort them into groups like:
requires at least JavaScript 1.85
requires at least E4X (ECMAScript 4 EX)
requires at least ECMAScript 5
or something like this.
I am interested in any solution, but especially in those which work using JavaScript or PHP. This is used for creation of automated specifications, but it shouldn't matter - this is a nice task which should be easy to solve - however, I have no idea how and it is not easy for me. So, if this is easy to you, please share any hints.
I would expect something like this - http://kangax.github.com/es5-compat-table/# - just not for browsers, rather for a given file to be checked against different implementations of JavaScript.
My guess is, that each version must have some specifics, which can be tested for. However, all I can find is stuff about "what version does this browser support".
PS: Don't take "now it is your job" literally, I used it to demonstrate the task, not to imply that I expect work done for me; while in the progress of solving this, it would be just nice to have some help or direction.
EDIT: I took the easy way out, by recquiring ECMAScript 5 to be supported at least as good as by the current FireFox for my projekt to work as intendet and expected.
However, I am still intereseted in any solution-attemps or at least an definite answer of "is possible(, with XY)" or "is not possible, because ..."; XY can be just some Keyword, like FrameworkXY or DesignPatternXY or whatever or a more detailed solution of course.
Essentially you are looking to find the minimum requirements for some javascript file. I'd say that isn't possible until run time. JavaScript is a dynamic language. As such you don't have compile time errors. As a result, you can't tell until you are within some closure that something doesn't work, and even then it would be misleading. Your dependencies could in fact fix many compatibility issues.
Example:
JS File A uses some ES5 feature
JS File B provides a shim for ES5 deficient browsers or at least mimics it in some way.
JS File A and B are always loaded together, but independently A looks like it won't work.
Example2:
Object.create is what you want to test
Some guy named Crockford adds create to Object.prototype
Object.create now works in less compatible browsers, and nothing is broken.
Solution 1:
Build or find a dependency map. You definitely already have a dependency map, either explicitly or you could generate it by iterating over you HTML files.
Run all relevant code paths in environments with decreasing functionality (eg: ES5, then E4X, then JS 1.x, and so forth).
Once a bundle of JS files fail for some code path you know their minimum requirement.
Perhaps you could iterate over the public functions in your objects and use dependency injection to fill in constructors and methods. This sounds really hard though.
Solution 2:
Use webdriver to visit your pages in various environments.
Map window.onerror to a function that tells you if your current page broke while performing some actions.
On error you will know that there is a problem with the bundle on the current page so save that data.
Both these solutions assume that you always write perfect JS that never has errors, which is something you should strive for but isn't realistic. This might; however, provide you with some basic "smoke testing" though.
This is not possible in an exact way, and it also is not a great way of looking at things for this type of issue.
Why its not possible
Javascript doesn't have static typing. But properties are determined by the prototype chain. This means that for any piece of code you would have to infer the type of an object and check along the prototype chain before determining what function would be called for a function call.
You would for instance, have to be able to tell that $(x).bind() o $(x).map are not making calls to the ecmascript5 map or bind functions, but the jQuery ones. This means that you would really have to parse out the whole code and make inferences on type. If you didn't have the whole code base this would be impossible. If you had a function that took an object and you called bind, you would have no idea if that was supposed to be Function.prototype.bind or jQuery.bind because thats not decided till runtime. In fact its possible (though not good coding practice) that it could be both, and that what is run depends on the input to a function, or even depends on user input. So you might be able to make a guess about this, but you couldn't do it exactly.
Making all of this even more impossible, the eval function combined with the ability to get user input or ajax data means that you don't even know what types some objects are or could be, even leaving aside the issue that eval could attempt to run code that meets any specification.
Here's an example of a piece of code that you couldn't parse
var userInput = $("#input").val();
var objectThatCouldBeAnything = eval(userInput);
object.map(function(x){
return !!x;
});
There's no way to tell if this code is parsing a jQuery object in the eval and running jQuery.map or producing an array and running Array.prototype.map. And thats the strength and weakness of a dynamically typed language like javascript. It provides tremendous flexibility, but limits what you can tell about the code before run time.
Why its not a good strategy
ECMAScript specifications are a standard, but in practice they are never implemented perfectly or consistently. Different environments implement different parts of the standard. Having a "ECMAScript5" piece of code does not guarantee that any particular browser will implement all of its properties perfectly. You really have to determine that on a property by property basis.
What you're much better off doing is finding a list of functions or properties that are used by the code. You can then compare that against the supported properties for a particular environment.
This is still a difficult to impossible problem for the reasons mentioned above, but its at least a useful one. And you could gain value doing this even using a loose approximation (assuming that bind actually is ecmascript5 unless its on a $() wrap. Thats not going to be perfect, but still might be useful).
Trying to figure out a standard thats implemented just isn't practical in terms of helping you decide whether to use it in a particular environment. Its much better to know what functions or properties its using so that you can compare that to the environment and add polyfills if necessary.

Is there a tool to remove unused methods in javascript?

I've got a collection of javascript files from a 3rd party, and I'd like to remove all the unused methods to get size down to a more reasonable level.
Does anyone know of a tool that does this for Javascript? At the very least give a list of unused/used methods, so I could do the manually trimming? This would be in addition to running something like the YUI Javascript compressor tool...
Otherwise my thought is to write a perl script to attempt to help me do this.
No. Because you can "use" methods in insanely dynamic ways like this.
obj[prompt("Gimme a method name.")]();
Check out JSCoverage . Generates code coverage statistics that show which lines of a program have been executed (and which have been missed).
I'd like to remove all the unused methods to get size down to a more reasonable level.
There are a couple of tools available:
npm install -g fixmyjs
fixmyjs <filename or folder>
A configurable module that uses JSHint (Github, docs) to flag functions that are unused and perform clean up as well.
I'm not sure that it removes undefined functions as opposed to flagging them. though it is a great tool for cleanup, it appears to lack compatibility with later versions of ECMAScript (more info below).
There is also the Google Closure Compiler which claims to remove dead JS but this is more of a build tool.
Updated
If you are using something like Babel, consider adding ESLint to your text editor, which can trigger a warning on unused methods and even variables and has a --fix CLI option for autofixing some errors and style issues.
I like ESLint because it contains multiple plugins for alternate libs (like React warnings if you're missing a prop), allowing you to catch bugs in advance. They have a solid ecosystem.
As an example: on my NodeJS projects, the config I use is based off of the Airbnb Style Guide.
You'll have to write a perl script. Take no notice of the nay-sayers above.
Such a tool could work with libraries that are designed to only make function calls explicitly. That means no delegates or pointers to functions would be allowed, the use of which in any case only results in unreadable "spaghetti code" and is not best practice. Even if it removes some of these hidden functions you'll discover most if not all of them in testing. The ones you dont discover will be so infrequently used that they will not be worth your time fixing them. Dont obsess with perfection. People go mad doing that.
So applying this one restriction to JavaScript (and libraries) will result in incredible reductions in page size and therefore load times, not to mention readability and maintainability. This is already the case for tools that remove unused CSS such as grunt_CSS and unCSS (see http://addyosmani.com/blog/removing-unused-css/) and which report typical reductions down to one tenth the original size.
Its a win/win situation.
Its noteworthy that all interpreters must address this issue of how to manage self modifying code. For the life of me I dont understand why people want to persist with unrestrained freedom. As noted by Triptych above Javascript functions can be called in ways that are literally "insane". This insane fexibility corrupts the fundamental doctrine of separation of code and data, enables real-time code injection, and invalidates any attempt to maintain code integrity. The result is always unreadable code that is impossible to debug and the side effect to JavaScript - removing the ability to run automatic code pre-optimisation and validation - is much much worse than any possible benefit.
AND - you'd have to feel pretty insecure about your work to want to deliberately obsficate it from both your collegues and yourself. Browser clients that do work extremely well take the "less is more" approach and the best example I've seeen to date is Microsoft Office combination of Access Web Forms paired with SharePoint Access Servcies. The productivity of having a ubiquitous heavy tightly managed runtime interpreter client and its server side clone is absolutely phenomenal.
The future of JavaScript self modifying code technologies therfore is bringing them back into line to respect the...
KISS principle of code and data: Keep It Seperate, Stupid.
Unless the library author kept track of dependencies and provided a way to download the minimal code [e.g. MooTools Core download], it will be hard to to identify 'unused' functions.
The problem is that JS is a dynamic language and there are several ways to call a function.
E.g. you may have a method like
function test()
{
//
}
You can call it like
test();
var i = 10;
var hello = i > 1 ? 'test' : 'xyz';
window[hello]();
I know this is an old question by UglifyJS2 supports removing unused code which may be what you are looking for.
Also worth noting that eslint supports an option called no-unused-vars which actually does some basic handling of detecting if functions are being used or not. It definitely detects it if you make the function anonymous and store it as a variable (but just be aware that as a variable the function declaration doesn't get hoisted immediately)
In the context of detecting unused functions, while extreme, you can consider breaking up a majority of your functions into separate modules because there are packages and tools to help detect unused modules. There is a little segment of sindreshorus's thoughts on tiny modules which might be relevant to that philosophy but that may be extreme for your use case.
Following would help:
If you have fully covered test cases, running Code Coverage tool like istanbul (https://github.com/gotwarlost/istanbul) or nyc (https://github.com/istanbuljs/nyc), would give a hint of untouched functions.
At least the above will help find the covered functions, that you may thought unused.

Categories