April 16, 2010

This week’s highlights

Here is the summary of my lurking around the past weeks. Probably the Calacanis VS Dhh episode of Twist is my favorite on this set. But also Eric Ries’s interview about Lean Startup Thinking was very interesting. As usual, the link is followed by opinionated summaries. Enjoy.

[FoRK] Programming languages, operating systems, despair and anger… Ah ah, enjoyed this one. There is definitely truth in the rant. Especially the fact that many if not all main stream languages are more written for computers than humans, with some noticeable exception in languages like Ruby or Python. The point to take away from the post in my opinion is that language design should take into account the list of all the common programming tasks listed here. It looks that we need again another layer of abstraction on top of programming languages, something similar to a DSL where the domain is day to day programming for an average application. Good stuff.

I’m quitting the Internet. Will I be liberated or left behind? - By James Sturm - Slate Magazine… An interesting reading with thoughtful comments. I went information diet myself and from that short 15 days experience I understood a lot about my mistakes. I also realized that the all-or-nothing is not a solution. I need and I enjoy to keep up with the Internet buzz. But I understand who needs to quit completely, at least temporary, to understand where the limit is, as in this blog post.

Episode 159: C++0X with Scott Meyers | Software Engineering Radio… So even C++ gets lambdas, type inference and power support for concurrency (along with the other features added in this last re-incaranation). As I heard already a few times, Java is apparently dead. When lambdas will be included in Java most of the developers will be already using Scala or Groovy. The JSR is a remarkable high ceremony process that forces people to create their own flavor of Java with the features they miss the most.

Daring Fireball: New iPhone Developer Agreement Bans the Use of Adobe’s Flash-to-iPhone Compiler… Maybe not only Flash. What about MacRuby? This is an high risk move from Apple. True, they can protect the quality of the product and avoid third parties to create tools that can compile down iPhone, Android and other platforms at the same time like Titanium. On the other hand, other languages are more expressive and maintainable than Objective-C giving iPhone app a quality boost. Although I’m developing iPhone in Objective-C it sounds to me like nonsense. I’d like the option to use the right tool for the job and maybe Objective-C is not always the right tool. I’m worried that Apple will stop the MacRuby team on working on an explicit garbage collector, thus preventing MacRuby to run on the iPhone.

TWiST #46 with David Heinemeier Hansson… Here we go. Every once in while there is something you can’t miss. Two interpretations of capitalism (or maybe just one is and the other is not): the one that Calacanis defines old school and maybe European is in my opinion the new school or the anti-american school. David explains perfectly well what the differences are, but I think it all comes down to the presence of an upper limit. With no limit, the model is to raise money and move to something else to raise possibly more money, often by creating a bubble of expectation and excitement made of meaningless metrics. The other way (David) gives less prominence to money accumulation and more importance to searching the best idea to implement, an healthy life style and real profit. Overall it means doing business with the idea that when your income is enough to afford everything, there is no need to raise more money just because you can. With a nice side effect: better wealth distribution overall.

danieltenner.com ‚Äî How to¬†nap… Glad to see I’m not the only exercising how to nap. It also took me some time to get to the point where I’m now. My experience is very similar to the one described in this post. I still use sometimes white noise tracks from 20 to 30 minutes based on the mood of the moment. And yes, never ever go over 30 minutes, or you risk drowsiness as described here. Something I’m doing lately after the muscles relaxing focus part, is to focus my thinking to someone walking and just visualizing the legs and almost nothing about the surrounding of the scene. Sometimes it takes some effort, but apparently it puts the brain on some useless thinking that removes other thoughts and prepare for napping. At least, this works for me!

Show #49 Eric Ries, Lean Startup and product/market fit ¬´ The Startup Success Podcast… You should really listen to this one. Eric is great explaining what this is all about and I very enjoyed his clarity. The relation to acceptance tests idea is mine though. So: continuous deployment + production cluster + revenue metrics and an automatic halt and revert system for production is the recipe to drastically reduce the importance of acceptance testing. The scary part is that we are accepting and embracing the fact that bugs will make it to production even if we fight them hard (it will happen anyway). By gradually deploying to a cluster if there are bugs only a small portion of our customer will find out. The presence of a “revenue” metric will trigger the revert button automatically, reducing the loss to the bare minimum. By accepting the risk of some bugs passing to production we can leverage a very tight customer feedback loop and learn very early how to change direction to achieve market fit. This works well for startups, where the kernel idea need to be validated ASAP.

