Good engineering design decisions for startup companies
May 14, 2013
Having worked at the same startup for several years, joining at the beginning of the product and watching it evolve, I (hopefully) can provide some sage advice to new startups about key engineering design decisions. This will be especially useful for companies targeting the enterprise space, as they will very likely be forced to make difficult changes in order to gain customers. However, consumer facing companies may gain some wisdom from this as well.
As an an engineer, many times I wanted to say “NO!” to a customer requirement that I viewed as too ridiculous, too much work, or useless. However, if the sale will generate enough revenue, the change will happen. With a little foresight, you can plan ahead without adding too much work to your development lifecycle.
Companies who use your product won’t want your name splashed all over it. Very often they don’t want your company visible at all. The best way to solve this is to put all your graphics and color scheming in an easy to modify config file (YAML, a CSS file, whatever). This will make it ridiculously simple to rebrand on a moment’s notice, and slipstream into an automated build system like Jenkins.
Even better- if your sales team is walking into a meeting with MultiNational XYZ, they’ll have a leg up on the competition with their entire demo painted with a “MultiNational XYZ Rules!” graphics branding. This is such a simple, effective technique that it’s a shame that more engineering departments don’t make this a key design decision.
Start it from the beginning for all applications, be they web / desktop / mobile, and it will pay dividends quickly.
Plan for On Premises Deployment - EVEN IF YOU’RE CLOUD BASED!
You’re starting a new cloud based company and are envisioning million$ pouring in when companies start consuming your services. SCORE- Your sales team just nailed a preliminary meeting with a CTO, and an enormous organization wants to partner with you and help sell your product. Only problem- they want to host it themselves.
This isn’t as rare as you think, especially in the enterprise world- every company has their own security team, with its own (often ridiculous) requirements, and sometimes they need to host it themselves. Or maybe they want to resell it on their own servers. Or maybe you’re trying to sell to the government- they are definitely going to want to host it themselves, behind a closed firewall.
Luckily, this isn’t that hard. From the beginning, have a mechanism for building a server from scratch. It can be as simple as a bash script, or maybe a puppet manifest, or just have a virtual machine image. Whenever you make a change to the server’s architecture, maybe a new package, or a config change, or anything- you update the script / manifest / VM / etc. Now, not only do you have a simple way to ramp up servers, but you can also use your factory to produce working servers for customers. Bonus points if developers can use the same method for creating a local development server.
Maintain a Central Configuration File
As a startup, you will be tempted to take shortcuts- hard-coding in values, referencing a file by absolute path, etc. This is a horrible mistake! From the start, make a configuration file (YAML would be a good choice!) and put any values that are likely to change per environment, server, customer, etc. into it. Using a password salt? Put the salt in the config. You have a shared directory between your various subsystems? Put the absolute path to the directory in the config. You want to use an HTTP accessible third party API? Put the hostname and authentication parameters into the config and reference it EVERYWHERE. Why? Because now you can easily change these parameters and have them instantly reflected in the code. You can also easily customize servers, on premises deployments, etc. etc. etc.
This simple method will greatly increase code maintainability and reduce millions of headaches later… maybe even billions.
Choose Lightweight Frameworks
This may be personal preference, but after observing various components of my company’s product, the best pieces were built upon lightweight, extensible frameworks. A startup may be tempted to use a framework that claims to do everything. “It takes care of authentication! It’s secure! It’s fast! It comes with a million features, so we won’t have to do anything! Money, please!”
Unfortunately, it becomes very apparent that you made a huge mistake. You can’t predict what components of your system will need to be optimized, changed, improved, etc. as you start getting customers and the requirements start to get out of control. When you use a one-size-fits-all framework, you start having problems scaling. You can’t add a new feature without ripping out the one they provided. You start fighting the framework.
Better to choose a lightweight framework that is (at least) somewhat mature, has an easy way to add custom plugins, and has an active open source community that is fixing it and adding features. Now, you’ll have a simple library that you can dig into and comprehend, is much faster, without bloat, and can be extended if necessary.
Don’t Use Email Addresses for User Identification
You’ll be tempted to overload a user’s email address for authentication and communication. DON’T. Should you allow email addresses as a means to authenticate? Sure, if you want. But under the hood, don’t double the user ID field and the email address field as the same thing. Why? You will have customers that won’t want an email address as the method of authentication. You will very likely have customers who don’t want to use email addresses at all.
Example- your company sells Software as a Service (SaaS) in the cloud. All your customers have email addresses. Then, you get a customer order that wants to use your product in a way you didn’t intend at all. They want their users to be unmanned computer terminals… or maybe robots… who knows! The point is, they have an algorithm to assign ID’s to these dummy terminals, and none of them have email addresses because they have no use for email…they aren’t people! (Or more likely, they simply don’t want your database to have 20,000 of their employees’ email addresses)
By decoupling email from authentication, you plan ahead for this common scenario. However, if you ignore this, changing your architecture later will be an enormous undertaking that requires rewriting various core aspects of your system. Make your user accounts flexible!
Here is a situation where being lazy will actually benefit you. Some engineers want to internationalize (translate user facing strings) from the get-go. Great idea… except that the odds of you needing it to land initial customers is zero, and 99% of the time it’s trivial to go through code later and tokenize strings that need translation.
Bottom line- wait until your product is a hit before investing engineering resources in translating your product. 9/10 startups will fail anyway, so don’t even bother.
These are some easy decisions you can make to plan for the future. Doing them will also keep you from pulling out your hair, so give it some thought!