Photo by Federico Beccari on Unsplash

Owning features, and how to deliver in an organized way

RoxSWEngineering
CodeX
Published in
8 min readApr 9, 2022

--

Agile software engineering has become the top way of working in the industry in the last many years, and we love it. We can call it sprints or iterations, but the mission is the same — plan, deliver, reflect, and start again. We can deliver faster, we can get to the coding faster and the processes are shorter, awesome right? So why is it that sometimes we can feel like we are “floating” along with the sprint, or that many sprints pass and we do not feel like we have delivered on the feature we wanted?

The answer is not simple, as it can involve many factors that influence how a team is delivering, but what I would like to focus on, is what can make us, software engineers, work effective and organized in an agile setup, and drive those features to completion.

Own it

One of the steps in the software engineer career development, is driving and owning features. To own a feature means that you are in the driver seat (almost) from start to end, and this comes with a lot of responsibility, but also a lot of freedom in the way we choose to approach this. A feature needs grooming, an execution plan (how will we implement this), testing and understanding the acceptance criteria, finally deploying and some more validation testing.

Feature ownership is a great step to take in the software engineer career, but it is also a learning process, and there are some bumps on the road. Some of the bumps which can be seen are the following: “take and disappear” or “getting lost in the scope”.

Take and disappear means that there is only one person implementing this, but the person does not share any details around implementation approach, or visible progress (on any kind of agile board). It can end up with one very long code review, which will take time to complete.

Getting lost in the scope means that while our mission is to go from A to B, we either got distracted with “what about C?” or with “oh I should probably also do this, and this ANNND this!”

I found myself doing both. Remember, there is a learning curve, so for this reason I would like to share my personal toolbox for working efficient in an agile setup (and yes owning those features!)

It is important to remember that this is a process, a process that took me 3 years to master my approach to, and while not all tips work perfectly in all situations, those are still good tips I would share with anyone seeking to find their way into mastering feature ownership.

Be clear on the scope of the feature — align expectations

Have you ever worked really hard on a feature, tried your absolute best to deliver, delivered the feature, was super happy about it and then got the feedback of: “the feature was not done done”… well, I have! At the time, I got very sad over this feedback, to be fair none of the features given to me had any description… But this is when I realized, description and aligning of expectations is very important, and if there isn’t one, I will make sure there is one.

Since this piece of feedback, any tickets I executed on had a description. Stories or bigger tasks had not only description, but also what we would like to achieve and ideally some acceptance criteria.

The importance of aligning expectations will not only make us more efficient, but it will ensure that we deliver the right things, and that we scope the piece of work needed to be done. This will also ensure that one has the right understanding of the feature, and will reduce the possibility of getting lost in the scope delivering too much or too little.

Research — Slowing down in order to speed up!

So we have the feature, we are the owners of that feature, great, now let’s code! Well not so fast…

This connects to the feature description, as in order to answer some questions and write that description we need to research. Often, features might have already come with description, the question is: do we fully understand it?

Research goes into the domain, but it also goes into the technical aspects.

When researching the domain, we need to make sure that we understand what is it that we expect from the feature, and this can be done by asking questions, taking notes or writing acceptance criteria. This process will also give a strong hint of what domain functionality we need to test in order to make sure the results are correct.

With researching into the technical aspects, we create an idea around how are we going to approach this. Sometimes it helps using diagrams in order to describe the aspects we are exploring, but also discovering any kind of obvious issues we might face. A good example is doing sequence diagrams, just writing down function names, where those are invoked in the code, and where would those call, one can find a missing integration, a functionality that needs more exploring, or just being aware that some parts might just take a bit longer.

Break down things into smaller tasks

Divide and conquer. This is, by far, the best practice that I have in my toolbox.

Breaking things down into smaller tasks, really gathers all the work done in the previous points, and puts it into actionable items. It shows that the person executing on the feature has a plan, an understanding of what they need to solve and how are they going to approach it.

This is where software engineers really get effective, as the road from A to B is not something to be figured out on the way, but it is more clear how to get there, and less of a chance to get lost in the scope.

It gives visibility not only on how big or small something is, but also around progress. If the person misses a daily meeting, the status of the feature they are driving is clear to everyone.

Smaller tasks means smaller testable units and faster code reviews.

Remember, that if a feature is to be worked on by multiple people, it is important to not only align, but also add description to those smaller tasks as well.

Note number 1 — This practice is very useful, but not all features or tasks that we do are the same. Remember that the mission is to have a plan, and the plan does not have to be perfect. By trying to use this in different kinds of situations, we can actually improve our approach, and learn something about ourselves and how do we like to work.

Note number 2 — When pair programming, we can skip breaking things down in a way, but I would highly recommend using a checklist of the things that need to be done. It help keep the collaboration on track, and knowing where to continue after a well deserved break.

Know your unknowns

Having unknowns is very normal in software development, this is why estimating something to perfection is impossible. Usually we would start executing on something with maybe 70–80% confidence of what we know, but it is important to discuss and reflect on what we don’t know and how might it impact the development.

Make sure to make a note, raise this as soon as it surfaces, and try to think what suggestions can be made to address this.

Not all unknowns are solvable, but documenting them and the assumptions/agreements we made, is valuable.

Blocked? Not always a problem…

So what happens if we get blocked? It can happen, in some cases it can be resolved and in others we just need to wait.

So let’s focus on the cases which we can resolve, and not just wait if we can do something about it.

The most common reason I have encountered of why people wait when something can be done, is the “API is not ready” situation. In this situation, we either wait on a team to develop an endpoint, or modify the returned response with something new, any of those cases can be resolve by a very simple thing: collaboration.

Align with the team, explore their contract, and just mock it for now, if an agreement on a contract is made, or at least to some degree, we can continue working on the feature, and thanks to tests, converting the mock into the “real” system should not be too hard.

This can be abstracted into a bigger idea: if I am blocked, is there anything I can do, anyone to align with, in order to work in parallel? Do not wait if something reasonable can be done, remember “floating around the sprint”, yup that is one of those situations.

One important note on this — if a system is mocked, then feature is not “done done”, this means that the scope might need to change, and a follow up task should be made. Be visible about this, as it can send the wrong impression that something is done, when it is not.

Forgot something? Create a buffer task

This is one of my favorite, the fit & finish task. This is a task that acts like a buffer, I would usually accumulate small, but needed things to be done that might not fit in the context of one or another code review.

Any comments that pop in the review that might not directly related to the solution, but to coding style which can impact more than the context one is working on, I would always add it to fit & finish.

This can also be for wrapping up things, maybe doing some housekeeping on the code, or adding that one last test you forgot about.

It is a great place to document all the little things we find while we develop, and make sure we have time to solve them.

Software engineering is a beautiful field to work in, as one learns something new every day, but if we look beyond the technical aspects, it is also an amazing field to discover and align on: how do I approach different problems? How do I collaborate and make my work visible? It is rarely today, that we get 2 tasks that are just the same, but the principles we apply to solve them can still be the same. With time we grow and understand: how am I most efficient, in a collaborative and agile working setup?

The 3 year time period (2014–2017), which was my learning process on all of the above, was a big part in shaping the engineer I am today, and for that I am thankful. I still learn, grow and discover every day.

--

--

RoxSWEngineering
CodeX
Writer for

Software Engineer, been in the industry for 10 years and was lucky enough to work for some of the biggest tech companies in the world.