QR Code - Wikipedia, the free encyclopedia… Thinking seriously to place this on my business card. Slick and if you have a modern phone, readable!

Emphasized Insanity - Using Sinatra to test remote services in Rails… In my last project I had a lot of stubbed request response to stub out web services like S3 or MTurk. I did everything by hand and it was not difficult, what is difficult is to reproduce the call and dump the raw response when you realize you need just another slightly different test case. For the next time I’d like to user something like FakeWeb or this Sinatra server built on top of it. Recording and storing should be much easier and repeatable improving the maintenance of integration tests with stubbed web services.

Comments (View)
April 7, 2010

Billable Pomodoros

So you are ready to start the next project and you are a freelancer and a good Pomodoro Technique practitioner. Of course all those tracked pomodoros are a good source of information for billing. But how the pomodoro should be converted into time and then into money on the bill? My rule of thumb is the following:

1P ~= 35’

The math behind the equation assumes that breaks related to the technique are part of the job (a very important part indeed). If you take more or less 5 minutes short break and a long break of 20 minutes you have 140 minutes every 4 pomodoros which are exactly the 35 minutes shown above.

There are great days and there are bad days, but let’s say you’re a 12P/day kind of guy. Twelve pomodoros is 7 hours (I know the very last long break is not included but as an average I don’t think it’s important). If you have an hourly wage of 40$ and 12p is your daily average for a month, you’ll charge ~5600$ to your customer. Just an example. If you prefer to bill days of work, then is up to you to decide how many pomodoros make up a day.

The interesting part of making pomodoros a billable unit is the high quality of the work sold to the customer. If you bill pomodoros and the customer is able to understand the technique, they can be sure that what they receive is high quality, focused work that can be tracked down to the single 35 minutes unit (if you keep the history). With tools like Pomodori this is plain easy.

Would you agree with my conclusions? What you would do differently instead?

Comments (View)
March 13, 2010

Lean startup thinking and acceptance tests

Listening to this great podcast where Eric Ries speaks about product market fit and validated learning I thought that lean startup thinking can drastically reduce the importance of automated acceptance tests to the bare minimum. Nothing that I had the pleasure to test in person unfortunately, but something to think about for the next project with the right business context.

What’s the deal with acceptances? At the last Agile 2009 I participated at a panel where the audience was required to brainstorm on the need of acceptance testing and the options to replace them some way or the other. The outcome of the session was a general consensus that acceptances are hard to maintain and they should only cover the most important paths of the application and accepting the fact that exploratory or manual testing is still needed to cover the rest of the application. How true. I was burned several times by the huge maintenance cost, cryptic deployment issues and general outcome disappointment even for the best crafted acceptance suite. After that experience I started reducing the acceptance suite size accepting a small manual and not automated testing phase as an unavoidable fact.

Lean startup thinking is a set of principles and values that can be applied to an existing process such as Extreme Programming. There are a few main goals (this is just my modest understanding of the whole thing which is way bigger to summarize here):

  • The process should focus on the steps to achieve the product market fit which is the point where the core fundamental business value of the product is appreciated by customers and put to good use. You can measure product market fit with customer retention rate for example.
  • The development process should be able to quickly create and execute feature changes based on the customer feedback as part of the iteration loop. The product market fit won’t be achieved If the project is too slow transforming the customer feedback into value. This is especially true for startups where there is always a good amount of uncertainty about the business value of the final product until real customers determine its success or not. Validated learning takes care of carefully collect the customer feedback and put in place the necessary metrics (such as A/B testing percentages) to validate that what we think the customer wants is really what the customer want.
  • Since we want customer feedback so badly we have to deploy as soon as we add new value to the product. The immediate feedback cycle loop helps the team deciding what has to be changed to achieve market fit as soon as possible. The team embraces the inevitable presence of defects in the final product but learn how to keep that number low and how to revert and fix the problem keeping the damage as low as possible. Continuous deployment on a cluster connected to business metrics such as the revenue/minute and an automatic halt and revert system is an optimal context to create such a tight loop while minimizing the revenue loss

