⇥ Universal Save for iOS Apps

September 29, 2011
No comments
 
⇥ Permalink

Federico Viticci, commenting on a piece in which Ted Landau argues that iOS needs a “Universal Save” for iOS Apps:

Specifically, Landau notes that the lack of a “universal save” option for documents that can be read by third-party apps (PDFs, text files, images) leads to an annoying and pretty much useless duplication of content.

[…]

For Ted and me, yes, being able to avoid file duplication and tedious exporting processes would be nice. But I do wonder how much does Apple care about such functionalities considering the underlying paradigms of iOS and the upcoming iCloud functionalities of iOS 5. For one, Apple really cares about application sandboxing: each app has its own controlled data environment and only a few items can be shared between multiple apps.

I’m firmly with Federico on this point. The average iOS user has no use for filesystems, files, and the concept of “saving.” That’s probably one of the biggest innovations that iOS brought forth; of course, it’s going to be unpopular with us power users, because, having learned to live almost symbiotically with our computers, we have the hardest time letting go and learning this new paradigm.

This is also a problem for developers. I see tons of threads on mailing lists where folks are desperately asking how they can get out of supporting some of Lion’s new features and keep their app’s old functionality the way it was.

That’s not the right way to go about things. If you want your app to feel at home in a new operating system1, you have to embrace and implement the user-interface paradigms that the OS describes. This is probably the most fundamental step towards providing users with a consistent experience instead of a hodgepodge of half-baked ideas—and one step that, as a developer, you skip at your own risk.

What’s interesting is that, in my opinion, these “limitations” that we power users are complaining so much about matter very little to regular folks, as demonstrated by the great success of apps that have adopted Lion’s features in full. As sandboxing makes its way to OS X, this is going to be particularly important, because Apple gives its desktop apps much more freedom, and the addition of freedom to the ability to develop software results in a very flammable mixture.

Consider, for example, the case of 1Password. When Agile Bits released its popular software on the App Store, sandboxing forced them to introduce some seemingly arbitrary limitations on how it back its data up to DropBox. The reaction from power users was duly indignant that such limitations should be imposed on them.

The reaction from the public-at-large? 1Password quickly reached the number-two spot on the App Store. You do the math.

  1. And make no mistake about it, Lion *is* a new operating system.

⇥ You are not “Mr. X”

September 22, 2011
9 comments
 
⇥ Permalink

I keep coming across code like this (lifted, verbatim, from an OSS project I’ve been working with recently):

$a = $num * $coeff + $_SANITIZED_GET['val'];

What, in the name of all that is good and just, is “a?” Or, for that matter, what are “num” and “coeff?”

Computer manufacturers, OS vendors, and programming tool developers have worked for decades to give us the ability to create identifiers of arbitrary length. Personally, I’d much rather see someReallyLongNameThatLooksALittleRidiculous than a function or variable name that won’t tell me what it does at first sight.

The same goes for data. A “1” and “0” in a database don’t tell you as much as “Yes” or “No,” which are just as localizable, indexable, and searchable. Enumerations, as far as I’m concerned, should be verbose unless there are very compelling space or performance requirements that say otherwise.

I know that there are many people who disagree with this approach, but their arguments tend to fall in the “that’s the way I’ve been taught to do it” camp. The reality is, a numeric enumeration is just as arbitrary as a string-based one, but much harder for the human eye to make sense of—and we all know that, sooner or later, all data is looked at by a human eye. There are some circumstances in which performance and space constraints come into play, but otherwise the development tools at our disposal are mature enough to handle either type as easily as the other.

Besides, using numbers to identify non-numeric value is a domain violation. It used to be a necessity twenty years ago, but the vast majority of us work in environment that are well past that point. You wouldn’t want to be called “492829,” right1?

So, if you are writing a book or teaching a course on programming, please teach your readers and students to write descriptive code. They’ll be better for it, and we’ll be grateful that you did.

  1. Yes, I know. You probably have some kind of social security number assigned to you by your government. But that’s not your name—it’s an index (that is, a numeric value) in a table that *contains* your name. Big difference.

⇥ Generations sideways

September 20, 2011
No comments
 
⇥ Permalink

