Sunday, September 14, 2014

Don't read Design Patterns


Consider the following code:

1:  int x,y,z;  
2:  str a,b,c;  
3:    
4:  x=0;  
5:  a="A0";  
6:  print(x, a);  
7:    
8:  y=x+1;  
9:  b="A1";  
10:  print(y, b);  
11:    
12:  z=y+1;  
13:  c="A2";  
14:  print(z,c);  
15:    

and compare it to:

1:  for (int idx=0; idx < 3; ++idx)
2:      print(idx, "A" + str(idx))

Both do exactly the same thing, but anyone who has been writing code for more than a few months knows that the second version is vastly better. And if you ask us why it is better, we will tell you that
  1. It is easier to read
  2. It is easier to debug
  3. It is easier to modify
All of these are correct and fall under the umbrella of maintainability.

We are trained very early to write code which is easy to maintain. This means that other people should be able to understand it, it means that we should be able to understand it when we look at it a year later, it means that the clever bits should be easy to reuse. All worthy goals, all of them eventually translate into time and money, and all have to do with software development and management.

Many developers continue to explore this aspect of programming, and study class design, and interface design, and design patterns. People will engage in debates on underscores vs. camelcase, or on composition vs. inheritance.

It is not the contention of this post that these discussions are without merit. They are the process-aspect of software development, and processes are important. Standards are important. It is important not to make mistakes, which could have been avoided by standing on the shoulders of those who came before.

But sometimes we forget that we write programs to do things. When I was a younger programmer, I was just so excited that there were so many ways to express my ideas, so many ways to design my functions, and my classes, and my class templates, and oh-look-isn't-this-the-command-pattern.

This post contains my view of how a programmer should develop, heavily biased by my own experience and my own mistakes.

Stage 1
Programs are mysterious and esoteric. Error messages from development tools are frightening and make no sense. But working on the command line feels cool. You hope that people will notice the code on your screen and be in awe of you.

Stage 2
The compiler / interpreter works. You understand that the program has an entry point, does some stuff, and then exits. You understand control structures and you know that your functions and variables should have descriptive names. And you're learning that debugging is a huge pain.

Stage 3
You can use libraries and modules written by other people. You have become comfortable with incomplete or incorrect documentation, and can get your programs to do what you want them to. Debugging is no longer a pain and you see it more as a challenge. But you still spend too much time doing it. You view your programs and a collection of classes and functions, and understand the relationships between them. You read Design Patterns and start looking at your own code to find patterns (patterns!) and update your resume accordingly.

Here's some advice: Don't read Design Patterns. Not as a young programmer anyway, not unless your job demands it. Don't read about class design in general, the meaning of protected inheritance, or about when virtual functions should be private.

Instead, focus on making your programs run better. No bugs, tight execution, compact memory footprint etc. Yes, RAM is cheap nowadays, I'm not trying to encourage cost savings here. But I think it is more useful for a programmer to consider the run-time aspect of their program rather than its static nature.

Stage 4
You have developed a data-centric viewpoint, i.e. you know what the data looks like, where it comes from, how it is modified, where it ends up. You know which data is short-lived and which is going to be around for a while. You can shift your viewpoint of a program back and forth between "procedures passing data to and from one another" and "data being acted upon through its lifecycle".

Let me talk about these two viewpoints for a minute. Viewing a program as being made up of entities passing messages to one another is very useful. We tend to talk of those entities as being "objects", and these objects usually do things i.e. they are actors.

But objects can also be just data (although some people frown upon objects with only state and no behavior), and one can view their programs as being collections of objects in different stages of development. In this viewpoint, the actors are de-emphasized and the focus is on the objects being manipulated. For example, one may talk about how a string field in an object is converted to uppercase - with no mention of the TextConvertor which derived from a StringManipulator and created by a DataModifierFactory.

You may also start looking at data management libraries and services, like caching servicesservice buses, and message queues. You wonder if you are dealing with Big Data, and put it on your resume anyway. And you can often debug problems in your head because you don't have to look at the code to know what it's doing.

Stage 5
Now that you view your programs primarily as runtime entities, you can come back to the static viewpoint. Now when you think about class design and modularization, you will have the runtime model in mind - first and last. And now you will create beautiful designs, engineered for performance as well as for manageability.

Thursday, September 4, 2014

Online security and Uber

Credit card theft

It seems like credit card data gets stolen all the time. In 2011 Sony made the news with details of over 12000 credit cards being stolen (some reports claimed 2.2 million, I don't know what the final numbers were). Then from March of this year, the Target breach - in which 40 million numbers stolen. There were breaches in between of course, which one could look up if one were so inclined; I'm not taking the trouble since I'm pretty sure everyone reading this knows that it happens, and happens regularly. I just typed "credit card theft" into Google Search and found this story, from yesterdayNearly all US Home Depot stores hit.

How can credit card data be stolen? Here are five ways. Here's a news report on YouTube. Most of us have seen videos like this one before. And when someone steals card data, they can sell it on sites like rescator.cc (not hyperlinked, I'm not sure that going there is a good idea).

