Entries Tagged as Best Practices

Why Tabs Are Superior To Spaces

Once and for all, I have the answer! I've long known and exercised my belief that tabs are (far, far) superior to spaces, but only recently have I gained enlightenment as to exactly why they are superior.

Spaces are "hard coded", while Tabs are "dynamic".

What does that mean, exactly? Every IDE worth a damn allows you to adjust the number of spaces that a tab appears to take up. This is commonly referred to as "tab size" or "tab width". If your team agrees (begrudgingly?) to use spaces, then everyone has the exact same view of the code.

The problem is that people's preferences are different. I might like to use 3 space indents so that things don't start flying off the right side of the screen after just a few levels of nesting, whereas you might like 5+ spaces, to really draw attention to where things nest. There's nothing wrong with either preference. And the beautiful thing is, using Tabs and letting everyone set their own tab width (because one person's tab width has no affect on anyone else's view), everyone gets to see what they want to see.

So there you have it. Tabs win. You're welcome.

in Best Practices | Meta | 5 Responses Posted 2011-11-01 09:36

Taking the next step

Something I spend a fair amount of time thinking about is what's on the horizon. What sorts of things should my team and I be learning and implementing to make ourselves better developers and a better team, as a whole?

Part of that involves knowing what we already do, and in some cases, do pretty well.

  • We have a pretty well defined code-review process and we try to integrate as much feedback from them as possible.
  • We are getting better at creating automated tests to make long term application maintenance easier.
  • Some of our applications have ANT scripts that make producing Production builds (combined, minified JS + CSS, etc) easier
  • We're using Distributed Version Control (git) like a champ, now!
  • We pair program, when possible. (It can be difficult to find significant chunks of matching free-time on a small team.)
  • We're starting to expose some of our reusable code as REST API's so we don't have to waste time copying and re-integrating them into every application

So knowing what we do well, what are the logical next steps? What should we learn and do to continue growing and taking those next steps? Here are some ideas and my thoughts on each. These are just some things I came up with off the top of my head. What else do you think could be useful?

Chef

Our colleague Lew G has written at some length about his experience learning and using Chef. It sounds wonderful! It sounds ideal! It sounds like it could be kind of... hard.

For one, our group has only one server that we manage currently, and it runs on Windows. The rumor mill says that the Chef support for windows is not nearly as good as it is for unix/linux. Of course, this is third- or fourth-hand information, and subjective at that; so it bears some investigation.

You may be able to find people who would argue against automated server configuration like this, but I doubt any of them will be from our team. Being small means that we have to think about our agility and plan ahead for the worst case scenarios or continually find ourselves dealing with the fall out from the previous week's issues. Having one or two people spending two or three days recovering from a total server loss would be catastrophic to our team productivity. Learning Chef and writing/testing scripts ("recipes", right?) to rebuild a server quickly and at a moments notice would definitely go a long way in our personal DR plan.

Jenkins

Continuous integration is the holy grail of automated testing, and with Jenkins now so available and approachable, it's never been easier. How nice would it be to make a commit to source control, and then a few minutes later get an IM letting you know whether or not the tests are passing? Pretty darn nice! ... And just the tip of the iceberg, of course.

Document-based data stores / NoSQL

I recently did a one-day workshop for Hadoop and learned a lot about it and its sibling nosql/document databases. The biggest takeaway for me and our team was something the trainer said. I'm paraphrasing from memory but he said something like, "If you're not working with 1TB of data or more, NoSQL is not for you." I don't think the Learning Lab has 1TB of data from all of our applications combined (maybe not even breaking into double-digit gigabytes), so it's not really an obvious win for us.

That doesn't mean there's no place for NoSQL in the Learning Lab, though. Suppose we need to write an application that will need to support 10,000 concurrent users for a short period of time. Given a Chef script, it could be pretty simple to spin up a few dozen Cassandra/Couchdb/etc nodes to scale as wide as needed, and adjust on the fly according to performance. I imagine scaling a system like this would be much more manageable than trying to get a single machine powerful enough to run MS SQL at the same scale on a temporary basis (Not to mention the licensing costs, since MS SQL is licensed based on the resources it has available!). So while we probably won't dive into this topic right away, we should keep it on our periphery.

LESS CSS

CSS is a very powerful, and when used well, terse way to style html documents. But it can be a pain in the rear to use. Over time stylesheets tend to grow to unmanageable size, and it's incredibly difficult to write them DRYly. Enter LESS CSS. To quote a friend of mine, LESS "makes CSS think like programmers do." You can create and use variables and functions, include files, and much more... and it all compiles (almost instantly, from what I hear) to the native CSS we know and ... erm... love (?) today.