Matthew Baxter-Reynolds on the various toolsets available to mobile developers:

The fact is that if your day job involves sitting in Visual Studio writing C# applications, or building Java applications in Eclipse (which will be most of you – albeit not necessarily in Eclipse), when you fire up Apple’s Xcode and start building CocoaTouch applications in Objective-C you’re going to come face-to-face with a toolset that has not had the sort of love put into it that the open source community has put into the Java toolset and associate platforms, or that Microsoft has put into VS and .NET over the past 10 years. Apple has been caught on the back foot by the popularity of its tools and is at least one, if not two, generations behind. For example, the iOS version of Objective-C does not have garbage collection.

Leaving aside the mistake at the end (which Baxter-Reynolds corrects at the bottom of the article), I’d say that Apple’s approach to its toolset is simply different, in some cases for the better, and in some for the worse.

Cocoa seems to be built on a simple premise: that developers know how to develop, but don’t know how to design interfaces; which, I am sorry to say, is probably not far off the mark.

Thus, Apple’s assumption is that developers don’t need fifteen ways to parse an XML file, because they already share enough common knowledge to do it on their own—and if they don’t, chances are that they will be smart enough to come up with their own solution and share it with the world.

The focus of Xcode is, instead, on creating an environment where even a person who is not well versed in user-experience design can still write an app that looks and feels good. Therefore, a lot of emphasis goes into good interface metrics, good look and feel, and so on.

In other words, Apple is counting on engineers commoditizing the aspects of software development with which they are most familiar, and focuses instead on filling the gaps in other disciplines that, traditionally, trip them up.

Case in point, Objective-C has lacked a public JSON framework for a really long time1. By all accounts, this should have made OS X and iOS very unsuccessful platforms for Web service-enabled apps; instead, developers simply built (and collaborated on) several JSON frameworks of their own. On the other hand, both of Apple’s operating systems present their users with an environment in which apps use a consistent design vocabulary that is well within the grasp of even the hard-core Luddite.

There are two reasons why this is important. The first is that a lot of development is still done without the benefit of a designer’s expertise. Even medium-size teams that build apps for large audiences place much more focus on engineering than on usability and ergonomics; thus, a toolset that promotes basic design principles can be beneficial from the get-go.

Second, even where designers are involved, developers are still responsible for implementing the code that makes design possible. Therefore, a development platform that emphasizes design creates a more collaborative environment for all involved.

That said, there are some aspects in which Apple’s toolset has dragged behind its competitors. Memory management, for example, has long been one, but Apple’s approach to solving the problem of managed memory has been a very deliberate one: they tried garbage collection, figured out that it didn’t quite work (particularly on iOS, where resources are relatively scarce), and moved to a different solution (ARC) that somehow manages to create a managed-memory environment with less overhead than its unmanaged predecessor.

All in all, my personal experience has been that every development environment has its flaws and benefits. Even Xcode’s focus on design doesn’t prevent the creation of plenty of really horrible apps. Still, that’s a far cry from saying that it’s generations behind—I’d rather say it’s generations sideways.

(Via Daring Fireball).

  1. Though that is getting resolved soon.

⇥ Right conclusion, wrong reasons

September 19, 2011
8 comments
 
⇥ Permalink

ORM is an anti-pattern:

The reason I call ORM an anti-pattern is because it matches the two criteria the author of AntiPatterns used to distinguish anti-patterns from mere bad habits, specifically:

  1. It initially appears to be beneficial, but in the long term has more bad consequences than good ones

  2. An alternative solution exists that is proven and repeatable

It is the first characteristic that has led to ORM’s maddening (to me) popularity: it seems like a good idea at first, and by the time the problems become apparent, it’s too late to switch away.

I agree that ORMs are, in general, to be treated with much suspicion. Their main shortcoming is that they are a square-peg solution for a round-hole problem: attempting to map a data model to another inevitably leads to conflicts and issues, or there wouldn’t be a need for the two different data models in the first place.

The real problem with this blog post, however, is that it uses an incomplete definition of anti-pattern (there’s Wikipedia for you). In his original article on anti-patterns, Andrew Koenig1 speaks specifically of anti-patterns as juxtaposing to patterns; like ying and yang, you can’t have anti-patterns without having patterns that they can be related to.