So how come this doesn't happen to us sitting in India?

Credit card use in India

In India, having a person's card information is not enough to use it. Even having the physical card itself won't work - because we always have to go through an additional authorisation step.

When we use a physical card in a physical store, we are required to enter a 4-digit PIN number. I remember getting my replacement "chip"-style cards a few months ago, and every merchant I visit has the new machine which reads the chip and asks for my PIN. This method prevents your card from being usable unless the thief also managed to steal your PIN number - and ATM and debit cards work the same way. I don't know what happens if the thief just tries all the numbers from 0000 to 9999, maybe your bank's fraud detection software kicks in.

Online transactions work similarly, when we provide card payment information to a site we are required to authorise the transaction on a different site, showing MasterCard SecureCode or Verified by Visa. This other site is hosted by your bank, and this is important because this way the merchant cannot get your security passcode. Of course it is entirely possible that your bank could get broken into, but it is easier to regulate and monitor a few hundred banks rather than a few hundred thousand online businesses.

Aside: When we transact using Net Banking, we often have passcodes for individual transactions - I know that at least AXIS and Kotak do this - after you initiate the transaction they send a code to your email address or to your phone via SMS, and you have to provide this code to complete the transaction. I wish we had this for card-based transactions as well.

In summary, stealing credit card information in India is basically useless.

Unless...

Well, unless the merchant is outside the country. Our regulators have no sway over outside merchants, and while they could certainly block us from transacting with them, that would be hugely inconvenient for us. So when we transact with foreign merchants, a credit card number and expiration date are enough. And probably the name. No other authentication, no passcodes to be entered on a trusted site, nothing.

Naturally this is not great. It is the online equivalent of walking through a shady part of town - sometimes you have to go, but you don't want to be doing it regularly. I used to buy music on cdbaby, now I don't even do that. What I've heard is that if you are an American consumer, your loss is capped at 50,000 USD. I don't know if that is true, but I do know that if you are Indian consumer you would just be S.C.R.E.W.E.D.

Hello, Uber

