I have been working in a start up concerned basically with mobile development since my graduation 2 years ago. I develop apps for iOS but it's not really relevant. The start up structure is simply founders > developers, with no middle-tier technical supervision or project management whatsoever.

A typical project cycle of ours is like this: meet with a client > send very vague requirements to an outsourced graphics designer > dig in development right after we get the design, no questions asked > then improvise improvise improvise! It's not that we are unaware that stuff like requirements analysis, UML, design patterns, source code control, testing, development methodologies... etc. exist, we just simply don't use them, and I mean like never.

The result is usually a clunk of hardly-maintainable yet working code. Despite everything we are literally flourishing with many successful apps on all platforms and bigger clients each project. The thing is, we want the chaos to stop and we're looking for advice.

How would you fix our company technically? Given that you can't hire project managers or team leaders just because we are barely 5 developers, so it wouldn't be a justified cost for the founders, but one-time things like courses, books, private training... etc is an option. Lastly, if it's relevant, we are based in Egypt.

@Code-Guru Chaos can be invigorating. The key is to keep some level of control over it.
–
IzkataSep 11 '12 at 23:45

1

@Izkata Sure, I understand that. However, that particular sentence didn't read well in the context of the rest of the post. At least I stumbled over it in my first reading. Now that I go back and reread, though, it makes a bit more sense...
–
Code-GuruSep 11 '12 at 23:48

1

Hey, if it's working for you... But as you allude to in your question, even great developers who put enough "garbage-in" will eventually get "garbage-out." I can't recommend a specific methodology so much as an attitude that some code needs to be continuously cleaned and improved, even as new changes are thrown into it. At year 6 where I work, refactoring is a continuous improvement effort.
–
GlenPetersonSep 12 '12 at 4:21

1

Careful what you wish for - it might be chaos, but your company is flourishing! Don't change too much at once, or that may stop as well.
–
Joris TimmermansSep 12 '12 at 7:29

6 Answers
6

I have a start up background. What you are experiencing is highly typical, and despite what many say - if you are making enough money to survive, you are doing it right....for now. Your question is very valid, very relevant, and (assuming the start-up is about 2-3 years old, based on how long you have been there) very timely.

The most common failure time for a company is where you are now - at about 2-4 years, you need to transition to a small company from a start up. To avoid failure at this point, one phase that comes to mind is "Speculative investment" Read up on it, understand it, and understand when you are doing it. (Spending more time coding than needed to get the job done is speculative investment.) I am not saying don't do it, I am saying understand when you are doing it and make a conscious decision that it is appropriate (or not) for today. Adding Unit Tests is a very good example.

The transition will require some changes, however, those changes must not jeopardize the finances. No point bringing in a BA, a PM, and "Manager of software" and all sorts of unproductive processes if it drives you bust. Evey thing you do must be done in the context "How can we make this happen today, and still be in business tomorrow"

One start up I worked for the team wrote software for a product. Four years later it was describe as a ball of mud/pile of S..., the worst code he had ever seen etc, that should never have been released, by a new recruit. I pointed out to him the shareholders had just sold the company and put $50Million into their back pockets based on it. I asked him how he intended to make 50Mil in 4 years, and how "doing it right" would have helped - In fact, doing it right would have taken us 8 months, not 8 weeks, the cash reserves would have lasted 3 months, the competitors would have released into the market, and the company would have folded. I left and he became a team lead. They rewrote the code from scratch using "best practice" bla bla bla, the company now has less than 5% of market share, down for about 75%... revenues down from $250Mil to about $40mil.....

So here are my suggestions

keep "hacking" balls of mud.

Introduce Agile/SCRUM - but don't let it slow you down- do courses on this if nothing else.

Consider TDD and Unit testing. It will help keep on top of those balls of mud - careful - don't spend too much time on it or you won't be in business to reap the rewards

Perform DeBono's 6 Hats at the end of each project.

As you grow, be careful - be very very careful - who you bring in. You need people who have through the transition before. Do NOT recruit big company types.

read this - I particularly like "And there's another factor involved, which is that you can divide our industry into two kinds of people: those who want to go work for a company to make it successful, and those who want to go work for a successful company. Netscape's early success and rapid growth caused us to stop getting the former and start getting the latter. "

I'm curious though, do you in your heart of hearts think that a talented, flexible, fast moving team could have kept that big ball of mud moving and successful, or was the $50 Million payout the product of a bubble economy and investors with deep pockets who didn't have the sense to recognize they were buying a big ball of mud that had reached the limit of sustainability? I'm not trying to be snarky here, but I've seen examples of both.
–
Charles E. GrantSep 11 '12 at 23:11

I agree with Charles, I think. Just because you can scam someone into thinking your product is better than it is doesn't make it right or ethical by any means. But some people believe money is more important than their integrity, so I guess it's right for those type of people.
–
DunkSep 11 '12 at 23:39

1

