Showing posts with label rant. Show all posts
Showing posts with label rant. Show all posts

cleartrip.com - so usable you lose all your money

Quoting Cleartrip's about section, "Cleartrip is dedicated to making travel simple". So simple that you can easily buy tickets worth thousands of rupees. And then lose thousands of rupees by clicking the 'Cancel Booking' link by accident.
ClearTrip is so easy to use that it apparently doesn't believe in confirmation dialogues - your booking will simply be canceled (see the actual steps involved in cancellation on cleartrip here). Cool, what? The good Mr. Narla just lost Rs. 8000/- this way. That's what I call usabilty in action.

Update
Looks like cleartrip.com isn't bad at all once you get past the call centre. Narla contacted them via the feedback section of their website and this elicited a very quick response. They've been exceptionally helpful and have offered to refund Rs. 4000, half the cancellation charge due. This is pretty decent of them, keeping in mind the fact that cleartrip.com cannot recover the cost (it's already been canceled at the airline). Good stuff!

'Programming to interfaces' strikes again

Why oh why do people create interfaces which are implemented only by a single class. There's no polymorphism there that necessitates the interface. What value can there possibly be in writing that superfluous code?
For the umpteenth (well, OK, second) time , 'Programming to interfaces' does not mean 'create one interface for every concrete class'.

Extract an interface if you have two or more classes doing the same 'things', but with differences in the implementation, or if you are designing a framework and want to define a contract for future extension. Not otherwise.

Static or dynamic, use whatever works best

All this hype and noise about static vs. dynamic is starting to get to me. You know what? As a developer, I don't care if a language is static or dynamic. I want to write code to get things done quickly, efficiently and in an aesthetically pleasing manner. The last also translates to 'very maintainable', by the way.

Today, Ruby does that for me. Yeah, so it's dynamic. So is Python. Why am I not using Python? Because it doesn't, for one, support first class function objects. I love my blocks and closures. I can do everything in Ruby that I can do in Python, but it'll run slightly slower - that's a trade-off I'm prepared to make in my current context. Because I started out with Ruby and haven't needed something faster, so never really looked at it seriously (thanks, Paul, for pointing out that Python does have first class function objects). I'm also very very productive in Ruby as opposed to Java - I can create elegant code without having to create a bunch of interfaces first. Programming to an interface is not the same as creating a blessed Java interface, jeez, why the constant misunderstanding? Just because you create an interface first in Java doesn't mean you have a better design. In fact I'd argue that you should extract your interfaces in an evolutionary manner, not design them up-front.

However, I'm fairly convinced that Ruby doesn't work on teams of more that 10 people, unless all the developers are absolutely superb. Even then, you still need good documentation in the form of both rdocs as well as unit tests to ensure that code quality doesn't drop. If I'm on a large project, I'd probably vote against Ruby. I'd want to eliminate trivial errors by having a compiled, statically typed language. If it gave me blocks and closures I'd jump at it. Maybe something like Scala. But here's the point - I will use whatever helps me get my job done well given the current context.

An important thing to remember is that all the programming 'swords' we use cut two ways. Take Java - it was designed to reduce developer error. It's fairly successful at that, but is consequentially a singularly ugly and verbose language and the libraries aren't very intuitive. I have seen more crap code in Java than you'd believe possible and half the enterprisey OSS projects out there are an attempt to make development in Java half-way productive. And without a decent refactoring IDE like IntelliJ IDEA or Eclipse, you've already lost the battle. But hey, it's pretty damn fast, and that hotspot JVM is really cool.

Ruby, on the other hand, was designed for the programmer. It has a superb set of libraries which are arguably more intuitive than Java's. Ruby gives a disciplined developer the power to work miracles. Your code will be readable and elegant without being verbose. Every thing's an object and you get blocks, closures, continuations, first class function objects, message based method invocation, meta-programming...
But you know what? It's kinda on the slow side. And all that freedom in the hands of a novice is a sure recipe for disaster. Class behaviour hacked at runtime to fix bugs. No unit tests. Lots of magic in method_missing. Duck-typing misused causing type errors at runtime. Need I go on?

What I'm getting at is that there is no silver bullet - everything has its place. Your average 70,000 employee outsourcer trying to do Ruby projects on a large scale is probably a bad idea, because they can't always guarantee developer quality. Java on the other hand, combined with CMM, ISO and three other certifications may them help achieve some minimum level of code quality.
On the other hand, take something like Mingle or Slideshare, both running on Rails. I know for a fact that Mingle has a very small team (< 10 including devs, analysts etc) and yet managed a 1.0 release in about 9 months. Slideaware on the other hand supposedly started out with Ruby but I believe has now moved to Erlang for performance reasons.

Deciding which language to use should be based on factors like the delivery timeline, experience level of the team, level of discipline in development (TDD, CI) and performance requirements. Not because you like interfaces and believe that you can't use them in a dynamic language.

So the moral is this. Get. The. Job. Done. And use what it takes to do it quickly and well in that context. Period.

Links 2007-08-07

Take a look at HÃ¥kan's post on 'Why code?'

Avoiding hell at work by spotting Dilbertian job descriptions

Everyone wants that dream job, but it's often hard to tell a dream job apart from the Dilbert job - you know what I mean - boring work, lots of finger pointing, technical people marginalised, pointy haired boss makes all the money...

So here's the thing about job descriptions - they always contain a certain amount of hyperbole. It's a fact of life. The trick is to take a close look at the bits which use words like 'leverage', 'teamwork' and more recently, 'rock star'. Examining the hyperbole in a particular job description can give applicants a fair idea about the nature of the company, and possibly even the nature of their future boss.

Here are some of the standard JD patterns that any Google search will turn up. I'm compressing job description to JD - I'm too lazy to type it every time.

1) Requirements that aren't filters
So there's this JD which has a requirement 'should be a team player'. Do you seriously think any applicant is going to look at that, say 'Nah, teamwork isn't for me' and move on? Or to put it another way, some requirements simply state the obvious. This is especially true if adjectives are used, but without any subject. For example, compare these two extracts:

