====== Git ======
''[[https://git-scm.com/|git]]'' is a "distributed version control system" (dVCS) or "source control management" (SCM) tool used to track changes, primarily for source code in text files. git has command line and graphical interfaces.
Alternative SCM tools include ''[[https://fossil-scm.org/|fossil]]'', ''[[https://www.mercurial-scm.org/|hg]]'', ''[[https://pijul.org/|pijul]]''. For version controlling (large binary/non-text neuroimaging) data, see [[https://handbook.datalad.org/|datalad]] or [[https://dvc.org/|dvc]]
''git'' is not github. [[https://github.com|Github]] is a Microsoft-owned source forge adding a social network, identity services, and other features not included in the git system (issue tracking, patch/fork management). Other forges include [[https://gitlab.com|gitlab]], [[https://sr.ht/|sr.ht]], [[https://codeberg.org/|codeberg]].
For more see
* https://happygitwithr.com/
* http://neuroimaging-data-science.org/content/002-datasci-toolbox/002-git.html
* https://git-scm.com/doc
===== Using =====
==== Track Changes ====
On the command line in terminal/with shell, using git follows the ''add'',''commit'',''push'' pattern:
git add $file # move changes in $file to "staging"
git commit # annotate staged files, commit to history
git push # send changes to a server (e.g. github)
By default, ''git commit'' will open [[:tools:vim]] to use to write the commit message.
- Push ''i'' to put vim in insert mode.
- write your message.
- push ''Esc'' to go back to command mode
- '':wq'' to write and quit.
=== Commit messages ===
Each commit in git includes a human-annotated short description in prose. While it's tempting and easy use `"update"` as the entire commit message, future you and colleges will appreciate a more detailed history. There are competing specifications to help guide better commit messages:
* https://www.conventionalcommits.org/
* https://gitmoji.dev/specification
== Examples ==
Two commit messages in ''conventional commits'' vs ''gitmoji''
feat: age model with GAM instead of LM
fix: outlier detection applied to all EEG columns
✨️ model.py: age GAM instead of LM
🐛 plot.R: apply outlier detection ∀ EEG cols
==== See Changes ====
A huge benefit of version control is to see the what's changed. This can be done with web, graphical, and command line interfaces.
The command line/terminal commands for viewing what's changed include
git log # history of all changes
git status # what's been git add-ed/git rm-ed, modified, and untracked
git diff # what's changed in tracked files
git blame $file # show what commit/author is responsible for each line
If the output is more than a screenful, these commands will launched put the output in the pager ''less''.
* arrow keys navigate
* push ''/'' to start a search
* push ''q'' to quit
==== Github https push ====
To push to ''https'' (vs ssh like ''git@'') repos, you'll need to use a personal authentication token when prompted for a password. See [[https://docs.github.com/en/authentication/keeping-your-account-and-data-secure/managing-your-personal-access-tokens|github's documentation]]
==== ssh push ====
''git push'' can use ssh authentication. You need a key likely in ''~/.ssh/id_rsa.pub''.
Contents of ''~/.ssh/id_rsa.pub'' should be pasted into ''new ssh key'' modal on https://github.com/settings/keys ((''top right user icon''->''settings''->''ssh and GPG keys'' -> ''new ssh key''))
{{:tools:pasted:20231024-130110.png}}
If ''~/.ssh/id_rsa.pub'' doesn't exist, ''ssh-keygen'' can make it (use empty password for convience. hit enter at password prompt to leave blank). See more [[https://docs.github.com/en/authentication/connecting-to-github-with-ssh/generating-a-new-ssh-key-and-adding-it-to-the-ssh-agent|documentaiton on github]]
==== Advanced ====
* [[https://git-scm.com/docs/git-worktree|working trees]] for working on more than one branch at a time
* ''git add $file; git commit --amend --noedit; git push --force''
* rebase, esp with [[https://magit.vc/manual/magit/Rebasing.html|emacs+magit's rebase UI]]
* [[https://jvns.ca/blog/2023/11/01/confusing-git-terminology/|confusing terms]]
* [[https://jvns.ca/blog/2024/02/16/popular-git-config-options/|popular git config options]]