The last practice is specifically related to acceptance testing. We strategically accept a compromise. The compromise is especially useful in a startup context where the business value of the final product is a moving target. By delegating to a small subset of our customer base the manual testing of the application we can keep the acceptance test suite size at the minimum. Sounds scary uh? But just think for a moment: the project infrastructure is able to revert the system in minutes as soon as some sensible metrics drop (remember also that the latest build went only to a portion of the cluster exposing the new deploy only to a subset of the customer base), stop new commits until the team fixes the issue (in case of real disasters) or just alert the team that the results of the A/B metric from the last deploy was just not as appreciated as expected. Sure you risk to have customers pissed about your product, unless…, unless you demonstrate that you recover in minutes and respond to customer feedback on the next iteration. Lean thinking.

Comments (View)
March 4, 2010

Resumed this week highlights

I never stopped my weekly reading, listening and watching but I stopped talking about it here. No notes means I forget about everything, what a waste. So I resumed the habit: just a few lines when the topic is interesting and thoughts provoking. Very opinionated! Enjoy.

Sketchnotes iPhone Tapstack App by SixVoices… An interesting case of a company (SixVoices) selling a product which is an User Experience concept. The idea is then adapted and implemented down to iPhone apps like this one to illustrate sketchnotes. The concept is to reproduce with the iphone what happens to a stack of cards or pages when they are on a table and can be browser with your finger. The effect is very intuitive.

About Mike Rohde’s Sketchnotes… Here is a concise introduction to sketch notes. Mike Rohde explains the process and tools needed. What is actually amazing considering the quality and quantity of details of the illustrations is how this can be done realtime while possibly paying attention to the presentation. I think at least at the beginning I’d be completely absorbed by the sketching part. Maybe start incrementally: just writing, then a few geometrical sketches, then some more typography and fonts to create the finger memory. Anyway,

37signals Podcast - Rework… A few simple annoying facts about business books (and sometimes not only business) which I agree with in this interview about the soon to be published 37signals book. Very often the main topic of the book is thoroughly explained in the first 60 pages which by them selves sell the book. Money well spent and a lot of a-ha moments. The remaining 250 pages “rework” the same topic killing completely my interest in the book. Unfortunately there could be the same treatment at the beginning too and this is enough to abandon the book right away. The second are those 15+ pages before chapter 1, with 20% interesting contents. But I hate prefaces (why I wrote the book, why I decided to republish the book, etc) copyrights and so on. Needless to say, “Rework” refused the format in both cases. I knew also about Rohdesign, the mind behind sketchnotes. This reminds me of the importance of engaging right brain thinking using all the possible senses. Wondering if to use the technique for my learnings.

Confreaks: RubyConf 2009 - Solid Ruby Jim Weirich… I’m always sure that whatever presentation by Jim will teach me something. I had the opportunity to reflect on a few important facts. Changing behavior by monkey patching is dangerous because it is triggered by a require statement at the beginning of a file which nothing has to do at least apparently with the patch. It triggers unexpected behavior. Changing by subclassing instead depends on the type of the instance receiving the message which usually is dependent on the instantiation context and therefore planned more carefully. There are no enforced interfaces in Ruby as for example in Java. But there is an implicit protocol to obey which has more to do with discipline. The protocol is in the documentation and parameters name, much more freedom, no need for ceremony with interfaces. A protocol is basically a subset of the methods of a class. So in Ruby OCP and DIP does not need the creation of a new interface to invert dependencies.

Podcast Interview With Oceanhouse Media Brands And Their Impact On Volume and Price… One reason to choose volume over complexity in the app store is discoverability: many apps in the app store makes more likely to be found. The app store is a search engine: we need SEO kind of rules. Simplicity is the key, not necessarily low-quality. A working iphone prototype is the new business card to catch the attention of the next customer. After 80+ apps created their experience is you can’t predict what will sell the best. The development effort should be 3-4 weeks to minimize the impact of low number of units sold. You accept 3-4 months project only when you know is a guaranteed seller.

Jon Skeet - World’s Greatest Living Programmer… Heard an interesting and simple trick to make 2 services built on top of the same API but supporting different versions. If the version of the response retrieved by the server is not the wanted one, the client can make a second request of translation with downgrading of the default version to the previous one (for example). The service that upgraded the version of the API is supposed to provide the translation service and to know how to downgrade the response version (when applicable). Jon then tells us how he achieved the best contributor status on StackOverflow. There is really nothing surprising here, he doesn’t plan for a daily StackOverflow session. He just fills all the possible holes during his working day with StackOverflow, that’s it. As simple as it sounds, being really focused on only one or few goals is the key for success. The problem is learning how isolate from all the possible external distractions. Pomodoro rules.