+ Should be passionate about Ruby

+ Should be self motivated and open to learning and working on new languages and platforms

as opposed to

- Should be passionate and self-motivated
- Should be dynamic, with high energy and enthusiasm

In the first case, it is clear that someone who knows something about the job has used those adjectives, not some HR drone trying to create meaningless filler content. The subjects to which those adjectives are applied are clear and applicants can use them to make decisions.

Count the number of requirements which don't really help you as an applicant decide if you're a fit for the job. Less is, of course, better.

Some key phrases to look out for:
  • Excellent team player
  • Strong work ethic
  • Highly motivated, dynamic, passionate
  • High energy and enthusiasm
  • Flexible
  • Open and honest (ha ha, I'm sorry, remembered some Dilbert cartoons)
2) Requirements that are plain impossible
This one is simple and obvious, so I won't spend too much time on this one. If you see any of these, run for your life - the company hasn't a clue.

Look for stuff like:
  • Minimum of five years experience with Rails
  • Minimum of nine years experience designing and developing enterprise class applications in .Net
Rails was released in 2004, and .Net in 2001. This article was written in 2007.

3) Requirements that are all over the map
I'm talking about a JD where the requirements are so generic and broad that they cover just about everyone in the field. The requirements aren't necessarily contradictory - but they aren't complementary either.
Here's a sample:
  • Extensive experience developing in Perl/PHP
  • Strong foundation in XHTML and CSS
  • Extensive experience in developing in Visual C++ including MFCs
  • Strong foundation in networking protocols
Steer clear of such JDs unless there is a clear thread linking all the requirements. It's most likely that their HR is just fishing or there is a major disconnect between HR and the department looking to do the hiring. In India, there's a clear and present danger that you're being hired for the bench.

4) Weird or pompous designations
Watch out for weird designations for the job in question, especially if not accompanied by an explanation - either the job is really cool or really mundane. The people writing JDs often invent weird designations for a position if

a) They want to stand out and attract cool people
b) They want to disguise a mind numbingly mundane job as a funky one
c) They want to use your ego to get you do something fairly run-of-the-mill

It's the latter two that you need to watch out for. For example, in Bangalore, it's now understood that if someones designation is 'Marketing Executive', they are essentially salespeople. Every fifth person in Bangalore is an executive of some sort these days. Unfortunately there is no hard and fast rule to tell the first apart from the second and third except to research the background of the company. A designation of 'Hacker Dude' at a startup is much more plausible than 'Hacker Dude' at any one of our 70,000 employee local outsourcing behemoths. Companies which let you choose your own designation are the best (shameless plug: guess which company fits the bill...)

5) Corporate babble
You've seen this in a thousand places - stuff like "As a senior architect, you will focus on developing collaborative strategies to leverage the latest technologies and maximise productivity". Yeah. Whatever.

OK, my example is a bit over the top, and you'll always find some amount of this gunk, especially around the description of the company itself. Often it's fairly innocuous - stuff like 'work on cutting edge technologies', or 'leading innovator'. Sure, that's sort of OK, you can understand why it's there and it doesn't directly affect you.
However, the more babble there is, the more care you need to take. If meaningless babble like that is being used to describe the job itself, steer clear - PHB ahead.

6) Appeals to a misplaced sense of duty
I've met people who've been brainwashed by their employers into thinking that working fourteen hours a day, every day, is really cool. They (the employers) manage this by appealing to employees (misplaced) sense of duty and loyalty. JD writers know this, so watch out for stuff like "aren't afraid of working around the clock to make things happen". Again, this depends on context. Working for a startup is very much a 24 hour job, and you're doing it because you own a part of the gig. Not so with your regular company.

