## File: README.md # Obsidian Git Plugin A powerful community plugin for [Obsidian.md](https://obsidian.md) that brings Git integration right into your vault. Automatically commit, pull, push, and see your changes โ€” all within Obsidian. ## ๐Ÿ“š Documentation All setup instructions (including mobile), common issues, tips, and advanced configuration can be found in the ๐Ÿ“– [full documentation](https://publish.obsidian.md/git-doc). > Mobile users: The plugin is **highly unstable โš ๏ธ !** Please check the dedicated [Mobile](#-mobile-support-%EF%B8%8F--experimental) section below. ## Key Features - ๐Ÿ” **Automatic commit-and-sync** (commit, pull, and push) on a schedule. - ๐Ÿ“ฅ **Auto-pull on Obsidian startup** - ๐Ÿ“‚ **Submodule support** for managing multiple repositories (desktop only and opt-in) - ๐Ÿ”ง **Source Control View** to stage/unstage, commit and diff files - Open it with the `Open source control view` command. - ๐Ÿ“œ **History View** for browsing commit logs and changed files - Open it with the `Open history view` command. - ๐Ÿ” **Diff View** for viewing changes in a file - Open it with the `Open diff view` command. - ๐Ÿ“ **Signs in the editor** to indicate added, modified, and deleted lines/hunks (desktop only). - GitHub integration to open files and history in your browser > For detailed file history, consider pairing this plugin with the [Version History Diff](obsidian://show-plugin?id=obsidian-version-history-diff) plugin. ## UI Previews ### ๐Ÿ”ง Source Control View Manage your file changes directly inside Obsidian like stage/unstage individual files and commit them. ### ๐Ÿ“œ History View Show the commit history of your repository. The commit message, author, date, and changed files can be shown. Author and date are disabled by default as shown in the screenshot, but can be enabled in the settings. ### ๐Ÿ” Diff View Compare versions with a clear and concise diff viewer. Open it from the source control view or via the `Open diff view` command. ### ๐Ÿ“ Signs in the Editor View line-by-line changes directly in the editor with added, modified, and deleted line/hunk indicators. You can stage and reset changes right from the signs. There also commands to navigate between hunks and stage/reset hunks under the cursor. Needs to be enabled in the plugin settings. ## Available Commands > Not exhaustive - these are just some of the most common commands. For a full list, see the Command Palette in Obsidian. - ๐Ÿ”„ Changes - `List changed files`: Lists all changes in a modal - `Open diff view`: Open diff view for the current file - `Stage current file` - `Unstage current file` - `Discard all changes`: Discard all changes in the repository - โœ… Commit - `Commit`: If files are staged only commits those, otherwise commits only files that have been staged - `Commit with specific message`: Same as above, but with a custom message - `Commit all changes`: Commits all changes without pushing - `Commit all changes with specific message`: Same as above, but with a custom message - ๐Ÿ”€ Commit-and-sync - `Commit-and-sync`: With default settings, this will commit all changes, pull, and push - `Commit-and-sync with specific message`: Same as above, but with a custom message - `Commit-and-sync and close`: Same as `Commit-and-sync`, but if running on desktop, will close the Obsidian window. Will not exit Obsidian app on mobile. - ๐ŸŒ Remote - `Push`, `Pull` - `Edit remotes`: Add new remotes or edit existing remotes - `Remove remote` - `Clone an existing remote repo`: Opens dialog that will prompt for URL and authentication to clone a remote repo - `Open file on GitHub`: Open the file view of the current file on GitHub in a browser window. Note: only works on desktop - `Open file history on GitHub`: Open the file history of the current file on GitHub in a browser window. Note: only works on desktop - ๐Ÿ  Manage local repository - `Initialize a new repo` - `Create new branch` - `Delete branch` - `CAUTION: Delete repository` - ๐Ÿงช Miscellaneous - `Open source control view`: Opens side pane displaying [Source control view](#sidebar-view) - `Open history view`: Opens side pane displaying [History view](#history-view) - `Edit .gitignore` - `Add file to .gitignore`: Add current file to `.gitignore` ## ๐Ÿ’ป Desktop Notes ### ๐Ÿ” Authentication Some Git services may require further setup for HTTPS/SSH authentication. Refer to the [Authentication Guide](https://publish.obsidian.md/git-doc/Authentication) ### Obsidian on Linux - โš ๏ธ Snap is not supported due to its sandboxing restrictions. - โš ๏ธ Flatpak is not recommended, because it doesn't have access to all system files. They are actively fixing many issues, but there are still issues. Especially with more advanced setups. - โœ… Please use AppImage or a full access installation of your system's package manager instead ([Linux installation guide](https://publish.obsidian.md/git-doc/Installation#Linux)) ## ๐Ÿ“ฑ Mobile Support (โš ๏ธ Experimental) The Git implementation on mobile is **very unstable**! I would not recommend using this plugin on mobile, but try other syncing services. One such alternative is [GitSync](https://github.com/ViscousPot/GitSync), which is available on both Android and iOS. It is not associated with this plugin, but it may be a better option for mobile users. A tutorial for setting it up can be found [here](https://viscouspotenti.al/posts/gitsync-all-devices-tutorial). > ๐Ÿงช The Git plugin works on mobile thanks to [isomorphic-git](https://isomorphic-git.org/), a JavaScript-based re-implementation of Git - but it comes with serious limitations and issues. It is not possible for an Obsidian plugin to use a native Git installation on Android or iOS. ### โŒ Mobile Feature Limitations - No **SSH authentication** ([isomorphic-git issue](https://github.com/isomorphic-git/isomorphic-git/issues/231)) - Limited repo size, because of memory restrictions - No rebase merge strategy - No submodules support ### โš ๏ธ Performance Caveats > [!caution] > Depending on your device and available free RAM, Obsidian may > > - crash on clone/pull > - create buffer overflow errors > - run indefinitely. > > It's caused by the underlying git implementation on mobile, which is not efficient. I don't know how to fix this. If that's the case for you, I have to admit this plugin won't work for you. So commenting on any issue or creating a new one won't help. I am sorry. ### Tips for Mobile Use: If you have a large repo/vault I recommend to stage individual files and only commit staged files. ## ๐Ÿ™‹ Contact & Credits - The Line Authoring feature was developed by [GollyTicker](https://github.com/GollyTicker), so any questions may be best answered by her. - This plugin was initial developed by [denolehov](https://github.com/denolehov). Since March 2021, it's me [Vinzent03](https://github.com/Vinzent03) who is developing this plugin. That's why the GitHub repository got moved to my account in July 2024. - If you have any kind of feedback or questions, feel free to reach out via GitHub issues. ## โ˜• Support If you find this plugin useful and would like to support its development, you can support me on Ko-fi. [](https://ko-fi.com/F1F195IQ5) --- ## File: docs/dev/LineAuthorFeature.md # Line Authoring Feature - Developer Documentation - This feature was developed by [GollyTicker](https://github.com/GollyTicker). - [Feature documentation for users](https://publish.obsidian.md/git-doc/Line+Authoring) ## Architecture To understand how this feature integrates with the [Codemirror 6 editor](https://codemirror.net/) used in the Obsidian editors, it is adviseable to read the following sections of the [Codemirror Guide](https://codemirror.net/docs/guide/): - Architecture Overview > (everything) - Data Model - Configuration - Facets - Transactions - View > (intro) - Extending Codemirror - State Fields Furthermore, the following concepts are necessary: - [EditorState](https://codemirror.net/docs/ref/#state.EditorState) - [State Field](https://codemirror.net/docs/ref/#state.StateField) - [Transaction](https://codemirror.net/docs/ref/#state.Transaction) - [Creating a transaction](https://codemirror.net/docs/ref/#state.EditorState.update) - [Annotation within a transaction](https://codemirror.net/docs/ref/#state.Annotation) - [ChangeSet](https://codemirror.net/docs/ref/#state.ChangeSet) (for the unsaved changes gutter update) - [Exmaple: Document Changes](https://codemirror.net/examples/change/) - [Example: Configuratoin and Extension](https://codemirror.net/examples/config/) Given changes/updates of the file or file-view within Obsidian, we want to re-compute the line authoring (via [git-blame](https://git-scm.com/docs/git-blame)) and show it in the line gutters left to the editors. When doing this, we need to integrate with the declarative modeling of Codemirror - and have its views automatically updated, when we change its associated data. We achieve the goal via the following steps: 1. Every new editor pane in Obsidian subscribes itself by its filepath ([LineAuthoringSubcriber](/src/lineAuthor/control.ts)) and listens in an internal publish-subscriber-model ([eventsPerFilepath.ts](/src/lineAuthor/eventsPerFilepath.ts)) for updates on that filepath. 2. Any changed file in the Obsidian Vault or anytime when a new file is opened, [lineAuthorProvider](/src/lineAuthor/lineAuthoProvider.ts) initiates the asynchronous computation of the [LineAuthoring](/src/lineAuthor/model.ts) via [simpleGit.ts](/src/simpleGit.ts) - which parses the output of `git-blame`. 3. Once the `LineAuthoring` is computed, the publish-subscriber-model is notified of the new value for the corresponding filepath. 4. The notified `LineAuthoringSubcriber` creates a new transaction (via [newComputationResultAsTransaction](/src/lineAuthor/model.ts)) containing the `LineAuthoring`. 5. The `LineAuthoringSubscriber` [dispatches the transaction on the current EditorView](https://codemirror.net/docs/ref/#view.EditorView.dispatch). 6. The [StateField's update](https://codemirror.net/docs/ref/#state.StateField^define^config.update) method is called by Codemirror due to the dispatched transaction. The [lineAuthorState](/src/lineAuthor/model.ts) updates itself with the newest `LineAuthoring`, if it one was provided in the transaction. 7. The [lineAuthorGutter](/src/lineAuthor/view/view.ts) is automatically re-rendered, due to the dispatch and the changes of the state-fields. The re-rendering now accesses the newest state-field values - resulting in a new DOM. ## Development You can use this test-vault https://github.com/GollyTicker/obsidian-git-test-vault-online. Once the watchmode npm is started, one can simply open the `test-vault` in Obsidian to test the plugin. The Git plugin files are symbolic links to the automatically re-compiled files at repository root level. One can additionally use the [docker-setup from this branch for a reproduceable developer setup](https://github.com/GollyTicker/obsidian-git/tree/docker-setup). ## Edge cases and error cases These cases should be tested, when changes to this feature have been made. - running outside of a git repository - opening an untracked file - opening and closing obsidian windows of panes/notes - notes with a starting "--" in their filename - special characters in filenames - unicode filenames - empty file - file with populated last line - multi-line block with differeing line commits - examples for moving/copy-following - submodules - vault root != repository root - error in git blame result - open multiple files simultanously - open same file multiple times - and edit - open same files in multiple windows - and edit - open empty tracked file and make edits. quick update should respond sensibly - open file in a large, complex real-world vault with unknown characteristics (the private vault of the developer GollyTicker suffices) and repeatedly press Enter in a tracked file. - We expect no errors, but after adding the unsaved changed gutter update feature, an early bu was present, where errors would occur during rendering and the view would become messed up. - UI should render correctly regardless of whether line numbers are shown as well or not. - [[see obsidan forum discussion](https://forum.obsidian.md/t/added-editor-gutter-overlaps-and-obscures-editor-content/45217) - indentation changes and changes after last line (without trailing newline) with 'Ignored whitespace' enabled/disabled - [Unsaved Changes Gutter Update Scenario](#unsaved-changes-gutter-update-scenario) - commit file in a different time-zone than the current Obsidian user - check that time-zone "local" formatting is correct - time-zone "UTC" should always show the same result regardless of the local time-zone - line authoring id correctly uses submodule HEAD revision rather than super-project. - There was a bug with the old super-project identifier. It did not fully work with submodules as the following scenario lead to a different displayed line authoring, than the true one. 1. remember the lineAuthoringId A for a file in a submodule in the vault. - it uses the HEAD of the git super-project rather than of the submodule the file is contained in. 2. add a few lines in the file. The plugin will correctly detect the changed file-contents hash, which will trigger re-computation and re-render. 3. commit the changes in the submodule - without making a corresponding commit in the super-project. 4. Close the file and re-open it in Obsidian. - In the submodule, the HEAD has changed - but not in the super-project. - Since the file path and file contents are same after committing, they haven't changed. - The current cache key doesn't detect this change and hence the view isn't updated. - Reloading Obsidian entirely will evict the cache - and the line authoring will be shown correctly again. ### Unsaved Changes Gutter Update Scenario This scenario contains two main cases to test: #### 1. Untracked file 1. Open an untracked file. It should show +++ everywhere. 2. Make insertions, deletions and in-line changes. It should always show +++. #### 2. Tracked file 1. Open a tracked file with different line author dates and colors 2. Make insertions, deletions and in-line changes. - It should first show % until the changes are saved and the line authoring is computed. - The % should preserving the color of the changed line and insertions/deletions should shift the line authoring for subsequent lines accordingly 3. Make multi-line insertions, deletions and in-line changes (e.g. via cut-copy-pasting of blocks of text). - Hint: Use Ctrl+Z as well. - The behavior should be same as above. 4. Make changes at the intersection of unsaved and saved changes. The result should be consistent with above. ## Potential Future Improvements - show commit info when click/hover on gutter - show / highlight diff when hover/click on gutter - small tooltip widget when hovering/right-clicking on line author gutter with author/hash, etc. - show deleted lines - interpret new 'newline' at end of line as non-change to make gutter change marking more intuitive. - [one option is to add a setting which switches between compatibility-mode and comfort-mode](https://github.com/denolehov/obsidian-git/pull/288) - distinguish untracked and changed line (e.g. "~" and "+") - use addMomentFormat in settings.ts when configuring the line author date format. - main.ts: refreshUpdatedHead(): Detect, if the head has changed from outside of Git (e.g. script) and run this callback then. - Avoid "Uncaught illegal access error" when closing a separate Obsidian window. It doesn't seem to have any impact on UX yet though... - Unique initials option: [work in progress branch](https://github.com/GollyTicker/obsidian-git/tree/line-author-unique-initials) --- ## File: docs/Authentication.md --- aliases: - "04 Authentication" --- # macOS ## HTTPS Run the following to use the macOS keychain to store your credentials. ```bash git config --global credential.helper osxkeychain ``` You have to do one authentication action (clone/pull/push) after setting the helper in the terminal. After that you should be able to clone/pull/push in Obsidian without any issues. ## SSH Remember you still have to setup ssh correctly, like adding your SSH key to the `ssh-agent`. GitHub provides a great documentation on how to [generate a new SSH key](https://docs.github.com/en/authentication/connecting-to-github-with-ssh/generating-a-new-ssh-key-and-adding-it-to-the-ssh-agent?platform=mac#generating-a-new-ssh-key) and then on how to [add the SSH key to your ssh-agent](https://docs.github.com/en/authentication/connecting-to-github-with-ssh/generating-a-new-ssh-key-and-adding-it-to-the-ssh-agent?platform=mac#adding-your-ssh-key-to-the-ssh-agent). # Windows ## HTTPS Ensure you are using Git 2.29 or higher and you are using Git Credential Manager as a credential helper. You can verify this by executing the following snippet in a terminal, preferably in the directory where your vault/repository is located. It should output `manager`. ```bash git config credential.helper ``` If this doesn't output `manager`, please run `git config set credential.helper manager` Just execute any authentication command like push/pull/clone and a pop window should come up, allowing your to sign in. Alternatively, you can also leave that setting empty and always provide the username and password manually via the prompted modal in Obsidian. All available credential helpers are listed [here](https://git-scm.com/doc/credential-helpers)., ## SSH Remember you still have to setup ssh correctly, like adding your SSH key to the `ssh-agent`. GitHub provides a great documentation on how to [generate a new SSH key](https://docs.github.com/en/authentication/connecting-to-github-with-ssh/generating-a-new-ssh-key-and-adding-it-to-the-ssh-agent?platform=windows#generating-a-new-ssh-key) and then on how to [add the SSH key to your ssh-agent](https://docs.github.com/en/authentication/connecting-to-github-with-ssh/generating-a-new-ssh-key-and-adding-it-to-the-ssh-agent?platform=windows#adding-your-ssh-key-to-the-ssh-agent). # Linux ## HTTPS ### Storing To securely store the username and password permanently without having to reenter it all the time you can use Git's [Credential Helper](https://git-scm.com/book/en/v2/Git-Tools-Credential-Storage). `libsecret` stores the password in a secure place. On GNOME it's backed up by [GNOME Keyring](https://wiki.gnome.org/Projects/GnomeKeyring/) and on KDE by [KDE Wallet](https://wiki.archlinux.org/title/KDE_Wallet). To set `libsecret` as your credential helper execute the following in the terminal from the directory of your vault/repository. You can also add the `--global` flag to set that setting for all other repositories on your device, too. ```bash git config credential.helper libsecret ``` You have to do one authentication action (clone/pull/push) after setting the helper in the terminal. After that you should be able to clone/pull/push in Obsidian without any issues. In case you get the message `git: 'credential-libsecret' is not a git command`, libsecret is not installed on your system. You may have to install it by yourself. Here is an example for Ubuntu. ```bash sudo apt install libsecret-1-0 libsecret-1-dev make gcc sudo make --directory=/usr/share/doc/git/contrib/credential/libsecret # NOTE: This changes your global config, in case you don't want that you can omit the `--global` and execute it in your existing git repository. git config --global credential.helper \ /usr/share/doc/git/contrib/credential/libsecret/git-credential-libsecret ``` ### SSH_PASS Tools When Git is not connected to any terminal, so you can't enter your username/password in the terminal, it relies on the `GIT_ASKPASS`/`SSH_ASKPASS` environment variable to provide an interface to the user to enter those values. #### Native SSH_ASKPASS In case you don't want to store it permanently you can install `ksshaskpass` (it's preinstalled on KDE systems) and set it as binary to ask for the password. To use `ksshaskpass` in Obsidian as the tool for `SSH_ASKPASS` add the following line to the "Additional Environment Variables" in the plugin's settings in the "Advanced" section. ``` SSH_ASKPASS=ksshaskpass ``` You should get a new window to enter your username/password when using a Git action needing authentication now. #### SSH_PASS integrated in Obsidian The plugin now automatically provides an integrated script for the `SSH_ASKPASS` environment variable, if no other program is set, that opens a modal in Obsidian whenever Git asks for username or password. ## SSH With one of the above [[#SSH_PASS Tools]] installed to enter your passphrase, you can use ssh with a passphrase. Remember you still have to setup ssh correctly, like adding your SSH key to the `ssh-agent`. GitHub provides a great documentation on how to [generate a new SSH key](https://docs.github.com/en/authentication/connecting-to-github-with-ssh/generating-a-new-ssh-key-and-adding-it-to-the-ssh-agent?platform=linux#generating-a-new-ssh-key) and then on how to [add the SSH key to your ssh-agent](https://docs.github.com/en/authentication/connecting-to-github-with-ssh/generating-a-new-ssh-key-and-adding-it-to-the-ssh-agent?platform=linuxu#adding-your-ssh-key-to-the-ssh-agent). --- ## File: docs/Common issues.md ## xcrun: error: invalid developer path This is an error occurring only on macOS. It's easy to fix though. Just run the following snippet in the terminal. `xcode-select --install` See #64 as an example. ## Error: spansSync git ENOENT/ Cannot run Git command This occurs, when the plugin can't find the Git executable. It takes it from the PATH. Head over to [[Installation]] to see if everything is properly installed for your platform. If you think everything is correctly set up and the error still occurs try the following: In case you know where Git is installed, you can set the path under "Custom Git binary path" in the settings. If you don't know where Git is installed, you can try to find it by running the following in the terminal: ### Windows Run `where git` in the terminal. It should return the path to the Git executable. If it fails, Git is not properly installed. ### Linux/MacOS Run `which git` in the terminal. It should return the path to the Git executable. If it fails, Git is not properly installed. ## Infinite pulling/pushing with no error That's most time caused by authentication problems. Head over to [[Authentication]] ## Bad owner or permissions on /home/\/.ssh/config Run `chmod 600 ~/.ssh/config` in the terminal. ## Files in `.gitignore` aren't ignored Since the plugin uses the native git installation, I can assure you that if the `.gitignore` file is properly written and git is correctly used, everything should work. It's important to note that once a file is committed (or staged) changing the `.gitignore` doesn't help. You have to delete the file from your repo manually to ignore the file properly: 1. Run `git rm --cached ` in your terminal. The file will stay on your file system. It's just deleted in your repo. 2. The file should be listed as deleted in `git status` 3. Commit the deletion 4. Now any changes to the file are properly ignored. ## Cannot run gpg ``` Error: error: cannot run gpg: No such file or directory error: gpg failed to sign the data fatal: failed to write commit object ``` See [[Integration with other tools#GPG Signing]] on how to solve this. ## This repository is configured for Git LFS but 'git-lfs' was not found on your path. See [[Integration with other tools#Git Large File Storage]] on how to solve this. --- ## File: docs/Features.md ## Source Control View Open it using the "Open source control view" command. It lists all current changes like when you run `git status`. It provides the following features - Stage/Unstage individual files - Discard any changes to a specific file - Open the diff view for changed files - Stage/Unstage all files - Push/Pull - Commit or [[Start here#commit-and-sync|commit-and-sync]] - Switch between list and tree view using the button at the top ## History View Open it using the "Open history view" command. It behaves like `git log` resulting in a list of the last commits. Each commit entry can be expanded to see the changed files in that commit. By clicking on a file, you can even see the diff. ## Line Authoring For each line, view the last time, it was modified: [[Line Authoring|Line Authoring]]. Technically known as `git-blame`. ## Automatic commit-and-sync See [[Start here#commit-and-sync|commit-and-sync]] for an explanation of the term. The goal of automatic commit-and-sync is that you can focus on taking notes and not care about saving your work, as this plugin will take care of it. There are multiple ways to trigger an automatic commit-and-sync. The default is a basic interval to run commit-and-sync every X minutes. Use the "Auto commit-and-sync interval" setting for that. The interval works across Obsidian sessions to ensure opening Obsidian only for short times doesn't prevent running commit-and-sync. For example, if you set a 15 minutes interval, you don't have to keep Obsidian open for 15 minutes. If you close Obsidian before the interval end, the commit-and-sync will automatically run the next time you start Obsidian. Another method is to enable "Auto commit-and-sync after stopping file edits". This waits X minutes after your latest change for the commit-and-sync. This is useful if you don't want to get interrupted by a commit while typing. The last mode is the "Auto commit-and-sync after latest commit" setting. This sets the last commit-and-sync timestamp to the latest commit. By default, the plugin only compares with it's own latest run of commit-and-sync. So if you manually commit and want the commit-and-sync timer to reset, enable this setting. ## Commit message The plugin uses [momentjs](https://momentjs.com/) for formatting the date, so read through their documentation on how to construct your date placeholder. ## Submodules Support Since version 1.10.0 submodules are supported. While adding/cloning new submodules is still not supported (might come later), updating existing submodules on the known "Commit-and-sync" and "Pull" commands is supported. This works even recursively. "Commit-and-sync" will cause adding, commit and push (if turned on) all changes in all submodules. This feature needs to be turned on in the settings. Additional **requirements**: - Checked out branch (not just a commit as it is when running `git submodule update --init`) - Tracking branch is set up, so that `git push` works - Tracking branch needs to be fetched, so that a `git diff` with the branch works --- ## File: docs/Getting Started.md # Desktop You can either start by cloning an existing remote repository as described [[#For existing remote repository|here]] or start with initializing a new repository locally and optionally push that to a remote repository as described [[#Create new local repository|here]]. ## Create new local repository 1. Follow the [[Installation]] instructions for your operating system 2. Call the `Initialize a new repo` command 3. Create your first commit by creating some files and calling the `Commit all changes with specific message` command 4. If you want to Setup to push it to a remote repository like to GitHub: 1. Setup [[Authentication]] 2. Ensure that the remote repository is empty. Otherwise delete the repository and instead proceed to clone the remote repository as described in the [[#For existing remote repository|next section]]. 3. Call the `Push` command. It should ask you for a name and URL of the remote repository. Just enter `origin` for the remote name and copy the URL to push to somewhere from your remote git service. ## For existing remote repository To clone, you have to use a remote URL. This can be one of two protocols: either `https` or `ssh`. This depends on your chosen [[Authentication]] method. `https`: `https://github.com//.git` `ssh`: `git@github.com:/.git` 1. Follow the [[Installation]] instructions for your operating system 2. Setup [[Authentication]] 3. Git can only clone a remote repo in a new folder. Thus you have two options - Use the "Clone an exising remote repository" command to clone your repo into a subfolder of your vault. You then have again two choices - Move all your files from the new folder (including `.git` !) into your vault root. - Open your new subfolder as a new vault. You may have to install the plugin again. - Run `git clone ` in the command line wherever you want your vault to be located. 4. Read on how to best configure your [[Tips-and-Tricks#Gitignore|.gitignore]] > [!info] iCloud and Git > When syncing your vault with iCloud and using Git on your desktop device the whole `.git` directory gets synced to your mobile device as well. This may slow down the Obsidian startup time. > - One solution is to put the git repository above your Obsidian vault. So that your vault is a sub directory of your git repository. > - Another solution is to move the `.git` directory to another location and create a `.git` file in your vault with only the following line: `gitdir: ` # Mobile The Git implementation on mobile is **very unstable**! I would not recommend using this plugin on mobile, but try other syncing services. One such alternative is [GitSync](https://github.com/ViscousPot/GitSync), which is available on both Android and iOS. It is not associated with this plugin, but it may be a better option for mobile users. A tutorial for setting it up can be found [here](https://viscouspotenti.al/posts/gitsync-all-devices-tutorial). Another alternative for iOS is [Working Copy](https://workingcopy.app/). ## Restrictions I am using [isomorphic-git](https://isomorphic-git.org/), which is a re-implementation of Git in JavaScript, because you cannot use native Git on Android or iOS. - SSH authentication is not supported ([isomorphic-git issue](https://github.com/isomorphic-git/isomorphic-git/issues/231)) - Repo size is limited, because of memory restrictions - Rebase merge strategy is not supported - Submodules are not supported ## Performance on mobile > [!danger] Warning > Depending on your device and available free RAM, Obsidian may > - crash on clone/pull > - create buffer overflow errors > - run indefinitely. > > It's caused by the underlying git implementation on mobile, which is not efficient. I don't know how to fix this. If that's the case for you, I have to admit this plugin won't work for you. So commenting on any issue or creating a new one won't help. I am sorry. ## Start with existing remote repository ### Clone via plugin Follow these instructions for setting up an Obsidian Vault on a mobile device that is already backed up in a remote git repository. The instructions assume you are using [GitHub](https://github.com), but can be extrapolated to other providers. 1. Make sure any outstanding changes on all devices are pushed and reconciled with the remote repo. 2. Install Obsidian for Android or iOS. 3. Create a new vault (or point Obsidian to an empty directory). Do NOT select `Store in iCloud` if you are on iOS. 4. If your repo is hosted on GitHub, [authentication must be done with a personal access token](https://github.blog/2020-12-15-token-authentication-requirements-for-git-operations/). Detailed instruction for that process can be found [here](https://docs.github.com/en/authentication/keeping-your-account-and-data-secure/creating-a-personal-access-token). - Minimal permissions required are - "Read access to metadata" - "Read and Write access to contents and commit status" 5. In Obsidian settings, enable community plugins. Browse plugins to install Git. 6. Enable Git (on the same screen) 7. Go to Options for the Git plugin (bottom of main settings page, under Community Plugins section) 8. Under the "Authentication/Commit Author" section, fill in the username on your git server and your password/personal access token. 9. Don't touch any settings under "Advanced" 10. Exit plugin settings, open command palette, choose "Git: Clone existing remote repo". 11. Fill in repo URL in the text field and press the repo URL button below it. The repo URL is NOT the URL in the browser. You have to append `.git`. - `https://github.com//.git` - E.g. `https://github.com/denolehov/obsidian-git.git` 12. Follow instructions to determine the folder to place repo in and whether an `.obsidian` directory already exits. 13. Clone should start. Popup notifications (if not disabled) will display the progress. Do not exit until a popup appears requesting that you "Restart Obsidian". ### Clone via Working Copy on iOS Depending on the size of your repository and your device, Obsidian may crash during clone via the plugin. Alternatively, the initial clone can be done via [Working Copy](https://workingcopy.app/). None that this a paid app. The usual commit-and-sync can then be done via the plugin. The following guide assumes you don't commit your `.obsidian` directory. 1. Make sure any outstanding changes on all devices are pushed and reconciled with the remote repo. 2. Install Obsidian for Android or iOS. 3. Create a new vault (or point Obsidian to an empty directory). Do NOT select `Store in iCloud` if you are on iOS. 4. If your repo is hosted on GitHub, [authentication must be done with a personal access token](https://github.blog/2020-12-15-token-authentication-requirements-for-git-operations/). Detailed instruction for that process can be found [here](https://docs.github.com/en/authentication/keeping-your-account-and-data-secure/creating-a-personal-access-token). - Minimal permissions required are - "Read access to metadata" - "Read and Write access to contents and commit status" 5. Swipe up and away Obsidian to fully close it. Open Working Copy app. 6. Clone the repo using Working Copy. Instead of logging in to GitHub through the Working Copy interface, enter the clone URL directly. Then enter your username, and for the password your Personal Access Token. 7. Open Files app. 8. Copy the repo from Working Copy. Delete the vault from Obsidian and paste the repo there (repo has the same name as the vault). 9. Open Obsidian. 10. All your cloned files should be visible. 11. Install and enable the Git plugin. 12. Add your name/email to the "Authentication/Commit Author" section in the plugin settings. 13. Use the command palette to call the "Pull" command. ## Start with new repo Similar steps as [existing repo](#existing-repo), except use the `Initialize a new repo` command, followed by `Edit remotes` to add the remote repo to track. This remote repo will need to exist and be empty. Also make sure to read on how to best configure your [[Tips-and-Tricks#Gitignore|.gitignore]]. --- ## File: docs/Installation.md --- aliases: - 02 Installation --- > [!important] > Although the plugin itself is desktop platform independent, an incorrect installation of Obsidian or Git may break the plugin. ## Plugin installation ### From within Obsidian Go to "Settings" -> "Community plugins" -> "Browse", search for "Git", install and enable it. ### Manual 1. Download `obsidian-git-.zip` from the [latest release](https://github.com/Vinzent03/obsidian-git/releases/latest) 2. Unpack the zip in `/.obsidian/plugins/obsidian-git` 3. Restart Obsidian 4. Go to settings and disable restricted mode 5. Enable `Git` # Windows Installing [GitHub Desktop](https://github.com/apps/desktop) is **not** enough! You need to install regular Git as well. ## Git installation > [!info] > Ensure you are using Git 2.29 or higher. Install Git from the official [website](https://git-scm.com/download/win) with all default settings. Make sure you have `3rd-party software` access enabled. ![[third-party-windows-git.png]] Enable Git Credential Manager. You can verify this for existing installations by executing the following. It should ouput `manager`. ```bash git config credential.helper ``` ![[credential-manager-windows-git.png]] # Linux ## Obsidian installation Known **supported** Obsidian installation methods: - AppImage Known **not fully supported** package managers - Snap (Snap puts Obsidian in a kind of sandbox, so that Obsidian can't access Git) - [Flatpak](https://flathub.org/apps/details/md.obsidian.Obsidian) can access Git, but not all system files, so it's not recommended. If you installed Obsidian a while ago via **Flatpak**, and it doesn't work, please run the following snippet. ``` $ flatpak update md.obsidian.Obsidian $ flatpak override --reset md.obsidian.Obsidian $ flatpak run md.obsidian.Obsidian ``` [Source of this snippet](https://github.com/flathub/md.obsidian.Obsidian/issues/5#issuecomment-736974662) # MacOS ## Git Installation In order to install `git` on your Mac Computer please follow a suitable route explained in the [Official Git documentation](https://git-scm.com/install/mac) ## Keychain Run the following to use the macOS keychain to store your credentials. ```zsh git config --global credential.helper osxkeychain ``` >[!info] > You have to complete a **single authenticated action** (either clone, pull or push) after setting the helper in the terminal. Once done, you should be able to sync Obsidian without any issues. --- ## File: docs/Integration with other tools.md Most issues with the integration of other installable tools are that their installation path is not added to the `PATH` environment variable. The `PATH` environment variable contains the directories where to search for executable programs. You probably don't have issues with executing your tools from the terminal, because you edited the `PATH` in your `.bashrc`,`.zshrc`, but those files only apply to your shell and not to desktop applications like Obsidian. So some installation directories are missing in the `PATH` and the plugin can't find them. # Git Large File Storage Git Large File Storage is supported, but may need a bit configuration for the plugin to find the `git-lfs` executable. ## MacOS 1. Make sure to install [git-lfs](https://git-lfs.com/) using `brew install git-lfs`. - This will install `git-lfs` to `/opt/homebrew/bin/`, which is probably not in your `PATH` environment variable when using Obsidian. 2. To make `/opt/homebrew/bin/` available in Obsidian, add `/opt/homebrew/bin/` to the "Additional PATH environment variables paths" setting under "Advanced". 3. Restart Obsidian. ## Linux 1. Make sure to install [git-lfs](https://git-lfs.com/). - The place where `git-lfs` is installed to varies by package manager and distribution. Usually there is no need to manually add it to your `PATH`, but if the plugin can't find `git-lfs`follow the next steps. 2. Run `which git-lfs` in your terminal to get the installation path. It should output something of the form `/git-lfs. 2. Add the `` part of the previous step to the "Additional PATH environment variables paths" setting under "Advanced". 3. Restart Obsidian. ## Windows There is no need to change anything for the plugin, because git-lfs is installed with Git for Windows and should be available if Git is available as well. # GPG Signing GitHub provides a great [documentation about GPG](https://docs.github.com/en/authentication/managing-commit-signature-verification/generating-a-new-gpg-key), which should work with Obsidian as well. One issue you might encounter though is the following: ``` Error: error: cannot run gpg: No such file or directory error: gpg failed to sign the data fatal: failed to write commit object ``` This means there is no `gpg` binary in your PATH, which you may have only properly configured for your shell. But since Obsidian is started in a different way, these PATH modifications don't affect Obsidian. To get the binary path of your `gpg` installation, run `which gpg` on Linux and Mac-OS and `where gpg` on Windows. A common location may be `/usr/local/bin/gpg`. - You can either add that to the "Additional PATH environment variables" plugin setting to provide the gpg binary to your plugin installation only. - Or set it in your Git config via `git config --global gpg.program ` to set the gpg binary globally for all git repositories. Please create an issue if you encounter any issues and the documentation needs to be improved. --- ## File: docs/Line Authoring.md # Quick User Guide A quick showcase of all functionality. This feature is based on [git-blame](https://git-scm.com/docs/git-blame). โ„น๏ธ The line author view only works in Live-Preview and Source mode - not in Reading mode. โ„น๏ธ Currently, only Obsidian on desktop is supported. โ„น๏ธ The recently released Obsidian v1.0 is fully supported. The images and GIFs in this document are however not yet updated. ## Activate It can also be activated via Command Palette `Git: Toggle line author information`. ## Default line author information Shows the initials of the author as well as the authoring date in `YYYY-MM-DD` format. The `*` indicates, that the author and committer (or their timestamps) are different - i.e., due to a rebase. ## Commit hash and full name via config ## Natural language dates ## Custom date formats via config ## Commit time in local/author/UTC time-zone **UTC+0000/Z** The simplest option to start with is showing the time in `UTC+00:00/Z` time-zone. This is independent of both your local and the author's time-zone. It is shown with a suffix `Z` to avoid confusion with local time. This is the time displayed in the guter is the same for all users. **My local (default)** By default, the times are shown in your local time-zone - i.e., `What was the clock-time at my wall showing, when the commit was made?` This depends on your local time-zone. For instance, this is the view for a user in the `UTC+01:00` time-zone. Note, how the displayed time is `1h` ahead of the above `UTC+0000` time. **Author's local** Alternatively, it can show it in the author's time-zone with explicit `UTC` offset - i.e., `What was clock-time at the author's wall and their explicit UTC offset, when the commit was made?` This is independent of your local time-zone and the same time is displayed for all users. **Configuration** ## Age-based gutter colors The line gutter color is based on the age of the commit. It adapts to the dark/light mode automatically. Red-ish means newer and blue-ish means older. All commits at and above a certain maximum coloring age (configurable; default `1 year`) get the same strongest blue-ish color. The colors are configurable and the defaults are chosen to be accessible. ## Adjust text color CSS based on theme By default, the gutter text color uses `var(--text-muted)` which is whatever is defined by your theme. You can however, change it to a different CSS color or variable. Example: | `var(--text-muted)` | `var(--text-normal)` | |----------------------------------------------|-----------------------------------------------| | | | ## Copy commit hash ## Quick configure gutter ## New/uncommitted lines and files show `+++` ## Follow lines across cut-copy-paste-ing within same commit / all commits By default, each line shows the last commit, where it was changed. This means, that cut-copy-paste-ing lines will show the new commit, even though it was not originally written in that commit. However, if for instance following is set to `all commits`, then this is the result: Configuration: ## Soft and unintrusive ansynchronous view updates Since computing the line author information takes time (due to a `git blame` shell invocation) the result appears delayed. To minimize distraction and improve user experience, the view is updated in a soft and unintrusive manner. When opening a file, a placeholder is shown meanwhile: While editing, a placeholder is shown as well until the file is saved and the line author information is computed. ## Multi-line block support The markdown rendering of multiple lines as a combined block is also supported. In this case the newest of all lines is shown in the gutter. ## Ignore whitespace and newlines This can be activated in the settings. | **Original** | **Changed with preserved whitespace** | **Changed with ignored whitespace** | | ---------------------------------------------------- | ------------------------------------------------------- | ----------------------------------------------------- | | | | | Note, how ignoring the whitespace does not mark the indented lines as changes, as only additional whitespace was added. ## Submodules support Line author information is fully supported in submodules. --- ## File: docs/Start here.md --- aliases: - "01 Start here" --- # Git plugin Documentation ## Topics - [[Installation|Installation]] - [[Getting Started|Getting Started]] - [[Authentication|Authentication]] - [[Integration with other tools]] - [[Features|Features]] - [[Tips-and-Tricks|Tips-and-Tricks]] - [[Common issues|Common Issues]] - [[Line Authoring|Line Authoring]] > [!warning] Obsidian installation on Linux > Please don't use Flatpak or Snap to install Obsidian on Linux. Learn more [[Installation#Linux|here]] ![[Getting Started#Performance on mobile]] ## What is Git? Git is a version control system. It allows you to keep track of changes to your notes and revert back to previous versions. It also allows you to collaborate with other people on the same files. You can read more about Git [here](https://git-scm.com/book/en/v2/Getting-Started-About-Version-Control). > [!info] Git/GitHub is not a syncing service! > Git is not meant to share your changes live to the cloud or another person. Meaning it should not be used to work with someone live on the same note. However, it's perfect for async collaboration. You build your history by batching multiple changes into commits. These can then be reverted or checked out. You can view the difference between version of a note via the [Version History Diff](obsidian://show-plugin?id=obsidian-version-history-diff) plugin. Git itself only manages a local repository. It becomes really handy in conjunction with an online remote repository. You can push and pull your commits to/from a remote repository to share or backup your vault. The most popular provider is [GitHub](https://github.com). Git is primarily used by developers and thus the command line is sometimes needed. Obsidian-Git is a plugin for Obsidian that allows you to use Git from within Obsidian without always having to use the command line or leaving Obsidian. ## Terminology and concepts ### Backup - no longer in use For simplification, the term "Backup" refers to staging everything -> committing -> pulling -> pushing. ### Sync Syncing is the process of pulling and pushing changes to and from a remote repository. This is done to keep your local repository up to date with the remote repository on e.g. GitHub. ### Commit-and-sync Commit-and-sync is the process of staging everything -> committing -> pulling -> pushing. Ideally this is a single action that you do regularly to keep your local and remote repository in sync. It's recommended you set it up from the plugin's settings to be run automatically every X minutes. You can also disable the pulling or pushing part from the "Commit-and-sync" section in the plugin's settings. This reduces the "commit-and-sync" action to either a "commit and pull", "commit and push" or just commit action.