6 ms·
Why Git Is Hard
- sys_64738 3y agoman tig
- nathias 3y agoWhen I was learning to code, I first learned git. It was the most intuitive program I've ever used, I still think its one of the best software ever written.
- deleted 3y ago[deleted]
- GuB-42 3y ago> I first learned git. It was the most intuitive program I've ever used Maybe because it is because it was the only one, since it is the first you learned :p I wouldn't call git "one of the best software ever written", though it certainly was influential. It was a hack job by Linus Torvalds because he was dissatisfied with the existing offering when it comes to source control. What he achieved in so little time was truly impressive, and the foundation of it is good, but it was still a hack job and I guess it gained most of its popularity because of Linux, and later GitHub. Now, git has much improved, certainly due to its popularity, but its roots as a hack job still show. Maybe, in an alternate universe, Mercurial would have been the one, it is very similar, or maybe Bazaar, or Fossil, which have different philosophies, but are still very capable DVCSs. Interestingly, they all came out at about the same time (2005, except for bazaar, that came out in 2006).
- nathias 3y agoI mean the best in terms of the base ux, the hackiness that you encounter sometimes is proably mostly because of the coupling with remote services (github, gitlab) where there is some friction, but imo pretty minimal (some unaccounted hashes with rebasing etc.). I'm now interested to try the alternatives just for comparison...
- j16sdiz 3y agoI have problem understand why git is hard for some. It is super easy for me. This article nailed it -- it's the mental model.
- AceJohnny2 3y ago> It’s the alien mental models Hm. I love Git because its core is so simple it fits on a napkin [1]. From such a simple mental model, everything else flows. It's an extremely simple mental model because it compresses so well: from only the first principles, I can derive the rest. Any other computer system, I try to dig and find its first principles, but nothing is quite so clean, so I have to keep in mind a bunch of exceptions and add-on warts to understand them, a larger mental load. That said, I seem to often be the one around my teams most comfortable around Git. I can't explain it. Perhaps I've erased my initial struggle to understand it. Perhaps others don't conceive of Git as a datastructure... [1] files=blobs (named after the SHA1 hash of its content), dirs=trees=collections of blobs+trees (named after the SHA1 hash of its content), a commit=top-level tree + parent commit(s) + commit comment (named after the SHA1 hash of its content). A branch is a reference is a pointer to the latest commit in a series. Creating a new commit adds to the top and updates the pointer.
- aiunboxed 3y agoYes personally I also can't co relate with git being hard, I mean yes during the initial days of learning you get stuck, but it is the same with everything right ?
- rjblackman 3y agoI tend to agree, however it took learning about git internals to get to this point. Most developers don't read stuff like that. Also git creators made the mistake of using terms like add and checkout to mean completely different things to older version control systems. I think that's where a lot of the confusion stems from.
- saghm 3y agoI think the disconnect is that the "first principles" that you can derive from are implementation details; in other words, git makes the most sense if you embrace the inherent leakiness of the abstraction. > Perhaps others don't conceive of Git as a datastructure The problem is that git doesn't really look much like a datastructure at first glance; it's ostensibly a shell command that you invoke, which makes people look at it in terms of inputs and outputs rather than spending time learning the details of all of the parts that aren't obviously in plain sight. > A branch is a reference is a pointer to the latest commit in a series. Creating a new commit adds to the top and updates the pointer. I think this is a pretty good demonstration of the issue I'm talking about; I've talked to engineers who totally understand git's underlying model but still are incredibly resistant to this definition of a branch, even though it's the accurate one. The idea of a branch conceptually being the entire chain of commits from the most recent one to the initial one is so pervasive that even the term "branch" heavily implies it (when arguably the more accurate analogy would be to call them "leaves"). When the definition of one of the most fundamental concepts defies people's common intuition, the finer details of advanced operations on them like rebasing don't have a chance of being widely understood. Git's failing isn't that it's complex, it's that the only effective logical unit to think about the system is the entire thing, and that lack of abstraction is the alien model to the way we're encouraged to think of things as programmers.
- johnny22 3y agoi've mostly gotten the mental model but not > The forward slash is sometimes a special namespace separator to denote a cached remote branch, and sometimes not. that's something i have to keep looking up.
- bvrmn 3y agoBecause local objects names could be mapped freely to anything, it's only a convention to use <remote>/ as a prefix.
- bvrmn 3y agoFrom my teaching experience it could be a fear to do something wrong. I've come from SVN and ClearCase where doing wrong was quite a trivial thing. And Git relaxed me a lot. Knowing only push/pull makes actual changes and you have reflog to revert any possible mess is a big relief.
- tjoff 3y agoI don't think I have ever met a beginner of git that hasn't fucked up their repo to a state where the effort to get back is more than just redo everything. In the beginning the fear is paralyzing and it is not without reason. For sure it is recoverable, but not to a beginner. I do agree that fear is a very important factor. I disagree that it was easier to do things wrong with SVN. The times I got in a weird state with SVN was usually related to a merge. But it was the clunkiness of the tool and not fear of loosing anything or not having a way out. Last resort was just to do the merge manually. No risk to it, just tedious work.
- gpderetta 3y agoIt was harder to do things wrong in SVN, but it was also harder to do things right, or at all.
- nanna 3y agoThis is definitely why I hate git. It really is possible to lose your work by doing a a bad reset (and really the vocabulary of hard, soft and mixed resets is a blatant cop out from coming up with meaningful terms). Or by checking out another branch and not committing or stagsing all your files - yes I know this is a no no but it's trivially easy to do and git would be better if it just had to get them back. If only there was just a 'revert whatever I just did to git' even if what I did was destructive. Or better, if only navigating my git history was as easy as an undo tree in Emacs. Every change seems frought and so for me and probably a lot of others it becomes easily very stressful.
- deleted 3y ago[deleted]
- zvmaz 3y ago> Commits are unique and immutable, and are anchored to a specific point in the graph of history and causality. This means that a commit’s identity is made up of both its content and its context. > This in turn means that you need to be comfortable and fluent in a branching many-worlds cosmology, so you can distinguish between changes and snapshots that have the same intent and content but which are completely non-interchangeable and imply entirely different flows of historical events. "Graph of history and causality", context, content, "many-worlds cosmology", changes, snapshots, "flows of historical events"... This makes Git even harder.
- JohnFen 3y ago> "Graph of history and causality", context, content, "many-worlds cosmology", changes, snapshots, "flows of historical events"... This makes Git even harder. Thank you for saying that. I had to pretend I didn't read it because it made me even more confused, and assumed it was because I was an idiot.
- zvmaz 3y agoThere is still worse: > Sometimes this devolves into me talking about wave/particle duality as a crucial metaphor for getting through a rebase intact [...] Wave particle duality as a crucial metaphor for a functionality of Git?! This is nonsense.
- JohnFen 3y agoYes, it is. What I found amusing was the preface to the article: > While doing so, I have often failed to get the basics to stick, which is incredibly aggravating to someone who prides themselves on explaining things. [...] > So, I’ve spent some time thinking about this before this weekend. And yet, what he wrote after thinking about it only muddied the waters for me, not clarified. Which tells me that git is fundamentally really difficult to explain.
- RichardCA 3y agoYeah I agree. I actually had the same thought as the author, use the example of wave/particle duality in Physics. The problem is most people don't understand that (how to grasp the paradox and have the right intuition about it) and you will just come across as a pedantic smartass. The ones who do know some advanced Physics will see you as a dilettante. Teaching Physics with correct pedagogy is hard. Even harder than Git.
- drewcoo 3y ago> [branches are] like little bookmark go-karts Well that clears it up! /s I think trying to avoid talking about SHA1s of content makes everything blurrier, not clearer. Because them people say things like this, which really don't make sense and instead seem like speculative SF: > A commit is its entire worldline Honestly, most Git problems I see stem from long-lived branches. Git flow is a common culprit.
- civopsec 3y agoIt's not the same thing but Git Flow reminds me of Conway's Law. Just that the branches end up representing the dev-test-release workflow. Another variation is that you reify branches according to whatever team that is working on it, like dev and qa and release. As in they have these literal branches and they need to follow a workflow diagram in order to remember what to merge into what and in what order. Then they mess something up and they go to StackOverflow to ask such easily inteligble questions like: > We are using a standard branching model. But sometimes we find a bug in release/5613248 and need to deploy a hotfix. So naturally we branch hotfix/5613248 from release/5613248, fix the bug, do a PR against release/5613248/joe-the-gatekeeper, then Joe merges that into release/5613248 and also into pre-release/5613248, qa, and finally into develop. But sometimes we get weird merge conflicts when merging into for example qa or develop. How do we avoid that? Slight hyperbole here.
- KronisLV 3y agoI think Git can be a pretty pleasant experience for most folks, as long as you use the basic features and maybe even consider a GUI, anything from Git Cola (free: https://git-cola.github.io/ https://git-cola.github.io/), to something like GitKraken (paid for all features: https://www.gitkraken.com/ https://www.gitkraken.com/). Curiously, the latter also let me setup different accounts that I can switch between with a simple dropdown, which was otherwise annoying when you have Gitea, GitHub, GitLab and others to manage, way easier than https://docs.github.com/en/account-and-profile/setting-up-and-managing-your-personal-account-on-github/managing-your-personal-account/managing-multiple-accounts?platform=windows https://docs.github.com/en/account-and-profile/setting-up-an... Either way, suddenly you see the graph of your repo and most of the common actions are a click away, you can just let your brain idle and think about other things you're doing instead, in addition to that working really well with staging chunks of your code, or individual files, cherrypicking and so on. Even Git LFS or ignoring stuff is a context menu away. Then again, personally I prefer squashing in merge/pull requests instead of rebasing, or even just doing regular merge commits and leaving the history as is (which doesn't really scale, but I haven't gotten to the point where that matters that much), so how I use Git won't work for everyone.
- avgcorrection 3y ago> Git commits are stored on disk as snapshots, but that's not necessarily how Git treats them! Various Git commands treat a commit as either a complete repo snapshot or as a change set, depending on what you’re doing. The problem is that the documentation and the developers go between these modes so fluently that you have to know the context in order to distinguish them. Of course to them it's obvious that you are treating the incoming changes as a “changeset” since it's a diff (a patch) from an email (not a snapshot). This is the “name” section for `man git-rebase`. > git-rebase - Reapply commits on top of another base tip How should someone new guess that this means to (effectively) take the diff of each commit and applying those changes? Instead of working on the snapshots?[1] Because I think you could also interpret it as: take the tree (the snapshot) of each of these commits and make an alternative subgraph where the parents are different, propagating from the new base tip. Which means that you can make a new root commit (disregarding old history by “squashing” seems to be popular on SO for some reason) starting from A by rebasing A on `--root`. But it doesn't work like that. If you want to do that you should instead use git-replace. In my experience, for every little question about cherry-picking or rebasing, you have to go down to the fundamental concepts. Because the way people work is not like a sponge which only absorbs the information that it is given; people learn 10% about something and then automatically infer the rest, and sometimes 50% of that is wrong. So then you have to unnest that. I guess this is my long-winded way of agreeing with the author. [1] Working on the snapshots would also be useful. You could use that to format all of the commits on the branch.
- tener 3y agoI think of branches as variables pointing at immutable points in the commit tree. Git commit creates a new node in the tree and updates the pointer. You can manually move pointer around if needed.
- shele 3y ago> Also, Git's CLI aggressively obscures those core concepts, so any learner is in an uphill battle even if their mind does happen to work the right way Thank you, that resonates
- jasonkester 3y agoMy big issue with Git is the way it handles Merges. It throws up this dialog saying "there are conflicts", and by the time you see this, it has already monched a bunch of files in your local version and now the only way out is through. You need to drop everything and fix all this stuff right now before you can proceed. Even if it's last thing on Friday night and you'd rather just go home and try again on Monday. If there was just an "Abort" button that stopped trying to push or commit or whatever and just put things back the way they were before, that would take all the worry out of it. Because usually it would have been easy to avoid the conflict if only you knew it was coming before Git f'd your whole project.
- Kwpolska 3y agoThere is an "Abort" button. It’s `git merge --abort`.
- korm 3y agoIt's so frustrating when people joining my team often scoff at the idea of using a git GUI. They're hired to write software, not fumble with ancillary tools that they've been using incorrectly for over 10 years. Either use the cli effectively, without messing up simple tasks, or use a gui that will teach you how. There's surprisingly a lot of resistance even though we provide Gitkraken licenses for free. To be clear, we have a few people using only the cli, we don't bring this topic up unless it's a problem.
- alexchamberlain 3y agoOh I'm the complete opposite. Why does everyone use a GUI for everything? You get good at dealing with the good plan _OK_, but if something goes wrong or you want to automate something, there's no flexibility.
- rcxdude 3y agoGit's core abstractions map pretty dang well to a GUI. And the commit graph is inherently pretty visual. I find it a heck of a lot easier to navigate a repository graphically than via the CLI (it can be done, it's just not fast). For most people a GUI works better when they get into a sticky situation with git than the CLI. Automation is different, of course, but it's not generally hard to map actions in the GUI to commands if necessary.
- matricaria 3y agoI tried to add the `git log` alias which didn’t work for me. The much simpler `git log --graph --color` works great.
- tester756 3y ago>It’s not the bad CLI Nah, really, it is terrible. Git is one of the best examples of "great tool with terrible API". Funniest thing is that people always argue "learn git internals and it'll click" Yea, git is the only tool that people argue with straight face that you should know internals of software and act as if it wasnt sign of terrible API design. Imagine if people acted as if you needed to know Visual Studio's or Firefox's internals in order to use those tools even in "far from very advanced scenarios", rofl.
- jrockway 3y agoYou should understand the internals of tools that you use. Abstractions and simplifications do only one thing: delete features in the hope of being easy to understand. As a software engineer you have the unique privilege where the people that make your tools have literally the exact same job as you, so you can pretty easily understand their work. As for understanding Visual Studio's or Firefox's internals, that's basically what you do to write Visual Studio plugins or apps that run in Firefox.
- alexchamberlain 3y agoWhen I work with graduates, I often encourage them to try and understand "1 level down" - that is to say, understand the general design philosophy and how to navigate the tools and libraries you are using. That gives you a better understanding for how to use them, whilst also allowing you to side step the documentation when you need to. On the other hand, if you try to understand what the atoms are doing on the silicon when you run an SQL command, you might be a tad overwhelmed...
- BoorishBears 3y agoVS and Firefox don't demand you understand writing plugins to use them. They wrap their internals with an interface that has well documented entry points, but you don't need to delve into them to get a lot of value out of them. > As a software engineer you have the unique privilege where the people that make your tools have literally the exact same job as you, so you can pretty easily understand their work. That's not how that works. Writing frontend apps doesn't teach you MUMPS. _ At the end of the day Git gets "easy" but honestly most people who say Git is easy are like people saying JS is easy: the people who know either well enough will claim anyone who thinks either is easy simply doesn't know them well enough Linus himself: Generally, the best way to learn git is probably to first only do very basic things and not even look at some of the things you can do until you are familiar and confident about the basics.
- TheChaplain 3y agoI must be some kind of genius, as I find git quite easy? I've been using it daily for years now, but I started out with subversion which was quite nice because it had TortoiseSVN. Later went to Mercurial which was pleasant to work with but since GitHub arrived to the scene the choice both private and professionally became the obvious. Besides git and hg are IMHO not that different anyway from a daily use pov.
- edu 3y agoSame story here.
- Charlie_26 3y agoI feel sort of in the same boat, at least from reading this blogpost. Though it might be time for me to master fetch rather than pull. What I wonder is how anyone (read: most people) get by with using GUIs for Git that tend to abstract some of these fundamentals away
- bboygravity 3y agoOK, Git is easy? I got a trivial sounding task for ya: delete 1 file from (all commits in) a repository with 100's or 1000's of commits. Without using any external tools. You've got 5 minutes. Should be plenty of time to delete 1 file and/or figure out how to do that simple task right? Good luck.
- softwaredoug 3y agoI don't the inconsistent, bad CLI be dismissed so easily. That’s the barrier that first must be overcome to get to any mental model stuff. People have learned more complicated things, but have had better abstractions to work with. Numpy is hard. But it’s less about accidental complexity of the interface and more about the array programming paradigm being unusual for most people. Spark is hard. But it’s because distributed data frame processing is hard. Whereas pyspark had made a lot of the actual abstractions easier to work with. Compare this to Hadoop back in the day which has both accidental and real complexity.
- famahar 3y agoI remember seeing someone post a conversation with chatgpt about making git make more sense. The naming of actions seemed to be one big hurdle. Pull, push, merge, commit are actually confusing terms that don't clearly explain what you're doing. Simply renaming the terms or being slightly more verbose was enough to demystify what was happening.
- m_niedoba 3y agoI don't think so, even as a game artist. It took me a while to understand the concept of branches (that they are basically modes or variants of a project). That clicked. But for daily game development, the most thing I do is just commit+push / pull. That's 90% of the work and Git does a great job here. There are desktop applications such as Anchorpoint (https://www.anchorpoint.app/ https://www.anchorpoint.app/), which make it even easier for non coders. So the whole big ecosystem of Git makes it easier to use.
- mobiuscog 3y agoI think a lot of the git problems come along due to 'good ideas'. Basic git isn't too bad. A learning curve, but manageable. However, next thing you know you're in a sprint and your work depends on somebody else's (process problem, but happens often) and so you are now working on top of their branch. You make some commits, and have to merge in (or rebase - force push) their changes... ... and then you come in to work after the weekend and find that they have merged their code into main. Cool ! You'll just merge/rebase main, except you find that they had also been working on top of someone else's branch, and now you have all sorts of fun trying to unpick how your changes actually relate to what is in main. Sure, some people are just happy to rebase and force-push, but if you're happy to force-push then the 'control' has gone.
- nighthawk454 3y agoHow would one expect to use a tool they have no mental model of? It's a tool not a service. What tool do you not need to understand (at least some of) the core principles?
- qwery 3y agoI'm not sure how many people struggling to learn git (the 'git novices' of the article) are competent with any comparable tool. Maybe "why git is hard" isn't the right question? Speaking from personal experience, if you already learned Mercurial, you might find it annoying that commands with the same name do different things, or worse: almost the same thing, but it's practically the same[0] system. Coming from a centralised system to a decentralised one is a bigger jump but understanding the 'distributed' part of "distributed version control system" seemed to me (speaking from personal experience) pretty straightforward, compared to the V, C, & S. It's just that a lot of the points made here seem only loosely git-related? Not that that makes them wrong or invalid, by any means -- they do all apply to git. Fully agree that teaching people `git fetch` as a separate thing to `git pull` is probably wise. [0] the same: git doesn't believe in curtains, mercurial just painted and doesn't need curtains
- JohnFen 3y ago> I'm not sure how many people struggling to learn git (the 'git novices' of the article) are competent with any comparable tool. I am extremely competent with a couple of other version control systems, but that doesn't really help me in terms of understanding git. I agree that many of the attempts to explain it that I've read (including a number of the comments here) are really explaining things that all version control systems have in common. For me, those aren't the parts that I struggle with. It's how those things map onto actually using git that I find difficult.
- akho 3y agoThe things that this post describes are the easy parts (except pull). Then you come at it with your new understanding of an immutable commit DAG, and run into things that shouldn’t be there at all, yet everybody uses — rebase, cherry-pick, &c.
- ahofmann 3y agoGit is hard because it solves a non trivial problem. But also, because it uses a lot of bad defaults (naming the remotes "origin" for example) and it uses the same name for different things. It's almost like the founders of the project didn't understood the problem space at the start of the project and now it's too late to set sane defaults and behavior. Just like bash, PHP, MySQL and others.
- JohnFen 3y ago> Git is hard because it solves a non trivial problem. But other version control systems are solving the same non-trivial problem, yet I don't find them hard to understand and use...
- GuB-42 3y agoI think the CLI is more to blame than the author says. For example, the "branches are more like bookmarks" point. Well, I think it would have been easier if git called them bookmarks, like Mercurial. About the "fuzzy identity" part, it is mostly a consequence of git fuzzy naming scheme. Like the "git reset" command that does many different things, the result is that no one know what a "reset" is. I have never struggled with the idea that a commit is a "worldline". I think that calling it a worldline is making it more confusing than it is. For me, it just represents some work done, but the git tendency to mix high level concepts with implementation details gives people weird ideas.
- tempodox 3y agoGit is hard because it has the most confusing, inconsistent, and atrocious CLI of all the programs that I use.
- beej71 3y agoThe stage, as well. I find that since most students just `git add .` (a habit I strongly encourage them to break) and then `git commit`, they don't see why the extra staging step exists or is useful. It's just a nonsensical hoop to jump through.