14

JavaScript has obviously become pretty indispensable; however, I'm still new to it, and I've found it's hard to fight the feeling that it seems such a mess and I don't want to deal with it right now. I'm much further in my understanding of other languages than I am with JavaScript, because I can't seem to get a handle on this fear. I get a feeling that, when I'm writing JavaScript, I'm trying to paint a portrait of Weimaraner puppies.

It usually helps me to keep a handful of the most important directives in mind that I can ask myself for each move I make. (To my mind, a handful is five or less.)

Can you list five (or fewer) questions specific to JavaScript I should ask myself for each move I make, when I'm coding JavaScript? What would they be?

Update: to clarify, I'm not asking for five things to keep in mind when learning JavaScript; I'm asking for five questions to always ask myself going forward, that everyone should alsways ask. High-level questions like: "Am I likely to repeat this somewhere else?" or "is this variable/function name specific enough (or too specific)" <== except these example questions are not peculiar to JavaScript. I'm looking for directives that are peculiar to JavaScript.

2
  • 4
    The question as phrased is encouraging many answers, each of which would be equally valid. These sort of questions don't make good questions. Can you rephrase it all? Otherwise it stands a good chance of being closed.
    – ChrisF
    Commented Sep 29, 2011 at 13:18
  • 2
    "Top 5 lists" is not what we do here on Programmers.SE. If you're interested in getting in the answer to a specific problem you're having, feel free to ask about that. Otherwise, I'd suggest Reddit's r/Programming for generating lists like this.
    – user8
    Commented Sep 29, 2011 at 17:14

8 Answers 8

6

I'm going to answer this in two parts. One is "Five or fewer tips on learning to write good JavaScript". The other is "Five or fewer tips on writing good JavaScript".

Learning:

  1. Ask Questions
  2. Listen
  3. Read
  4. Make Stuff

Doing:

  1. Avoid globals (modularize)
  2. Do the hard stuff outside of loops (DOM selection, function declarations, etc.)
  3. Learn how scope works
  4. Learn when and how to use closures
  5. Learn how Object Oriented JS works

EDIT (adding questions to comply with the OP):

What scope am I referencing?

This should help with leaked globals, event handlers, and when to use closures.

Am I repeating myself?

Proper abstraction and use of OO techniques is important. Use them wisely.

Is my code repeating itself?

It is remarkably easy to find yourself putting DOM access into a loop, or creating functions (anonymous or otherwise) in a loop. Note that this can be true of code that uses setTimeout or setInterval as well as traditional loops.

Does this mean what I think it means?

Truthy and falsy values in JS can be a little tricky, especially when using non-strict comparisons (== as opposed to ===). Dynamic typing, type coercion, and whether you're referencing objects or literals can be relevant as well.

28

First, know how the technology behind it works.

You need to know this because the knowledge behind how it works, because you're going to run into networking issues, or, as I've seen countless times, people entirely faily at understanding what server-side and client-side actually is. One of the most common newb questions I see is "How can I make JS change a variable in my ASP code?!"

  • Do you understand ethernet/wifi and TCP/IP to have a general idea of what's going on?
  • How much HTTP do you actually know?
  • Do you actually get HTML? Sure, you might know how tags work and nest stuff, but do you actually understand doctype and quirks mode? Do you understand that you shouldn't put paragraph tags around a list element?
  • Invent JavaScript (and explain it can be run server-side). ecmascript, livescript, mocascript, jsscript, node...
  • Learn the Window API, learn the DOM API, and learn the XHR API. If you don't know these three things you have no business writing code for the browser.