@Dunk: No one was scammed - the buyout was buy a multi - billion dollar organisation who knows business and to be honest, they buyer was not that interested - they knew what they bought and cash-cowed it.
–
mattnzSep 12 '12 at 3:25

@Charles: I beleve the software potentially had a many years of commercial life, just the technical debt needed to be paid. Measuring I did showed a few modules (10% of total code) were responsible for about 80% of defects and cost twice as much pre function point compared to others - consistant with lots of research. A rewrite from scratch was not the appropriate action. However you have missed the point - the business would not have survived had we tried to do it "properly"
–
mattnzSep 12 '12 at 3:32

1

@mattnz You asume, that doing it right would take much more time than "hacking" it to "just work". I believe this is wrong and if you know what you are doing, you can do it right and you can do it fast. Only unexperienced devs think that those two things exclude each other.
–
EuphoricSep 12 '12 at 9:53

When I've worked with companies that were very ad hoc in methodology, we looked at the top two or three process or infrastructure issues that mattered "right now" and started investing time in them alongside our normal commitments.

I don't think traditional "software engineering" is necessarily the right model for a small team that's dealing with frequently changing business requirements; software engineering is more important for dealing with multiple vendors and situations where change is very expensive and needs risk and quality gates. If you're building software for space shuttle parts or cars, the software engineering approach may make sense.

Instead, I advocate a "software craftsmanship" approach for most organizations. But software engineering has created tools and discovered processes that work for lots of kinds of teams, so I am not saying that you should ignore those lessons, just that you should work from a different perspective that's more about continuous improvement, dealing with ambiguity and change, and taking a couple of hours every month or so to do retrospectives on what's working well and what's not working well with your development and business processes.

In your shoes, I'd say you can probably not worry about UML for now; you need to focus on getting a lightweight version control system into place. Just start with Git or Mercurial, and either sign up for private repositories with a third party vendor to push your repositories to (Bitbucket, Github), or set up a local server to push to.

Then worry about setting up a continuous build system (like Jenkins).

Small teams may not be able to afford full time testers, but they can start building automated unit test coverage; even starting this practice without religiously adhering to any particular methodological dogma may help you start writing new code in a more maintainable state, because you'll get annoyed enough by any friction in writing tests that you'll either want to fix your code or give up testing. If you've got the other stuff in place, and you start to get even the slightest value out of testing, you'll probably prefer to fix your code rather than give up testing.

You can do this on your own by just investing time in it. It may be worthwhile to hire a person to work on either your infrastructure or process problems, but the three items above are usually low hanging fruit that will show immediate returns and require relatively minimal investment.

As for books, read the Pragmatic Programmer, Software Craftsmanship: The New Imperative, and any of the books available on distributed version control and continuous integration. You should evaluate Extreme Programming, Scrum, and Kanban to see what you think will work best for your team . To get better at process, attend local meetups or events with other small software shops and talk about what's working and not working for you, and get better ideas from your peers on how to cope with high velocity with small teams. Software Engineering isn't really about maintaining velocity, it's about maintaining control of things that interact with your product.

Once you have a 5 person team, though, some sort of process management help makes financial sense for most organizations. Hiring a program manager or ScrumMaster or something along those lines will have some value to your founders if it will help you deliver work more consistently and predictably.

The result is usually a clunk of hardly-maintainable yet working code.

Correlation doesn't imply causation. You have clunky and hard to maintain code because you write clunky and hard to maintain code. I think the best tool for improving this are code reviews. A project manager is not going to help you write better code. Hiring a more experienced developer may help but it's really up to everyone to drive improvement.

Despite everything we are literally flourishing with many successful
apps on all platforms and bigger clients each project.

So you must be doing something right. Whatever you do make sure you keep doing the right parts. Proceed with caution and make sure the process changes you adopt are targeted at fixing some specific problems that you identify.

It's not that we are unaware that stuff like requirements analysis,
UML, design patterns, source code control, testing, development
methodologies... etc. exist, we just simply don't use them, and I mean
like never.

I concur with @JasonTrue that source version control should be your first priority. In this day and age it is inexcusable not to use source control. Tools are freely available (git, mercurial, subversion), they are easy to install and use, and the return on investment is practically immediate. I would suggest starting to do some code reviews and some design reviews, not more than a few hours every week. Simply taking some time to look at what you are doing, share your experiences and consider better ways of doing can be a big helper. Agile practitioners will call this a retrospective.

Again I concur with @JasonTrue that build automation and test automation are the natural next steps.

Once you have version control, automated builds, you're doing some code reviews and retrospectives and basic simple automated testing things will look a lot better. Just add your desired amount of chaos on top of that :-)

My absolute biggest tip: Don't try to fix everything at once, or change too much in one go!

Exactly how you proceed from here will depend on a few things: how busy your team is, how on-board everyone is with the idea that things even need to be improved, etc.

If people need convincing, you'll probably have to do a lot of the groundwork yourself to begin with. Identify a few key areas you see as needing improvement, work out a nice 'easy fix' for each (you can always improve again from there), put together some estimates on how long each would take, and then take this information to your colleagues to see if you can get some momentum going.