This is another post originally written for my team's blog

in Best Practices | Learning | 2 Responses Posted 2011-09-16 02:51

TDD: Good Idea... or Great Idea?!

I originally posted this on my team's blog, but once again I'm cross-posting it here as well due to its relevance.

I bet that if you ask programming job applicants what their thoughts on automated testing are, the vast majority will say it's a good thing. Yet, like most of the development shops I've worked for over the years, we aren't always afforded the time to write automated tests. Most of the time, we only have ourselves to blame for this: Who creates the project estimate? Who creates the project plan? We do! So we should plan additional time for them... But I will admit that while I personally have written tests for some of my personal and professional projects, they are few enough and far enough between that testing still isn't quite second nature for me; and I probably spend more time writing my tests and mocks than someone who does 100% Test Driven Development.

I know you already believe in automated testing, but I'll continue just in case there's a non-believer reading over your shoulder. TDD slows you down (less when you're an experienced, disciplined TDD'er)... there's no doubt. Writing tests is almost as counter-productive for the initial development period of the application as checking your Facebook page, your Twitter feed, and your G+ stream, before taking a long lunch. Even for that parenthetical TDD Ninja. Where TDD saves you mountains of time is in refactoring.

Refactoring

A significant number of refactorings are fairly simple; limited to one or two files and maybe a couple of dozen lines of code changed. But we've all been here: What about that change that you were expecting dreading the client would request, that takes you two days to complete, and touches dozens of files, and hundreds of lines of code? Sure... you know that what you just spent two days agonizing over works pretty well. But did you break anything?

If you have tests, you just push a button, go get some coffee, and come back to find out what, if anything broke. Effectively it costs you zero time, and you can either publish your flawless refactored code or, perhaps a touch more realistically, get to work fixing the bits that you broke.

Without tests? Best case? You spend a few hours poking around, trying to remember all of the things this app does, seeing if it still does them correctly. If you're lucky, it's only been a year since you last thought about this application. You might find some or most of the bugs you've introduced, but the more code you've changed, the more likely it is you'll miss something.

Case in Point

I just finished writing some mocks that the tests for the authentication and registration module use to verify different response scenarios from the remote authentication and permissions API without actually interacting with the remote API. I realized pretty early in the process of coding the module that it would need to use a façade to make the mocking easier, and this was something we had done with another module that used the same remote API -- but unfortunately we were a little short-sighted and that façade was specific to the module that was using it, not the API it was wrapping. Since my new functionality was somewhat complex, I decided to take on the short-term technical debt of simply creating another module-specific façade, and get it working, so that my coworkers weren't waiting on me for too long. After finishing the functionality and the tests passed, I knew had two jobs to tackle:

  • Add in the mock so that the remote API was not a dependency for the tests
  • Refactor the new façade I created for my module and the other module-specific façade into one API-wrapper façade

The change spanned 8 files and affected hundreds of lines of code. And when I was done, luckily, only one test was now failing. Instead of turning more of my hair gray and wondering how much code is broken that I don't know about, I can say with near certainty none is. I love TDD.

My new Rule of Thumb

Of course TDD (and automated testing in general) is a great thing to have for your average project; I don't think anyone would argue that point. But a lesson I've learned this month is that automated testing is particularly necessary when writing an application that uses ORM. Time and time again I've made what seems to be a tiny, innocuous change to my ORM configuration, and all of a sudden I've got 6, or 8, or 11 failing tests. Entirely my fault, of course; but the point is that what seems like a trivial change to ORM configuration can have nuanced effects on lots of existing code.

So I've got a new rule of thumb: Don't write an ORM-backed application without automated tests.

in Best Practices | Hibernate | No Responses Yet Posted 2011-08-22 03:03

CFHtmlFoot

I regularly use the CFHtmlHead tag to add things like CSS to the header section of a page from various places. It's a very handy tool.

For a long time now, I've wanted a CFHtmlFoot tag, for putting JavaScript at the end of the page, which has been a known best practice for what seems like a millennia. Tired of waiting, I created my own. Here's the custom tag (save it as "htmlfoot.cfm" in your custom tags folder):

<cfif thisTag.executionmode eq "end">
    <cfparam name="request._htmlFoot" default="#arrayNew(1)#" />
    <cfif structKeyExists(attributes, "output") and attributes.output>
        <cfloop array="#request._htmlFoot#" index="i">
            <cfoutput>#i#</cfoutput>
        </cfloop>
    <cfelse>
        <cfset arrayAppend(request._htmlFoot, thisTag.generatedContent) />
        <cfset thisTag.generatedContent = "">
    </cfif>
