jaidetree83 downloadsEnforce shared base settings across multi-user vaults by deeply merging template JSON files into config files.
An Obsidian plugin for enforcing shared base settings across multi-user vaults.
Define partial JSON files that get deeply merged into .obsidian config files on startup and whenever settings change. Base template values always win on conflict, ensuring shared settings are enforced while still giving each user freedom to add their own customizations.
Teams or projects with multiple contributors can commit a folder of base template files to version control. When any user opens the vault, the plugin automatically merges those templates into their local .obsidian config — enforcing required plugins, shared hotkeys, or any other settings without overriding everything the user has configured.
.obsidian/ to hold your base templates (e.g. .obsidian/base-settings/).obsidian config files you want to manage (e.g. app.json, community-plugins.json).obsidian file — template values take precedence over user values on any conflicting keysIf a target config file does not exist yet (e.g. a plugin hasn't been installed), the template is skipped and will be applied on the next sync after the file is created by Obsidian.
By default the plugin deep-merges objects and replaces all other values (arrays, scalars) with the template value. For arrays you may want a different behaviour — for example, adding required plugins to the user's existing list rather than replacing it entirely.
A merge directive lets template authors declare the strategy for a specific key:
{
"plugins": {
"value": ["required-plugin-a", "required-plugin-b"],
"__mergeDirective": {
"strategy": "concat"
}
}
}
The directive object must have a __mergeDirective key. Any object without that key is treated as a normal value and deep-merged as usual.
Type enforcement: when source and target values both exist for a key, they must share the same type (e.g. both arrays, both strings). A mismatch throws an error. This applies to both plain merges and directive merges — a directive also requires the target key to already exist with a matching type.
| Strategy | Behaviour | unique supported |
|---|---|---|
replace |
value replaces the target value entirely (explicit version of the default) |
yes |
concat |
[...value, ...targetValue] — base items first, then user items |
yes |
unique flagAdd "unique": true to any directive to remove duplicate entries from the result. Deduplication uses value identity, so it works best with primitive arrays such as plugin ID lists.
{
"plugins": {
"value": ["dataview", "templater-obsidian"],
"__mergeDirective": {
"strategy": "concat",
"unique": true
}
}
}
With unique: true, if the user already has "dataview" in their list, it will appear only once in the merged result. First-occurrence order is preserved, so value items always take precedence over target duplicates.
base-settings/community-plugins.json:
{
"value": ["dataview", "templater-obsidian"],
"__mergeDirective": {
"strategy": "concat"
}
}
A user whose community-plugins.json already contains ["calendar"] will end up with ["dataview", "templater-obsidian", "calendar"] after sync.
| Setting | Description | Default |
|---|---|---|
| Base templates path | Folder containing template JSON files, relative to .obsidian/ |
(empty) |
| Debounce interval | Milliseconds to wait after a file change before syncing | 500 |
A sync runs automatically on:
.obsidian/ file changes — re-enforces settings if a user manually reverts a managed value, or when a new plugin config file appearsA Sync base settings command is also available in the command palette to trigger a sync manually.
main.js, manifest.json, and styles.css from the latest release.obsidian/plugins/obsidian-base-settings/ in your vaultnpm install
npm run dev # watch mode
npm run build # production build
npm run lint # lint