All things said and done, there are a bunch of cool people out there, and a bunch of cool companies where they'd like to work, and who in turn would love to hire them. We just need to figure out standard patterns to identify each. In this case, the cool companies somehow tend to have a minimum of these JD anti-patterns so it isn't too hard to identify them simply by examining the JDs they put out.

Do let me know if you've come across any JD patterns or anti-patterns of your own.

Read the other side of the story: Be the nail that sticks out - how to get hired by an interesting company

Some banks never seem to get the net

How about this for a muck up? I've received an email purportedly from Axis Bank (formerly UTI Bank), warning me against fraud. It has set off a whole bunch of alarms at the spam filtering service my employers use. See for yourself.
The MessageLabs Email Security System discovered a possible virus
or unauthorised code (such as a Trojan) in an email sent to you.
The email has now been quarantined and was not delivered.
Please read the whole of this email carefully. It explains the status
of your email, the nature of the intercepted virus and the next steps
for addressing the problem.
To help identify the quarantined email:
The message sender was
Onlineservice@axisbank.co.in

The message originating IP was 81.169.146.190
The message recipients were
***@thoughtworks.com

The message title was Urgent Fraud Notification! From AXIS BANK Account Review Department
The message date was Thu, 16 Aug 2007 11:17:05 -0700
The virus or unauthorised code identified in the email is
>>> Possible MalWare 'Exploit/Phishing-www.axisbank.co.in-07f0' found in '865236_1X_PM1_EM7_MH__message.htm'. Heuristics score: 350

Some viruses forge the sender address. For more information please
visit the virus FAQ's link at the bottom of this page.
The message was diverted into the virus holding pen on
mail server server-*.tower-**.messagelabs.com (pen id *****_**********)
and will be held for 30 days before being destroyed
Please contact your IT Helpdesk or Support Department for further
assistance.

I know I'd dropped my business card in a collection box at their ATM a few weeks ago for some promo or the other. I know they've picked it up, because I'd received a call last Saturday at an obscene hour (9 am on a Saturday morning after a night out is an obscene hour) from one of their 'executives' about it. I'm very careful with my office mail id and ensure that I only use it for work related stuff, so I never get any spam on it - consequentially I'm pretty sure it isn't on any database anywhere.

I'm guessing either the email is authentic and someone screwed up with the attachment, or possibly someone at Axis bank has been careless with the data they've gathered, allowing e-mail ids to reach phishers. It's just too much of a coincidence that this happens a few days after I got that call. Either way, a fair number of the unsuspecting customers of Axis bank who receive this e-mail will have been phishing targets. You'd think banks would have learned to be more careful by now...

Update 20071011
The Axis bank phishing saga continues, with two more emails sent from Axis Bank . See for yourself. This I received on the 9th.
Dear Customer,
You have 1 new Personal secure message
Please login to your online and visit the secure Messages,
section in order to read the message,