Understand your code is bigger than you, or your specific situation

  • Sure, you wrote something, but everyone can see it. It's all "open" source. Sure, you can obfuscate it, minifiy it, whatever... at the end of the day, if I want to see you code, it's trivial for me to defeat any methods you put in place.
  • You need to understand multiple browsers differences. Target the most popular ones, or the ones your market demographic has. For instance, ie6 won't render DOM table-cell elements if you appendChild rather than the DOM API methods specifically for tables. More examples exist, you need to learn them.
  • You need to understand how to write code around all of these issues in browsers, not your specific browser. You'll quickly learn things that work well in one browser are slow in another. You'll have to figure out how browsers work and why they're different.
  • For the love of Odin's beard, don't write code that permits me to do cross-site-scripting attacks on your code. If you make an ajax call to a cell and do something like cell.innerHTML = "<script>alert("xss")</script>", and an alert box shows up, you've done it wrong.
  • Stay the bloody hell away from DynamicDrive, w3Schools, and websites that give bad advice. You need to find comunities that give good advice. Here on Stack Overflow we have the JavaScript and Node.JS chat rooms, and we do our best to keep pushing the limits of what's "better", where as sites like w3s keep outdated data and never bother with it. You should stick with the offical spec sites such as the W3C, the Mozilla Developer Network (MDN). Ask for peer-review of your code. When you feel like you're doing something painful with your code, when you're doing a lot of cut+paste+tweak with your code, you should immediately come to a chat room and ask for guidance on writing better code.
  • When you come for guidance, or want to share that really cool thing you made... please, pretty please. Please, make sure you documented it, make sure your variable names make sense, make sure it's not all one-lined. You need to write clean code. If you have a pile of garbage, not only have you failed, nobody who knows how to help you will want to. Help us help you.
  • You want to write JavaScript-- that's cool, respect that not everyone supports JavaScript. Two reasons for this-- 1) Faster Internet for everyone (rather than "ajax all the things" which leads to a slower experience). 2) Web's more accessible to people on console-based browsers, people running no-script, mobile phones. What I'm trying to say is, your site should degrade gracefully if someone doesn't have JavaScript and at the very least, use <noscript> tags to alert them as to such.
  • Because of the prototype nature of JavaScript, you can make changes to how the language actually works-- which is really sweet. You see, JavaScript is evolving, we're pulling out of "ECMA Script 3", which is the older version of JS, and into "ECMA Script 5" (aka, es5). Because of prototype, we can fix the es3 language in the field to work like es5. That means, ie6, a 10 year old browser gets language feature that came out last year. Use es5-shims wherever you can, they're really cool and you need to look into it.
  • The western world of English speaking white kids isn't who uses the internet. Code accordingly. This means you need to understand internationalization, and writing code that deals with higher demand. 10 years ago there were less than 500 Million people on-line, today it's roughly 2 billion, and in another 10 years? Probably close to every person on the planet will have internet access, that means you need to support names that don't fit the regex of /[a-z ']/i, but include Hindi, Arabic, accents (this is an existing problem from short-sighted developers), Chinese, and others. Understand character sets, Unicode and UTF-8.

You're a programmer, not a pasta factory. Stop writing spaghetti.

  • Name your variables after things that make sense.
  • Document your code. I don't care if you're using JSDoc powered by rhino or you have a bunch of scribbles. Write documentation that helps the person who is going to use your code. Write documentation for someone who wants to improve or maintain your code. Include useful comments. Comments like "This fizzes the bizz" or ones half-English half-french aren't helpful. Describe what a function does. Describe complex sections of code.
  • Figure out how to limit repetition of code. Look for modular design or functional patterns. See what you can abstract. You should never end up cutting+pasting+tweaking large segments of code to do the same thing.
  • You need to understand the DOM API. The DOM and window objects provision for a lot of great things. This sounds like a lot of work but that's because it's a big scary acronym. A lot of you JavaScript ninjas like to write code such as <a href="javascript:alert("foo")">. FFS DONT DO THAT. Wait for the full document to be loaded, separate your JavaScript code from the html document. This is basic OOP practices 101, just don't in-line your JS or CSS into your html document, ever. Figure out how to do it properly or find someone who knows how to show you how to do it. Again, ask questions.
  • the Javascript:foo("buz") is a psudeo-protocol, it's not fully supported, and if you don't in-line javascript you wouldn't be using it in the first place. I promise you from the bottom of my heart there is no reason what-so-ever on this earth or anywhere in the universe that you NEED to put your javascript inside of an HTML element. Ever. So don't do it. I won't even help people that do that any more, it's that bad.

Figure out how to write code in such a way it does't break all the time.

  • Global variables are one of the biggest problems. Figure out how functional programming in JavaScript works. Figure out what hoisting is. Figure out how to avoid global variables.
  • Use static code analysis tools. These will alert you right-away to all the little "oops" you made when writing your code. Forgot a semicolon somewhere? Oh, there it is. Have a global somewhere? Oh, there it is. Code that might throw a bunch of mystery errors when you try to run it? OH! There they are! No more screwing around and staring into a pile of code for hours trying to figure out something that's just a syntax error. (Well, hardly any, you might have done something it can't catch, but it's generally awesome).
  • Unit test. There's no reason not to be. There's tons of unit testing tools out there. Basically, unit testing is "Here's my function" and "I want it to output Y" "Here's some test inputs" And the test is "Did they all work?" There's many JS testing frameworks, like the popular QUnit. Take a tour through your favorite search engine and see what tickles your fancy. But use them.
  • Source control management, also known as version control. Git's popular, and with good reason. So is SVN and a few others. What you need to stop doing this very instant is editing production code. You need to stop renaming files main_backup_20110911.js.bak.1 You lose stuff, your directory gets messy, you can't easily "rewind" to a previous point in time. You can't see what's going on, you can't make code patches. So, just start learning GIT, it should take you an hour and you'll never go back.
  • Peer review. You're not that good, neither am I. I get better by asking for feedback as much as I can. That's how you should do it too.

