4 ms·
Yes! I agree with you mostly, except that we try to keep from having junior developers for too long. Nobody is really a junior developer, and everyone should g
by yebyen 8y ago
Yes! I agree with you mostly, except that we try to keep from having junior developers for too long. Nobody is really a junior developer, and everyone should get a turn as release manager. The main benefit of this is that people can see directly how their work style impacts the release engineering process, if they do know exactly what that process involves and actually get a turn at it. (You have to stub your own toe in order to know how bad it hurts.)
Our team is actually really small, and we like to make sure everyone knows about the hassles involved in putting together a release and doing a complete code review when it's needed. The main reason I encourage rebasing is because it helps avoid a messy graph, and a messy graph makes it immediately much harder to do a rebase across any number of merges, or any non-trivial span of time.
So in other words, I like to selfishly expect the other developers on my team to do rebases at the appropriate times, in order to preserve my own capability to easily do rebases when needed. (We also learned last week that git rebase has a --preserve-merges option that I feel foolish to not have known about sooner. We've wiped out so many merge commits unnecessarily.)
We treat the master branch as carved in stone like anyone should, but other branches should clearly flow their merges only one way (features into releases, or features into environments), and if a branch hasn't actually been included in a release tag, it's considered fair game for rebasing. It helps us to prevent our three developers' sometimes too many concurrent trains of thought from resulting in equally too many confusing merges, or an intractable number of HEADs to manage and organize into releases.
One of the places we struggle is that we're not all-the-way onboard with CI/CD processes, but we do the best we can so that whenever support for that kind of thing materializes, we will mostly not need to change our processes at all and can obtain the benefits of that kind of tooling as quickly as possible.
- WorldMaker 8y ago> other branches should clearly flow their merges only one way I tend to disagree on this as well. The best person to merge a conflict is the developer creating the conflict in the first place, as soon or nearly as soon as they create the conflict, because they are most likely to know why the conflict exists in the first place. "Merge early, merge often." Delaying "reverse" merges until the last possible second means you often don't have the integration expertise needed without research involved, even if it was "you" that introduced the conflict you may have moved on to other problems since and not recall why you did something one way or another, or which bits are important to integrate. Delaying those merges as rebases I feel is even worse, because not only do you not have the resources to know why an integration needs to be made, you also aren't recording a history of the merge conflicts you saw in the rebase such that you can easily revisit the integration if you made an integration mistake (which does happen, because we are, after all, only human). My advice tends to be to use a good PR system of some sort that makes your proper, code reviewed "forward" merges clear and obvious, and then don't worry about a mess of other merges "underneath" that top-level of strong PR merges. (Hence the key suggestion is that `git log --first-parent` is your best friend if you want a "clean" view of the DAG. It gives you a linear list of just your PR merges in master, or branch work and PR merges to that branch in any other branch.) Also, yes, CI/CD are really good ideas.
- yebyen 8y ago> you also aren't recording a history of the merge conflicts you saw in the rebase This is a good point. Mistakes are made during merge conflict resolution. But if you are tracking your upstream when you develop a long-lived feature branch, and rebasing when there are changes to the base, and actually comparing your rebased feature branches to the version that you had before you force push over the old remote version, then the only thing you really need to track is "does my diff still look like the change I intended to make." The most valuable skill we are learning from Git is how to avoid merge conflicts altogether, and it tends to be more a human problem than a technological issue. (You don't avoid merge conflicts with some special commit strategy, you do it by ensuring that two people are not actively changing the same part of the codebase unless it's absolutely necessary.)
- WorldMaker 8y agoI still think you are better off preserving every merge point-in-time when they were made than ever rebasing feature branches. Because yes, every rebase is an opportunity for mistakes to go unnoticed, and there's no "rebase log" to try to unwind a mistake weeks or months later. Also, every rebased branch is its own likely source of merge conflicts for people working on "differently rebased" versions of the same code. > The most valuable skill we are learning from Git is how to avoid merge conflicts altogether, and it tends to be more a human problem than a technological issue. (You don't avoid merge conflicts with some special commit strategy, you do it by ensuring that two people are not actively changing the same part of the codebase unless it's absolutely necessary.) Definitely. Communication is a key. It's also why I think "merge early, merge often" works better, because it forces communication as early and often as possible ("I'm seeing a merge conflict with this work you are doing, can you explain it to me?"). Keep branches as short-lived as possible, and try to avoid "separate but equal" work where you can't comingle features and have to intentionally fence your branches from integrating with each other. Merge feature branches between each other, even, to keep communication up. Find tools like feature flags that allow you to "ship" to master "unfinished" work faster to save yourself from trying to integrate long running branches after the fact. (If you are going to let "marketing" choose which features "ship" in a version, it is much nicer to do so by flipping flags in a dashboard somewhere, maybe even one Marketing can use themselves, than to try to furiously merge long-running feature branches at release time.)