Railscasts 199 - Mobile Devices… Pretty impressive here the ease you can setup your Rails web app to serve better content for a mobile device or even completely look like a mobile device with JQTouch. You can start by just a better looking UI by defining a css which is only triggered when the user agent matches a certain string. You can create an helper method for that. If you want a link to switch back and forward from mobile to normal version, you need to save which UI you’re on in the session. If you need instead the pages to look different beyond what a CSS can do, you need a custom template for a specific new format. When the page is called with the new format (.mobile instead of .html) a completely different layout is triggered. JQTouch can be used at this point only for the mobile layout to render the application very similar to a native iPhone interface. This is all concisely and beautifully explained by Ryan Bates in this screencast. Enjoy.

Comments (View)
November 30, 2009

MacRuby CoreData Tutorial

There is an useful tutorial on the Mac Developers Center about how to use CoreData programmatically. The tutorial has been ported to RubyCocoa here and partially on MacRuby as part of the template installed in XCode when you install MacRuby. With the help of both the sources I ported the tutorial to MacRuby introducing just a few ruby-isms but without altering the general structure of the program.

The tutorial is very useful if you intend to use CoreData to persist programmatically your objects without the visual help of Interface Builder. If you look at the listing below, you can see a “Run” object extending NSManagedObject persisted into the local store. The way CoreData works remembers me of EOF in WebObjects and it’s generally “old school” relational mapping and persistency. In this model, you request managed instances from the context and the context is then used to persist those objects. Persistency operations are not part of the object model like many ORM tools nowadays.

The following short example is just a starting point for a more abstract persistence API based on CoreData. Methods can be better encapsulated into smaller methods or different classes and in general I think it’d be a good idea to make it more ActiveRecord-like (i.e. transparent) for the final user to use. My intent here is to clone the original tutorial so please be patient if the code is not perfect and sorry for the odd line wrapping.

I tried this with MacRuby 0.5 beta 2. Just install MacRuby and run the example using the macruby command line interpreter. It will create a persistent XML store in ~/Library/Application Support/CoredataUtilityTutorial

Comments (View)
September 20, 2009
Comments (View)
September 17, 2009
Comments (View)
Comments (View)
August 30, 2009

Agile 2009 Report

Finally I managed to attend the biggest of the agile conferences around. Unfortunately I missed the first 2 days which means 50% of the conference. For the 2 full days I was there I had the pleasure to attend interesting talks, knowing smart people and get a sense of how agile is doing these days. The organization was almost perfect, excluding the confusing aspect of “stages” as categorization for talks. But that’s a minor problem in my opinion. Please jump right at the bottom if you only care about the conclusions.

The first talk I attended was almost by accident considering the complete lack of time I had to go through the program and decide carefully what to see. So the criteria was: choose a title that sounds like new stuff, at least you’ll learn something different. With that in mind I attended “Stepping Up and Stepping Back: the Leadership tipping point” by Pollyanna Pixton. Project leadership talks are not usually on my radar, but I knew Pollyanna by fame. The talk was centered around the idea that today’s style of leadership should be less intrusive as possible to foster team creativity. This is also the topic of the last book of Pollyanna. The exact opposite is the command-control kind of leadership, the one where is the leader who takes ownership of actions instead of letting the team assume the control. The leader should step back even when they know exactly the solution for a problem and let the team learn from mistakes. Apparently leaders appear to do nothing while instead they prepare the team to take responsibility. Not imposing doesn’t mean not to lead. We even practiced how not to answer questions!

Then it was my turn to speak. I think You Say Tomato I Say Pomodoro talk went great. I worried that speaking for 90 minutes was too long, but when you put practice into the mix, finishing earlier is never an issue. I had around 15 people attending which is not a lot considering the size of the conference. Feedback was great, averaging 4 to 5 stars. Probably people already got their Pomodoro talk the day before and they were not interested in another one. I think my title was misleading in this sense, it sounded more like an introduction and it was not. Also: Neal Ford was talking about emergent design in the other room and that didn’t helped a lot :) I’d like to extend the talk to a 3 hours session in which instead of driving the exercises I give them to the public with my supervision.