The significance of this is that an anti-pattern is not just something that is “bad on its own.” More often than not, it is more like “a pattern that has gone bad”—the right concept being applied under the wrong circumstances.

Thus, ORMs are not inherently bad. They are just inappropriate for a number of settings in which they are, admittedly, used. An ORM can be an excellent solution to scenarios in which a key-value store is not available, or in which a very simple schema is all you need. In those cases, the overhead of an ORM may be an acceptable tradeoff for the simplicity that it brings to an application.

This, in turn, brings me to another point: using an ORM does not excuse you from understanding the underlying data model and the way the ORM uses it. If you do, the ORM becomes almost inevitably an anti-pattern, because you’re resorting to magic and applying a solution without knowing the problem.

Thus, while it’s true that ORMs encourage (and mostly fail) the developer not to think in terms of SQL queries, there is no way to use an ORM well without understanding relational data mapping. Or, put another way, the ORM doesn’t replace your knowledge of SQL—it simply adds one more layer of indirection to it.

An argument could be made that ORMs do not scale well over time, because the relationship between the overhead they introduce and the complexity of the underlying data model is not linear. This, however, seems to me like a symptom of application design, rather than an inherent flaw in ORMs.

Let me give you an example; if you’re writing an application that you know you will only need to run once (for example, some sort of importer or data analysis function), an ORM can greatly simplify your job and bring immense benefits. Will you care if it doesn’t scale? No, because you’re writing a single-use application.

If, on the other hand, you’re writing a more complex application, then you need to evaluate how well an ORM will hold up over time. That’s as much an art as it is a science, but it doesn’t make ORMs inherently bad; it simply means that you need to learn to design software properly.

  1. The original article in JOOP is not available online, but it’s included in Linda Rising’s Patterns Handbook

⇥ Dashes, spaces, and incompetence

September 14, 2011
8 comments
 
⇥ Permalink

Take, if you would, a look at your credit card. Unless you come from a different planet, chances are that it, like mine, has a series of digits separated by spaces. Depending on which kind of card you’re looking at, these numbers may be grouped in different ways, but, generally speaking, this is probably a valid statement for every kind of credit card in existence.

Those spaces are there for a very specific purpose: they break the visual flow of your credit card number, providing your brain with anchors that it can use to group the digits together in a way that makes them easy to process. Although the number as a whole is no easier to remember, it’s much simpler to copy and compare something like “123 457 789″ than “123457789.”

Why, then, do so many developers still insist on asking users to enter their credit card numbers “without dashes or spaces?”

The problem here is not just one of developer laziness. Sure—in the specific example of credit card numbers, all that needs to be done at the code level can be expressed with a regular expression that borders on the stupid:

$creditCardNumber = preg_replace('/\D/', '', $originalCardNumber);

In some other cases, building good heuristics that are flexible enough while providing the proper constraints can be a little trickier, but the real issue is that so many programmers don’t even try. And that, unless you’re writing your applications in assembler, is simply incompetence.

Learned helplessness

There is a beautiful concept in cognitive psychology called learned helplessness. The basic idea behind it is that people who repeatedly fail at a task will eventually blame themselves for the failure and give up trying to do it.

This, in a nutshell, describes perfectly the way I see most non-technical folk relate to computers. They’ve just been hit so many times by software that makes no sense to them that they approach every task with fear and uncertainty—instead of making users more productive (and, therefore, happier), software makes them more depressed.

Why does this happen? Because of a million little (and big) things like the credit card snafu. Every time the user encounters a scenario in which an application creates a disconnect between reality (spaces on my credit card) and its software representation (no spaces or dashes!), the sense of helplessness increases, and productivity decreases as a result.

Let me fix this for you

The good news is, this kind of problem is due entirely to developer incompetence, which makes it easy to fix—after all, there are far fewer of us than there are users, so education should be a far simpler task.

In the specific example of credit cards, the issue is usually related to the fact that the upstream credit card provider requires that numbers be passed to them without any extraneous character, and we simply transfer that constraint up to our downstream user.

