In the process of getting proficient with Git a mental model for what Git really is under the hood helped me a LOT. And I have shared this analogy with co-workers enough times that it felt like writing down.
The best analogy for my mind was that of a 3 ring binder. Maybe this is somewhat age specific. I used 3 ring binders a lot in school. FiveStar FTW!
Each commit is a page. Each page has a special identifier, in the Git world this is known as a hash. This is different than a page number because hashes are not seqential, but git makes up for this by having each page also says what page it comes after using these ids.
Staging a commit is composing what goes on the page, but you haven’t put that into the binder yet in any way. Committing is actuall putting it in there.
Stashing is putting all your work on a page that sits next to the binder. But, you can pull that page into the binder later pretty easy if you want.
Cloned repos are complete copies of the binder. Pushing and pulling relates to pages in the binder - the repo you push or pull to/from is the binder target. When you push or pull you don’t send and recieve the whole binder again, just the new pages. If you changed the ordering of pages that existed before you will need to force push. If other people were also using a copy of that binder they may not be happy with you for doing that sort of thing.
Branches are like pages you have inserted into a certain spot in the binder (the spot where you branh off / insert them determines the parent node of the branch) but haven’t actually opened up the rings and put them in. Merging to a main or shared branch of the repo is a bit more permanant - like opening up the rings and putting the pages in. You may want to combine pages or do some edits (squash or ammend) before merging.
Rebasing a branch is like pulling a stack of pages out from whereever they are and putting them at the back (or front?) of the binder.
Squashing is taking a bunch of pages and combining them into one page. Squash merging is then putting that one page into the rings onto the end of the stack. The new page would have a new id (hash) and a new parent id.
No analogy is perfect but this one stretches further than most before falling apart.
This series of comics that tries to illustrate git concepts looks good as well.
A related tip: Good commit messages make a huge difference this whole article is good, but my TL;DR summary whould have to be that a solid way to compose a quality git commit message is to complete the sentence “if applied, this code change will …”