Write JavaScript that people love

  • Figure out why your code is slow. Use jspref and create tests.
  • Stop binding events to one DOM element, it's slow, and creates serious event bubbling issues that will waste a lot of your time. Research "event delegation" in JavaScript.
  • STOP using innerHTML to edit the DOM. This goes back to learning what HTML is, and learning what the DOM is. HTML is data sent from the server that your browser rendering engine uses to create a bunch of programming objects that end up being a Document Object. When you use innerHTML you're asking your browser to re-render the whole thing. Thankfully, like way over 10 years ago, we created the DOM API, and it lets you "append child" or "create text node," without having to update the whole thing. innHTML is a disgrace that Microsoft invented -- if you use it, you also lose all privileges to whine about IE6 being awful because you're helping it's garbage stick around forever. Learn the DOM.
  • It needs to work everywhere it can. If something isn't supported, it needs to degrade gracefully so the experience doesn't suck-- you can't just slap your users in the face and crash.
  • Copyright and licence are important. Don't rip-off other people's hard work. If someone says "not for resale," you can't sell it. Don't be a jerk, or we'll hate your code for ripping off hard-working-people.
  • JS is prototypes, not classes. Stop doing that. If you don't understand how prototype works, you need to. Google it. JavaScript is not class-based, stop trying to make classes, it very rarely works out well. People try to write classical code in a prototype language and use that as a case for "why the language sucks", I could make the same case for Ruby not being able to support prototype. Learn something new and stop doing it wrong.

Focus on the basics, always.

  • You're wrong, and that's awesome, because you know something now. Nothing is worse than someone who won't admit to being wrong and keeps slamming bad code out the door like they're some renegade rock-star superhero ninja. They're just fools. Admit you can be wrong, admit you might be wrong, ask for help.
  • You don't always need jQuery. jQuery creates a lot of slow code and helps people who don't know JS to write JS. This is further a problem as JS doesn't require you know JS to write JS. Go figure. Once you understand a few of the things I mentioned above such as learning events, learning the DOM, learning about innerHTML, you'll see why jQuery can be harmful to your code. It can be used correctly in a lot of places, but often you can use a smaller library or even gasp the standard JavaScript that comes with your browser to accomplish something. You don't need jQuery to do anything, it makes it easier to write some code which is cool if you're learning but you need to start doing better and learning more -- when you know more, you'll figure out how to write better code in jQuery anyway. Check out some other JavaScript libraries and stop being so close-minded.
  • You don't need cut+paste+tweak, make DRY code. I've mentioned this before, but it's important here as well. You can't write quality code if your code base is a disgrace.
  • Don't abuse arrays/object differences, learn how to loop. Learn why you use a for (;;) and why you use a for( in ) loop. When to use a while loop. Stop nesting IFs when you can just use a switch case. Objects do not preserve order, so don't use them as an array; old Opera/FF, old MISE, sometimes Flash won't respect the order of your objects. Use an array if you want to keep an order of things, use an object if you want an object (something that doesn't have order of elements).
  • How decision structures can be used to your advantage, not add complexity to your code. Stop nesting IFs, figure out how Boolean logical operators work. Figure out how switch-case works.
  • RTFM. The best place to learn about better code is by reading the actual spec. Read the RFC specs on that part of code you're trying to use. Read the ECMAScript document. Read the W3C DOM spec. Read the W3C XHTML/HTML/HTML5 spec. Read the specs, they're good.

Focus on the long game, not a quick flash and die.

  • You should help the community, you should write code that will be around for a long time. Have some passion about your code and community. If you left bad knowledge somewhere, go the hell back and fix it. Bad information is really hard to purge and sticks around for ever. Do your part. Don't help w3schools make the web worse.
  • Don't jump in from nowhere and say "Hey I got a great idea for how to use which" drop a bunch of code that nobody can use and disappear. You contributed nothing. Don't use variables like a and chezburger.
  • Learn to spot the bad code and the good code, find it in your own code, make your bad code into good code.
  • Create something, learn something, teach something.
  • Broaden your horizons. You can't just write JavaScript forever -- take a sabbatical into something else that interests you, come back, share what you learnt and see if you can find a place for it in the community. Try to show the other world what value JavaScript has as well while you're out there.
  • You're still wrong, even when you do know everything. Use a proof to be correct, not your status/authority. You can never be right, but your proof is always correct. Don't get into pissing matches, as hard as it is to avoid sometimes. Either there's proof or there isn't. Flames help nobody.

