Monday, 15 June 2020

Gone Are The Days Of Vertically Sliced Stories


While working in an agile development team be it any role Business Analyst, Scrum Master, Product Owner or even Developer, we all would have heard how and why user stories must be vertically sliced. Wikipedia describes a vertical slice as: 
 

 “... a cross-sectional slice through the layers that form the structure of the software codebase. For example, a simple vertical slice would encompass the data access layer, the business logic layer, and the user interface layer”.       Below is the diagram we’ve seen with this definition, where the story is sliced vertically across different layers of the application. 


This was true a few years back when multiple services and the UI layer were deployed as a single artifact and, most of the time, developed by a single team. But with microservices architecture and an increase in the number of channels that an API can be consumed by, having a vertically sliced story from persistence to the UI layer is impossible

Let's look at an example of a video streaming service. Let’s call it Binging. In the past, to display the average ratings for videos we would have written this story:

As a user of Binging
I want to see the average rating for each video
So that I can decide which video to watch.

This story would have needed to cover pulling the ratings from the database, calculating the average, and displaying it on the UI. But, in the current world, we don’t know which channels are going to display ratings and in which format. For example, how the ratings are displayed on the web will be different from how they are displayed on the Roku app and the android app might not even display the ratings. 

Let's go a little deeper into this example. The high-level architecture of Binging service would look something like this:



And the team structure would replicate the above architecture:




Hence, it is impossible to have that one story to display the average ratings for the videos. We will have to have one story for the “Ratings” service and one for each channel consuming that service. Following are some of the examples:
 
  1. As a consumer of Ratings service
    I want to get the average rating for the list of videos
    So that I can display it to my users
  2. As a user of Binging Roku app
    I want to see the average rating for all the videos
    So that I can decide which video to watch
  3. As a user of Binging website
    I want to see the average rating for a particular video
    So that I can compare it with other videos 

The question here will be, are we increasing the effort and time to deliver the feature of displaying the average ratings? 

I would say no because the number of channels that the ratings are now displayed on has increased. Plus, we’ve got the flexibility of displaying ratings in different formats on different channels. For example, the ratings on the Roku app can be displayed with the listing of videos. But, on the website, the ratings can be displayed on the video details page. Along with this flexibility of the display, it also reduces the new feature rollout time. For example, “Sort by Ratings” can be quickly added on any channel without making any changes to the “Ratings” service.

Additionally, the “Ratings” service can be consumed for analytics, reporting, market research, etc. For example, we can answer questions like ‘which are the highest rated videos?’, ‘which videos are rated high by which demographics?’ and  ‘which videos are rated high or low in which countries?’. These questions can be answered by the “Ratings” service without impacting any of the channels.

To summarise, the concept of vertically sliced stories is still valid, but the size of the slice has changed. If we consider each channel and microservice as a product, then stories within those products must be vertically sliced. As in the above example, the story in Ratings service will pull all the ratings from the data store, calculate the average, and emit the average rating for a given video or list of videos. The story for the web channel will make a call to Ratings service and display the average rating for each video in an intuitive and user-friendly format.   

Each of these stories is vertically sliced, providing a business value of its own and can be tested and deployed independently. 

One important thing here to remember is that all the PODs should understand and agree on their Product Boundaries. This will help in the end to end feature prioritization and planning. It will be slightly difficult and challenging when you are starting to move from a monolithic application to Microservices architecture but once all the PODs understand the responsibilities of their respective products, it becomes business as usual.



In the days of the monolithic applications, vertically sliced stories were compared to the above slice of cake, where no one would like to have horizontal layers of a cake. One would prefer to eat a vertical slice with all the layers. But with the evolution of microservices platforms and increasing channels, we will have to think differently, like providing the cake base, frosting, whipped cream and sprinkles separately so that we can serve

cupcakes...


Or ice cream sundaes..

 
Or a completely new dessert to our customers...


Tuesday, 12 August 2014

Pairing -- Effective tool for quality software

Pair programming or pairing in short is one of the many practices followed in agile software development where two people work together on the same piece of code. Usually a user story or a task is assigned to a pair of developers and they work together on its implementation on a single machine. One person is the driver who types the code and other is the navigator. There is no rule on who is the driver and who is the navigator but they should rotate roles frequently. 


