Tell me more ×
Code Review Stack Exchange is a question and answer site for peer programmer code reviews. It's 100% free, no registration required.

I'm a JavaScript newbie who was first introduced to JavaScript by jQuery. I'm trying to switch over some of the small things I've written in jQuery to JavaScript as a way of learning. I was wondering how I could make my code cleaner and if there were any bad habits which I am guilty of doing.

function getTweets(user) {

    //Adds a little animation to the body when function is executed
    $('.container').html('<div class="loading"></div>');
    var container = document.getElementsByClassName('container')[0]; 
    container.innerHTML = "<div class='loading'></div>";

    $.getJSON("https://twitter.com/statuses/user_timeline.json?screen_name=" + user + "&callback=?&count=50", function(data) {

        var date = {
            Sun : 'Sunday, ',
            Sat : 'Saturday, ',
            Mon : 'Monday, ',
            Tue : 'Tuesday, ',
            Wed : 'Wednesday, ',
            Fri : 'Friday, ',
            Thu : 'Thursday, ',
        };
        // Creates a box and puts JSON data into it.
        for ( var i = 0 ; i < data.length; i++) {
            // Makes the dates readable and links work.
            data[i].text = data[i].text.replace(/(http[s]*:\/\/[\w/\.]+)/, '<a href=\"$1\">$1</a>')
            day = date[ data[i].created_at.match(/\w+/)[0] ];
            data[i].created_at = data[i].created_at.replace(/(\+\d+)/g, '').replace(/\w+/, day);

            var art = document.createElement('article');

            art.innerHTML = "<h3>" + data[i].user.name + "</h3><span class='date'>" + data[i].created_at + "</span><p>" + data[i].text + "</p>";
            container.appendChild(art);

        };
        //Everything after this is to dynamically create a Pinterest type layout
        var width = Math.floor( ( $(window).width() - 200 )/225),
            col = [],
            small = 0,
            articleArray = document.getElementsByTagName('article');

        while ( col.length < width ) {
            col.push(0)
        };


        for (var o = 0; o < articleArray.length; o++) {

            articleArray[o].style.top = col[small] + "px";
            articleArray[o].style.left = small*225 + "px";

            col[small] += articleArray[o].clientHeight + 5;

            for ( var j = 0; j < width; j++ ) { 

                if (col[j] < col[small]) {
                    small = j
                }

            };
        };

        container.style.height = col[small] + 'px';
        container.style.width = col.length * 225 - 5 + 'px';

        $('.container .loading').fadeOut();
        $('article').fadeIn();

    });

};
share|improve this question

2 Answers

up vote 2 down vote accepted
  • First step to making the code look good is proper indentation. JSBeautifier can do that for you.

  • Next is consistency. If you use jQuery, you can go all-out with jQuery to make it as neat and uniform. Of course, you can do vanilla JS if you want to for optimization.

  • Then remove duplicate code or code that does the same thing over and over again.

  • Watch out for missed vars. This can make variables to globals which isn't good.

  • When declaring, follow this order:

    • variables
    • functions
    • "prep code" like initializers, code to fill arrays, fetching values etc.
    • actual operation of the function

The rest are commented so keep a sharp eye. Can't really debug the code but the idea of what to do are there:

function getTweets(user) {

    //cache an object if it's to be used more than once
    var container = $('.container').html('<div class="loading"></div>'),

        //put the url up here so it does not clutter the getJSON below
        //i prefer using single quotes than double quotes for a cleaner look
        url = 'https://twitter.com/statuses/user_timeline.json?screen_name=' + user + '&callback=?&count=50';

    $.getJSON(url, function (data) {

        //it's logical to only put things where they are needed
        //in this case, the following variables are only needed
        //when the callback completes
        var date = {
            Sun: 'Sunday, ',
            Sat: 'Saturday, ',
            Mon: 'Monday, ',
            Tue: 'Tuesday, ',
            Wed: 'Wednesday, ',
            Fri: 'Friday, ',
            Thu: 'Thursday, '
        },
            width = Math.floor(($(window).width() - 200) / 225),
            col = [],
            small = 0,
            articleArray = $('article');

        //prep codes after vars
        while(col.length < width) {
            col.push(0)
        };

        //consistency and ease, use jQuery instead.
        $.each(data, function (i, value) {
            //watch out for missed "vars"
            var day = date[value.created_at.match(/\w+/)[0]],
                //shorthand notation for creating a variable, appending it to the container directly
                //we can hand it over to a reference to do more on it
                art = $('<article>').appendTo(container);
            value.text = value.text.replace(/(http[s]*:\/\/[\w/\.]+)/, '<a href=\"$1\">$1</a>')
            value.created_at = value.created_at.replace(/(\+\d+)/g, '').replace(/\w+/, day);
            art.html('<h3>' + value.user.name + '</h3><span class="date">' + value.created_at + '</span><p>' + value.text + '</p>');
        });


        container.css({
            width : col.length * 225 - 5,
            height : col[small]
        })

        //using the built in each to loop through DOM
        articleArray.each(function (i, article) {
            $(article).css({
                'top': col[small],
                'left': small * 225
            });
            col[small] += article.clientHeight + 5;
            for(var j = 0; j < width; j++) {
                if(col[j] < col[small]) {
                    small = j
                }
            }
        }).fadeIn(); //chain whenever necessary

        //using context to limit the scope of the selector search
        $('.loading', container).fadeOut();
    });
}
share|improve this answer

Just a small note:

  1. 225 should be constant, the code uses it three times. (Unnamed numerical constants on Wikipedia)

  2. Comments often could be function names and the commented code could be extracted out to these functions. For example:

    • // Creates a box and puts JSON data into it.: createBoxWithFilledData(...),
    • // Makes the dates readable and links work.: makeDatesReadable(...), fixLinks(...),
    • // Everything after this is to dynamically create a Pinterest type layout: createLayout(...).

    Reference:

    • Clean Code by Robert C. Martin, Bad Comments, p67: Don’t Use a Comment When You Can Use a Function or a Variable.
    • Refactoring by Martin Fowler, Chapter 3. Bad Smells in Code, Long Method
  3. In the for loop I'd create a local variable for data[i]. I'd make the code readable and shorter.

share|improve this answer

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.