I then moved on the other building where the Software Craftsmanship North America was taking place. I attended Ward Cunningham’s talk about “bacteria oriented programming”. Don’t be fooled by the apparent non-sense biology, electronics and programming mix of this “old guy” of the agile community. There is an important take away: never stop to a single discipline, move around, let the side thinking permeate your daily programming. He gave us an example of a “fuzzy” protocol called Bynase, where instead of defining a communication protocol, a continuous stream of impulses is used between computers and sometimes the pulse is accepted and sometimes it’s not. This resembles cellular communication where the cell transmission triggers communication between other cells. You can find more here. The line up of speakers for SCNA was impressive but I decided to go back to Agile 2009. That was an hard decision though!

I needed some rest, but I was just in time to hear the remote pairing experience report by Tim Ottinger and Tim Gifford. I was already following Tim’s effort from his blog while doing a similar experience in parallel with my team. Conclusions are the same: no silver bullet but just a mash-up of tools to use to fail-over when connection isn’t perfect. And it’s never perfect. You also need to think about a specific “remotiquette” and learn what you can and what you can’t do at the phone/screen. Mostly common sense I’d say. I agree with their conclusion that we are still lacking a complete solution for remote working even if features should be clear by now. C’mon vendors!

I then participated to my first Agile Jam Session. I’m talking about a real jazz jam session at the Muzic Masti stage where we self-organized to create the band: yours truly at the piano, Chris McMahon at the bass, Paul Rayner at the guitar and Henrik Kniberg at the drums (he was the pianist but he kindly accepted to let me play). We’ve got several other instruments coming and go and unfortunately I don’t remember the names. I stopped only 2 hours later to move to the DWR party at the Elephant Castle with Paul. We were able to stay only 1 hour because after a while we couldn’t hear each other or anyone else because of the confusion. Anyway, great night.

First talk I attended on Thursday was Styles of TDD: First tests by Naresh Jain and Michael Feathers. This was a practice session on TDD with an exercise based on a billing system application to develop. I abandoned after the first break. I couldn’t understand what the goal of the session was. I had the impression we had to develop test first a few features and then discuss what went good or bad, but I’m not sure. If that was the goal, it was too much basic stuff for me. I expected to learn different styles of TDD (whatever that means, that was my curiosity) but it was just an introductory session with people discussing why you should or shouldn’t test a specific feature.

It was then the time of Metrics in an Agile World by Rob Myers and James Shore. After an interesting start about the meaning of “measure” for common life things like the grade for an egg or what is exactly a “good tomato”, I got lost in the pictures. I think I’m becoming very impatient (which is not always good) so maybe this time I was too quick in judging the talk. But I started feeling frustrated when: I realized the pictures were too invasive and when James Shore asked the audience to organize into groups to brainstorm a few ideas about metrics. It’s true: sometimes the best talk is the one where you don’t receive answers but where the attendees collectively found solutions. But in this case I was looking at pretty pictures on the screen and listening to curiosities about grading eggs and then asked to find a definition for metrics. I was not ready to workshop at the table because I couldn’t understand the goal. As I said, I was too quick. I should have done the exercise and stayed a little more. The critique for the presenter is: pretty pictures are fine until it’s evident that they are just used to catch the attention.

I closed the morning with some bureaucracy at the speaker booth and then lunch. For the afternoon, frustrated by the lack of pragmatism of the previous talks, I selected something very practical and Ruby-ish like Acceptance testing Java Applications with Cucumber, rspec, and Jruby by Dean Wampler and Aslak Hellesøy. I was curious to be taught by Aslak about something I knew like cucumber, but not in all the details. It went pretty well, I learned a few things about cucumber I never used and also how to use in cross-language environments. I also got a chance to go back to my Java days and remembering how to program in Java. Man, that was so quick! All those years are still there. Anyway, I had to left before only because there was a talk I wanted absolutely to see.