Perks of pairing

  1. Code quality:- 

    When two people are trying to solve the same problem, they bring in their individual experiences and different approach to solve the problem. They question each other, discuss the details, brainstorm and then arrive at the best solution. This definitely improves the design and code quality as compared to an individual working alone.  A study has revealed that the code resulted out of pair programming has around 15% to 20% less defects than the code written by an individual.
  2. Individual learning:- 

    There is constant knowledge sharing happening while pairing. Pairs learn a great deal from each other, right from smaller keyboard shortcuts to design patterns there is a constant learning happening. Most of the time when two people pair, one is an expert in one area and other in another. For example, one person is a java script guru while other is  nosql expert and eventually when they pair they shower their blessings on each other.
  3. Elimination of human errors:-

    There are two pairs of eyes constantly looking at the code which eliminates human errors and silly mistakes are caught while programming. There is no scope of a person being lazy and taking shortcuts because there is another person sitting next to to him/her reviewing the code all the time.
  4. No knowledge pockets or dependencies created:-

    There is no dependency created on a single person. Every functionality is being implemented by a pair and with frequent pair rotations almost everyone in the team would have a fair idea of everything. There are no knowledge pockets created hence there is no need for a full fledged KT plan if a person is rolling off the project or leaving the organization.  There are definitely some module experts but continuously pairing with them spreads the knowledge across and pairing in itself is the best way of doing knowledge transfer.
  5. Increased productive time:- 

    People avoid unnecessary meetings and calls because they know their pair is waiting for them.  People are not usually pulled into distracting conversations if they are pairing which otherwise they would have. People don't waste time on social media, gaming or chatting while pairing but they still have someone to talk to in person all the time. It is being observed that people spend more productive hours while pairing rather than working alone. Along with this there is no dedicated time required for code review because as people pair they also review.

What pairing is not?

Many people/organizations have some misconception about pairing. Pairing is not where
  • one person implements and other reviews the code. 
  • two people distribute tasks among themselves and work individually.  
  • one person implements and explains the code and the other person listens.  
Pairing is where two people work simultaneously on the same piece of code where one is typing and other is reviewing and they switch roles frequently. Pairing is done on a single work station often known as a pairing machine.  Person who types the code is the driver and the one who reviews is the navigator and they switch roles frequently by taking the keyboard control. There is no rule on when to switch roles but it is advisable to switch on a logical break point. It is also recommended in one of the articles that not one person should not drive for more than 20 minutes. But again as I mentioned there is no hard and fast rule as long as people are switching roles.

Effective pairing combinations

To get maximum out of pairing, it is very important to have a proper pairing combination. It is advisable that an experienced developer pairs with a novice developer. This enhances the learning curve for the novice developer and provides mentoring opportunities for the experienced person. But then the experienced person should rotate pairs with someone who is more experienced than  him/her so that he/she also gets to learn and he/she is questioned and challenged enough. Sometimes it is also important that a novice person pairs with someone with same experience and similar skill set. This helps them explore more rather than just listening to the mentor. Hence, all the three pairing combinations are effective when used appropriately:-
Expert pairing with novice:- Most effective and most recommended.
Expert pairing with expert:- Most productive for complex features but an overkill for simple functionality.
Novice pairing with novice:- Advisable for simpler implementations with more learning space.

Pair Rotations:-  

One important aspect of pairing is frequent pair rotation. One person should not keep pairing with the same person for a long time. There is no defined time on when the pairs should rotate but it is always advisable at a logical point in the story or the functionality. Sometimes the stories are so small that the same pair can finish it but then ensure that they don't pair for the next story.  With proper pair rotations almost everyone in the team gets to work on the functionality and gets some idea around the code.

Who can pair? 