If everyone is already on-board but you don't know where to start, collaborate with them to identify the key areas and some potential solutions, and estimates for doing them. It will probably help to think about this from a what-problems-are-we-experiencing perspective rather than a what-do-we-think-we-ought-to-be-doing perspective. You'll find it's easier to identify solutions to known problems than pin down specific actions from a vague wishlist.

Once you have your list, prioritise it however makes most sense for your group. Since it sounds like things are just a little chaotic rather than totally dysfunctional, I'd suggest going with a 'least upheaval first' approach. Go for the low-hanging fruit to start knocking stuff off the list, it will let everyone get used to changes happening and refine your strategy for handling the bigger changes.

Version control is probably the change which will give you biggest bang for your buck. Make yourself a test repo to practice with for a bit, get used to the workflow, then demo it to your colleagues and get it into full operational use.

When you fix a bug, write a test which you can use to check for regressions in future versions.

Gather together a set of basic functionality tests to be run for every build, and set up reporting if any of them fail so it can be fixed ASAP.

Create and keep a mapping of which tests cover which requirements/functionality/bugs

In terms of the code itself, try to go for incremental improvement. Whenever you (the team) update a method, check that it's properly commented. Set up code reviews for big/important changes. It's rarely a good idea to try change the design of existing code, but for new projects, hold a design review early on in the lifecycle where you consider how easy the design would be to update, adapt, extend, or reuse (is it sufficiently modular? is it tightly coupled?)

Above all, keep chipping away! If you're going slowly because you're busy, don't worry about it too much. Just go back to the list when you do have the time.

You are actually on a right direction to see all the shortcomings of the software development process that is followed in your company. Fixing this software and becoming more reliable, testable and maintainable will NOT happen overnight. You can achieve it gradually, step-by-step.

You may start to discuss this with colleges about what can be improved through introduction of proper SDLC and the ways how to gradually achieve it. For sure, it will take time and will to make this happen. However, sooner you start better for yourself :)

I don't think your problem is weird. It is very common and is one of many causes for failure of up to 95% of start up companies fail (and also many non-start ups). You mentioned that you graduated two years ago but did not identify the degree. If it was computer science, some people would already say you are a software engineer.

Software Engineering Institute (SEI), with funding from US Department of Defense, created a scale and batteries of assessments called the Capability Maturity Model (CMM) to measure the level of preparation to succeed in software development contracts from the government and others. They characterize maturity by level, where level 1 is called Initial or Chaotic because software development is undocumented, ad-hoc, uncontrolled and reactive. The raw skill of someone involved in the project is the main thing holding things together to create a deliverable for the customer. Most of us have been on a lot of level 1 projects where hard work and smart people saved (or almost saved) the day.

Original CMM recommended progressing up the levels in sequence. Level 2 called repeatable was all about management related processes. Level 3 called defined, was about team practices defined by management for developers. There were five layers (4 is Managed, 5 is Optimizing) and spread among the layers were many Key Process Areas (KPAs) that organizations were expected to learn and practice.

A revised model, CMMi (CMM integration), identifies similar layers, and discusses core process areas. It has the same kind of level oriented progression called staged, and a road map oriented progression called continuous. With continuous, it is possible to select core processes that are most valuable to the organization, and to emphasize them to the exclusion of other processes.

Certification for CMMi is an expensive business, and the documentation is huge and daunting. Understanding some of its concepts can be valuable, but mostly in answer to your question "How to be a Software Engineer?"

Your other question about how to fix the company technically is related, but needs more concrete suggestions.

Understand the concepts behind software life cycle models (waterfall, spiral, feature oriented, and most importantly iterative/incremental). Somewhere during development you should do not only code, but also analysis, design, and testing. For agile, this can be making story cards or use cases with alternative flows, creating unit tests, and writing code, often a feature at a time.

Insure that each project is scoped at a reasonable size for your team (requirements management).

Create plans and track progress with a flexible tool like Atlassian Jira or something similar that will create a database of tasks among the team (integrated planning and tracking).

Have a quality assurance strategy that runs the full duration of the project. Test Driven Development (TDD) may supply much of this requirement, but you should also read about the V-Model.

The code you write should follow some rules, so you should create or adopt coding standards appropriate to your development language. Having these rules will boost code quality and provide a guide for peer review of code.

Utilize some kind of peer review where members of the team look at each others work for defects and recommend corrections and improvements. This is a key teaching and learning opportunity, so don't dismiss it as too expensive.

Code and documentation assets of the project need to be source controlled, version numbered, and described by change logs and release notes.

This is certainly a partial list, and others will suggest other very helpful additions. Everyone in the team needs to be thoroughly trained to understand and use each of these, but you may see benefits as you progress. Open source tool support is available for most, so if the first option in a category is too expensive, look around and ask around for some options that fit you better.