Uber is a fantastic service. I followed the news about how they were scaring taxi unions around the world, and getting banned one city at a time, and I remember thinking "Go Girl"(I don't know why I made Uber a girl). I thought the tax unions' safety claims were horseshit, and while I knew that they had to do what they had to do to protect themselves, I also felt that they should be crushed mercilessly (which I don't think has happened yet? I can wait). I also generally believe that the State should regulate lightly and let businesses thrive, especially when large numbers of consumers could benefit.

So Uber came to India (yay!), and I guess they didn't want to subject their users to the extra step of credit card authorisation. Because when people reach their destination they don't want to type things into their phone. Because it's inconvenient.

Yes, it is inconvenient. Just like locking and unlocking your car is inconvenient. Or the door to your house. Or having to show ID when you access your locker in the bank.

We deal with, and even welcome these inconveniences because they protect us. This is about security, and not some abstract "national security", but concrete, personal, financial security. Every one of us should want that level of security.

Well, Uber decided that rather than subjecting their users to standard financial security practices, they were going to bypass them, by... routing the payment through a non-Indian processor. Genius! What an idea. Someone got a bonus for that one.

WHAT WERE THEY THINKING

When I first read that this is what they did, I didn't know whether to laugh or to cry. But that's not all - then I read, and heard, many smart people saying that this was a good thing because it saved time and therefore contributed to GDP growth. And when the regulators told them to stop, that this was regulatory paternalism.

This is not paternalism. This is not cultural policing, this is not the Big Bad Government trying to be your father and telling you what is right and what is wrong. And the GDP of the country is not going to be touched by the time saved when people get out of their taxis. This is not of that, and dressing up a crappy argument with big words and numbers is like putting lipstick on a soowar.

The better approach

As responsible consumers, we want our financial transactions to be protected. But as lazy consumers, we still want the convenience of speed. Technology exists so that we can have it both ways - we shouldn't have to choose.

Rather than trying to be so smart and jugaad-ing the loopholes, Uber should have worked on a real solution. E-commerce is big in India, and I'm sure the large online retailers also want to save their customers the hassle of entering credit card information into their sites and apps every single time they buy something. A process needs to be invented, with the involvement of businesses, regulators and security experts.

California is not going to do this for us - it's our use-case, and we need to solve it.


Saturday, May 3, 2014

Programming with Callbacks

I wrote this as an answer on StackOverflow, and have decided to make a copy here as well. The question was "What is a callback function?"

Opaque Definition
A callback function is a function you provide to another piece of code, allowing it to be called by that code.

Contrived example

Why would you want to do this? Let's say there is a service you need to invoke. If the service returns immediately, you just:
  1. Call it
  2. Wait for the result
  3. Continue once the result comes in
For example, suppose the service were the factorial function. When you want the value of 5!, you would invoke factorial(5), and the following steps would occur:
  1. Your current execution location is saved (on the stack, but that's not important)
  2. Execution is handed over to factorial
  3. When factorial completes, it puts the result somewhere you can get to it
  4. Execution comes back to where it was in [1]
Now suppose factorial took a really long time, because you're giving it huge numbers and it needs to run on some supercomputing cluster somewhere. Let's say you expect it to take 5 minutes to return your result. You could:
  1. Keep your design and run your program at night when you're asleep, so that you're not staring at the screen half the time
  2. Design your program to do other things while factorial is doing its thing
If you choose the second option, then callbacks might work for you.

End-to-end design

In order to exploit a callback pattern, what you want is to be able to call factorial in the following way:
factorial(really_big_number, what_to_do_with_the_result)
The second parameter, what_to_do_with_the_result, is a function you send along to factorial, in the hope that factorial will call it on its result before returning.
Yes, this means that factorial needs to have been written to support callbacks.
Now suppose that you want to be able to pass a parameter to your callback. Now you can't, because you're not going to be calling it, factorial is. So factorial needs to be written to allow you to pass your parameters in, and it will just hand them over to your callback when it invokes it. It might look like this:
factorial (number, callback, params)
{
    result = number!   // i can make up operators in my pseudocode
    callback (result, params)
}
Now that factorial allows this pattern, your callback might look like this:
logIt (number, logger)
{
    logger.log(number)
}
and your call to factorial would be
factorial(42, logIt, logger)
What if you want to return something from logIt? Well, you can't, because factorial isn't paying attention to it.
Well, why can't factorial just return what your callback returns?

Making it non-blocking

Since execution is meant to be handed over to the callback when factorial is finished, it really shouldn't return anything to its caller. And ideally, it would somehow launch its work in another thread / process / machine and return immediately so that you can continue, maybe something like this:
factorial(param_1, param_2, ...)
{
    new factorial_worker_task(param_1, param_2, ...);
    return;
}
This is now an "asynchronous call", meaning that when you call it, it returns immediately but hasn't really done its job yet. So you do need mechanisms to check on it, and to obtain its result when its finished, and your program has gotten more complex in the process.
And by the way, using this pattern the factorial_worker_task can launch your callback asynchronously and return immediately.

So what do you do?

The answer is to stay within the callback pattern. Whenever you want to write
a = f()
g(a)
and f is to be called asynchronously, you will instead write
f(g)
where g is passed as a callback.
This fundamentally changes the flow-topology of your program, and takes some getting used to.
Your programming language could help you a lot by giving you a way to create functions on-the-fly. In the code immediately above, the function g might be as small as print (2*a+1). If your language requires that you define this as a separate function, with an entirely unnecessary name and signature, then your life is going to get unpleasant if you use this pattern a lot.
If, on the other hand, you language allows you to create lambdas, then you are in much better shape. You will then end up writing something like
f( func(a) { print(2*a+1); })
which is so much nicer.

How to pass the callback

How would you pass the callback function to factorial? Well, you could do it in a number of ways.
  1. If the called function is running in the same process, you could pass a function pointer
  2. Or maybe you want to maintain a dictionary of fn name --> fn ptr in your program, in which case you could pass the name
  3. Maybe your language allows you to define the function in-place, possible as a lambda! Internally it is creating some kind of object and passing a pointer, but you don't have to worry about that.
  4. Perhaps the function you are calling is running on an entirely separate machine, and you are calling it using a network protocol like HTTP. You could expose your callback as an HTTP-callable function, and pass its URL.
You get the idea.

The recent rise of callbacks

In this web era we have entered, the services we invoke are often over the network. We often do not have any control over those services i.e. we didn't write them, we don't maintain them, we can't ensure they're up or how they're performing.
But we can't expect our programs to block while we're waiting for these services to respond. Being aware of this, the service providers often design APIs using the callback pattern.
JavaScript supports callbacks very nicely e.g. with lambdas and closures. And there is a lot of activity in the JavaScript world, both on the browser as well as on the server. There are even JavaScript platforms being developed for mobile.
As we move forward, more and more of us will be writing asynchronous code, for which this understanding will be essential.

Thursday, May 1, 2014

Writing a small application using Parse and Backbone - Part 3

The Story So Far

In the last post, I set up a Backbone view and a model, and connected the two. I also connected the view to a route so that we could see it render with the data. This time I want to figure out:
  1. How to query the Facebook Graph API
  2. How to persist data to the Parse backend

The Graph API

The first thing you will need to hit the Graph API is an access token. This token as an associated set of permissions which will determine which of your queries succeed. When you play with the Graph API Explorer, you will see a button saying "Get Access Token", which brings up a window asking you which permissions you are going to ask the Facebook user for:


When you do this through Parse, you will ask for permissions in the call to Parse.FacebookUtils.logIn. If the user grants you the permission you want, the access token will be in Parse.User.current()._serverData.authData.facebook.access_token.

To use this token to make a query, you call the FB.api function. Which works fine... except when the FB object doesn't exist yet. Or the Parse.User hasn't signed in. Or the access token has expired. All of which are possible, especially if the initialization flow is still in progress.

To handle this I wrote a little helper:

 facebookQuery = function(queryString, callback) {  
     var doer = function () {  
       if ((!!window.FB) && (!!Parse.applicationId) && (!!Parse.User.current())) {  
         window.FB.api(queryString, { 'access_token': Parse.User.current()._serverData.authData.facebook.access_token }, function(response) {  
           // token expired! this logic needs to be a)understood, and b)put everywhere  
           if(response.hasOwnProperty('error') && response.error.code === 190) {  
             Parse.User.logOut();  
             Invite.loginUser(doer);  
           }  
           else {  
             callback(response);   
           }  
         });  
       }  
       else {  
         // wait 0.1s  
         setTimeout(doer, 100);  
       }  
     };  
     doer();  
   };  

The 190 error code is what Facebook returns if the access token has expired. What I do is I log out and log back in, and this seems to work.

Persisting to Parse

They have actually made this pretty easy - the Parse.User object has a save method you can call. Here is some code which shows a Graph query for the logged-in user's profile information - you can see that I am asking for only the name, gender, and cover photo. Then I call the set method to assign to the fields, followed by save to send it to their servers.


 facebookQuery('/me?fields=name,cover,gender', function(response) {  
       
       // information to populate the model  
       var info = {  
         fbId : response.id,  
         realname : response.name,  
         gender : response.gender,  
         privacy_non_fb_see_only_name : Parse.User.current().get("privacy_non_fb_see_only_name"),  
         photoURL : response.cover && response.cover.source  
       };  
       // overwrite existing values, if any, and send to Parse  
       _.each(info, function(val, key) {  
         Parse.User.current().set(key, val);  
       });  
       Parse.User.current().save();  
       //   
       next(info);  
     });  


Next Time

In the next post I'm going to build the core functionality of this application, which is the creation of an invite. The code is on GitHub if you want to follow along!


Update (May 10 2014)

I'm not going to get to the next post for a while, some other tasks have come up at higher priority! I'll get to it when I get to it.


Wednesday, April 30, 2014

Writing a small application using Parse and Backbone - Part 2

Last time

In the previous post I created a Backbone application and integrated it with Parse. I also managed to log the user in using their Facebook account. This time I'm going to create a couple of pages, which will require some understanding of how Backbone's views work.

I managed to figure this out yesterday, so in this post I will just record what worked, along with a few of the problems I recall having encountered.

Routes

First I'm going to add a route called invites. Backbone's routing system is simple enough to get started with, you create a Router object and specify your URL patterns and their handlers. My first handler isn't going to do much; here is the code:

 Invite.Router = Backbone.Router.extend({  
      routes: {  
           "invites"          : "allInvites",  
      },  
      allInvites : function() {  
           console.log("allInvites");  
      }  
 });  

When the user navigates to /#invites, the handler allInvites is called. If you don't have the #, this won't work! The router only works on whatever comes after it, and it needs that starting point. This is not specific to Backbone, and if you Google "fragment identifier URI" you will learn more. I plan to do that one day myself.

The next route I added is to look at the details of a specific invite. This route takes a parameter, the invite's id.

 Invite.Router = Backbone.Router.extend({  
      routes: {  
           "invites"         : "allInvites",  
           "invite/:id"      : "viewInvite"  
      },  
      allInvites : function() {  
           console.log("allInvites");  
      },  
      viewInvite : function(inviteId) {  
           console.log("viewInvite, id=" + inviteId);  
     }  
 });  

You can see how the parameter is specified in the URL, and you will also notice that the parameter name in the URL doesn't need to match the parameter to the handling function.

Now let's make the handlers do something.

Views

To create a view in Backbone, you run Backbone.View.extend passing it a configuration object. This object could contain a function called initialize, which will be called without parameters when the view is created. In order for the view to do anything i.e. modify the HTML of a DOM element, you probably want to add a function which you can call when you're ready, and typically this is called render. But note that you have to call this function yourself, Backbone doesn't call it for you.

After five minutes I realized that setting the HTML of a DOM element is quite easily the most painful experience in the world, and why don't they have a template mechanism, integrating with things like Handlebars? If I knew more about how Handlebars worked, I could have probably figured out how to plug it in, but as it happens, Yeoman came to my rescue again. I ran yo backbone:view AllInvites and it generated this nice file for me:

 Invite.Views = Invite.Views || {};  
 (function () {  
   'use strict';  
   Invite.Views.AllInvites = Backbone.View.extend({  
     template: JST['app/scripts/templates/all_invites.ejs'],  
     tagName: 'div',  
     id: '',  
     className: '',  
     events: {},  
     initialize: function () {  
       this.listenTo(this.model, 'change', this.render);  
     },  
     render: function () {  
       this.$el.html(this.template(this.model.toJSON()));  
     }  
   });  
 })();  

Here's what I noticed:
  • The initialize function sets up the render function to list to the change event on the model
  • (There's something called a model)
  • The render function takes the model and runs it through a templating mechanism, the output of which is HTML which is set to a DOM element called $el. According to this helpful site, the el is a div which is created automatically by Backbone if we don't specify it ourselves.
  • The template seems to be in a file with an EJS extension.
So it looks like I need a model. This model object receives (generates?) a change event, and also has a JSON serialization method. So it can't be any old object, it's probably a Backbone.Model. No problem, I can look that up, and generate one using yo backbone:model once I'm ready.

But what is EJS...oh here it is. With example usage! I love the Internet. It doesn't look at pretty as Handlebars, but I don't care, it will get my work done.

 <h2>AllInvitesView</h2>  
 <ul>  
 <%   
           _.each(this.model.models, function(invite) {  
 %>  
   <li>  
     <a href="#/invite/<%= invite.get('id') %>">Detailed View</a>   
 <%=  
   invite.get('what') + ' ' + invite.get('who') + " " + invite.get('when') + " " + invite.get('where').venueName  
 %>  
   </li>  
 <%  
   });  
 %>  
 </ul>  
 <a href="#">Home</a>  

There's really only one thing to pay attention to: if you want to run JavaScript, enclose it in <% %>, but if you actually want the results to be inserted into the HTML, you have to use <%= %>.

Notice that the data is coming from this.model.models. I actually just stumbled upon it (with a little help from the Chrome developer console), and it worked . A little more exploring led me to understand that this.model refers to a collection (if the view is set up correctly), and the collection provides access to its objects via models. More on this below.

It's time to talk about the models now.

Models and Collections

Running the Yeoman generator yo backbone:model gave me a very simple file, which I haven't needed to touch yet. I ran it to create a model called Invite.Models.Invite, and left it there. But there is a separate generator for collections - yo backbone:collection - and that's what I want right now, since I'm working on a view which displays a collection.

The backbone collection definition looks like this:

 Invite.Collections = Invite.Collections || {};  
 (function () {  
   'use strict';  
   Invite.Collections.AllInvites = Backbone.Collection.extend({  
     model: Invite.Models.Invite  
   });  
 })();  

You can see that the Invite model is referenced in the configuration object, this clearly tells the collection what it's going to hold (in addition, I inferred that that Backbone collections are homogeneous, this turned out to be incorrect).

Creating objects is easy, as is creating a collection and adding these objects to it. Here is some example code which creates some dummy data for my application:

   var invDate = new Date(2014, 04, 19, 15, 0, 0, 0);  
   var venue = {  
     venueName:'Pizza Hut',   
     venueId: 1  
   };  
   appController.allInvites = new Invite.Collections.AllInvites();  
   appController.allInvites.add(new Invite.Models.Invite({ id: 1, what: 'fun', who: 'rohit', when: invDate, where: venue }));  
   appController.allInvites.add(new Invite.Models.Invite({ id: 2, what: 'fun', who: 'abrar', when: invDate, where: venue }));  
   appController.allInvites.add(new Invite.Models.Invite({ id: 3, what: 'fun', who: 'arun', when: invDate, where: venue }));  

You can see that I have created the collection inside an object called appController (which I will get to soon), and then just called the add method on the new Invite objects. There is no schema for the Invite model, and it accepts numbers, strings, dates and sub-objects with no extra work on my part! These objects can now be found in the models property of the collection, i.e appController.allInvites.models.

Now that we know how to create models and collections, and to insert models into a collection, it's time to link them to our views. I'm going to start by linking the appController.allInvites collection to the AllInvites view created earlier.

The way to associate data to a view is just to set the view's model property to the model or collection you want. So I create my view like this:

 var invitesView = new Invite.Views.AllInvites({model:Invite.appController.allInvites});  

Now when I render the view, the template code will find the individual models and iterate over them in the loop

  _.each(this.model.models, function(invite) {  
   ....  
 });  

The App Controller

I have been referring to an object called , which I haven't talked about too much yet. I'm using it as a global state holder and data store, and as I go forward I will figure out what else I want it to do. But I wanted to mention one piece of state it holds - the current view.

I lifted this from this StackOverflow answer, it performs some cleanup on any current view before switching to the new view and calling render. Then it takes the current view's el HTML and assigns it to a div I created in the index.html.

 function AppController() {  
   this.showView = function(view) {  
     if (this.currentView){  
       this.currentView.close();  
     }  
     this.currentView = view;  
     this.currentView.render();  
     $("#targetElement").html(this.currentView.el);  
   };  
 }  
 Invite.appController = new AppController();  

The way I use this is I set up the view in each route handler, and ask the appController to show it.

Next time

That's it for this post. In my next post I'm going to figure out how to use Parse's models and collections.

Tuesday, April 29, 2014

Writing a small application using Parse and Backbone - Part 1

Motivation

A few weeks ago I discovered the Parse backend-as-a-service, and immediately loved what I saw. So now I'm going to put together a small application, called Invite. I'm going to use Backbone as my front-end framework, because that's what Parse is based on.

My usual strategy is to read one good post on the subject at hand, and then just Google everything else I need as I need it. Sometimes I find a tutorial which is so well written and suited to my immediate need that I can get by with only that one, but normally I just bounce around a bunch of different ones.

The code is on Github, you will find it here.

Yeoman

To get started, I figure I should install a Yeoman generator for Backbone. And... Yeoman craps out on me. Bunch of error messages about not being able to find files in the global node_modules etc. So instead of trying to make it work, I just removed my ENTIRE node.js installation and built it from source. Only this time, I specified a value for the --prefix flag while running configure.sh, essentially telling it to install to a folder in my home directory.

No problems - it installs, and I run npm config ls to ensure that it shows the correct prefix. It doesn't, so I update the .npmrc in my home directory, which I had completely forgotten even existed.

The upside? Now I can install Yeoman globally without using sudo. Which I shall immediately do... and it works. Next I need the generator for Backbone, so I run Yeoman and asked it to find it for me. Yeoman is smart, it shows me a list of possible generators, and I choose generator-backbone since the others looked like Backbone + other stuff. And this time it works. Yeoman even confirms that it has installed the generator as a global node module. Thank you, Yeoman!

The scaffold

Now I'm running the Backbone generator, and Yeoman is doing its thing. It looks like it's installing a million node modules, mostly grunt stuff which I will not be looking at today or anytime soon. But more interestingly, it creates  the scaffolding for my Backbone application! Let's take a look at what we've got:
  • An invite/app/index.html
  • An app/scripts/main.js - this is where the application definition is. The application object has been named Invite (which Yeoman figured out from the name of the folder), and has been placed inside the global window object.
  • Other files I'm not interested in right now
I start up the application by running grunt serve, and the page which shows up looks good. It says I should run some more Yeoman commands, for models views and controllers. Ok, why not... I run

 yo backbone:router places  
 yo backbone:collection places  
 yo backbone:model places  
 yo backbone:view places  

which create a bunch of files which I will get to soon. Ok, great. Now I can get back to actually building this application.

The Application

This would be a good point for me to pin down exactly what I want to build. So here it is:
  1. Users must sign in, and sign-in must be through their Facebook account
  2. Once signed in, they can see a list of People, initially just their Facebook friends
  3. They see a list of places they could hang out at in their city. Also from Facebook
  4. They can invite their friends to meet them at a place, after specifying when this should happen. I am going to find the absolute simplest date & time control to do this with.
  5. Their friends will see the invitation when they sign in, and will be able to accept or reject. A notification goes out. 
Ok, that's enough to get started. So here's a list of pages we will need:
  1. Sign-Up / Sign-In
  2. List of People
  3. Person Details
  4. List of Places
  5. Place Details
  6. Invite
  7. See invitations, respond, see other responses and other updates

Facebook Login

What I want to do first is integrate with Facebook. I want my users to be able to authorize my app to access their profile, and then I will create a User object using their profile information. I also want the app to detect if they already have an account with me, and retrieve that User instead of creating a new one.

Naturally, I expect Parse to be able to handle this simple workflow, so I just need to figure out how they do it. I'm going to read the documentation and just note down over here what I did.

1. Integrate the Facebook JavaScript SDK. Instructions are here. I put the fb-root div into index.html right after the opening <body> tag, and I include the Parse JavaScript SDK just before scripts/main.js is included.

2. Parse says that fbAsyncInit should contain a call to their own initialization routine rather than directly to Facebook's.

3. Hmm their init function wants a channel URL...

4. StackOverflow to the rescue. Created my local channel.html

5. I placed the Facebook code along with the Parse init in main.js 

So far, so good. Now the Parse documentation wants me to call a function called Parse.FacebookUtils.logIn. But where should I call it from...hmm.

6. Ok, I'm going to put it into fbAsyncInit right after the call to Parse.FacebookUtils.init. So now fbAsyncInit contains calls to  Parse.initialize,  Parse.FacebookUtils.init  and  Parse.FacebookUtils.logIn.

7. Chrome blocks pop-ups from localhost by default. Changed the policy.

8. Now Facebook is complaining that the URL is wrong. Changed it in my Facebook app's settings page i.e. https://developers.facebook.com/apps/<my app id>/settings/

9. Refreshed my app. The browser's console logs tell me that the user is "signed up and logged in through Facebook!".


Next

In the next installment I will figure out routes, views and models, and build one of the pages for the app.

Saturday, February 1, 2014

What modern web frameworks do for you

Motivation

If you are like I was, a former CS major whose programming experience consisted of writing command-line programs using C++, the world of web applications might seem mysterious and foreign.

You know how computers work i.e. you know processor architecture, you know the basics of operating systems, compilers, networking protocols… but this web stuff is something else. And it’s hard to get started – for one because there’s all this terminology, but even if you learn the terminology it feels like there’s all this magic going on.

This blog post is for people who were in the position I was in 6 months ago. It is not a tutorial – it is meant to be read before your tutorials so that things make sense.

Web Application – Basic Flow

First let’s break down the basic structure of a web application.

  1. An application will expose multiple endpoints, which usually correspond to different parts of the application but don’t necessarily need to. An endpoint is represented by a URL, like www.myapp.com/register or www.myapp.com/logout.
  2. Clients make requests to these endpoints. These use the HTTP protocol, which I won’t get into other than to say that a request is made up of:
    1. Headers, some of which are used during transit and delivery, but you can add your own
    2. The desired endpoint
    3. An HTTP verb, like GET or POST
    4. GET requests will often have a query string attached, like                                              /getInfo?name=Rohit&age=36
    5. POST requests will usually have a body, which could be XML, JSON or something called “form-data
  3. When the application starts up, it registers its endpoints with the web server (a separate process running on that machine). Registration means providing callbacks for these endpoints.
  4. When a request comes in, the web server matches the URL against the endpoints it has registered, to see if there is a listener available. If not, it returns an error message (following what the HTTP protocol defines, hopefully). Otherwise it passes it on to the registered handler.
  5. The handler does what it needs to, and then sends an HTML response back to the web server
  6. The web server sends this response back to the client

Ok, simple enough.

Web Frameworks

So what do web frameworks do for you? Keeping in mind the steps above, the framework should provide:

  1. A simple endpoint & handler registration mechanism
  2. Automatic parsing of the request, putting the information into some simple data structures
  3. Simple ways for handlers to redirect a request (possible modified) to other endpoints

Another useful feature is an authentication framework, so you can mark certain endpoints as "protected" i.e. requiring a logged-in user. Of course to do this you need the concept of a user, so let's not get into that.

But an even more useful feature is layout templating. Think of your final page as being data placed in a layout container. The layout defines the colors, the text areas, navigation controls, where the scroll bars are, which buttons do what etc. Some of these don't change depending on the data being presented, and some do. The template will define the data-independent portions and indicate where the data is meant to go. It might be as simple as

<div id="userName" class="userNameDisp">
    {{userNameVar}}
</div>

The framework will read this HTML template, figure out that userNameVar is a variable whose value is required, and get that variable's value from the interpolation context. You can imagine this working like this:

getPage (templateName, dataContext):
    response = loadTemplateAsString (templateName)
    for every {{varName}} in the response string
        look up varName in the dataContext
        replace {{varName}} by this value in the response string
    return response

The two web frameworks which I know of which work this way are Django, written in Python, and Ruby on Rails, which is written in Ruby.

A different strategy

Nowadays everyone loves JavaScript, supposedly because browser support is so much better than it was before (I don't know how it used to be, this is just what I hear). In fact browsers are so good at running JavaScript now that applications are being written so that a large part just sits in the browser! 

One of these frameworks is called AngularJS, and I've actually written a small application using it. But I don't fully know how it works yet. Here's what I do know/ believe at this point:
  1. Request to the web application loads a whole bunch of JavaScript code. This contains all the endpoint definitions and associated handlers.
  2. As the user interacts with the application, requests will be triggered to different endpoints. These will, as far as possible, be trapped by the client-side application and NOT be translated into fresh requests to the server (since the application logic has already been loaded into the browser)
  3. Of course certain requests do need to go to the server, like requests for data. The server will now just send back JSON or XML.
  4. Layout templates will also be sent on request, though a framework might also provide a mechanism for pre-requesting and caching them locally. One would hope that a layout template is not loaded more than once though.
Now the server sends only three types of responses: the initial application code, layout templates, and raw data. Less network traffic, but more work for the browser.

I hope this helped. If you want to learn more about these JavaScript frameworks, you can Google 
  1. AngularJS for the client side (and yes there are others)
  2. Express for the server (again, there are others) 
  3. and for solutions which combine both the client and server - Meteor and Sails! 


Thursday, January 30, 2014

App Architecture and the Basics of Scale

Motivation
Recently a friend asked me about building applications. He is a graphics designer, and doesn't want to learn how to write code. He just wants to get a "big-picture" view of some of the common themes that arise when designing applications today. This blog post is aimed at people like him - interested but non-technical.

I'm going to start off by saying that what I'm about to describe does NOT describe all the different types of software being written today. In fact I know developers who never touch these issues. But my feeling is that this will be accurate for the vast majority of developers.

What Kind of Applications are We Talking About?
Here are some examples:
  1. A blogging platform
  2. An order and procurement system
  3. A recruitment platform
  4. A corporate HR system
  5. A corporate finance system
  6. A (software) bug tracking system
  7. An email and chat platform
These are all very different, but let's see what's similar for most or all of them.
  1. There are UI elements through which users can enter data. Very often these take the shape of forms.
  2. There are UI elements which show data to users. This could be:
    1. the data which they, or other users entered into the system,
    2. data from external systems (machinery, sensors, the Internet),
    3. the results of aggregation and computation, generally shown in a report. Think of "monthly sales totals", or your bank statement.
    4. Often people want to see entire collections of similar data (your MakeMyTrip search results); these are displayed in a list.
  3. There are processes which run in the background which actually do something with this data. These processes may only involve computers (generating your bank statement), or sometimes other people (processing your loan request). For something like email, one process would be the delivery of mail, which might involve looking up email addresses from nicknames; another process would be receiving mail, and running it through a spam filter.
  4. All this data has to be stored somewhere, since it is generally not just sent from user to user. Even in the case of a chat system, users generally want a history of their chats stored for later. So there needs to be a database.
More and more applications today are being developed on the browser - whether Internet-facing or inside an organization, the browser is the portal of choice. We can book hotels, apply to university, check football scores... all through a single portal.

(I am completely ignoring stand-alone applications like Photoshop, Excel, Mathematica, StarCraft... I'm not understating their importance, but they're not relevant right now).

Another medium which is gaining in popularity is the mobile app. They don't run in browsers, but many of them provide functionality which would be natural on a browser. Many of them (LinkedIn, Facebook, Twitter) actually have browser counterparts.

How They Work
The following flow is widely applicable:
  1. A request arrives at some endpoint. For web applications, an endpoint is just a URL, like http://www.my-awesome-app.com/login 
  2. The web server decides whether or not the application can handle this request. For this to happen, the application needs to have told the web server what it can handle. Anything not on that list is a fail.
  3. If the request is valid, and the endpoint exists, the web server forwards it to the appropriate handler in the application.
  4. The handler takes the request and does what it needs to. This usually involves talking to the database. The list of tasks which needs to be performed fall into a workflow. Workflows will have portions which are straightfoward - "after checking that their ZIP code is valid, check their area code" - and portions which are conditional - "if their account balance is too low then deny their ATM request. Otherwise give them their money".
  5. If the request has arrived "bearing data", it gets written to the database. Before that, there will usually be
    1. validation e.g. the user entered their birth date. People from the future are not allowed.
    2. clean-up or sanitization e.g. the user entered their name all in lowercase, so the application capitalizes the first letter
  6. If the request is for data from the database, the application will ask the database for the data. When it comes back, maybe it gets re-formatted, or cleaned-up, before being sent back to the user
  7. Many types of requests need to be authorized, so that not just anybody can get into the system and do just anything. Sometimes this is done using usernames and passwords. Sometimes it is outsourced to another service (sign in with Facebook!).
In summary (and since I'm too lazy to draw a picture):

    User --> Web Server --> Application --> Database --> Application --> Web Server --> User

Scaling Them Up

Now suppose you have more users - more customers, more employees, whatever. It might be obvious that the system will slow down, but how exactly does this happen?

Let's consider an analogy from the real world (which is actually more than an analogy, it really works just like this). Think of a fast-food restaurant, say one which makes sandwiches. They have 4 cashiers where customers place their orders (their requests) and the cashier forwards their order to the kitchen (the application, which starts the workflow). The workflow might look like this:
  1. Get some bread
  2. Put mustard on the bread
  3. Put meat and cheese on the bread
  4. Put the bread in the oven for 3 minutes
  5. Put it on a plate with some chips and signal that its ready
Then the cashier would pick it up and give it to the user. We also assume that the restaurant hasn't figured out how to let a cashier serve more than one customer at a time - which means that until the sandwich has been made, that cashier's tied up.

Now imagine that the restaurant has a lot of customers one day. What happens?

Well, the cashiers work pretty fast, so they can handle the load. And the cooks are pretty fast too. But:

  1. The oven can only handle one sandwich at a time, so there's more waiting there
Okay, so the customers wait. But if this happens repeatedly, the restaurant owners will want to do something about it. They have a few options, all of which will have an impact, but none of which will "solve" the problem permanently.
  1. Buy a bigger oven
  2. Buy more ovens
  3. Hire more cooks
(Also, until the kitchen problem is solved, there's no point in hiring more cashiers).

Here's the analogy: The oven is the database server. A bigger oven is a more powerful server - more memory, faster CPU. More ovens means more database servers. The cooks are the application servers and the cashiers are the web servers.

The cashiers are all the same, and their job is easy. The cooks are all similar, but maybe some specialize in Reubens and some in pastrami on rye. 

The database is the real work-engine, that's where the time is spent. The performance of the application will eventually just be the performance of the database.

Terminology
Let me close with some terminology.
  • Scaling up: This means making a component more powerful, generally by throwing CPU and RAM at it
  • Scaling out: Add more components of the same type at that layer (like hiring more cashiers). Scaling out is cheaper (2 Marutis are cheaper than a Mercedes), but the application needs to have been designed to work that way.
  • High Availability: A deployment that is fault-resistant due to intentional redundancy. Like having extra cooks waiting in case a working cook gets sick or injured.
  • Disaster Recovery. How does the application react when something really bad happens e.g. the data center gets hit by a hurricane, or a virus attack. DR strategies generally involve setting up an entirely separate (and geographically separated) center, ready and waiting for such scenarios. Of course if they're ready and waiting, they cost money even while there's no disaster in-progress!
  • Replication: Keep copies of the data, to protect against drive failure. Disk drives are mechanical objects, and they are the components which fail first and fail often. Data must always be stored in multiple locations
One part I left out is the entire portion of flow between the client and the web servers i.e. the network part. I left it out because one generally has no control over the network, especially if one is using the Internet. Your control starts at the web front-end, and that's where you start optimizing.