The last talk for Thursday was Slow and Brittle: replacing End-to-End testing by Arlo Belshee and James Shore. I went there because I think Arlo is a genius and also because I appreciate James’ writing on his blog. It turned out to be a little different from my expectations, but overall a great session. In this case, the fact that the audience was required to work on a problem was clear since the beginning. That’s ok, no pictures, not even slides. Trust engaged. The problem of end-to-end testing is the problem of maintaining and executing acceptances, integration or any other kind of test where the components involved are loosely connected. We decided to name these end-to-end. Now, execution and maintenance of end2end tests is notoriously such a big pain that many teams decide to remove or to do a light use of them. Given the fact that you can’t sell the customer buggy applications, in which way we can replace end2end testing? There was no definitive answer but a list of common alleviators such as good mocking, just the right amount of exploratory testing and even a language tailored explicitly for end 2 end testing. Arlo’s approach is probably the most interesting: they delete end2end tests when the feature is stable and necessary unit tests are in place. I proposed a Pareto-like solution: let’s instrument the application so that the most common usage paths are recorded. Knowing that those usage paths cover the 80% of the application business value, let’s use end2end to cover them and something else for the rest. I was not able to explain my idea to the table, so we opted for a better use of plugin oriented architectures based on the facade pattern. I enjoyed the conversation and the challenge. Impressive was to see James driving the room full of people and the lighting talks.

This is basically the end of my first Agile conference. But probably the best talk of the entire week went on during the banquet. I had the pleasure to see Jared Spool in action with a talk about the importance of user experience design. A great build-up of anecdotes and facts to sustain the thesis that user interface design is the most important aspect of software development. Totally agree and you have to be good at it. He’s just a great speaker, you have to watch it to understand. Some interesting take away: there must be a vision for the product and everyone in the company should endorse it. Good design cannot always be explained completely: you need to learn from the masters and then reproduce in some sort of unconscious way. And many many more. I think this presentation and probably a few others should be online on www.InfoQ.com any time soon.

I had a great time. Too bad I was not there from the beginning and I was too busy the days before. My planning certainly suffered from my poor conference preparation. I also met wonderful people that is probably the most important part. As I heard from others the last year, attending this conference gives the impression Agile crossed the chasm. My impression is more that Agile stalled right before crossing the chasm. Many know about Agile but they are still early adopters and it looks like there will be no more innovation from now on to increase the interest. The Agile 2003 program, for example, isn’t very different from this year program except for the quantity of sessions: after 6 years TDD should be considered as a complete obsolete topic, but we are still here struggling with it.

Comments (View)
August 11, 2009

Not Reinventing The Wheel?

http://www.flickr.com/photos/vrogy/

It depends.

Have you ever been asked to not “reinvent the wheel” by a customer or maybe your boss to implement some functionality for an existing project? It’s a pretty common situation I think. Extension by reuse is a nice thing to have and all well crafted projects with low technical debt are ready to be improved without the need of “reinventing”. But what exactly the boss is asking to the team? The boss is probably just afraid of the team writing the same code twice, without copy pasting (!). If you’re lucky maybe your boss is smart enough to imply “writing the same code twice instead of reusing already existing components”. Anyway, the final goal for the boss is to reduce developing time as much as possible without you wasting time re-thinking something that is already built in the application.

The problem is that to know if you can reuse effectively, you need to know the code-base. If the methods are 100 lines long with high cyclomatic complexity values, chances are that they are very tied to specific use cases and the business logic is scattered across the sources without the necessary modularization. Let’s say you agree to work on this project by just re-using the existing classes and hoping everything will be smooth and easy. The reality is that to avoid to reinvent that wheel you’re now forced to add even more conditionals, follow convoluted paths and potentially breaking other use cases (especially for low test coverages).

What happened? The new feature could potentially take twice as necessary to pay for those wheels that were not reinvented. Second: the wheels are now more tangled than before and exponentially more complicated. The solution is not of course to re-write the code (even though you might be forced to if the situation is desperate) but to apply the legacy code workflow (cover with tests, extract logic, refactor). If your boss fails to understand that the price to not reinvent the wheel is way higher than extending well crafted software, then the project is doomed. This seems often the case for startups with the need to monetize as fast as possible and sell the mess right after. By the way, why do you think your car repair shop wants to call you back to give you an estimate about the damage of you car before moving forward?

Let’s say you explain the danger of accumulating technical debt to your boss. You shouldn’t be tempted to consider copy-pasting a faster alternative to deal with the mess. Reuse by copy-pasting is possibly more exponentially dangerous than spreading conditionals across the code. It’s just a matter of days that you’ll find your self fixing the previous use case forgetting about the copy-pasted-changed added functionality. Seriously bad idea.

Conclusions

So the next time you’re asked to not reinvent the wheel, instead of blindingly accept on the spot because you totally agree, you have to know what the current state of the code is and only after that you can give an informed answer and a meaningful estimate.

Comments (View)