Posted by kathysierra
on February 16, 2004 at 5:13 PM PST
You KNOW you shouldn't have this much trouble, so you think, "Am I getting stupid, or did someone go out of their way to make this API confusing?" In my case, I probably *am* getting stupid, but I am SO not going to take ALL the blame...
There have been some interesting and useful discussions and guidelines on API design from people like Steven Clarke and Bill Venners . And the discussion can get pretty heavy.
But I'll just mention one idea: APIs should not be exempt from fundamental usability principles. I'm coming from the selfish perspective of one who has to actually learn to *use* these things, and, more recently, as someone who has to try to help others do the same. And if for no other reason than to make myself feel better, I'm going to suggest that if you have real trouble working out an API and you're thinking that it REALLY shouldn't be that hard... perhaps it really isn't YOU. So before you start questioning how on earth they ever gave YOU a PhD in astrophysics when you can't even work out one frickin' interface, take a deep cleansing breath and repeat this little positive affirmation: "It's not me. I AM smart. I have the to prove it. But oh what I wouldn't give to wrap my hands around the neck of the one who designed this API..."
It's easy to rail on API designers when you're on the other side, I know. I've personally authored some of the most unreadable and unmaintainable code in the history of software. But at least I have the decency to feel guilty about it, especially after having spent a few years studying usability and learning theory. I don't want to single any group out, but I have to make at least *one* example; it's from the EJB spec (which, don't get me wrong, I LOVE. It's perhaps one of the most reader-friendly specifications to come from Sun).
Usability principal: Things which behave differently should look different.
This is fundamental user interface or product design 101. Humans will assume that if two buttons share the same shape and color, for example, that they'll generally have the same kind of behavior. So product designers are expected to do things like, "Make the navigation buttons look and feel different from the control buttons..." One of the worst violations of this is in products which use the pure evil of "modes". You know what modes are--where a button is overloaded so that in one mode it does THIS but in another mode it does THAT and... Donald Norman (who recently spoke at the Emerging Tech conference) writes fabulous books, at least one of which should be REQUIRED reading for every programmer: "The Design of Everyday Things". He does a great job of letting you off the hook by explaining how it's not your fault you can't work that device, and that product designers are either being lazy or trying too hard to save money by making fewer buttons.
Example API violation: lifecycle callback methods for Entity and Session beans.
When I try to help someone learn EJB, I spend way more time than I should with things like, "What's that? Why is there an unsetEntityContext() for Entity beans but NOT for Session beans? Oh, because you have to have a callback for when the bean instance is being destroyed. What? That's what ejbRemove() is for? Oh, no, that's just for Session beans. With Entity beans, ejbRemove() means "delete from the underlying persistent store", so... since ejbRemove() was given a profoundly different meaning for Entity beans than what it means for Session beans, well, they had to have something else to call when an Entity bean instance is about to die." And then do all that again with ejbCreate(), of course. (And don't forget that both ejbRemove() and ejbCreate() have corresponding methods in the client interfaces... remove() and create(), which also share these differences.)
According to usability fundamentals, giving the Entity bean interface the same methods as the Session bean interface, but giving those methods completely different meanings, adds MUCH more cognitive strain than if developers simply had to learn two totally new method names. You simply can't wrap your brain around learning that a set of methods does one thing for this object, and something drastically different for this other, very closely related, object. In other words, they made ejbRemove() and ejbCreate() use modes! If you're in Entity mode, they mean one thing. If you're in Session mode, something different. Not that we all don't *get it* and remember it, eventually, but it takes longer and we could be doing other more important things. Like skiing.
Again, I feel a little bad picking on this one example from EJB, especially when there are so many other things I really like about that spec. But it's the one that's caused me the most frustration, because I have to go through this process of helping people learn—and then unlearn/relearn—these methods every time I try to teach EJB.
Now, for some APIs it probably is just a question of better docs. But better docs wouldn't help the fundamental problem of something like modes, so better docs isn't the solution for everything.
My suggestion is that each and every programmer be strapped into the Don Norman Appreciation Chair and forced to read "The Design of Everyday Things". It's fun, fascinating, and enlightening. I have a whole book list after that, but I'll save those for later. My goal in life is to make MY life as easy as possible, and I truly believe that if everyone pitches in, you'll really help me out on that. Because unlike so many of you, I am one of those unfortunate souls who is NOT a quick learner. If not for speed dial, I wouldn't be able to call home. Imagine how long it takes me to memorize well-designed and well-named APIs, let alone the truly confusing ones...