To Login, please click the link below:
Go to Online Banking ( http://ipoly-taj.hu/components/com_zoom/lib/Axis/Axis_Security.htm )

Regards
Axis Bank Ltd, N.A. and its affiliates

I haven't linked to that url, but it's a very poor fake of the Axis Bank homepage, logo and all.
Today I received this:
Update Your Online Banking Records.!!!
In accordance with our major database relocation we are currently
having major adjustments and updates of user accounts to verify
that the informations you have provided with us during the sign
up process are true and correct. However,We have noticed some
discrepancies regarding your account at UTI & Axis Bank.
Possible causes are inaccurate contact information and invalid logout process.
We require you to complete an account verification Process
procedure as part of our security measure.

You must click the bottun below to complete the process

[Button - Update your records]

Unable to do so may result to abnormal account behavior during
transaction.

Sincerely,
Thank You for using Axis Bank,

The Axis Bank Security Team.
___________________________________
© 2007 AXIS Bank Group plc. All Rights Reserved. Privacy | Helps | Legal

Clicking on the link leads to http://ipoly-taj.hu/components/com_sef/www.axis.co.in/RetailSignOn.html?server_error.signon=Update+Your+Records

So anyways, beware of these phishers.

The best of the worst: Standard patterns of horrible code from Java and .Net

There are some standard worst practices in code which make my teeth ache when I see them. They can appear at any time in a code base and look very innocent but will turn everything around them into spaghetti in short order. Someone somewhere near you is typing out one of these insidious bits of code as you read this. You have been warned.
I've already written about the one where people create namespaces and constants to handle types. Something like

public interface CarType{
public static final String AUDI = "audi";
public static final String MARUTI = "maruti";
}
The constants are usually ints, or even worse, Strings. The latter start popping up everywhere, including (in one bad case) eventually showing up as a piece of text on a UI. But enough of that, let's move on to today's rant.

Today, recruitment had bribed some of us developers into a code review session (our interview process requires candidates to submit code) over lunch by ordering from Subway. Some of the code I reviewed brought back two of the most annoying, yet widespread development worst practices. Here they are, one from Java and the other from .Net

.Net: Everything is a DataSet
Aargh. Why of why is there this obsession with mapping everything to the rows and columns of a DataSet? Everything is not a DataSet. They're People and Employees and Magnolias. I've seen code where there wasn't a single developer created class! And this from people with several years of experience, not freshers. The flow inevitably looks something like Create DataSet -> Read from xml file/webservice -> Optionally pipe it around a bit using a few web services -> Pump into DataSet -> Perform operations, creating and manipulating DataTables, DataColumns and DataRows by the dozen with no classes and tons of procedural logic -> Bind these to UI objects. If you're really unlucky, that 'tons of procedural code' I mentioned will be in a class which inherits from Form. A more thorough, consistent and violent violation of OO principles I am yet to come across.

I would suggest that XStream .Net and NHibernate be used instead to achieve the convenience that DataSets offer in the short term, but over a longer period and while maintaining code quality.

Java: Every field must have a getter and a setter
That strange and wonderful idea, the bean, has made a whole generation of Java developers completely inured to the idea of maintaining encapsulation. The bean was created to solve a specific category of problem, but the structure of the bean has spread like a virus, destroying the integrity of the most innocent of domain objects. When doctors wish to test the reflexes of such developers, the preferred method is no longer a mallet applied smartly just below the kneecap. No, you need just give them a class in an editor, ask them to add a field and check if they automatically add a getter and a setter for it.
The only time using a setter is acceptable is
  • if the state of the class cannot be corrupted by using it (calling setText on a TextBox can change its state, but does not corrupt it)
  • if the framework demands it
Getters aren't as bad as setters, but over time on a large code base they encourage the processing of data outside of the class to which it belongs. From there, it's a short and slippery slope to code duplication and other evils. In combination, getters and setters can reduce once healthy domain objects to pale DTOs.

I would suggest simply avoiding setters unless a change of state for that field does not corrupt the object. A lot of frameworks now understand this and help developers do away with setters. Hibernate, for example, allows you to configure field level access (Hibernate will populate your domain object fields directly using reflection, even if they are private), thus removing the need for setters.
For getters, use them only when the data read using the getter will never be processed - in other words, only in situations like binding to a UI or persisting to a database.

What it takes to buy a .in domain and other stories

I've been trying to buy a .in domain for about five days now with little success. First the provider's (hostindia.net) servers were down, so every attempt to create an account with them would produce a ton of SQL error trace. I gave up after a couple of tries.
I was pleasantly surprised to get a (very polite) call the next day from someone at HostIndia apologising for the downtime and asking me to please try again - and this kind of customer care goes a long way with me.
So I tried again. I was able to order a domain, but when I got to the ICICI bank credit card gateway, it produced a bill for Rs.1398/-, twice the due amount. Turns out that HostIndia's billing system was duplicating orders, putting in two copies of every item on the bill.
Trusting in the fact that the customer care I'd already experienced wasn't a blip, I sent off a mail with a copy of the order. They got back to me immediately apologising again, saying that they'd removed the duplicate order from my account and I could now log in and pay up the 699/- that the domain costs.
So I login and get to the gateway just fine, make enter my info and hit 'submit' - and all I get is

RespCode=2&Message=Required+parameter+missing

from this url: https://payseal.icicibank.com/mpi/Moto.jsp

So there's no way I'm trying that last bit again. And am I following up with ICICI customer care this time? Probably not. I am going to be royally pissed if the transaction doesn't go through but I get billed for it. At the moment I'm quite happy if I don't get my domain - it just isn't worth the effort.

There's a trend here that I'm seeing more and more of late - decent companies (others I know have used HostIndia too) are getting bitten because the apps they use just aren't up to the mark. Some of them try to make up for this with amazing customer care - HostIndia is one example, TimesJobs is another. I'd signed up at TimesJobs quite some time ago, and though my profile clearly says 1.5 years of experience, I started getting mails for jobs requiring 5 years and up of experience. When I checked the site, sure enough, it showed my experience as being 5 years. A mail to customer care changed the number back to 1.5 - but failed to stop the mails. Another mail to customer care had no effect.
Tired of being spammed, I started looking for an 'un-register' option on the website. Not finding one, I just went ahead and disabled 'alerts' (as they are called). No result.
Next I removed all my contact information from my profile, including e-mail id. Still no result.
It took something like four (non-local) phone calls and five emails to get this fixed. The strange thing was, support seemed as bewildered about the whole thing as I was because all their systems told them my account was disabled.
I have a feeling that many of the companies in India, from the biggest to the smallest are getting taken for a ride when they get bespoke software built for them.