However, the constraint is not transitive: it makes sense in one direction because the provider has created an interface built for engineers, who (at least in principle) should be able to deal with the resulting requirements. Our users possess no such ability, and expect an interface built for them.

From a more general perspective, solving this kind of problem is not that difficult: you simply need to look at the constraints you create from the user’s point of view. Credit cards numbers have spaces in them in real life, and that’s how users will want to input them. There. Simple as pie.

This doesn’t mean, however. that you need to take this too far in the other direction and create skeuomorphs that attempt to reproduce reality too closely. For example, making your credit card input form look like a credit card is dangerous because the various types of credit cards are different enough that it could create confusion instead of dispelling it. Besides, the user is probably capable of abstracting the underlying data model enough that such a skeuomorph would feel patronizing.

And, please, do not think that this is something that only designers should worry about. Developers are meant to solve problems, not churn out bytes. If you don’t want to be treated like a code monkey, stop acting like one.

⇥ Suggestions for a younger developer

September 13, 2011
5 comments
 
⇥ Permalink

Every now and then, I get asked by developers who are just getting started in the trade if I have any suggestions to help them out—favourite language, tips and tricks, and the like.

None of these things matter, really, but there are a few things I wish I had known when I started out that have nothing to do with the mechanics of software development.

1. Be humble

You just finished college with full marks. You know hundreds of algorithms backwards. You’ve read Don Knuth’s seminal programming series cover-to-cover (something that Professor Knuth himself would probably be disinclined to believe).

Alas, that does not a programmer make you. You’ll find out soon enough that being successful at writing software means quickly discarding options that are unlikely to lead nowhere, while zeroing in on those that will. And, more often than not, it means throwing away the book and violating every rule to get where you need to go.

2. There is no magic

Never assume that other developers are necessarily smarter than you. Remember that the people who write the tools you use have access to the same kinds of resources and techniques as you do.

Never accept the frameworks and APIs at your disposal as black boxes; understanding how they work internally will help you write better code against them.

3. Programming is a craft, not an art

Good code, like art, is many things to many people. Working code, however, is undisputedly code that performs its tasks properly and efficiently.

A good developer is like a good artisan, constantly balancing the needs of form and function, but always focused on making things work in the most practical way possible.

4. Software solves problem

Writing code is a crucial, but relatively minor, part of the software development process. You write code to solve problems, and can’t be good at one without being good at the other.

Strive to be part of the entire process that leads to the development of a system; insist on being treated not as a code monkey, but as an integral part of the overall team that contributes more than mere lines of code.

5. Code doesn’t leave sawdust

One of the best aspects of software development is the fact that it is a purely intellectual exercise. With a modicum of precaution, we can experiment knowing that our only waste is time; there is no wood to chop, pencils to sharpen, chemicals to react, or paper to crumple.

Sometimes, trying things out in practice leads to unexpectedly efficient solutions that all the planning in the world could not have anticipated. And, when it doesn’t, there’s always source control to take you back in time, ready for another try.

⇥ The easiest way to add unit tests to your application

September 8, 2011
One comment
 
⇥ Permalink

Unit testing shouldn’t be hard. In fact, given its usefulness, it should be easy and pleasant—a tool that every developer would never want to do without.

And yet, I see programmers (and, more frighteningly, systems architects) struggling with it constantly. In many cases, they are saddled with large codebases that have never seen any tests whatsoever on one hand, and the fact that a recent changes has caused their entire system to crap out on the other.

The unfortunate thing is that most “experts” will tell you that you need to drop everything you’re doing right now and spend however long it takes to build a complete testing harness for your project.

These people, in my oh-so-humble opinion, live in a fairy-tale land in which deadlines are things that happen to other people and management is made entirely of sugar cookies.

Back in the real world, stopping development for weeks while you figure out how to add unit tests to cover your entire codebase is simply something that cannot be done (at least, not if you want to keep your job), no matter what future benefits it might bring.

The good news is, adding unit testing to your existing project only takes five minutes—which is pretty much how long it takes to get a unit testing framework installed. That’s it. Move on.

A test today is better than a thousand tests tomorrow

Still here? OK, read on.