</cfif>

And here's how you use it. First, let's say you need to add jQuery to the end of your page.

<cf_htmlfoot>
    <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1/jquery.min.js"></script>
</cf_htmlfoot>

This adds the content between the <cf_htmlfoot></cf_htmlfoot> tags to an array in the request scope. Next, we need to output the contents of that array. This works best when you are using a framework or a custom tag to wrap your content in a consistent layout, because then you only need to put it in one (or a few) places. To output the saved bits of content, add this line:

<cf_htmlfoot output="true" />

in Best Practices | ColdFusion | 1 Response Posted 2011-01-07 09:25

Protecting Usability in The Age of Like

As the web continues to evolve, the popularity of little widgets to display on your web pages -- Facebook "Like" buttons, "Tweet This" buttons, and the like -- are growing more popular. Like it or not, you may be asked to implement one (or a dozen) of them one day. This introduces potential points of failure, as each external resource could potentially go offline at any time for any duration. Nothing drives home the idea that nobody is immune more than the fact that the behemoth social network Facebook has unexpectedly gone offline twice in the last two weeks. How do you protect your websites from additional stress in the form of delayed page loading when an event like this occurs?

With careful planning.

The first thing we need to do is understand the problem. I will use the Facebook "Like" button because I'm familiar with it, but the concept applies to nearly anything you include directly from another website.

The problem

When you include a <script> block in the middle of your <body> block, the browser will stop rendering the DOM at that point, download the script file, execute it, and then continue. This is referred to as Blocking (of page rendering), and is the most severe example. This is why conventional wisdom says constantly reiterates that you should place <script> blocks as the very last thing inside the <body> block -- so that if the script source is unavailable or slow, the rest of your page is not waiting on it.

Facebook "Like" buttons, fortunately, don't require a <script> block to embed themselves on your pages. Instead, they use <script>'s slightly less evil cousin, iFrame. IFrames do not block page rendering; which is to say that they are rendered in parallel with everything else on the page. However, they still present two problems. First, they share their connection pool with the parent page, and second, and probably more importantly, they do block the page's onLoad event.

The onLoad event is what a majority of JavaScript frameworks recommend waiting for to initialize your applications (rightfully so). What this means is that, if Facebook were to go down, and you have 1 "Like" button on the page, the browser's downloading/busy indicator won't stop until the request to Facebook for the iFrame content times out -- the duration of which depends on the user's browser -- and then, and only then, will the onLoad event fire. If you are unlucky enough to have multiple "Like" buttons on a page, then they each must timeout before onLoad will fire. Depending on the number of buttons you're using, they could either all be executing in parallel, or if you've got more buttons than threads in the connection pool, then you'll have some queued up, effectively doubling (or more!) the already seemingly-eternal wait.

If your website isn't of much use without the JavaScript that runs when the onLoad event fires, then chances are good that users aren't going to wait around for 30 seconds to a minute. I know I wouldn't -- I give up on even the most interesting link after what feels like 5 seconds.

The solution

Not to fret, there is a simple and elegant way to add Facebook "Like" buttons (and their ilk) after the page has completed loading, which will provide your users with the best experience, especially when the external sites you depend on end up on a milk carton.

My suggestion is to start with a placeholder that contains all of the information you need to build the iFrame.

<a class="fbLike" href="{iFrame url}"></a>

If, instead of adding an iFrame, you use the same URL in an Anchor (<a></a>) tag, then the page will continue to load as normal, and the user will see nothing. I've added a class to make identifying all of the placeholders for my FB Like buttons simple.

Now, after the page has loaded and the onLoad event fires, we want to replace our placeholders with iFrames to inject the buttons. I'll do this with a few lines of jQuery:

$(function(){
  $(".fbLike").each(function(){
    var t = $(this);
    var info = t.attr("href");
    t.replaceWith("<iframe src='" + info + "'></iframe>");
  });
});

Note that I've left off some of the iFrame tag attributes for the sake of keeping the code sample short and sweet; just add them back as needed.

What this does is iterate over every placeholder on the page and replace it with an iFrame, using the same URL that the placeholder anchor tag had been using. I'm not sure if this will restart the browser's busy indicator, but at least the rest of your website will be usable.

Bonus

Since you're setting a placeholder, one nice usability improvement would be to style that placeholder to indicate to users that your FB Like button is loading. Perhaps give it a background image of the Like button grayed out, and a tooltip of "Loading Like button from Facebook..."

in Best Practices | Facebook | JavaScript | jQuery | 8 Responses Posted 2010-10-06 11:40