(no title)
jsdalton | 2 years ago
Decouple users stories (customer/product outcomes) from tasks (units of work needed to achieve those outcomes). Jira is designed pretty well for this, since you can have sub tasks attached to user stories.
This works better when your user stories _are_ actually defining outcomes -- for example when you have stories like "User admins can filter jobs by category" and not "Build a category filter for the job search." The first can usually be successfully defined by a few acceptance criteria, whereas the second starts to get weird since you're focus is more on what it will take to build the thing vs. what is the result you want your customer to see.
With your outcome defined in the story you can define any number of implementation tasks it will take to achieve it. If you're a cross-functional team and you do "vertical" instead of "horizontal" splitting then you're sure to have a few coding tasks on the front end ("add the filter component to the search bar", "update the backend client to pass the category id as a query parameter") as well as a few on the backend ("update the API to accept the category parameter", "add the category param to the repository query service"). You probably have some non technical tasks too ("update the help documentation", "update the OpenAPI spec").
We almost never (save for absolutely trivial user stories) have a PR attached to the story but instead have PRs attached to sub tasks. If you're doing trunk based development with continuous deployment and feature flags, you can and should be shipping many PRs. Just yesterday I was in the middle of a task at the end of the day and decided to cut the PR where I was and split the task in two on the fly, since it was easier for me to ship the code like that and easier for my team to review it.
We do story grooming and estimation and all that -- but only for user stories. Tasks are the domain of the humans doing the work and they are meant to be flexible and even disposable. We usually have a session at the start of work on the user story when the engineers working on it align on the solution and then break the work down in to sub tasks, but these naturally evolve as the work progresses. I should had that multiple tasks invite collaboration instead of one story per engineer.
Lastly, I've found you have to preach the virtues of small PRs to your team and usually convert a few stragglers who don't see the value. I try to practice what I preach (i.e. by keeping my own PRs small) and also make a big deal out of it in retrospectives -- i.e. point out how painful the review process is with large PRs, usually entailing many rounds of comments and changes -- so that people quickly become believers if they are not already.
As a last point I try to encourage the value of "PR reviews are your top priority at any given moment" since every second a piece of code sits unreviewed adds to your team's cost of delay. There's a virtuous cycle here where smaller PRs lead to less painful code reviews lead to greater willingness to spend 10 minutes (vs. an hour) doing a code review, which helps really get PRs moving through.
I think PR stacking is great but I also find it's not as important if your PRs are getting reviewed and approved faster than you can write the code for your next PR.
(I didn't realize I'd write so much here, I forget that it's actually kind of a big topic that's built on a variety of different practices that all start coming together at some point when you get in a groove.)
tunesmith|2 years ago
jsdalton|2 years ago
Essentially you’re decoupling release from development here. This supports any number of QA practices. (We don’t have dedicated QA at the moment and instead have a biweekly “mob QA” session where we do a group deep dive into our current work.) We will capture most small fixes and improvements as sub tasks on the appropriate story (or file a bug ticket if the story was already done and we discovered a new issue.)
As a result of the above we don’t use long lived feature branches which become painful and slow, process wise. We just merge immediately after review. (Unmentioned but this is of course supported by automated testing and continuous deployment.)