Developers pairing with developers is common and that is what pair programing is all about. Sometimes it is advisable for QAs to pair with each other while testing a complex module or automating functional tests. But along with this, some cross functional pairing is also very important and useful for delivering quality software.
  1. Developers pairing with QAs:-

    Developers can pair with QAs while writing unit and integration tests. QAs can help developers in terms of scenarios to be covered at unit and integration level. Also QAs get a hang of what is already covered at unit level so that they don't repeat the same scenarios during functional testing.
    Also, developers and QAs can pair while automating functional test (UI driven). Specially when there is a framework to be built for functional automation, developers can utilize their programming expertise and pair with QAs for initial implementation and then QAs can enhance there onwards.
  2. Developers pairing with BAs:-

    Some stories require some amount of technical analysis and at such situations BAs should pair with developers. BAs and developers pairing help BAs to understand the technical implications and feasibility of an application whereas developers come to know which way the requirements are going so that he/she can start thinking about the implementation in the same direction. BAs and developers pairing help in eliminating most of the last minute surprises.

  3. QAs pairing with BAs:-

    BAs and QAs should pair while writing acceptance criteria for a story and also while designing test cases. QA mindset of breaking the application can help BAs to come up with the negative acceptance criteria. While BAs can help QAs to understand the business relevance and prioritization of test cases based on business value.

    People might find pairing costly but it is definitely way cheaper than fixing  production defects and sometimes even bringing the system down. It is like saying I cannot afford insulating the wires but I can bear the consequences of an electric shock.

     

Thursday, 7 August 2014

Faster Waterfall is not Agile

Most of the organizations have a myth that if they have shorter release cycles they are agile. And at most times they don’t even follow basic agile principles. There is a general misunderstanding among organizations that they are agile if :-
  • They have shorter release cycles
  • They don’t document
  • They don’t plan upfront
  • Their requirements change frequently
  • They do daily stand ups
Hence as part of this post I would throw some light on what is an actual agile world and how a software is delivered in quick releases by following agile practices like Continuous Integration, Dev box testing, client showcase, etc.

Most of us are aware of the agile manifesto which talks about :-
  • Individuals and interactions over Processes and tools
  • Working software over Comprehensive documentation
  • Customer collaboration over Contract negotiation
  • Responding to change over Following a plan
But how to achieve these on a project on a day to day basis is a challenge. Here are the few practices that would help you follow these agile principles and enable you to successfully adopt agile :-

Individuals and Interactions over Processes and tools:-  

  • Instead of  requirement gathering sessions that lasts for around two months, do shorter project inceptions for a week or two. 
  • Rather than Tech Lead estimating on behalf of everyone, involve the entire team in estimation.
  • Practice pairing instead of tech leads and managers reviewing code.
  • Conduct retrospectives rather than doing individual performance reviews.

Working software over Comprehensive documentation:-

  •  Document requirements in smaller chunks as user stories vs heavy requirement specifications.
  •  Do regular Dev Huddles rather than documenting technical designs.
  •  Have a good automated test coverage instead of documenting test scenarios with detailed steps. 
  • Make QAs do testing on a developer box to get early feedback rather than publishing release notes to them
  • Have user friendly and responsive design instead of heavily documented user manuals.

Customer collaboration over Contract negotiation:-

  • Rather than asking customer to review heavy requirement specs get their feedback and sign off on user stories
  • Instead of waiting till the end for a complete product demo keep doing story showcase and keep getting regular customer feedback
  • If there is a bad news like technical complexities, unknown discovered or any other blockers share it with customers as soon as possible rather than giving last minute surprises.

 Responding to change over Following a plan:-


  • Instead of having a dedicated design phase and having a complete design upfront let your design evolve along with the product.
  • Rather than having a full fledged product/project plan, plan in smaller chunks for an iteration or a sprint.
  • Instead of manager deciding who does what and assigning tasks to the team let the team do a daily sign up and decide what they want to work on.
  • Implement product feedback regularly rather than creating product backlogs.

According to me a successful agile project should achieve following 3 goals:-

I. Get early feedback and fail fast:-

  • Customer involvement:- Involve customer and get their feedback on every stage - inception, story sign off, story showcase, super showcase.
  • Continuous testing feedback:- Get testing feedback and defects identification at unit and integration tests level, dev box testing, build, smoke, regression. Earlier the failure easier the fix.

II. Easily adopt to new requirements and give your clients agility:-


  • Early feedback and Adaptability:- Getting feedback from clients at every stage helps clients to be flexible. Changes can be easily incorporated as they are requested at the start of the cycle.
  • Product Vision:- Clients can see the product evolve and hence can come up with better ideas for the short and the long term vision.

III. Improve quality of the product and yet deliver faster:-

  • Improve Quality:- With so many checks and safety nets at every stage, the product becomes stable and of a high quality.
  • Faster delivery:- Practices like continuous integration, test automation, etc. helps in reducing the cycle time.

A quality software which is delivered at a faster and regular releases and is easy to incorporate changes and keeps the team happy and customers satisfied, determines the success of agile.