For anyone interested, I've actually taken most of this from personal notes on a tutorial I'm nowhere done writing.

8
  • Your answer, towards the top, has completely confused HTTP and HTML.
    – Bryan B
    Commented Sep 29, 2011 at 17:56
  • @insta I'm quite intentional with saying you need to understand HTTP. As I said, "One of the most common newb questions I see is "How can I make JS change a variable in my ASP code?!". They don't understand the protocol that carries HTTP content, cookies, and headers from the server to the client. I'm trying to say one needs to know the layers so they don't get confused by these things. To express that functionally, I'd say: TCPIP(HTTP(ClientServerRelationship(), Cookies(), HTML(JavaScript(Knowledge))))
    – Incognito
    Commented Sep 29, 2011 at 17:59
  • 1
    "Do you actually get HTTP? Sure, you might know how tags work and nest stuff, but do you actually understand doctype and quirks mode? Do you understand that you shouldn't put paragraph tags around a list element?" Nothing in that quote involves the transport protocol, outside of the misused case of it.
    – Bryan B
    Commented Sep 29, 2011 at 18:01
  • 2
    @insta Ah sorry, I totally didn't see that, I've changed it to HTML. Thanks :).
    – Incognito
    Commented Sep 29, 2011 at 18:03
  • 2
    +1 This is a far better answer than the accepted one Commented Sep 29, 2011 at 18:56
7
  1. Read Douglas Crockford's Javascript: The Good Parts. That's quite a tip, but honestly, its the best piece of advice I've ever heard for writing good javascript.

  2. Relatedly, read Douglas Crockford's articles on Javascript.

1
  • 10
    But don't take it religiously. Look at it and make sure it makes sense to you. Ask questions where you don't understand the purpose.
    – Incognito
    Commented Sep 29, 2011 at 14:30
3
alert('This illustrates how JavaScript has first-class functions');
alert('It also illustrates how to use closures.  Try running this code in your browser.');

var funky = function(s) {
    alert("We're getting funky with " + s);
};

var makeFunkyObject = function(funkyFunction) {
    var numberOfTimesAlerted = 0;
    var fn = { };
    fn.alertFunky = function(s) {
        funkyFunction(s);
        numberOfTimesAlerted++;
    }
    fn.getNumberOfTimesAlerted = function() {
        return numberOfTimesAlerted;
    }
    return fn;
}

var funkyObject = makeFunkyObject(funky);

funkyObject.alertFunky('Alice'); // alerts We're getting funky with Alice
funkyObject.alertFunky('Bob'); // alerts We're getting funky with Bob
alert(funkyObject.getNumberOfTimesAlerted()); // alerts 2

alert('Also, be sure to distinguish between learning about JavaScript and learning about the DOM');
alert('The former is awesome; the latter, not so awesome.');
1
  • +1: Once you grok this, you will become a javascript ninja.
    – Spoike
    Commented Jan 31, 2012 at 19:47
2

Here are some questions that should get you going on JavaScript.

  1. How does JSON work and what is it good for?

  2. Why are functions objects in Javascript?

  3. Why shouldn't I use eval?

  4. How do I create events in javascript?

  5. How do I feature detect in javascript?

Pretty much covers most things you need to do in Javascript.

1
  1. Always use semicolons. Implicit semicolons (in JS) are a horrible idea, especially with some of the interesting syntax floating around in common usage. They are also generally required by any JS minifier.
  2. Avoid eval(). This causes all sorts of problems, and is a very quick way to slow down your application. Most uses are actually abuses. Every time you think you need to use eval(), double and triple check for another way; there is almost always a cleaner, easier way unless you are actually trying to execute an entire string worth of JavaScript.
  3. (function() {/* stuff */})() is a good way to encase a set of code and create a local scope for it. Using objects is another, often better, way; objects are more analogous to namespaces in other languages when used in this way. Just watch out for this. Unlike most other languages, this doesn't always reference what you might intuitively think it does. Also remember that unless otherwise specified all JS variables, functions and other objects are all global, even across multiple .js files.
  4. Find and learn/use a good JS library. jQuery is one of the more popular ones. These will do a lot of the heavy lifting for you including things like feature detection and abstracting away DOM manipulation and the multiple ways different things have been implemented in different browsers.
  5. Always use semicolons. Seriously. Get an IDE that warns you when you forget them. I don't want to sound ranty, but there's been a few times where bugs have been introduced just for the lack of a semicolon and the browser won't warn you about these.