Chances are that your application “mostly works” today. If it didn’t, you’d have much bigger problems to worry about than unit tests. Adding unit tests is not going to solve any problem because you don’t have any.

That’s fine; you just need to look at testing in a different light.

Where unit testing helps is in managing change. The job of unit testing is not to determine that your application works as advertised: that’s what your QA process—of which unit testing is part—is for.

Rather, unit testing is there to help you ensure that changes you introduce in your code do not have consequences that you did not intend.

Once you make this decision, adding unit tests becomes really easy—and very productive.

Fixing bugs

A typical example is correcting a deficiency in your code. Obviously, you can’t fix a bug until you’ve reproduced it. And, when you have figured out a way to consistently trigger the bug, you’ll have to do so multiple times as you try to figure out a solution to the underlying problem.

Curiously, that exactly one of the things that a unit test does well. Instead of triggering the bug manually, you can simply write a test that does so programmatically; in so doing, not only have you added a very important test to your code—you actually made reproducing the bug (something that you will probably need to do multiple times as you fix it) much easier.

Refactoring

Another place where writing unit tests is an easy part of the development process is refactoring existing code. The worst thing that can happen here is that a change you make breaks something else, and you don’t find that out until the code is in production. That, as they say, would be bad.

Since that’s something you (a) want to avoid and, therefore, (b) you will have to track anyway, writing a unit test is a great way to automate the process. More interestingly, it’s an easy way to write a meaningful test that validates how your application works as opposed to what your code does (more about that later).

Adding new functionality

This leaves with the scenario in which you’re writing completely new code1.

Proponents of TDD and (to a certain extend) AOP will tell you that you should either write your tests before your code, or alongside it.

I know I will probably catch a lot of flak for this, but here’s my recommendation: do absolutely nothing.

Writing code is often a process of near-scientific discovery. The abject failure of the waterfall model should have taught us by now that the idea development and architecture are two completely separate phases is simply at odds with reality.

In the real world, we have to contend with imperfect specifications, unknown constraints, and the distinct possibility that, halfway through the development process, we find out out that we’re trying to solve the wrong problem.

As a result, I, personally, prefer to write code in an almost free-flowing manner, focusing on finding the best solution to the problem at hand. Throwing testing in the mix, while definitely a good idea in principle, just adds one more level of complexity to an already overly complex task in practice.

This doesn’t mean, however, that tests are out of the picture.

If you think of unit tests as a tool to manage change, in this particular scenario their job is to ensure that the change you’ve made (adding new code) works the way you mean it to. In other words, once your code is completed and working the way you think it should, you can write a test that exercises it to “solidify” it as a future constraint.

The best time to do so is when you commit your code to HEAD2. That’s because committing to head indicates specifically that the code is complete and its behaviour should therefore be invariant from that point forward.

Better yet, if you work in a team with more than one person, you can simply make writing tests part of the code review process—when you push your branch for review, whoever reviews it also write the tests. In addition to spreading the workload, this ensures that another person validates the principles under which you built the software, increasing the likelihood that they will poke holes in your programming and reduce the incidence of defects.

Writing meaningful tests

Writing tests is pointless if they don’t actually help you manage change. The question, then, is: how do you write meaningful tests?

That’s a complex topic, but the best thing you can do is to think of unit tests in relation to software design. (Or, you can grab the slides from last year’s Codeworks Tour, where my colleague Keith Casey made a wonderful presentation on this topic.)

In architectural terms, software is a kind of mapping between visible affordances (what your application can and must do) and constraints (the ways in which it must be limited so that things are done properly). Any kind of QA that you perform on your software (including unit testing) must be built around the concept of validating your code as a whole, even when you are only exercising a small portion thereof.

A good test, therefore, is not concerned with replicating all the possible sets of inputs and output of a particular piece of code; it’s only concerned with replicating those sets of inputs and outputs that can happen during its intended usage.

The difference is critical, because in the first case you’re exercising the code in isolation from its surroundings, while in the second you’re exercising it based on the role it’s meant to play in the final product.

Of course, this still means that you need to test all the realistic inputs—including edge cases and input that is purposely incorrect or malicious in nature. And that’s why it’s often better to have another person write your tests, since they will be able to look at your code in a more detached way.

