News for hackers. Stuff that matters.
Re:Idiot Proof Git by danpalmer on Wednesday November 09, 2022 @09:56AM (#33532432)
Big fan of Git style guides in teams. We had one at Thread. It was common for engineers to come in and find we didn't do rebasing and find it weird, but we took the opinion that history should be exactly what you actually did, not some clean and idealised version of what you wish you had done. There are advantages and disadvantages to this, but having a defined approach was the most important aspect.

Also the fact that we didn't rebase and used merges everywhere was a major contributor to no one ever breaking their git repos, something that git seems notorious for elsewhere.

Re:Idiot Proof Git by idop on Wednesday November 09, 2022 @10:10AM (#33532665)
Obviously what works for you works for you, but I respectfully disagree with everything you said.

The "history should be exactly what you did" argument - which many people make - is really funny to me because a pull/merge-only strategy only preserves the _wrong_ history. As a tech lead, for example, I absolutely do not care one bit about the date of a commit, or when the developer started working on it, or what was the commit they started working on top of. That may be "what really happened", but it's worth nothing in the grand scheme of things. When a commit _has made it into the product_ is the only " what really happened" there is, and that is what I care about. And a linear history makes this much easier to analyze and understand, reducing cognitive load considerably.

Also, it's strange that you see merges as a contributor to keeping repos from breaking, as my experience is the opposite.

I advocate for a rebase-based strategy wherever I go as it helps developers push better code, it actually curbs hysteria-driven "merge it as fast as possible no matter how shit it is" cases, and I see how it turns the Git log into an actually useful source of information for developers and other personas. People start reading the logs!

The log should track the product's evolution, not the developers' activities.

Re:Idiot Proof Git by dec0dedab0de on Wednesday November 09, 2022 @10:24AM (#33532883)
The log should track the product's evolution, not the developers' activities.

Git is a development tool, not a product release tool. If you want to see the product evolution you could filter to just merge commits, or just merge commits in a specific format.

If you want to keep track of releases specifically, then use tags, that's what they're for. I suppose you could make a separate branch/repo where every commit = a release, but that opens you up to merge conflicts without any benefit over tags

Re:Idiot Proof Git by idop on Wednesday November 09, 2022 @10:37AM (#33533087)
At the end of the day everything depends on the organization. In a hectic startup where requirements change on an hourly basis and releases are made several times a day, I would absolutely insist on keeping the log linear and as clear as possible. Tags are important, of course, but they're not that useful for analyzing a repository.

When I say "the evolution of the product" I really mean "the "evolution of the code". When a small feature branch with 5 commits - four of which say "wip" and the last one says "added color support" - gets merged as is, and all relevant information is held hostage by whatever Git platform the company is using this week and not inside the repository itself, the log is not useful to me regardless of any strategy.

But in a different setting I would not necessarily insist in the same way.

Re:Idiot Proof Git by dec0dedab0de on Wednesday November 09, 2022 @10:59AM (#33533465)
When I say "the evolution of the product" I really mean "the "evolution of the code". When a small feature branch with 5 commits - four of which say "wip" and the last one says "added color support" - gets merged as is, and all relevant information is held hostage by whatever Git platform the company is using this week and not inside the repository itself, the log is not useful to me regardless of any strategy.

Yes, it can be annoying if your developers are committing nonsense, but then just tell them to not do that, or to rebase locally before pushing.

If you find yourself troubleshooting a bunch of nonsense commits, you can just do a diff to the merge commit, and it will show you all the changes. But you also have the option of figuring out exactly which commit caused the problem, and seeing it in context. If I see an error in the middle of a bunch of commits that look like "trying x with y." Then I know that this is a tricky problem, and the developer was lucky to get it to work at all. If it is in the middle of a standard looking commit, then the developer didn't struggle with this. So maybe they didn't put enough effort into it, or maybe it is a rare corner case.

When I'm troubleshooting other peoples problems, every bit of information helps. Especially when the developer who introduced the problems is no longer with the company. Squashing commits removes some of that information, without providing anything that I can't approximate by using merge commits in logging/diffs.

Re:Idiot Proof Git by Quekid5 on Wednesday November 09, 2022 @11:41AM (#33534136)
> If I see an error in the middle of a bunch of commits that look like "trying x with y." Then I know that this is a tricky problem, and the developer was lucky to get it to work at all.

Just an aside, but if there problem being solved is harder than it looks then this deserves a comment explaining why in either the commit message or in the code itself.

Re:Idiot Proof Git by idop on Wednesday November 09, 2022 @11:11AM (#33533663)
To be clear, what I'm advocating for is that feature branches get rebased regularly by the developer until PR-time and a clean merge into the mainline. I usually recommend squashing to one commit but do not insist.

I can definitely see how those intermediate commits can provide more information, but there's a tradeoff. More often than not, they do not provide me much value, and instead give me bloat, so I prefer to keep things simple.

Telling developers not to do something is like telling a kid not to push that red button. The average developer chooses what's easiest _right now_ and thinks it's someone else's job to fix the mess at PR time. And they're afraid, because that one time five years ago they ran a rebase without knowing what it does, and lost some code without knowing it's actually right there in the reflog, and since then they are deathly afraid of Git. I know how to use log and diff and all the others quite well, but most don't. So I'm trying to make things easier on everyone in the long term, not the short term.

Re:Idiot Proof Git by P5fRxh5kUvp2th on Wednesday November 09, 2022 @07:16PM (#33540263)
"Why doesn't git bisect work?"

"well, it landed on this rebased commit that's huge. I guess it was a kind of useful, just not as useful as we'd like".

Re:Idiot Proof Git by firesloth on Wednesday November 09, 2022 @07:42PM (#33540541)
Haha, true! On the other hand, is that better or worse than running into a string of "wip" commits that had the code in a broken state.
Re:Idiot Proof Git by Dylan16807 on Wednesday November 09, 2022 @10:37PM (#33541885)
But if the alternative is that it's ten commits and most of them don't work anyway, the bisect takes longer to give you the same lousy information.
Re:Idiot Proof Git by P5fRxh5kUvp2th on Thursday November 10, 2022 @05:13AM (#33544488)
That's not the alternative, who develops like that?

It's like the first time I saw the essay calling ORM's the "vietnam of the software industry". I remember reading it and wondering who the hell would use ORM's in that manner?

Apparently a lot of people, but if you're using rebase because you don't know how to create commits that build and are functional then I submit the issue is with you.

Re:Idiot Proof Git by idop on Thursday November 10, 2022 @11:06AM (#33548468)
> That's not the alternative, who develops like that?

As an independent contractor working with many different companies, unfortunately, virtually everybody.

Re:Idiot Proof Git by firesloth on Wednesday November 09, 2022 @07:39PM (#33540511)
I've been recommending making a git tag before rebasing. eg:

  git tag -f pre-rebase
Re:Idiot Proof Git by krinchan on Wednesday November 09, 2022 @12:35PM (#33534995)

    git add .; and git commit --amend --no-edit; git push origin --force
Rarely, I have to do pipeline work on repositories. You'd normally see twenty "Fix Jankins Issue" commits on the main branch because of some nonsense that only happens when you deploy UAT or whatever. Once I learned this little gem, this is also how I manage my feature branches mostly. But also my employer's fleet of laptops has been aging and I've had to do 3 swap outs this year, so I like to keep my in progress work pushed up just in case.
Re:Idiot Proof Git by sixstringtheory on Wednesday November 09, 2022 @01:29PM (#33535839)
I did this for a while but have moved on to

    git commit --fixup HEAD
and you can tack an -e on the end to add more notes in the commit message body. You can fixup prior commits by supplying their short hash, which is how I originally discovered this: I essentially wanted to amend a commit farther back in my branch.

This makes a commit with a “fixup!” prefix that works with

    git rebase --interactive --autosquash
you can also form that kind of commit directly, and there is also a “squash!” directive. Now you don’t have to force push amended commits. And it helps sometimes when you accidentally amend something you didn’t mean to–now you can just soft reset to HEAD~1 and try again.

I don’t even bother locally rebasing to autosquash it all anymore since we use squash-to-merge/rebase in github PRs now.

Re:Idiot Proof Git by firesloth on Wednesday November 09, 2022 @07:30PM (#33540423)
I did something very similar with a bash function:

  function git-commit-fixup() {
    git commit --fixup ":/$*"
  }
  alias gcf="git-commit-fixup"
  # Looks for the most recent commit that matches its arg
  # eg: we have three commits with messages: 
  #   "fix: the thing" 
  #   "feat: 5 percent cooler"
  #   "test: test coolness"
  # then we do some work and git add, then do:
  gcf cooler"
  # now we have 4 commits: "
  #   "fix: the thing" 
  #   "feat: 5 percent cooler"
  #   "test: test coolness"
  #   "fixup! feat: 5 percent cooler"
  # And autosquash will combine the fixup commit with the appropriate semantic commit as you say.
Sadly I've stopped using it as someone introduced a bunch of commit lint git hooks that choke horribly on the "fixup!" part. And you can't pass --no-verify while rebasing.
Re:Idiot Proof Git by tkot on Wednesday November 09, 2022 @04:31PM (#33538168)
I'd probably suggest --force-with-lease just to be sure ;)
Re:Idiot Proof Git by firesloth on Wednesday November 09, 2022 @07:36PM (#33540494)
Me too. I made an alias that was _shorter_ than --force to make it easier to type (and hence more likely for me to use by default).
Re:Idiot Proof Git by tremon on Wednesday November 09, 2022 @05:41PM (#33539119)
git add .

We have had multiple security incidents because some developer left a credential file inside the local git clone (no, not all tooling supports out-of-tree stored credential). Blind 'git add .' is the first thing I teach my developers not to do.

Re:Idiot Proof Git by ratorx on Wednesday November 09, 2022 @08:16PM (#33540861)
git add . is very useful though. Surely, the first thing to teach here is to always git status before committing?

My typical workflow is to git add . to see the mess I’ve made then decide how to clean it up. If I’ve mistakenly added a credentials file, the fix is to add it to the gitignore and unstage it, not JUST unstage it.

Not saying that you shouldn’t do both, but maintaining a gitignore and completely removing the potential problem for other people seems better than pretending your tool is more limited than it is.

Re:Idiot Proof Git by notpushkin on Thursday November 10, 2022 @02:31AM (#33543357)
If you can tolerate a GUI, Git Cola might be a solution. I'm using it exclusively for some 5 years now – it's lightweight enough, but still makes you think about what you're about to commit. You can add things to .gitignore directly from there, too.

https://git-cola.github.io/

Default layout is a bit weird IMO, here's what I'm doing instead: https://u.ale.sh/my-git-cola-screenshot.png

Re:Idiot Proof Git by krinchan on Thursday November 10, 2022 @09:43AM (#33547145)
You don't use .gitignore? All our projects use dotenv for local credentials with a .gitignore that covers build, log, and any *.env file.

Sounds like you need better tooling, tbh.

Re:Idiot Proof Git by ernestns on Tuesday November 15, 2022 @10:49AM (#33610655)
You can combine

  git add .; git commit --amend --no-edit;
with the `-a` option

  git -a --amend --no-edit;
Re:Idiot Proof Git by xenomachina on Wednesday November 09, 2022 @01:25PM (#33535792)
> Yes, it can be annoying if your developers are committing nonsense, but then just tell them to not do that, or to rebase locally before pushing.

I'm pretty sure rebasing locally is exactly what the person you're arguing with is arguing for. The original comment in this thread was saying you should never rebase, always just merge.

Re:Idiot Proof Git by mixmastamyk on Wednesday November 09, 2022 @02:50PM (#33536915)
> feature branch with 5 commits - four of which say "wip"

Merge+squash eliminates this and it works every time. One or two clicks on gitlab for example.

Re:Idiot Proof Git by smaudet on Wednesday November 09, 2022 @10:56AM (#33533429)
Actually you're both wrong, its a change tool, not a development or a product release tool.

"then use tags, that's what they're for"

No they're not - that's definitely a useful way of using them, but they are just labels.

Why is it useful to know this? Well, when you know your tool better (how it operates, not the porcelain or CLI), you have better insights and are able to use it better.

You can manage Agile-style "features" with nothing but hashes and tags, no branches necessary. Branches are actually somewhat antithetical to distributed development, they're a useful concept, but that's all they are.

I do tend to agree though, re-base is superior to merge, in a product setting. If you want to track a feature set, having the set of commits which represents that feature set is better than a litany of nonsense tangled up in twelve feature "roots" (branches which have been merged together).

In a "do what I want" setting, rebase and merge are about equal, though. If I want to work on 3 features independently, I'd like to be able to easily see both features in parallel. I also would like to squash my features to single commits, and rebase them into feature branches where I can then merge/rebase/whatever those into my final "product" branch.

Re:Idiot Proof Git by copperx on Wednesday November 09, 2022 @06:54PM (#33539987)
> Actually you're both wrong, its a change tool, not a development or a product release tool.

It's funny that HN can't agree on what Git is.

Re:Idiot Proof Git by idop on Thursday November 10, 2022 @11:12AM (#33548591)
If you ask me: a low-level SCM framework.
Re:Idiot Proof Git by idop on Wednesday November 09, 2022 @10:17AM (#33532777)
Also, keep on mind that Git is the engine with which Continuous Integration is made. CI is developers integrating with the work of one another on a regular basis. If the product changed since you started working on your new brach, then your branch is stale and you need to integrate with the recent changes. Why wait until you're done to find out that your branch can't be merged anymore and you have to make a ton of changes when you can keep on top of things at regular intervals and make the final merge as easy as possible, not just for you, but for the code reviewers, the QA guys, the DevOps guys, everyone.
Re:Idiot Proof Git by hinkley on Wednesday November 09, 2022 @10:33AM (#33533025)
Usually my strategy, but it breaks down if you have someone who is bad enough at merge conflict resolution. We had one guy Steve who was upset that he was not as in charge as he wants to be, but he was doing a few things that break my trust so we are keeping him on a shorter leash than he likes. His code and ideas are okay but not great. He’s picking on this guy Mark, who sat next to me, to make himself look more valuable. Mark was not the brightest senior dev I ever worked with but he had his uses, and I hate bullies. Last but not least he was that he was terrible at merges and his solution to this problem was to delay as long as possible. We are a full CI environment and he’s making work for others by doing this. Namely me. None of these are conducive to me giving out a lot of responsibility, so he has some but not what he was after.

One day he’s blaming Mark for a regression in the code. Being pretty loud about it in fact. When I look at the bug, it sure looks like the sort of mistake Mark would make, and the annotation says Mark. Only the thing is that I’m the one who reviewed this code and I know Mark so I was looking for exactly this sort of bug and was pleasantly surprised to find that he was learning and had dodged that pitfall. So I go excavating the history and sure enough, that bug wasn’t in the code I reviewed. It was in Steve’s merge resolution. Fuckin’ Steves, man. And the fact that git lets you do things like that is not a great feature either.

Re:Idiot Proof Git by smaudet on Wednesday November 09, 2022 @11:04AM (#33533545)
The one who does the merge is always the one responsible... even if your code is amazing if it doesn't work with the (working) body of code that's on you, not the people who came before.

Of course Steve can just commit terrible code to main-line, and Mark (or yourself) are always stuck fixing their code, but that's what review/testing are supposed to be for - maybe blame the reviewers and testers in that case instead.

Re:Idiot Proof Git by bornfreddy on Wednesday November 09, 2022 @04:30PM (#33538152)
I don't know either Steve, Mark or you, of course - but this sounds like a broken dynamic where boss's preference of one person (sitting next to Mark, probably mentoring him) pushes another, Steve, to show his fighting side.

Yes, Steve should have kept things honest. But being the boss, you need to be careful not to pick favorites and to treat everybody in a similar fashion. People are very touchy about how they are treated within the "tribe".

Also, if you identified the issues both of them are bad at, are you all solving them? Being "terrible at merges"... how does that even work? Isn't that kind of an important skill? As their boss, their know-how is your responsability too, are you solving it?

Sorry if I have misjudged the situation, I obviously don't know it first-hand, so you will need to see for yourself if the above is true. There were just too many red flags (for me) in your comment to let it pass... And the reason I see them is that I have misjudged colleagues in the past, and wish I had known better then. Ah well.

Re:Idiot Proof Git by Jenk on Wednesday November 09, 2022 @10:31AM (#33532992)
I advocate for rebasing, but I discourage using a linear history. The two may seem to contradict one another but they are distinct (enough) that I felt it worth mentioning. When a developer pushes, it makes sense for them to rebase first because they are shipping those commits at the time of the push.

But, depending on your git workflow, when merging to main, I prefer a merge commit so I can see the tree of activities that lead to any particular release.

Re:Idiot Proof Git by idop on Wednesday November 09, 2022 @10:43AM (#33533208)
That's fine of course. Personally, I prefer to make things as easy as possible to understand at that unspecified but probable future date when a customer opens a SEV1 and I have to consult with the log, among other things. Make it idiot proof later, when time is _really_ of the essence, rather than now, when you're being artificially pressured to deliver that story for the sprint review in two hours.
Re:Idiot Proof Git by Jenk on Wednesday November 09, 2022 @12:15PM (#33534702)
I'm advocating that merge commits in main make it easier precisely for the requirements you specify: To track what feature(s) was introduced at a given release. With merge commits you not only have groupings of commits for features developed, you have that ability to revert a whole feature with just one revert. If you rebase onto main you are flattening those groupings and the entire commit stack into one serial history. For super quick "fix forward" products, that's fine and I would be happy with that. In products that are not so quick or perhaps you have tighter controls/SLAs/etc. Being able to immediately identify and revert an entire feature from main is very valuable, above and beyond a feature toggle imho.
Re:Idiot Proof Git by pierrebai on Wednesday November 09, 2022 @02:39PM (#33536795)
Squash commit will squash everything done into a single commit, so reverting it is easier.

Also when you have to cherry-pick fixes into an older release branch, you get to fully appreciate squashed merges. If you did not squash, you need to cherry-pick all commits from the merge. If the feature branch was not rebased and the dev merged main into the feature branch multiple times, then the branch commits are inter-mingled with main commits and it is so easy to mess up the cherry-picking. Just imagine if the dev had to fix conflicts...

All that makes squash commit a time-saver.

Re:Idiot Proof Git by tremon on Wednesday November 09, 2022 @05:47PM (#33539204)
so reverting it is easier.

Only reverting the entire feature is easier. Reverting a single change (for example, because it introduced a bug but is not critical to the feature itself) becomes much harder after squash.

Re:Idiot Proof Git by seba_dos1 on Wednesday November 09, 2022 @05:52PM (#33539288)
> Squash commit will squash everything done into a single commit, so reverting it is easier.

No, it's just as easy, while needlessly throwing away other useful information.

> If you did not squash, you need to cherry-pick all commits from the merge.

...or use a single `git rebase` invocation.

> If the feature branch was not rebased

Linear workflows with merge commits usually require feature branches to be rebased on merge (just like squashes, just without the actual squashing), so that's not a problem at all.

Re:Idiot Proof Git by danpalmer on Wednesday November 09, 2022 @10:16AM (#33532769)
My point wasn't that this strategy was the right one, but that having a clear strategy is more important.

I personally prefer a more rebase-heavy approach, but what we had worked very well for us.

Re:Idiot Proof Git by idop on Wednesday November 09, 2022 @10:18AM (#33532787)
Oh definitely, a clear and enforced strategy and conventions are more important than anything.
Re:Idiot Proof Git by smaudet on Wednesday November 09, 2022 @11:09AM (#33533634)
Boundaries are equally important - a set of expectations in context is fine, letting people know there is a world outside your little ego-bubble is also important, them knowing how and when to live in both is valuable.
Re:Idiot Proof Git by Shacklz on Wednesday November 09, 2022 @11:49AM (#33534259)
> And a linear history makes this much easier to analyze and understand, reducing cognitive load considerably.

This, so much this! And the price you pay for it is a slightly more difficult "insert". We started to enforce linear history in one of our bigger repositories (about 100 devs) about two years back; the first months were quite the ride (I had to do plenty of support-sessions to recover 'lost' changes). But the devs really started to see the benefits, and once they got the hang of it which was actually faster than I anticipated for most, it was smooth sailing. Many actually started to embrace it and advocate it for other repositories as well.

For me, it became also evident that filtering for people capable of learning git (rebase, cherry-pick, reset etc.) was very good at finding out who I'd want to work with and who not. It's really not that big of a deal, the UX of the CLI might be lackluster but the underlying datamodel is rather straight-forward. It's such a quintessential tool in our every-day-workflow that it's really worth putting a bit of time into understanding it, and if someone can't or doesn't want to, well, it might just be better if they work somewhere else than I do.

Re:Idiot Proof Git by dbt00 on Wednesday November 09, 2022 @04:14PM (#33537934)
You can, 99.9% of the time, emulate linear history with first parent history, which is a post-hoc tooling choice that doesn't remove context.

Developers shouldn't try to merge branches with wip/wip/wip/wip histories either, that's just garbage. Commit messages are documentation, fix your documentation before you publish.

Re:Idiot Proof Git by Shacklz on Thursday November 10, 2022 @03:09AM (#33543604)
> You can, 99.9% of the time, emulate linear history with first parent history

Fully agreed, but that requires first of all to understand how this works and second requires you to run commands locally. If you're unfortunate enough to have to use e.g. bitbucket-server at work like I do, you'll always see the full graph, there which is A LOT easier to grok if it's linear. And since that's what's most devs look at (instead of git-log using some extra options) and also where CI-state happens to be reported (green/red build), that's worth a ton :)

Re:Idiot Proof Git by mibollma on Wednesday November 09, 2022 @05:22PM (#33538869)
I disagree with both of you :). Personally I prefer to squash to one commit per ticket but on a team level I don't care about a consistent way.

I've found that the history rarely doesn't matter at all to me. Finding out who modified a specific code section (git blame) is usually good enough.

Re:Idiot Proof Git by CBarkleyU on Saturday November 12, 2022 @10:59AM (#33574222)
In the hopes someone will see this: Why isnt this the standard? I've never been in the position of coordinating multiple engineers, but when I look at my colleagues code I never ever once cared about their individual commits. What am I missing?
Re:Idiot Proof Git by rtepopbe on Wednesday November 09, 2022 @05:26PM (#33538937)
My current thought on this is that the git model (or at least the interface for it) is probably a touch too simple to accommodate all the things people want to use it for. As a result, you get this whole 'clean history' vs 'what really happened' split. And often you can find a few more splits if you dig in a bit deeper into the actual mechanics people prefer.

Generally, bigger picture stuff works best with cleaner histories as they mop up a bunch of unnecessary and distracting details, and neatly package things together. But doing so also means you're getting rid of, well, the details. If you need them later - and some poor bastard always will - you're just screwed.

Unfortunately all we've got are commits, so you're constantly fighting different groups and even different people who value the benefits of different approaches due to their positions, histories, or preferences.

This isn't even a half-baked idea at this point, but at first glance something like a meta-commit which just contains more commits and a message seems like it might be better. The top-level commits could just be the 'clean history' while deeper levels could record more of the as-happened details.

Re:Idiot Proof Git by P5fRxh5kUvp2th on Wednesday November 09, 2022 @07:13PM (#33540235)
Most of what you said there isn't actually true. I don't doubt you believe what you're saying, I'm just pointing out it's not true.

My favorite is how apparently rebasing causes developers to write better code. If you say so.

Re:Idiot Proof Git by idop on Thursday November 10, 2022 @11:11AM (#33548569)
Thanks for pointing out my errors, I now see where I was wrong.
Re:Idiot Proof Git by hinkley on Wednesday November 09, 2022 @10:21AM (#33532848)
Telling people not to rebase and having code that was never rebased are two very different things. Have you asked former employees if they rebased when nobody was looking? If you haven’t then you have no reliable data on what happens.

When people set ridiculous absolute rules, what develops is an underground of people who don’t follow the rules and in some cases get a thrill from subverting the dystopia.

Re:Idiot Proof Git by eikenberry on Wednesday November 09, 2022 @05:22PM (#33538879)
When I hear 'no-rebasing' I hear 'no-rebasing after you've done a PR'. That's when my code and commits are ready for others. My ongoing commits are often more notes to myself as I find those more useful during the work but make no sense as pushed commit messages where you need to block things off logically. Organizing your commits is not much different than organizing your code into modules. Something that should be done purposefully and with forethought.
Re:Idiot Proof Git by danpalmer on Thursday November 10, 2022 @06:43AM (#33545082)
To clarify, this wasn't an enforced hard-rule, but instead just a written down style guide. Style guides can always be broken for good reason, but it's the sort of thing that a code reviewer might comment on or discourage. Generally rebasing before opening a PR was considered to be fine.
Re:Idiot Proof Git by tyingq on Wednesday November 09, 2022 @10:01AM (#33532522)
What about squashing commits in a merge? I don't do that all the time, but it is useful for certain things. Like repeated code changes to test something in the CI/CD pipeline (that I can't replicate well locally), where only the last change that got it working is of any interest.
Re:Idiot Proof Git by prettyStandard on Wednesday November 09, 2022 @10:06AM (#33532597)
Squashing is rewriting history.

It sounds like the grandcomment had a ban against rewriting history across-the-board, which would help make git idiot proof. I love rewriting history, not because it's what I wished I had done but because it's what I am going to want to review when I have to.

Rewriting history is a great way for gitiots to shoot themselves in the foot.

Re:Idiot Proof Git by peteradio on Wednesday November 09, 2022 @10:10AM (#33532671)
Couldn't you rewrite history locally on your own branch and nobody would know?
Re:Idiot Proof Git by chrisfinazzo on Wednesday November 09, 2022 @10:18AM (#33532792)
Hard agree. Do whatever the heck you want locally, just try not to screw everybody else up when you push.

(From the guy who force-pushed on a personal project yesterday to resolve a situation with multiple remote heads - I am ashamed)

Re:Idiot Proof Git by prettyStandard on Wednesday November 09, 2022 @10:13AM (#33532714)
Yeah... You should never rewrite history of shared branches. You are just asking for trouble in that case.
Re:Idiot Proof Git by danpalmer on Wednesday November 09, 2022 @10:17AM (#33532781)
We informally allowed whatever you wanted until you opened a pull request.
Re:Idiot Proof Git by opsy_ on Wednesday November 09, 2022 @11:53AM (#33534334)
Sure, unless you bork your local repo enough you need help from a teammate getting your work into a PR.

Not to say that doesn't make for a good learning moment.

Re:Idiot Proof Git by OkayPhysicist on Wednesday November 09, 2022 @12:46PM (#33535186)
At some point, every junior is going to mangle something, and need a senior to sit them down and give them the git reflog talk. It's an inevitability, and should be embraced as a natural part of the evolution of a developer.
Re:Idiot Proof Git by prettyStandard on Wednesday November 09, 2022 @02:01PM (#33536317)
Haha. what's the git reflog talk? To be clear I know what reflog is, but what's "the talk"?
Re:Idiot Proof Git by olddustytrail on Wednesday November 09, 2022 @03:08PM (#33537147)
Probably just making them aware of it. But I can give a slightly longer spiel:

Commits in git are immutable. They're identified by their hash, so they have to be. What's more they have the hash of the previous commits so the whole chain back to the first commit can't be changed. You can only add new chains.

As a consequence, if your main branch points to commit abc123 and your feature branch points to commit def456 then it doesn't matter if you merge, cherry pick, rebase or dance the fandango, if you point those branches back to those commits, the branches must by necessity look identical to the way they looked before you did anything.

And you can find out where they used to point in the reflog.

Re:Idiot Proof Git by chrisfinazzo on Wednesday November 09, 2022 @07:52PM (#33540638)
I'm certainly aware of reflog and have (thankfully) only had occasion to use it once or twice that I can remember.

To my original comment - having to force-push in order to resolve heads - is there a "correct" way to do this that doesn't feel gross?

Re:Idiot Proof Git by Dylan16807 on Wednesday November 09, 2022 @10:43PM (#33541931)
You're going to have to explain your problem in more detail than "resolve a situation with multiple remote heads".
Re:Idiot Proof Git by chrisfinazzo on Thursday November 10, 2022 @11:57AM (#33549465)
To explain, I'll borrow the solution that I first saw in a Fog Creek presentation from ages ago ("DVCS University")...

Essentially, if you have more than one person making changes to the same piece of code, the method for resolving them is:

1) Pull - gets their changes

2) Merge - puts their changes together with yours and you can reorganize them at that point.

Note, this was done with Mercurial which doesn't have the concept of a stage, so Pull feels like it has a slightly different meaning when you look at it that way. One [suggestion][1] for Git if you want to achieve the same effect - getting a Fast-Forward at the end - is to Rebase, then Merge last.

Part of me knew this, I simply forgot and wanted to get out of this particular hole.

[suggestion]: https://www.atlassian.com/git/tutorials/rewriting-history/gi...

Re:Idiot Proof Git by Dylan16807 on Thursday November 10, 2022 @12:36PM (#33550124)
That's the start of a setup, but that's not enough information for me to figure out why you needed a force push.

I'm not going to demand you explain more, but if you want to explain more then I'll try to answer the question you had about whether there's a better method.

Also Pull is generally a shortcut for "Fetch then Merge", and just getting changes is Fetch.

Re:Idiot Proof Git by OkayPhysicist on Wednesday November 09, 2022 @03:12PM (#33537193)
Just the explanation of "no matter how bad you've fucked up your repo, as long as you haven't run 'git gc' or waited a few years, all you need to fix it is to find the commit hash from git reflog, git checkout that hash, and then git branch to give you an easily accessible reference to the commit". Followed by some pointers on how to efficiently dig through reflog.

It's pretty freeing to realize that it's basically impossible to lose committed code.

Re:Idiot Proof Git by bacon_waffle on Wednesday November 09, 2022 @09:55PM (#33541623)
Or made a "fresh clone". I've had colleagues nuke a repo when it gets in to a "bad state", start over with `git clone`, repeat the work that git lost...
Re:Idiot Proof Git by dec0dedab0de on Wednesday November 09, 2022 @10:16AM (#33532768)
What about squashing commits in a merge? I don't do that all the time, but it is useful for certain things. Like repeated code changes to test something in the CI/CD pipeline (that I can't replicate well locally), where only the last change that got it working is of any interest.

You can get the same effect by reverting-to/checking-out a merge commit, or doing diffs between merge commits. You can also get a fairly clean history by only showing merge commits.

My rule of thumb is that any commit that has been pushed to a shared remote should never be re-written[]. If you're going to rebase, do it on your computer before pushing, or on your own repo before opening a merge/pull request.

[] exceptions would be removing accidentally committed secrets or large files that are no longer needed.

Re:Idiot Proof Git by eternalban on Wednesday November 09, 2022 @10:43AM (#33533211)
> history should be exactly what you actually did, not some clean and idealised version of what you wish you had done.

This is a false premise. There is a product (and its various versions), and the team that develops it. Both have a claim to a meaningful definition of "history". What you are arguing is that the 'history of developer' is more fundamental than a less noisy 'history of the product development'.

Does it really matter (and need we record it for posterity) if developer x used n commits to post n incremental changes to a well defined software unit of the product?

It seems a comprise position of (1) no history rewrites before code review, followed by (2) post code review cleansing squash before merge would satisfy all concerns and history records have also served their purpose.

. A developer's timeline is relevant to her team lead, not the product manager.

Re:Idiot Proof Git by cnity on Wednesday November 09, 2022 @12:08PM (#33534597)
If the employer I worked for started micro-managing the way I use my tools (that affects nobody else) I would consider leaving, honestly. If I rebase on a branch that hadn't been shared with someone else, why does it matter what my boss or team thinks about that approach?

Code styles are one thing, what I type into my terminal is another.

Re:Idiot Proof Git by gardenhedge on Wednesday November 09, 2022 @04:30PM (#33538161)
When you commit you're sharing with your team and future team. I think it's fair to have a set of agreed guidelines around that. What if you wanted to put all your commit messages as "cnity did it"?
Re:Idiot Proof Git by bacon_waffle on Wednesday November 09, 2022 @09:47PM (#33541564)
I agree with the post you're responding to, and make a lot more commits than I share with my team. Pushing commits to a shared branch is where work is shared.

At my current employer, we used to use Perforce, and in that world you're totally right that committing (submitting in Perforce terminology, IIRC) did share changes. In that context, we developed a lot of bad patterns, losing code or holding up other people's work while a developer got their work ready to share. Transitioning to git has been super painful, due mainly to people treating git as if it's the same sort of thing as Perforce...

Re:Idiot Proof Git by cnity on Thursday November 10, 2022 @04:29AM (#33544132)
It's simple: I wouldn't do that. Do we need guidelines to not delete repositories too?
Re:Idiot Proof Git by gardenhedge on Friday November 11, 2022 @03:05PM (#33566093)
Yes of course
Re:Idiot Proof Git by ajkjk on Wednesday November 09, 2022 @01:17PM (#33535674)
gosh, wow, I want the opposite of that for any project I work on. In the last five years I have never used a merge commit and I love it. I'd honestly prefer a version of git that doesn't have em.
Re:Idiot Proof Git by umvi on Wednesday November 09, 2022 @03:15PM (#33537220)
Without merge commits you can never have more than 1 long-lived branch because said long-lived branches will not have any common ancestors which makes pulling changes between them a nightmare (literally every file will be in conflict)...

I like linear histories too, but if you have a production branch and a development branch you need merge commits between them.

Re:Idiot Proof Git by amrocha on Thursday November 10, 2022 @12:37AM (#33542684)
long lived branches are an anti pattern so this sounds like a plus to me
Re:Idiot Proof Git by erik_seaberg on Thursday November 10, 2022 @03:18AM (#33543660)
I’d rather wait until a project is finished, than to push incomplete changes that (I hope) aren’t reachable.

But a long-lived branch needs to be rebased before review, because conflict resolutions need to be reviewed. In fact reviewing the version without the conflict resolutions is a waste of time, because that version probably won’t ever be deployed.

Re:Idiot Proof Git by chociej on Thursday November 10, 2022 @02:32AM (#33543363)
I don't think either of those is necessarily true. I don't ever need to merge long lived branches if I don't want to. And I definitely don't ever merge my production branches with... anything. They are always just a fast-forward from another branch.
Re:Idiot Proof Git by umvi on Thursday November 10, 2022 @12:32PM (#33550072)
In my case I have 2 branches - production and development which map to different cloud environments. Pushing to development branch will run CI/CD to auto-deploy to development cloud, and pushing to production will run CI/CD to auto-deploy to production cloud. This particular software is also classified as a medical device under FDA which means there are regulations about what can be deployed to production and when. Hence, I cannot just fast forward production from another branch without first getting FDA approval. I can, however, cherry pick certain kinds of bug fixes into production without FDA approval, and then later (after FDA approval) merge the other approved changes into production as well. In this case fast forwarding isn't possible because of the cherry picks so we are using just normal merge commits.

Do you have a better git workflow in mind than what is described above?

Re:Idiot Proof Git by wizofaus on Wednesday November 09, 2022 @04:40PM (#33538281)
Technically your git history isn't a record of what you did, only what you committed. If I make a bunch of changes locally, commit then realise I need to make a few extra changes before pushing there's really no harm amending the commit. But once pushed, I agree, it should stay as is.
Re:Idiot Proof Git by throwawaylinux on Wednesday November 09, 2022 @11:19PM (#33542151)
> that history should be exactly what you actually did

That gives you the history of exactly what git commits you made, not exactly what you did and how you went about solving the problem though, right? git describes changes to the source.

It seems like you're getting the worst of both worlds, trying to understand how the source changed is much harder when you have peoples' experiments and draft changes and false starts littering the history. And understanding the approach to problem solving and why decisions were made is pretty unsatisfying by digging through that stuff too really. That seems better kept as documentation and/or in the commit logs.

Re:Idiot Proof Git by Shorel on Saturday November 12, 2022 @11:38AM (#33574658)
For me, there should be a balance between the detail of history and the usefulness of the information.

For the changes I do, not only I rebase them all in a single commit, I don't even merge branches. I cherry-pick my changeset. Clean commits, clean history.

Whatever I do before a push is my business and no one's else.

For anyone else changes, that's it, anyone who is not me: history is untouchable. No rebases, no squash, whatever it is already pushed, must stay as it is.

When I do a pull: git stash, git pull --rebase, git stash pop

I encourage everyone to clean their commits before a push. A clean history is a good history.