5
  • You don't always need semicolons, However I will agree it is good practise.
    – rlemon
    Commented Sep 29, 2011 at 14:37
  • 1
    ASI rules are the same in all JS engines so your code in one place should behave the same in another. It's nice to see semicolons in all the right places but it's probably not going to kill you like other problems will. That being said, you should beware of ASI, doing things like return, and the next line containing your data, you'll have actually said return ; due to ASI. I'd say it's more important to understand ASI and whitespace rules than it is "always use semicolons." But it's a great way to save yourself.
    – Incognito
    Commented Sep 29, 2011 at 14:41
  • +1 for avoiding eval, -1 for semicolon paranoia. JavaScript's semicolon insertion has particular rules which, when followed, are very logical. Check it out
    – Ryan Kinal
    Commented Sep 29, 2011 at 14:42
  • @Incognito +1 I'd say it's more important to understand ASI and whitespace rules than it is "always use semicolons."
    – rlemon
    Commented Sep 29, 2011 at 14:52
  • For everyone who says that you don't always need semicolons; come back to us when you've done actual cross-browser development in javascript (see IE6, 7, and 8).
    – Spoike
    Commented Jan 31, 2012 at 19:44
0

I believe classes to be a quite powerful tool to structure code. There's a lot of language agnostic rules on how to design class based systems and some OO principles are actually more obviously implemented when using classes.
Therefore I suggest you have a look at CoffeeScript.

From there, I suggest you just try to gather information about how to implement SOLID, DRY, GRASP, KISS and YAGNI, and more importantly how to go about situations, where they seem to conflict (they never do, only your understanding of them or the problem at hand does). It's quite easy to find, even on stackexchange.

Please note, that these principles apply to "raw" JavaScript development just as much. However a lot of content you will find on them will illustrate them using class based languages and it might therefore be of use to program in a language, where there's not too much overhead involved in understanding them.
Personally, I think JavaScript is an extremely powerful language, but actually you will have to first deeply understand other languages, to really appreciate this fact.

-7

I'm making the assumption that you're using JavaScript for client-side UI development in a web-application.

1) Should this be client side or should this be server side? I know that I've gone and written serious chunks of code that really deserved to be on the serverside and vice versa. A lot of times I'll head into making an AJAX call for something that ends up just better placed in the Server code to be included on the way over. Especially things that are static in nature but change fairly regularly (list of categories for example.)

2) Is there a plugin that does this already? I use JQuery a lot and the answer is almost always YES! I'll often take plugin code that someone's written and adapt it to my needs (usually adding extra classes to things, etc.) but rarely do I ever need to start from scratch.

3) Is Javascript the right place for this? Occasionally I'll catch myself adding a whole bunch of dynamic styling to something via Javascript when it makes much more sense to use intelligent CSS.

4) Should I be using a different tool? This is something I've been grappling with lately. There are some javascript alternatives like coffee script that are handled well in my stack (Rails 3.1) and I've been considering whether or not to move much of my code there.

5) Is this Javascript code good code? Javascript is code like any other code. Is this code as good as the rest of my code? If not, why not? Is it throwaway? Am I lazy?

18
  • 4
    Your tips on writing good JavaScript include "Don't write JavaScript" and "Write good JavaScript". Sorry, -1
    – Ryan Kinal
    Commented Sep 29, 2011 at 15:22
  • 1
    @RyanKinal It includes "Use jQuery most of the time." That alone is a big problem.
    – Incognito
    Commented Sep 29, 2011 at 15:23
  • 2
    @f0x Why do you say that? Why wouldn't you want to build on the work that someone else has done?
    – Drew
    Commented Sep 29, 2011 at 15:27
  • 2
    @Ryan, your answer to "list five or fewer questions I should ask myself" included three directives that started with "learn [such and such]..." which is good advice generally, but honestly I was asking something really specific here: questions I should be asking myself for each move I make while coding JavaScript. Not "what should I learn in order to understand JavaScript." Drew is the only person who answered the question as asked.
    – user25791
    Commented Sep 29, 2011 at 15:29
  • 2
    @f0x I'm not saying you should blindly use a plugin regardless of whether or not it makes sense but we all use tools others provide us, otherwise we'd all be using our own version of assembly. Plugins can give you an excellent point to start from by either (a) solving your problem outright or (b) giving you some insight to how others have solved the problem you're trying to solve.
    – Drew
    Commented Sep 29, 2011 at 15:36