Refactor obsidian options module

Signed-off-by: Nikolaos Karaolidis <nick@karaolidis.com>
This commit is contained in:
2024-07-12 12:54:13 +03:00
parent 60f12e7aa5
commit 124f6ab292
4 changed files with 192 additions and 66 deletions

View File

@@ -48,14 +48,26 @@
"tag-pane" "tag-pane"
]; ];
plugins = [ (import ./plugins/minimal-settings.nix { inherit pkgs; }) ]; plugins = [
{
cssSnippets = [ pkg = import ./plugins/minimal-settings.nix { inherit pkgs; };
./snippets/editor-monospace.css extraFiles."data.json".source = (pkgs.formats.json { }).generate "data.json" {
./snippets/file-explorer-separators.css labeledNav = true;
editorFont = "var(--font-monospace)";
};
}
]; ];
theme = import ./themes/minimal.nix { inherit pkgs; }; cssSnippets = {
"file-explorer-separators".source = ./snippets/file-explorer-separators.css;
};
themes = [
{
enable = true;
pkg = import ./themes/minimal.nix { inherit pkgs; };
}
];
}; };
}; };

View File

@@ -42,6 +42,103 @@ in
options.programs.obsidian = options.programs.obsidian =
with lib; with lib;
with types; with types;
let
cssSnippetsOptions =
{ name, config, ... }:
{
options = {
enable = mkOption {
type = bool;
default = true;
description = "Whether to enable the snippet.";
};
name = mkOption {
type = str;
defaultText = literalExpression "name";
description = "Name of the snippet.";
};
source = mkOption {
type = addCheck path (path: if path != null then lib.filesystem.pathIsRegularFile path else true);
description = "Path of the source file.";
};
text = mkOption {
type = str;
description = "Text of the file.";
};
};
config.name = mkDefault name;
};
pluginsExtraFilesOptions =
{ name, config, ... }:
{
options = {
source = mkOption {
type = path;
description = "Path of the source file or directory.";
};
text = mkOption {
type = str;
description = "Text of the file.";
};
target = mkOption {
type = str;
defaultText = literalExpression "name";
description = "Path to target relative to the plugin directory.";
};
};
config.target = mkIf (config ? text) (mkDefault name);
};
pluginsOptions =
{ config, ... }:
{
options = {
enable = mkOption {
type = bool;
default = true;
description = "Whether to enable the plugin.";
};
pkg = mkOption {
type = package;
description = "The plugin package.";
};
extraFiles = mkOption {
type = attrsOf (submodule pluginsExtraFilesOptions);
description = "Additional files to include in the plugin directory.";
};
};
};
themesOptions =
{ config, ... }:
{
options = {
enable = mkOption {
type = bool;
default = false;
description = ''
Whether to set the theme as active.
Only one theme can be active at a time.
'';
};
pkg = mkOption {
type = package;
description = "The theme package.";
};
};
};
in
{ {
enable = mkEnableOption "obsidian"; enable = mkEnableOption "obsidian";
package = mkPackageOption pkgs "obsidian" { }; package = mkPackageOption pkgs "obsidian" { };
@@ -84,22 +181,22 @@ in
]; ];
}; };
plugins = mkOption {
description = "Community plugins to activate.";
type = raw;
default = [ ];
};
cssSnippets = mkOption { cssSnippets = mkOption {
description = "CSS snippets to install."; description = "CSS snippets to install.";
type = raw; type = raw;
default = { };
};
plugins = mkOption {
description = "Community plugins to install and activate.";
type = raw;
default = [ ]; default = [ ];
}; };
theme = mkOption { themes = mkOption {
description = "Obsidian theme package."; description = "Themes to install.";
type = raw; type = raw;
default = null; default = [ ];
}; };
}; };
@@ -141,22 +238,22 @@ in
default = cfg.sharedSettings.corePlugins; default = cfg.sharedSettings.corePlugins;
}; };
plugins = mkOption {
description = "Community plugins to activate.";
type = listOf package;
default = cfg.sharedSettings.plugins;
};
cssSnippets = mkOption { cssSnippets = mkOption {
description = "CSS snippets to install."; description = "CSS snippets to install.";
type = listOf path; type = attrsOf (submodule cssSnippetsOptions);
default = cfg.sharedSettings.cssSnippets; default = cfg.sharedSettings.cssSnippets;
}; };
theme = mkOption { plugins = mkOption {
description = "Obsidian theme package."; description = "Community plugins to install and activate.";
type = nullOr package; type = listOf (submodule pluginsOptions);
default = cfg.sharedSettings.theme; default = cfg.sharedSettings.plugins;
};
themes = mkOption {
description = "Themes to install.";
type = listOf (submodule themesOptions);
default = cfg.sharedSettings.themes;
}; };
}; };
}; };
@@ -172,13 +269,13 @@ in
config = config =
let let
vaults = builtins.filter (vault: vault.enable == true) (builtins.attrValues cfg.vaults); vaults = builtins.filter (vault: vault.enable == true) (builtins.attrValues cfg.vaults);
getManifestId = readDir = dir: builtins.attrNames (builtins.readDir dir);
getManifest =
pkg: pkg:
let let
manifest = builtins.fromJSON (builtins.readFile "${pkg}/manifest.json"); manifest = builtins.fromJSON (builtins.readFile "${pkg}/manifest.json");
in in
manifest.id or manifest.name; manifest.id or manifest.name;
readDir = dir: builtins.attrNames (builtins.readDir dir);
in in
lib.mkIf cfg.enable { lib.mkIf cfg.enable {
home = { home = {
@@ -192,22 +289,29 @@ in
source = (pkgs.formats.json { }).generate "app.json" vault.settings.app; source = (pkgs.formats.json { }).generate "app.json" vault.settings.app;
}; };
}; };
mkAppearance = vault: { mkAppearance = vault: {
name = "${vault.target}/.obsidian/appearance.json"; name = "${vault.target}/.obsidian/appearance.json";
value = { value =
let
enabledSnippets = builtins.filter (snippet: snippet.enable) (
builtins.attrValues vault.settings.cssSnippets
);
activeTheme = lib.lists.findSingle (
theme: theme.enable
) null (throw "Only one theme can be enabled at a time.") vault.settings.themes;
in
{
source = (pkgs.formats.json { }).generate "appearance.json" ( source = (pkgs.formats.json { }).generate "appearance.json" (
vault.settings.appearance vault.settings.appearance
// { // {
enabledCssSnippets = builtins.map ( enabledCssSnippets = builtins.map (snippet: snippet.name) enabledSnippets;
snippet: lib.strings.removeSuffix ".css" (builtins.baseNameOf snippet)
) vault.settings.cssSnippets;
}
// lib.attrsets.optionalAttrs (vault.settings.theme != null) {
cssTheme = getManifestId vault.settings.theme;
} }
// lib.attrsets.optionalAttrs (activeTheme != null) { cssTheme = getManifest activeTheme.pkg; }
); );
}; };
}; };
mkCorePlugins = vault: [ mkCorePlugins = vault: [
{ {
name = "${vault.target}/.obsidian/core-plugins.json"; name = "${vault.target}/.obsidian/core-plugins.json";
@@ -229,14 +333,18 @@ in
}; };
} }
]; ];
mkCommunityPlugins = mkCommunityPlugins =
vault: vault:
let
enabledPlugins = builtins.filter (plugin: plugin.enable) vault.settings.plugins;
in
[ [
{ {
name = "${vault.target}/.obsidian/community-plugins.json"; name = "${vault.target}/.obsidian/community-plugins.json";
value = { value = {
source = (pkgs.formats.json { }).generate "community-plugins.json" ( source = (pkgs.formats.json { }).generate "community-plugins.json" (
builtins.map getManifestId vault.settings.plugins builtins.map (plugin: getManifest plugin.pkg) enabledPlugins
); );
}; };
} }
@@ -255,28 +363,35 @@ in
++ builtins.map ( ++ builtins.map (
plugin: plugin:
builtins.map (file: { builtins.map (file: {
name = "${vault.target}/.obsidian/plugins/${getManifestId plugin}/${file}"; name = "${vault.target}/.obsidian/plugins/${getManifest plugin.pkg}/${file}";
value = { value = {
source = "${plugin}/${file}"; source = "${plugin.pkg}/${file}";
}; };
}) (readDir plugin) }) (readDir plugin.pkg)
) vault.settings.plugins
++ builtins.map (
plugin:
builtins.map (file: {
name = "${vault.target}/.obsidian/plugins/${getManifest plugin.pkg}/${file.target}";
value = if file ? source then { source = file.source; } else { text = file.text; };
}) (builtins.attrValues plugin.extraFiles)
) vault.settings.plugins; ) vault.settings.plugins;
mkCssSnippets = mkCssSnippets =
vault: vault:
builtins.map (snippet: { builtins.map (snippet: {
name = "${vault.target}/.obsidian/snippets/${builtins.baseNameOf snippet}"; name = "${vault.target}/.obsidian/snippets/${snippet.name}.css";
value = { value = if snippet ? source then { source = snippet.source; } else { text = snippet.text; };
source = snippet; }) (builtins.attrValues vault.settings.cssSnippets);
};
}) vault.settings.cssSnippets; mkThemes =
mkTheme =
vault: vault:
lib.attrsets.optionalAttrs (vault.settings.theme != null) { builtins.map (theme: {
name = "${vault.target}/.obsidian/themes/${getManifestId vault.settings.theme}"; name = "${vault.target}/.obsidian/themes/${getManifest theme.pkg}";
value = { value = {
source = vault.settings.theme; source = theme.pkg;
};
}; };
}) vault.settings.themes;
in in
builtins.listToAttrs ( builtins.listToAttrs (
lib.lists.flatten ( lib.lists.flatten (
@@ -286,7 +401,7 @@ in
(mkCorePlugins vault) (mkCorePlugins vault)
(mkCommunityPlugins vault) (mkCommunityPlugins vault)
(mkCssSnippets vault) (mkCssSnippets vault)
(mkTheme vault) (mkThemes vault)
]) vaults ]) vaults
) )
); );

View File

@@ -1,3 +0,0 @@
.markdown-source-view.mod-cm6 .cm-scroller {
font-family: var(--font-monospace);
}

View File

@@ -5,16 +5,18 @@ let
with types; with types;
{ config, ... }: { config, ... }:
{ {
options.email = mkOption { options = {
email = mkOption {
type = nullOr str; type = nullOr str;
description = "Email address of the user."; description = "Email address of the user.";
}; };
options.fullName = mkOption { fullName = mkOption {
type = nullOr str; type = nullOr str;
description = "Full name of the user."; description = "Full name of the user.";
}; };
}; };
};
in in
{ {
options = options =