What about code coverage?

It should be obvious by now that complete code coverage is not a useful goal of unit testing. Instead, it should be a consequence of a good testing strategy.

Again, the difference is substantial. If you’re trying to achieve code coverage for the sake of it, anything less than 100 percent means that you need to write more tests.

If, on the other hand, 100 percent should be the consequence of a good testing strategy, situations where it is not achieved could simply indicate that you’ve got dead code branches that need to be pruned. Writing more tests then becomes the next step in the process.

Testing is a continuous process

All these things will help you get started with unit testing, but writing good, meaningful tests remains a hard thing to do.

This doesn’t mean that you should be discouraged, or that you should give up. Just think about testing as a process of continuous improvement. An imperfect test is better than no test at all—as long as you understand the limitations of your testing strategy and strive to make it better over time.

Some offbeat reading

You’ll find articles and books on how to write good unit tests all over the place. Most of them are bad, many are well-intentioned, and very few actually explain why you should write unit tests in a particular way.

Rather than give you yet another list of those, allow me to suggest three books that are not on unit tests at all, but, instead, on the psychology of design, which is, in turn, a great tool to help you understand how to write tests that are meaningful.

  • The Design of Design is a great read from Frederick Brooks (suggested to me by Joël Perras) on the process of designing software.

  • The Design of Everyday Things by Donald Norman (one half of Nielsen Norman) is an excellent exposition on the psychology behind design.

Both these books should help you understand what to test for in relation to how a software application works. Rather than focusing on the mechanics of your code, building tests around its intended functional specs will yield much better results (and help your sanity).

Finally, you may want to read Apollo by Charles Murray and Catherine Bly Cox. This book has little in the way of technical content, but shows how the Apollo program was almost destroyed by an insistence on disconnecting testing from development, until George Mueller told engineers to suck it up and test the whole thing as one unit.

  1. Note that this doesn’t include making old code do new things–that still falls under refactoring.
  2. Or when you push to the remote if you’re using a DVCS

⇥ Tunesque: better search for the iTunes Store

September 5, 2011
No comments
 
⇥ Permalink

Yes, I am still alive—it’s just been a really busy couple of months and I haven’t had a chance to update this blog…

…nor am I really going to today. It is, after all, a holiday.

I did, however, want to post about Tunesque, a small app for OS X Lion that I just released last week.

Tunesque is a replacement search for the iTunes Store. It sits quietly in the System Menu until called upon to perform a search against all of iTunes’s categories, including iOS and OS X apps.

I built this originally because I can’t stand searching the Store using the iTunes or App Store apps, but it seemed like a good enough utility that I should share it with everybody else. It’s completely free, although I do use affiliate links to make a little off the backend.

⇥ IP lawsuits and you: a short guide to preserving your sanity when you’re the small guy

While researching a story about the Lodsys affair, I came across an unusually high number of gratuitous legal opinions from people who have absolutely no idea what they’re talking about. Worse, the advice from people who should know what they’re talking about is even worse.

Being the slightly unbalanced person that I am, I feel compelled to point out a few things.

Lawsuits and you: don’t be the small guy

The main reason why I’m writing this is that I was, once, the target of a lawsuit myself. I’m not talking here about legal threats, nasty letters, or the likes; I speak of a full-fledged lawsuit brought against a small company of which I was a director by a much larger opponent with deep pockets and a veritable army of lawyers at their disposal—a lawsuit that ultimately took nearly ten years, thousands of hours of unpaid work, and several millions of dollars to resolve.

Unless you have plenty of disposal income, a lawsuit is an incredibly disruptive event in your life. If you’re the small guy, personal and financial ruin stares you blankly in the face, and you can’t afford to blink.

The psychological impact can be crushing and, inevitably, almost everyone around you only makes things worse and worse.

The first thing one learns is that the legal process has absolutely no connection with reality or common sense. Unless the relative power of the opponents is balanced, there is no such thing as a quick resolution, and the courts, which must maintain the appearance of impartiality, will bend over backwards to allow all the parties the most latitude possible. When you’re up against a corporation with much greater resources than yours, they will (and, in all fairness, they must) abuse that privilege to their largest possible advantage.

