Made Simple
by Amarin Phaosawasdi
Monday, May 13, 2013
The startup secret sauce
Through some reading, I found that profitable startups
1) make sure there's a market
2) solve a problem for the market with a solution
3) make the market know about their solution
4) make money from selling their solution
5) tweak the solution continuously
To acheive those things, you need a couple of basic skills: market research, building stuff, advertising, pricing, and risk taking.
There's only one rule you need to know for each of these skills.
The golden rule for market research: know your customers.
The golden rule for building stuff: use the right tools.
The golden rule for advertising: customers care about themselves.
The golden rule for pricing: price based on value that customers receive.
The golden rule for risk taking: validate ideas inexpensively.
Done. Follow these rules and you have a profitable startup.
So why am I not rich?
Because I don't go out there and do it. I've never run a startup before, and I'm writing as if I know everything. I just read stuff and bluff. I'm a phony.
It's easy to know how to do things, but it's a different story to actually do them. Skilled musicians don't read books, they practice.
There's no "secret sauce" in creating a profitable business. It just requires a lot of practice.
I think spending all day reading books and blogs on starting a business is a waste of time.
Yet so many people spend all day reading books and blogs on starting a business.
If there's one thing I've learned from reading, it's to stop reading too much and just do it. Read when you're in need of references or best practices, but only when you're actually about to or after you do it.
P.S. Just to be clear, when I say read stuff, I'm talking about stuff related to starting a business. Of course, I would still read other stuff for entertainment, inspiration, etc.
Friday, November 23, 2012
All Productivity Systems Are The Same
I've been reading here and there about productivity both on the web and on paper. A lot of info out there tend to either:
Maybe I haven't looked around enough, but that's kind of the pattern I noticed.
The way I see it, at the end, it all boils down to 4 things:
Several months ago, I mentioned what agile was. Now I'm going to take a step back and look at the more generic view of productivity and how several development techniques, as well as day-to-day examples, fall into this framework.
(1) Increasing Time
A person given 2 hours will be able to watch more episodes of Family Guy than a person given 20 minutes. The example is contrived but I hope you wouldn't argue that more time means a higher probability of getting more work done.
The main things people do to increase available time is automating or delegating tasks and reducing "waste".
(2) Doing what's important
There's not much point in working on something that gives little or no value.
The main things people do is prioritizing. Now prioritizing isn't the easiest thing to do. Priorities shift a lot and sometimes only somebody else can answer what is important. But there are general fixes. Priority shifts can be fixed by frequent reflection. In the software world, we call this tight feedback loops. As for unknown priorities, you just ask who knows.
Examples of prioritizing:
(3) Doing it efficiently
Once you know what to do, you learn how to do it efficiently.
The main things people do here is improving skills, leveraging tools, and being healthy.
(4) Doing it sustainably
All of the above can be accomplished but for how long? You need to keep yourself motivated.
This has more science to it than I originally thought. It turns out that our brains are programmed to work in a certain way. There's the emotion part and the logical part. The emotion part favors immediate and positive results. It doesn't care for long term goals. And most importantly in the long run, the emotion part almost always wins. That's why we hit snooze when we know we should wake up and work. And that's why we can force ourselves to wake up early but not for too long.
If you are a human, your brain works this way. No exception (unless you're not a human). So take advantage of how your brain works.
An effective way of keeping yourself motivated is to keep enticing yourself with small wins. They are easy to achieve, and you feel good about it right away. A lot of small wins snowball into big wins and that keeps you motivated further.
Examples of motivation techniques:
How I got started
I'm not a productivity expert. This is just information I deduced from reading and experience. But so far, what has worked for me is asking myself these questions everyday and tweak my process based on what works well and what doesn't.
The most important thing was I started small. I listed something that I could finish in 10 minutes and I got it done. The next day, I would add a little more. I accomplished something small and let it snowball.
It all started from there. And now I've been able to manage much more than before. A LOT more than before.
Maybe it will work for you too.
- list very specific things to increase productivity (e.g. don't check your email every 10 seconds)
- list less specific things to increase productivity (e.g. find a time you can focus and work during that time)
Maybe I haven't looked around enough, but that's kind of the pattern I noticed.
The way I see it, at the end, it all boils down to 4 things:
- increase available time
- do what's important
- do it efficiently
- do it sustainably
Several months ago, I mentioned what agile was. Now I'm going to take a step back and look at the more generic view of productivity and how several development techniques, as well as day-to-day examples, fall into this framework.
(1) Increasing Time
A person given 2 hours will be able to watch more episodes of Family Guy than a person given 20 minutes. The example is contrived but I hope you wouldn't argue that more time means a higher probability of getting more work done.
The main things people do to increase available time is automating or delegating tasks and reducing "waste".
- Automated testing saves hours of manual testing.
- Delegating tasks to developers frees up time for the lead developer to work on important issues.
- Having an assistant reduces time needed to keep track of things and context switching.
- Disconnecting cable TV saves many hours a day.
(2) Doing what's important
There's not much point in working on something that gives little or no value.
The main things people do is prioritizing. Now prioritizing isn't the easiest thing to do. Priorities shift a lot and sometimes only somebody else can answer what is important. But there are general fixes. Priority shifts can be fixed by frequent reflection. In the software world, we call this tight feedback loops. As for unknown priorities, you just ask who knows.
Examples of prioritizing:
- Asking clients what's the most important feature they want when they can't have all.
- Finishing presentation slide contents before making them look beautiful.
- Fixing bugs found in unit tests instead of waiting for it to reach production.
- Have daily meetings and re-prioritize issues if something comes up.
(3) Doing it efficiently
Once you know what to do, you learn how to do it efficiently.
The main things people do here is improving skills, leveraging tools, and being healthy.
- Use IDEs for code editing.
- Learn to factor code well.
- Learn to set your favorite channel instead of switching channels one by one.
- Learn how to use email templates.
- Have enough sleep and eat good breakfast. Vitamins also stimulate the brain.
(4) Doing it sustainably
All of the above can be accomplished but for how long? You need to keep yourself motivated.
This has more science to it than I originally thought. It turns out that our brains are programmed to work in a certain way. There's the emotion part and the logical part. The emotion part favors immediate and positive results. It doesn't care for long term goals. And most importantly in the long run, the emotion part almost always wins. That's why we hit snooze when we know we should wake up and work. And that's why we can force ourselves to wake up early but not for too long.
If you are a human, your brain works this way. No exception (unless you're not a human). So take advantage of how your brain works.
An effective way of keeping yourself motivated is to keep enticing yourself with small wins. They are easy to achieve, and you feel good about it right away. A lot of small wins snowball into big wins and that keeps you motivated further.
Examples of motivation techniques:
- Daily to-do lists instead of monthly ones.
- Working on small and easy tasks when stuck on a more complex one.
- Start working out 5 minutes a day instead of an hour a week.
How I got started
I'm not a productivity expert. This is just information I deduced from reading and experience. But so far, what has worked for me is asking myself these questions everyday and tweak my process based on what works well and what doesn't.
The most important thing was I started small. I listed something that I could finish in 10 minutes and I got it done. The next day, I would add a little more. I accomplished something small and let it snowball.
It all started from there. And now I've been able to manage much more than before. A LOT more than before.
Maybe it will work for you too.
Tuesday, November 13, 2012
Hack the scope, Engineer the solution
Lately, it seems like startups have become the center of attention. Coworking spaces and tech-meetups have sprung up everywhere. The term "hack" which used to have a negative connotation, is now viewed in more positive light. And given the agile and lean movement, it appears to me that hacking things up sounds like something cool.
Before I get to my point, it's worth talking about two great companies with different principles.
After some reading and talking to people, my understanding is that Facebook has the "hacker culture", where people try to make things happen as quickly as possible, test it out, and fail fast if it doesn't work. I think video on Facebook was hacked in one day or so.
On the other hand, Google "engineers" software. If you don't know Jeff Dean, know him a little bit. The reason I brought up this guy is to give you a peek into the amount of science that goes behind building software at Google.
This is pure speculation. What I think about the two companies is possibly inaccurate, but that doesn't change what I'm trying to get at. I wanted to talk about hacking versus engineering.
Given these definitions:
- hack = come up with something quickly that works
- engineer = create something based on well-thought and sound principles
When you code, how often do you hack and how often do you engineer?
1) always hack
2) try to engineer, but hack when there are time constraints
3) always engineer
Test-driven development has made (1) a viable solution. We can come up with something quickly, and if something needs changing in the future, we have test cases to prevent regressions. I think a lot of startups go with (1) just to validate ideas or create demos for investors.
In established companies, I would think (2) is what a lot of people do. I do it too. During slow days, I have all the time to think very carefully about the design of the software I'm writing. But when there are tight deadlines, I tend to write something that works, and add a TODO comment to come back and finish it later (if I don't forget).
I think governments and financial institutions do (3).
Although I do (2) a lot, I'm not really happy with it, because most of the time, there are time constrains. I feel bad when I have code that works but could have been written better if there was a little more time. Well, everybody would write better code given more time, but I recently came to a realization that we can still write good code even with we have the same amount of time.
It is possible to always engineer software. What we need to do is hack the scope instead. So I'll add (4) hack the scope and engineer the solution.
So what does this mean? Let me give an example.
Suppose I need to write a noob-detector. It's a device whose alarm goes off when noobs are around. I have this HUGE third-party library that claims that it implements the best noob-detecting algorithm in the world. However, its API is so complicated that it takes months to learn how to use it properly, and I need it finished this weekend.
If I went the (2) route, I would randomly tinker with the API until it kind of does what I wanted it to do. At first glance, it seems to work. It detects noobs when I test it. However, I might not be aware that the way I used the library only detects asian noobs. (By the way, asian noobs are hard to find.)
But if I went the (4) route, I would see that the scope is too large. I hack the scope instead. There's another library that's fairly simple to use, but uses an inefficient algorithm. Yet, its slowness is tolerable. I loosen the requirement that the software needs to run with the state-of-art algorithm and use this library. With this library, I can write beautiful code that does the right thing. At the end, this version is less buggy, and correct according to the new requirement.
In a sense, I am tackling the problem as early as possible to save time, and this goes along well with productivity principles.
Sure it sounds like common sense, but even after writing code for so many years, I still fall into trap (2) all the time. I'm getting better at it though. Hope this helps others as well.
Saturday, July 21, 2012
Multi-Threaded Development Checklist
I happened to notice a recurring pattern that keeps happening when developing multi-threaded applications.
Even locking alone, whose solution to avoid deadlocks is fairly simple -- just order the locks -- it turns out that implementing lock ordering is pretty hard to get right and there are many pitfalls to it.
So I've compiled a "checklist" that would hopefully help reduce some frustration when writing multi-threaded applications. These are more like "what worked for me" and not necessarily rules to follow. Also I'm not an expert, so keep that in mind!
Here goes, the "Multi-threaded-development-checklist-that-works-for-Um" checklist.
Are you locking on an arbitrarily long event?
Are you writing to disk/sending network packets/invoking user-supplied callbacks during locks? If you do, whoever is waiting for that lock, might be waiting for an arbitrarily long time as well.
Is your application layered?
If you're using fine-grained locks, layer your application so the locks have levels as well. It's easier to reason about lock ordering if your classes are well-layered. For example, if you have class Parent which holds a collection of class Child. Remembering the lock order Parent -> Child is intuitive.
Are layers in the same level interacting?
From the example above, Child objects should not interact with each other. If they need to share some information, do it in the Parent class. Otherwise, finding the right lock order would be hard.
Do lower layers release their locks before calling upper layers?
It's basically a violation of the lock ordering if Child locks before calling a method in Parent that locks the parent.
Are you aware of any locking inside your third-party libraries?
If you're using a third party library that says it's thread-safe, then that library is probably using synchronization primitives as well. In our example, the layering could be like this: Parent -> Child -> third-party object. What if the third-party can invoke some method Child::Callback()? Then that means there might be a lock order violation, e.g. the third party library holds a lock before invoking Child::Callback() which locks the child.
Is anything blocking forever?
If you have condition variables, do all code paths notify it at some point? If you're blocking to wait for an event (for example, via epoll), do you have a way to preempt it for have a timeout on it?
Is your application modifying a snapshot when it's suppose to modify shared data (or vice-versa)?
This bit us pretty hard recently at work, and we spent a couple of hours trying to find the cause. Suppose Parent contains a collection of Child. If for example, you wanted to remove a Child from the collection, but you only removed it from a copy of the collection. Then the real shared data won't be modified at all, and all weirdness follows. So make sure the data you're acting on is actually the data you want to act on.
That's all I have for now.
- application is single threaded
- throughput and latency is unacceptable
- make application multi-threaded with coarse-grained synchronization
- throughput and latency still unacceptable
- introduce finer-grained synchronization
- deadlock
- fix deadlock
Even locking alone, whose solution to avoid deadlocks is fairly simple -- just order the locks -- it turns out that implementing lock ordering is pretty hard to get right and there are many pitfalls to it.
So I've compiled a "checklist" that would hopefully help reduce some frustration when writing multi-threaded applications. These are more like "what worked for me" and not necessarily rules to follow. Also I'm not an expert, so keep that in mind!
Here goes, the "Multi-threaded-development-checklist-that-works-for-Um" checklist.
Are you locking on an arbitrarily long event?
Are you writing to disk/sending network packets/invoking user-supplied callbacks during locks? If you do, whoever is waiting for that lock, might be waiting for an arbitrarily long time as well.
Is your application layered?
If you're using fine-grained locks, layer your application so the locks have levels as well. It's easier to reason about lock ordering if your classes are well-layered. For example, if you have class Parent which holds a collection of class Child. Remembering the lock order Parent -> Child is intuitive.
Are layers in the same level interacting?
From the example above, Child objects should not interact with each other. If they need to share some information, do it in the Parent class. Otherwise, finding the right lock order would be hard.
Do lower layers release their locks before calling upper layers?
It's basically a violation of the lock ordering if Child locks before calling a method in Parent that locks the parent.
Are you aware of any locking inside your third-party libraries?
If you're using a third party library that says it's thread-safe, then that library is probably using synchronization primitives as well. In our example, the layering could be like this: Parent -> Child -> third-party object. What if the third-party can invoke some method Child::Callback()? Then that means there might be a lock order violation, e.g. the third party library holds a lock before invoking Child::Callback() which locks the child.
Is anything blocking forever?
If you have condition variables, do all code paths notify it at some point? If you're blocking to wait for an event (for example, via epoll), do you have a way to preempt it for have a timeout on it?
Is your application modifying a snapshot when it's suppose to modify shared data (or vice-versa)?
This bit us pretty hard recently at work, and we spent a couple of hours trying to find the cause. Suppose Parent contains a collection of Child. If for example, you wanted to remove a Child from the collection, but you only removed it from a copy of the collection. Then the real shared data won't be modified at all, and all weirdness follows. So make sure the data you're acting on is actually the data you want to act on.
That's all I have for now.
Thursday, May 31, 2012
Life at a startup
Hurray! I've been working at a tech startup for exactly a year already. This is one of the best things that ever happened in my life. Let’s just say it’s a super awesome and fun experience.
This post will basically be a condensed note to myself in the future, but it might benefit you as well if you're interested in starting your own company. (Or if you already have a company.)
The topics are pretty random and are not ordered in anyway.
I personally don't think opening an online web design firm or selling stuff online is essentially a startup. You might, but that's your opinion.
I think startups are companies that try to solve problems for the mass. Facebook for example, changed the way people interact. I don’t have the energy to call everyone of my friends in Thailand everyday, so I learn about them through Facebook. Facebook solved one of my problems.
If you have a good vision, then you'll be rewarded when you see your product help people.
My company has about 7 roles. At the beginning, the founder had to do all of them. As a result, he was too overwhelmed. That's when the hiring happened.
In established companies, you hire on a continuous basis because people leave all the time. However, in early-stage startups, you should hire from needs. If you spend too much time on customer support, you don't have time to improve your product. But if you don't answer customer calls, you'll end up losing business. You need a balance. If you're out of balance, it's probably time to hire.
Before I left my old job, I never thought work environment would be such a big deal, but it actually is. A big part of why I left my old job was that I was in a cube in a room with no windows and I developed wrist, back, and neck pain from sitting in that cube.
You don’t have to have a fancy office (and you probably won't have money to pay for an interior designer anyway), but the better-looking office will attract developers.
My advice is at least make the office look nice -- nice being if you invited your mom to the office, she wouldn’t complain.
Here are some concrete things that are good to have:
You certainly do, but you don't have to hire one. You only have to know where the money comes and goes so you know if you’re going out of business or not. Oh, and you need to pay tax correctly too. In my company, this is managed by another developer. She said she needed about three courses from a local community college to get from zero to workable knowledge. She spends one day each month for accounting.
It's good to have if you can afford one, but probably not. Server/network setup (including contacting the cable company) are skills that programmers can learn easily. It's just not fun when you do it a lot. I remember seeing the founder driving to Chicago (2 hours away) at 8pm to switch a hard disk in the data center.
One thing to note is that when you're small, there's not much security concerns to worry about. But once you're big enough to become a target of hackers (the bad type), you might need a network admin, or more of a network security expert.
You can probably do it by yourself for the first 10 customers, but if you want to scale, you need people to help. I'm stereotyping but most software developers don't have a gift for marketing.
At the first stage of your startup, try to get customers in the most straightforward way. It’s like hacking up a prototype. It doesn’t need to scale yet.
This includes cold calling as much target audience as you can. Ask your mom and friends to sign up and spread the word. Go to conferences and make direct connections. Ads don’t make sense yet at this stage. If you have enough income, hire a sales rep to help with this.
Again, you won’t need any until you get overwhelmed by calls. We tried outsourcing, but didn’t really work out. We lost the opportunity to know our customers better and improve our product.
So I think at an early stage, when you don’t have a lot of numbers to crunch on, the best source of customer feedback is support calls, so you want somebody inhouse.
A euphemism for “errand runner”. You as the company owner have to do everything from basic plumbing, to lighting installation, to making sure there are stationary and enough napkins. This is not too bad, because these things don’t happen too often. It’s just a little more work than taking care of your own two bedroom apartment with 5 other roommates.
Every role is important, but since I like to self-promote what I do, I personally feel that a company needs great software developers.
You’ll probably be looking for generalists who are not tied to a specific set of technologies, and don’t mind working on anything (including tedious stuff). You want somebody who can tolerate imperfect code to get things done, and at the same time, feel bad about imperfect code because it's not beautiful.
Many startups can afford to buy their employees all the meals they want, some companies just can’t. But that doesn’t mean you have to be cheap. Once in a while, you can take your employees out. My company buys us lunch once a week. That’s a good perk given the size of our company. As a general rule, be generous with perks if it improves work efficiency and teamwork, and as long as it’s reasonable.
Of course you don’t have 250k to pay your employees, but do research to find what’s a competitive market pay in your area and at least match that. You should never lose a good employee because of your pay was too low. In other words, if you hired the right person, they'll likely work for the job not as much for the pay, as long as the pay can maintain their lifestyle.
A reasonable way of thinking is: as long as you get the job done, it doesn’t really matter that much what your work hours are. If your employee needs to see the dentist or take his/her cat to the vet, by all means, be flexible and your employees will love the job.
Angel investors and venture capitals (VCs) are not the only sources of seed funding. If you start a business with a market that exists, you will get your first paying customers. You can use the revenue to bootstrap your business.
VCs have pros and cons. You are advised by very experienced people, so you have a higher rate of success. On the other hand, since VCs invested and have equity, you have to listen to them and sometimes do something you don’t entirely want to do.
One of the best things about startups is you have input on anything, be it the processes to use, the tools we use, the color of the lights, which soda to buy, everything.
I find it really rewarding when somebody as smart as my company leader asks input from me. If you’re the company leader, you should listen to your employees as much as you can.
This is one of the most important things about startups. Of course, you would need somebody with skills. But as importantly, you have to make sure everybody is a great fit culturally.
In startups, you can’t afford to hire the wrong person. Make sure that cultural fit is one of the highest priorities. When you don’t have 200 teams, you can’t avoid seeing the wrong person everyday.
When interviewing a potential coworker, include questions that will show their personalities. For example, try finding something the candidate totally disagrees and see his/her reaction to that. If the candidate uses strong words like “stupid” or “hate”, that’s a bad sign.
Most of the time, open source code is a great way to save cost. Try finding open source libraries as much as you can, but if buying software licenses will save you cost more than the time wasted finding the right open source software, by all means, spend your money on it.
You want to look for liberal licenses which don’t force you to release your source code. My favorites are BSD, MIT, and Apache licenses. I’ll blog about the differences one day.
And at some point, don’t forget to give back to society and open source what you can. Just be careful not to open source stuff that your competitors can use to kick you out of business.
There’s a lot of knowledge out there you can leverage. Having at least somebody with an MS or preferably higher in your team, who is used to reading research papers, will widen your point of views. We’ve applied solutions from at least 3 papers already in our system and have plans for future directions.
Not only research papers, but generally if you’re looking to solve hard problems, a lot of times when you include “site:edu” in your Google searches, you can find out how the academia solves it.
Even if you end up using nothing. Just reading for the sake of knowledge is fun enough (if you really enjoy what you do).
Don’t meet unless you have to. Multiple short meetings is better than one big meeting. Anything over 35 minutes might lose people’s attention.
I hope you find this post useful. Feel free to send me comments on what you agree or disagree. I’d love to hear from other people who work at startups too, especially learning what went well and what didn’t.
But anyway, happy one year (and 40000+ lines of code) anniversary to me! XD
This post will basically be a condensed note to myself in the future, but it might benefit you as well if you're interested in starting your own company. (Or if you already have a company.)
The topics are pretty random and are not ordered in anyway.
startup != consulting != ecommerce
I personally don't think opening an online web design firm or selling stuff online is essentially a startup. You might, but that's your opinion.
I think startups are companies that try to solve problems for the mass. Facebook for example, changed the way people interact. I don’t have the energy to call everyone of my friends in Thailand everyday, so I learn about them through Facebook. Facebook solved one of my problems.
If you have a good vision, then you'll be rewarded when you see your product help people.
When To Hire
My company has about 7 roles. At the beginning, the founder had to do all of them. As a result, he was too overwhelmed. That's when the hiring happened.
In established companies, you hire on a continuous basis because people leave all the time. However, in early-stage startups, you should hire from needs. If you spend too much time on customer support, you don't have time to improve your product. But if you don't answer customer calls, you'll end up losing business. You need a balance. If you're out of balance, it's probably time to hire.
Environment
Before I left my old job, I never thought work environment would be such a big deal, but it actually is. A big part of why I left my old job was that I was in a cube in a room with no windows and I developed wrist, back, and neck pain from sitting in that cube.
You don’t have to have a fancy office (and you probably won't have money to pay for an interior designer anyway), but the better-looking office will attract developers.
My advice is at least make the office look nice -- nice being if you invited your mom to the office, she wouldn’t complain.
Here are some concrete things that are good to have:
| computers that are fast enough | sufficient lighting | big tables | private rooms for meetings |
| air conditioning + heaters that work well | clean bathrooms | earphones | cupboards enough for everyone |
| chairs with neck rests | microwave(s) and fridge(s) | big windows | coffee/tea |
| water coolers or ice makers | coat hangers |
Do I need an accountant?
You certainly do, but you don't have to hire one. You only have to know where the money comes and goes so you know if you’re going out of business or not. Oh, and you need to pay tax correctly too. In my company, this is managed by another developer. She said she needed about three courses from a local community college to get from zero to workable knowledge. She spends one day each month for accounting.
Network Admin
It's good to have if you can afford one, but probably not. Server/network setup (including contacting the cable company) are skills that programmers can learn easily. It's just not fun when you do it a lot. I remember seeing the founder driving to Chicago (2 hours away) at 8pm to switch a hard disk in the data center.
One thing to note is that when you're small, there's not much security concerns to worry about. But once you're big enough to become a target of hackers (the bad type), you might need a network admin, or more of a network security expert.
How to grow? Do I need Sales / Marketing / Advertising?
You can probably do it by yourself for the first 10 customers, but if you want to scale, you need people to help. I'm stereotyping but most software developers don't have a gift for marketing.
At the first stage of your startup, try to get customers in the most straightforward way. It’s like hacking up a prototype. It doesn’t need to scale yet.
This includes cold calling as much target audience as you can. Ask your mom and friends to sign up and spread the word. Go to conferences and make direct connections. Ads don’t make sense yet at this stage. If you have enough income, hire a sales rep to help with this.
Customer Service
Again, you won’t need any until you get overwhelmed by calls. We tried outsourcing, but didn’t really work out. We lost the opportunity to know our customers better and improve our product.
So I think at an early stage, when you don’t have a lot of numbers to crunch on, the best source of customer feedback is support calls, so you want somebody inhouse.
Administrator (this is different than network admin)
A euphemism for “errand runner”. You as the company owner have to do everything from basic plumbing, to lighting installation, to making sure there are stationary and enough napkins. This is not too bad, because these things don’t happen too often. It’s just a little more work than taking care of your own two bedroom apartment with 5 other roommates.
Software Developers
Every role is important, but since I like to self-promote what I do, I personally feel that a company needs great software developers.
You’ll probably be looking for generalists who are not tied to a specific set of technologies, and don’t mind working on anything (including tedious stuff). You want somebody who can tolerate imperfect code to get things done, and at the same time, feel bad about imperfect code because it's not beautiful.
Perks
Many startups can afford to buy their employees all the meals they want, some companies just can’t. But that doesn’t mean you have to be cheap. Once in a while, you can take your employees out. My company buys us lunch once a week. That’s a good perk given the size of our company. As a general rule, be generous with perks if it improves work efficiency and teamwork, and as long as it’s reasonable.
Pay
Of course you don’t have 250k to pay your employees, but do research to find what’s a competitive market pay in your area and at least match that. You should never lose a good employee because of your pay was too low. In other words, if you hired the right person, they'll likely work for the job not as much for the pay, as long as the pay can maintain their lifestyle.
Flexible work hours
A reasonable way of thinking is: as long as you get the job done, it doesn’t really matter that much what your work hours are. If your employee needs to see the dentist or take his/her cat to the vet, by all means, be flexible and your employees will love the job.
Funding
Angel investors and venture capitals (VCs) are not the only sources of seed funding. If you start a business with a market that exists, you will get your first paying customers. You can use the revenue to bootstrap your business.
VCs have pros and cons. You are advised by very experienced people, so you have a higher rate of success. On the other hand, since VCs invested and have equity, you have to listen to them and sometimes do something you don’t entirely want to do.
Everybody is involved
One of the best things about startups is you have input on anything, be it the processes to use, the tools we use, the color of the lights, which soda to buy, everything.
I find it really rewarding when somebody as smart as my company leader asks input from me. If you’re the company leader, you should listen to your employees as much as you can.
Coworkers
This is one of the most important things about startups. Of course, you would need somebody with skills. But as importantly, you have to make sure everybody is a great fit culturally.
In startups, you can’t afford to hire the wrong person. Make sure that cultural fit is one of the highest priorities. When you don’t have 200 teams, you can’t avoid seeing the wrong person everyday.
When interviewing a potential coworker, include questions that will show their personalities. For example, try finding something the candidate totally disagrees and see his/her reaction to that. If the candidate uses strong words like “stupid” or “hate”, that’s a bad sign.
Use open source and open your source when you can
Most of the time, open source code is a great way to save cost. Try finding open source libraries as much as you can, but if buying software licenses will save you cost more than the time wasted finding the right open source software, by all means, spend your money on it.
You want to look for liberal licenses which don’t force you to release your source code. My favorites are BSD, MIT, and Apache licenses. I’ll blog about the differences one day.
And at some point, don’t forget to give back to society and open source what you can. Just be careful not to open source stuff that your competitors can use to kick you out of business.
Have a research mind
There’s a lot of knowledge out there you can leverage. Having at least somebody with an MS or preferably higher in your team, who is used to reading research papers, will widen your point of views. We’ve applied solutions from at least 3 papers already in our system and have plans for future directions.
Not only research papers, but generally if you’re looking to solve hard problems, a lot of times when you include “site:edu” in your Google searches, you can find out how the academia solves it.
Even if you end up using nothing. Just reading for the sake of knowledge is fun enough (if you really enjoy what you do).
Meetings
Don’t meet unless you have to. Multiple short meetings is better than one big meeting. Anything over 35 minutes might lose people’s attention.
The end
I hope you find this post useful. Feel free to send me comments on what you agree or disagree. I’d love to hear from other people who work at startups too, especially learning what went well and what didn’t.
But anyway, happy one year (and 40000+ lines of code) anniversary to me! XD
Monday, May 21, 2012
NoSQL vs SQL
I've been exposed to NoSQL for about a year now, and I think I am finally able to describe what it is to other people.
NoSQL is a marketing term, well-named to catch buzz, and ill-named to describe what it is.
It kind of implies that we should throw SQL away and move to this hip database. Before all the NoSQL fuss, the most popular databases were relational databases, which supported a language called SQL. The marketing idea was to say, we're the opposite team, so we're "NO SQL". I think it worked.
There are traits that relational databases vs NoSQL databases have. I think viewing them like this gives a better understanding of the differences.
At the end, a database is a system where you give it a question and it returns results. If you think of it as a map, you give it a key, and it returns a value.
A relational database's key is the primary key of the tables you specify.
For NoSQL databases, the key can be anything you want (including something like primary keys).
What people choose to use as a key depends on their design decisions. For example, Google's Bigtable specifies the key to be the row name, column name, and timestamp.
And you can see that nobody's stopping you from using relational databases to have a table whose primary keys are row name, column name and timestamp.
All relational databases I know of, support SQL and some language binding, so that's how you talk to the database.
For NoSQL databases, the API can be anything, but usually is some language binding or web service.
Note that nothing can stop you from supporting SQL in NoSQL databases. It just usually isn't supported by default by all NoSQL database.
Relational databases weren't designed from the beginning to be deployed in a distributed environment. They're usually on one computer as one process.
So if you want to support some data partitioning like,
But still, that means relational databases *can* scale with the help of application level code.
Many NoSQL databases were designed from the beginning to be distributed. This means, you get the partitioning above for free. This is why people say NoSQL databases scale better. It's because you don't need application code to scale.
Note that I said *many* NoSQL databases are distributed. A bunch of them aren't, but they're still called NoSQL because they have other NoSQL traits.
Relational databases need a schema and they strictly check that data conforms to that schema.
NoSQL databases might or might not have a schema, depending on the design. If you want a schema but the NoSQL database doesn't support it, then you need application level code to do it.
Relational databases have the ACID guarantee (you don't need to know what it is), but it means you can have transactions any way you like it. For example, your transaction could be modifying all the rows in the database in one shot. But note that whenever you make a relational database distributed though application code, you lose this guarantee just like NoSQL databases.
Distributed NoSQL databases normally have the BASE guarantee. Again you don't need to know the details what it is, but it means that if you have data across two machines, and you do a transaction on this data, then there might be a time lapse where the data in these two machines are not consistent. (They will eventually, but just not immediately.)
This relaxed guarantee is a tradeoff between performance and consistency. Technically, it's possible to have ACID guarantees for distributed transactions, but it doesn't perform well. On the other hand, you can have a pretty efficient distributed database if you relax this guarantee.
That said, if the transaction only involves data living on one machine in a distributed system, ACID can still be guaranteed. This also means that if the NoSQL database is a non-distributed one, then it can provide ACID guarantees easily, because data is on one machine.
So the guarantee boils down to this. If the data you're performing a transaction against is on the same machine, you can provide ACID. If the data is on different machines, but you need to perform a transaction, then there might be some inconsistencies for a short while if you want reasonable performance.
If you're deciding whether to use a relational database or NoSQL database, consider what traits do you want your database to have.
Any thing other than "yes" means you might need to write your own application level support.
As you can see with some amount of application level code, relational and NoSQL databases pretty much can support the same things.
The reason I see most people use NoSQL is for the non-strict schema and the scalability, which (1) requires a lot of work for application level code to handle, and (2) the current fashion for software is shipping fast (might need to change schema often) and scalable software.
Other things that might affect your decisions are: community support for the database, your boss says so, price, installation difficulty. These topics are pretty self-explanatory, so I didn't include them in this post.
I hope now you have a good answer when the next person asks you why you're using a NoSQL database.
NoSQL is a marketing term, well-named to catch buzz, and ill-named to describe what it is.
It kind of implies that we should throw SQL away and move to this hip database. Before all the NoSQL fuss, the most popular databases were relational databases, which supported a language called SQL. The marketing idea was to say, we're the opposite team, so we're "NO SQL". I think it worked.
The Traits
There are traits that relational databases vs NoSQL databases have. I think viewing them like this gives a better understanding of the differences.
How to Represent Data
At the end, a database is a system where you give it a question and it returns results. If you think of it as a map, you give it a key, and it returns a value.
A relational database's key is the primary key of the tables you specify.
For NoSQL databases, the key can be anything you want (including something like primary keys).
What people choose to use as a key depends on their design decisions. For example, Google's Bigtable specifies the key to be the row name, column name, and timestamp.
And you can see that nobody's stopping you from using relational databases to have a table whose primary keys are row name, column name and timestamp.
The API
All relational databases I know of, support SQL and some language binding, so that's how you talk to the database.
For NoSQL databases, the API can be anything, but usually is some language binding or web service.
Note that nothing can stop you from supporting SQL in NoSQL databases. It just usually isn't supported by default by all NoSQL database.
Scalability
Relational databases weren't designed from the beginning to be deployed in a distributed environment. They're usually on one computer as one process.
So if you want to support some data partitioning like,
- for row 1 to row 100, I want to contact the database on machine 1
- for row 101 to row 200, I want to contact the database on machine 2
- although they're two database processes running, we actually view it as one logical database,
But still, that means relational databases *can* scale with the help of application level code.
Many NoSQL databases were designed from the beginning to be distributed. This means, you get the partitioning above for free. This is why people say NoSQL databases scale better. It's because you don't need application code to scale.
Note that I said *many* NoSQL databases are distributed. A bunch of them aren't, but they're still called NoSQL because they have other NoSQL traits.
Schema
Relational databases need a schema and they strictly check that data conforms to that schema.
NoSQL databases might or might not have a schema, depending on the design. If you want a schema but the NoSQL database doesn't support it, then you need application level code to do it.
Transaction Guarantees
Relational databases have the ACID guarantee (you don't need to know what it is), but it means you can have transactions any way you like it. For example, your transaction could be modifying all the rows in the database in one shot. But note that whenever you make a relational database distributed though application code, you lose this guarantee just like NoSQL databases.
Distributed NoSQL databases normally have the BASE guarantee. Again you don't need to know the details what it is, but it means that if you have data across two machines, and you do a transaction on this data, then there might be a time lapse where the data in these two machines are not consistent. (They will eventually, but just not immediately.)
This relaxed guarantee is a tradeoff between performance and consistency. Technically, it's possible to have ACID guarantees for distributed transactions, but it doesn't perform well. On the other hand, you can have a pretty efficient distributed database if you relax this guarantee.
That said, if the transaction only involves data living on one machine in a distributed system, ACID can still be guaranteed. This also means that if the NoSQL database is a non-distributed one, then it can provide ACID guarantees easily, because data is on one machine.
So the guarantee boils down to this. If the data you're performing a transaction against is on the same machine, you can provide ACID. If the data is on different machines, but you need to perform a transaction, then there might be some inconsistencies for a short while if you want reasonable performance.
When to Choose Which
If you're deciding whether to use a relational database or NoSQL database, consider what traits do you want your database to have.
| Trait | Relational Databases | NoSQL Databases |
| represent data with tables and primary keys | yes | maybe |
| represent data with anything else | no | yes |
| sql support | yes | maybe |
| scalability | maybe | yes |
| schemas | yes | maybe |
| transaction on same machine | yes | yes |
| transaction across many machines | choose between relaxed guarantees vs efficiency | choose between relaxed guarantees vs efficiency |
Any thing other than "yes" means you might need to write your own application level support.
As you can see with some amount of application level code, relational and NoSQL databases pretty much can support the same things.
The reason I see most people use NoSQL is for the non-strict schema and the scalability, which (1) requires a lot of work for application level code to handle, and (2) the current fashion for software is shipping fast (might need to change schema often) and scalable software.
Other things that might affect your decisions are: community support for the database, your boss says so, price, installation difficulty. These topics are pretty self-explanatory, so I didn't include them in this post.
I hope now you have a good answer when the next person asks you why you're using a NoSQL database.
Tuesday, May 8, 2012
MVC vs MVP Design Patterns
Post length: about 1000 words and about 3 pictures.
Background (skip if you want; it's all about me)
A while back, my company's leader asked me if I knew what the MVP design pattern was. Clearly it wasn't the minimum viable product or most valuable player. It was that model-view-presentation (MVP) pattern. I think it's being used a lot in GWT.
I only had superficial knowledge about a related pattern called the model-view-controller (MVC). Just enough knowledge to make the interviewer of my last job believe I'm a guru when I'm in fact a big fat phony.
The thing is I never used these patterns in practice, so I didn't really know what's going on.
Try searching the web and you'll find tons of information on both of these patterns. A lot of them are 10 pages long, full of UML diagrams and code. On the other hand, a lot of them contain a lot of handwaving. I don't blame them. They're accurate and complete, but that wasn't what I was looking for.
After much reading and asking my friends around, I figured that not only were the patterns pretty easy to understand, but the idea behind it was also SUPER simple and is just object oriented common sense.
Basics
So there are 3 things
- MVC
- MVP Supervising Controller (ooh big name)
- MVP Passive View (ooh another big name)
After you read this post, and if I did a good job explaining, you should be able to throw these 3 things away because it doesn't really matter how you name them.
Examples
You wanna go home
Suppose you're from Thailand. You've come to USA and during vacation, you want to book a flight back to your hometown.
You don't have time for this so you asked your brother, Tony Jaa, in Thailand to help find info about the flights from Thai Airway.
Tony goes to Thai Airway's homepage. They update their flight info regularly according to the laws, fuel price, and market demand.
The flight info includes the flight rates, departure/arrival times, and the food menu served on board.
When this info is ready, they put it on their website, into a spreadsheet.
You ask him to copy and paste the flight info and
- send it to you by email
- send it to the printer to print it out and hand it to your mom
In MVC terms
Note that you and your mom see the actual spreadsheet data exactly as on the website.
Your boyfriend wants to join
Later on, your boyfriend, Stephen Chow, who's Chinese finds out that you're going to Thailand and wants in. He wants the flight info to be sent to him through a Facebook wall post.
The problem is the flight info includes the menu served on board, which is in Thai and Stephen won't know what's on the menu.
Luckily Tony knows Cantonese (one of my favorite languages), so before he sends the email to Stephen, he also translates ONLY the menu part before sending it out.
In MVP (Supervising Controller) terms
Note that in this case, the spreadsheet is massaged a little bit before it's posted on Stephen's wall.
You wanna go home cheaply
Finally, you figured that you don't really care about the spreadsheet. You're a cheap person and only care about booking the cheapest flight.
This time you ask Tony to only send out the cheapest flight info on that spreadsheet, and don't forget to translate the menu for Stephen.
In MVP (Passive View) terms
Note that the original spreadsheet is no longer seen by you, your mom, and Stephen. There's only the cheapest flight info.
Bottom Line
In the end, all patterns do the same, they try to cleanly separate responsibilities, which is object oriented common sense.
Model: Somebody who manages the raw data should be smart only about the data. In this case, the airlines need to know how to calculate the flight info and stuff before publishing the spreadsheet.
Controller/Presenter: Somebody who knows how to get info and send them out should be smart only about getting the right info and sending the right info out. In this case, Tony needs to know how to copy and paste before sending the info to different platforms, including email, the printer, and Facebook.
View: Somebody who knows how to display data should be smart only about showing the data to other people. In this case, my Gmail web app should know how to show the spreadsheet in my web browser. The printer should know how to print the spreadsheet onto paper. Facebook should know how to display the spreadsheet on its wall.
These patterns are only different by the amount of coupling between the view and the model. Some applications can use the data from the model directly. And a lot of times, it needs to do something more complex to the data such as Cantonese translation.
And the names are there just so you have a common language to communicate with other people in the field who already knows this.
That's MVC and MVP for you.
Background (skip if you want; it's all about me)
A while back, my company's leader asked me if I knew what the MVP design pattern was. Clearly it wasn't the minimum viable product or most valuable player. It was that model-view-presentation (MVP) pattern. I think it's being used a lot in GWT.
I only had superficial knowledge about a related pattern called the model-view-controller (MVC). Just enough knowledge to make the interviewer of my last job believe I'm a guru when I'm in fact a big fat phony.
The thing is I never used these patterns in practice, so I didn't really know what's going on.
Try searching the web and you'll find tons of information on both of these patterns. A lot of them are 10 pages long, full of UML diagrams and code. On the other hand, a lot of them contain a lot of handwaving. I don't blame them. They're accurate and complete, but that wasn't what I was looking for.
After much reading and asking my friends around, I figured that not only were the patterns pretty easy to understand, but the idea behind it was also SUPER simple and is just object oriented common sense.
Basics
So there are 3 things
- MVC
- MVP Supervising Controller (ooh big name)
- MVP Passive View (ooh another big name)
After you read this post, and if I did a good job explaining, you should be able to throw these 3 things away because it doesn't really matter how you name them.
Examples
You wanna go home
Suppose you're from Thailand. You've come to USA and during vacation, you want to book a flight back to your hometown.
You don't have time for this so you asked your brother, Tony Jaa, in Thailand to help find info about the flights from Thai Airway.
Tony goes to Thai Airway's homepage. They update their flight info regularly according to the laws, fuel price, and market demand.
The flight info includes the flight rates, departure/arrival times, and the food menu served on board.
When this info is ready, they put it on their website, into a spreadsheet.
You ask him to copy and paste the flight info and
- send it to you by email
- send it to the printer to print it out and hand it to your mom
In MVC terms
| Model | The flight info spreadsheet. |
| View | Your view is an email which shows that spreadsheet. Your mom's view is the spreadsheet printed on paper. |
| Controller | Tony is the controller. He accepts your order and go gets the data, creates the model (flight info spreadsheet) and shows them to you and your mom. |
Note that you and your mom see the actual spreadsheet data exactly as on the website.
Your boyfriend wants to join
Later on, your boyfriend, Stephen Chow, who's Chinese finds out that you're going to Thailand and wants in. He wants the flight info to be sent to him through a Facebook wall post.
The problem is the flight info includes the menu served on board, which is in Thai and Stephen won't know what's on the menu.
Luckily Tony knows Cantonese (one of my favorite languages), so before he sends the email to Stephen, he also translates ONLY the menu part before sending it out.
In MVP (Supervising Controller) terms
| Model | Same as MVC. |
| View | Same as MVC plus the spreadsheet posted on Stephen's facebook wall. |
| Controller | Tony is the presenter. He does the same for you and mom. For Stephen, he translates the menu part and leaves the other data as is. |
Note that in this case, the spreadsheet is massaged a little bit before it's posted on Stephen's wall.
You wanna go home cheaply
Finally, you figured that you don't really care about the spreadsheet. You're a cheap person and only care about booking the cheapest flight.
This time you ask Tony to only send out the cheapest flight info on that spreadsheet, and don't forget to translate the menu for Stephen.
In MVP (Passive View) terms
| Model | Same as MVP (Supervising Controller). |
| View | Same as MVP (Supervising Controller), just showing less info. |
| Controller | Tony is the presenter. He filters unneeded info, translates when necessary, and sends the info out. |
Note that the original spreadsheet is no longer seen by you, your mom, and Stephen. There's only the cheapest flight info.
Bottom Line
In the end, all patterns do the same, they try to cleanly separate responsibilities, which is object oriented common sense.
Model: Somebody who manages the raw data should be smart only about the data. In this case, the airlines need to know how to calculate the flight info and stuff before publishing the spreadsheet.
Controller/Presenter: Somebody who knows how to get info and send them out should be smart only about getting the right info and sending the right info out. In this case, Tony needs to know how to copy and paste before sending the info to different platforms, including email, the printer, and Facebook.
View: Somebody who knows how to display data should be smart only about showing the data to other people. In this case, my Gmail web app should know how to show the spreadsheet in my web browser. The printer should know how to print the spreadsheet onto paper. Facebook should know how to display the spreadsheet on its wall.
These patterns are only different by the amount of coupling between the view and the model. Some applications can use the data from the model directly. And a lot of times, it needs to do something more complex to the data such as Cantonese translation.
And the names are there just so you have a common language to communicate with other people in the field who already knows this.
That's MVC and MVP for you.
Subscribe to:
Posts (Atom)


