dioxus_docs_kit/config.rs
1//! Builder for constructing a `DocsRegistry`.
2
3use crate::registry::DocsRegistry;
4use std::collections::HashMap;
5
6/// Theme configuration for the documentation site.
7///
8/// Controls which DaisyUI theme(s) are applied and whether a toggle button is shown.
9#[derive(Clone, Debug)]
10pub struct ThemeConfig {
11 /// The default theme name (must match a DaisyUI theme defined in `tailwind.css`).
12 pub default_theme: String,
13 /// If set, enables a light/dark toggle button. Tuple is `(light_theme, dark_theme)`.
14 pub toggle_themes: Option<(String, String)>,
15 /// localStorage key used to persist the user's theme preference.
16 pub storage_key: String,
17}
18
19/// Builder for constructing a [`DocsRegistry`].
20///
21/// # Example
22///
23/// ```rust,ignore
24/// let registry = DocsConfig::new(nav_json, content_map)
25/// .with_openapi("api-reference", spec_yaml)
26/// .with_default_path("getting-started/introduction")
27/// .build();
28/// ```
29pub struct DocsConfig {
30 nav_json: String,
31 content_map: HashMap<&'static str, &'static str>,
32 openapi_specs: Vec<(String, String)>,
33 default_path: Option<String>,
34 api_group_name: Option<String>,
35 theme: Option<ThemeConfig>,
36}
37
38impl DocsConfig {
39 /// Create a new builder from a `_nav.json` string and a content map.
40 ///
41 /// The content map is typically generated by `build.rs` using `include_str!()`.
42 pub fn new(nav_json: &str, content_map: HashMap<&'static str, &'static str>) -> Self {
43 Self {
44 nav_json: nav_json.to_string(),
45 content_map,
46 openapi_specs: Vec::new(),
47 default_path: None,
48 api_group_name: None,
49 theme: None,
50 }
51 }
52
53 /// Add an OpenAPI specification.
54 ///
55 /// - `prefix`: The URL prefix for this spec's endpoints (e.g. "api-reference").
56 /// - `yaml`: The raw YAML string of the OpenAPI spec.
57 ///
58 /// The `prefix` must correspond to a nav group in `_nav.json` whose `"group"` value
59 /// matches [`Self::with_api_group_name`] (defaults to `"API Reference"`). The library
60 /// dynamically injects API endpoints into that group's sidebar — do **not** list
61 /// individual operation paths in the `"pages"` array of `_nav.json`.
62 pub fn with_openapi(mut self, prefix: &str, yaml: &str) -> Self {
63 self.openapi_specs
64 .push((prefix.to_string(), yaml.to_string()));
65 self
66 }
67
68 /// Set the default documentation path for redirects.
69 ///
70 /// Defaults to the first page in the first nav group if not set.
71 pub fn with_default_path(mut self, path: &str) -> Self {
72 self.default_path = Some(path.to_string());
73 self
74 }
75
76 /// Set the display name for the API Reference sidebar group.
77 ///
78 /// Defaults to `"API Reference"`. The value must match a `"group"` in `_nav.json`
79 /// so the library knows where to inject the API endpoint sidebar entries.
80 /// See [`Self::with_openapi`] for details.
81 pub fn with_api_group_name(mut self, name: &str) -> Self {
82 self.api_group_name = Some(name.to_string());
83 self
84 }
85
86 /// Set a single theme (no toggle button).
87 ///
88 /// The theme name must match a DaisyUI theme defined in the consumer's `tailwind.css`.
89 pub fn with_theme(mut self, theme: &str) -> Self {
90 self.theme = Some(ThemeConfig {
91 default_theme: theme.to_string(),
92 toggle_themes: None,
93 storage_key: "docs-theme".to_string(),
94 });
95 self
96 }
97
98 /// Enable a light/dark theme toggle.
99 ///
100 /// - `light`: Name of the light DaisyUI theme.
101 /// - `dark`: Name of the dark DaisyUI theme.
102 /// - `default`: Which of the two to use on first visit (`light` or `dark`).
103 pub fn with_theme_toggle(mut self, light: &str, dark: &str, default: &str) -> Self {
104 self.theme = Some(ThemeConfig {
105 default_theme: default.to_string(),
106 toggle_themes: Some((light.to_string(), dark.to_string())),
107 storage_key: "docs-theme".to_string(),
108 });
109 self
110 }
111
112 /// Build the [`DocsRegistry`].
113 ///
114 /// Parses all documents, builds the search index, and parses OpenAPI specs.
115 pub fn build(self) -> DocsRegistry {
116 DocsRegistry::from_config(self)
117 }
118
119 // Accessors for DocsRegistry::from_config
120 pub(crate) fn nav_json(&self) -> &str {
121 &self.nav_json
122 }
123
124 pub(crate) fn content_map(&self) -> &HashMap<&'static str, &'static str> {
125 &self.content_map
126 }
127
128 pub(crate) fn openapi_specs(&self) -> &[(String, String)] {
129 &self.openapi_specs
130 }
131
132 pub(crate) fn default_path_value(&self) -> Option<&str> {
133 self.default_path.as_deref()
134 }
135
136 pub(crate) fn api_group_name_value(&self) -> Option<&str> {
137 self.api_group_name.as_deref()
138 }
139
140 pub(crate) fn theme_config(&self) -> Option<&ThemeConfig> {
141 self.theme.as_ref()
142 }
143}