The judicial process, in other words, is a harsh mistress whose primary objective is its own self-preservation. Justice in the moral and ethical sense of the word, which is what you’re after, is a much distant second goal.

Lawyers don’t throw exceptions

Believe it or not, this is a very difficult concept for a lawyer to explain. At a moment where your life has been turned upside down and all you want is a little certainty, they can offer none.

To the novice, this is very frustrating. On one hand, you are thrust into an abstruse, complex, expensive, and drawn out process that makes absolutely no sense. On the other, the person you have chosen as a guide in this new world seems to be unable to offer any certainty or explain things in clear, unequivocal terms.

I used to think that, as part of the ritual of being called to the bar, lawyers have to undergo a surgical procedure in which the structure of their brain is physically altered in such a way that makes it impossible for them to use the words “yes” and “no.” It’s systemic—ask a lawyer if they like orange juice, and they’ll launch into a half hour explanation of how oranges are picked, grown, and squeezed—but you won’t get a yes or no out of them.

Then, one day, a lawyer did give me an unequivocal answer—one that seemed sensible, logical, and entirely applicable to our case. So, we followed his advice, and it nearly cost us everything.

It eventually dawned on me that the reason why lawyers seem to live in a perpetual state of indecision is that all they can offer is an opinion. The law is not an exact science, but rather the sum of a myriad contrasting ideas put forward by a myriad contrasting people. Like an old MS-DOS API call, any given set of inputs can result in a completely different output every time.

Armchair lawyering doesn’t help

When you get sued, everybody has an opinion. And, if the lawyers can’t get it right, I’ll let you imagine how valuable the judgment of those who don’t practice law can be.

The worst people are those who make it about right and wrong. The legal system doesn’t care about right or wrong—it cares about legal and illegal, a very different (and somewhat fluid) concept.

Here’s a piece of advice if someone you know gets sued: shut up. You don’t know what you’re talking about, and your armchair lawyering only helps increasing the confusion and anxiety of a person who is already anxious and confused enough.

The same goes for those people on the Internet who can’t help but rally against the injustice of a large company suing a small one into oblivion. I can only hope that a special place in hell is reserved for the coffee-shop activists who keep blaring left and right how Lodsys’s management is nothing but a band of scumbags, how their patents are unfair and just obvious, and so on.

If you want to help those who are hit by these legal threats, let the lawyers do their job, and be a human being. Offer constructive moral support, which they need, and spare them your legal opinions. Being on the other side of these conversations, every time someone offers you an uninformed legal opinion, you only feel incompetent and futile; after all, if everything your opponent does is so unfair and obviously wrong, why do you have to spend hundreds of thousands of dollars and risk everything you own fighting it over long periods of time?

And the worst: Internet lawyers

The absolute lowest common denominator in this entire equation, however, are what I jokingly refer to as “Internet lawyers,” people who profess themselves knowledgeable of the law and dish out advice so bad that it makes me want to cry.

As part of my research, I interviewed several professional lawyers who are not involved in the Lodsys case, and they all gave me exactly the kind of good advice I would expect from a competent practitioner: they laid out all the possible options and then proceeded to illustrate the possible consequences, concluding with a catch-all reminder that, in the end, the entire legal process is highly randomized—a bit like reading a multiple-ending novel written by a slightly schizophrenic author. I consider it a minor privilege, if the story gets published, that I have been able to quote these people and provide some useful information to my readers.

But for every one of these honest people who take the time to give you good counsel, there are ten who are too busy listening to the sound of their own voice and give you absolutely disastrous advice.

The typical example? Those who tell you that you should incorporate or form an LLC to protect yourself from a lawsuit.

That is horrible advice. Incorporation doesn’t protect you or your assets unless you are willing to defend them.

So, when someone tells you to “form an LLC because you can’t be sued,” don’t you believe them for one minute. You can, and you will be sued, and having an LLC won’t shield you from the fact that you still have to pay a lawyer to defend yourself when you get sued, regardless of whether the lawsuit has merit or not.

This is particularly true if you’re a small timer, because there is a fundamental disconnect between your approach to legal matters and the requirements connected with running a corporation, which is a somewhat complex process best handled by a lawyer. In the course of normal business, you will try (justifiably) to limit your legal expenses, and inevitably make a mistake or ten in the way your corporate legal affairs are managed by cutting corners.

If a larger corporation ever decides to sue you, the first thing their lawyer is going to do is subpoena and pour over every single scrap of paper your corporation has ever produced—or has failed to produce— and try to use every little inconsistency or omission as an excuse to pierce the corporate veil and come after you personally.

Now, my experience has been that these tactics rarely work, because the judge will keep your relative sophistications and means in consideration when deciding whether a particular mistake in your corporate conduct should be sanctioned. A one-person corporation that fails to conduct regular board meetings is not, as far as I’ve been able to see, held to the same standards of a multi-million dollar company that does the same.

That, however, won’t save you from wasting a metric truckload of money in making your case and defending against these accusations—and remember, you can’t win a lawsuit if you run out of money before a verdict, which is exactly what oppsing counsel will bank on.

My advice

Am I, then, advocating that incorporation is pointless?

No. I am advocating that it should be part of a broader legal strategy—one that you cannot afford to ignore until the day when Fedex shows up at your door with a nastygram.

And so, I will hand out the kind of advice I wish I had been given when I started my first business: hire a lawyer and establish a mutually-respectful working relationship with them now.

You don’t have to like them, but you do have to respect the fact that what they do is important to the long-term success of your business, even if they don’t contribute directly to your bottom line.

⇥ Creepy Apple is creepy

Ah, analysts. Where would the world be without them?

My current favourite is Alex Levinson, a mobile phone forensic expert who comments on the recent discovery that the iPhone tracks everywhere its users go.

Levinson makes a couple of reasonable points, like the fact that there is nothing new about this revelation, and that he has done extensive research on the subject well before yesterday’s sudden explosion of interest in the story.

It’s his analysis, however, that is all over the place. Allow me to illustrate:

Apple is not collecting this data.

Really? Is it materializing out of thin air? Is the CIA planting it on my computer?

Apple wrote iOS, and iOS is gathering the data without the consent of its users. Transitivity applies, which makes Apple responsible for the data being collected.

Perhaps Levinson means to say that Apple is not receiving a copy of the data, which is certainly lower on the creep scale than a database of every location you’ve visited being sent to Cupertino for, er, “service enhancement” reasons.

But that’s no different than what everybody else has been saying, nor does it make this whole affair any less creepy.

And speaking of creepy, here’s his explanation of why the data collection isn’t just not a big deal—it’s actually necessary:

That raises the question – how is this data used? It’s used all the time by software running on the phone. Built-In applications such as Maps and Camera use this geolocational data to operate. Apple provides an API for access to location awareness called Core Location.

My dear Alex, let me tell you—if there’s a way to find out where you’ve been with Core Location, I haven’t figured it out yet. Nor, I suspect, has any other developer who doesn’t work for Apple itself.

That’s because Core Location (which, by the way, is a great API) tells you where your phone is now, not where it’s been. It can advise of changes in your position as they occur, but it is a realtime framework—if you want to build a database of past location, you have to built it yourself. And your users must launch the app. And they must expressly authorize the app to use Core Location.

By contrast, it seems that the information in question is being surreptitiously collected, saved and archived without anyone’s permission.

But it gets worse. If the information were just collected and kept on the device, things would be slightly less frightening—iOS has a fairly strong sandbox model, which makes accessing files outside of an app’s directory nearly impossible. Plus, don’t forget that any app you put on your phone has to be vetted by the Mothership itself. Therefore, the data would be relatively safe from prying eyes.

Once this file makes its way onto your computer, however, all bets are off. Unless you encrypt your backups—which, I’m guessing, most people don’t—anyone who convinces you to run their app on your Mac has full access to every location you’ve been since you’ve owned a 3G device that runs iOS 4.0 or higher.

There is, as I see it, very little mitigation at play here. That’s not to say that there isn’t a good reason why this information is collected. Rather, none of the reasons given so far by analysts fits the problem well, and the only people who know exactly what the right answer is—the fine folks from Cupertino—are keeping mum.