maolan_plugin_host/
paths.rs1use std::path::PathBuf;
2
3pub fn home_dir() -> String {
4 std::env::var("HOME")
5 .or_else(|_| std::env::var("USERPROFILE"))
6 .unwrap_or_default()
7}
8
9pub fn push_macos_audio_plugin_roots(roots: &mut Vec<PathBuf>, plugin_dir_name: &str) {
10 roots.push(PathBuf::from(format!(
11 "/Library/Audio/Plug-Ins/{plugin_dir_name}"
12 )));
13 roots.push(PathBuf::from(format!(
14 "{}/Library/Audio/Plug-Ins/{plugin_dir_name}",
15 home_dir()
16 )));
17}
18
19pub fn push_unix_plugin_roots(roots: &mut Vec<PathBuf>, plugin_dir_name: &str) {
20 roots.push(PathBuf::from(format!("/usr/lib/{plugin_dir_name}")));
21 roots.push(PathBuf::from(format!("/usr/lib64/{plugin_dir_name}")));
22 roots.push(PathBuf::from(format!("/usr/local/lib/{plugin_dir_name}")));
23 roots.push(PathBuf::from(format!("/usr/local/lib64/{plugin_dir_name}")));
24 roots.push(PathBuf::from(format!("{}/.{plugin_dir_name}", home_dir())));
25 roots.push(PathBuf::from(format!(
26 "{}/.local/lib/{plugin_dir_name}",
27 home_dir()
28 )));
29}
30
31pub fn push_windows_vst3_roots(roots: &mut Vec<PathBuf>) {
32 roots.push(PathBuf::from(r"C:\Program Files\Common Files\VST3"));
33 roots.push(PathBuf::from(r"C:\Program Files (x86)\Common Files\VST3"));
34}
35
36pub fn push_windows_clap_roots(roots: &mut Vec<PathBuf>) {
37 if let Ok(common) = std::env::var("COMMONPROGRAMFILES") {
38 roots.push(PathBuf::from(common).join("CLAP"));
39 }
40 if let Ok(common_x86) = std::env::var("COMMONPROGRAMFILES(X86)") {
41 roots.push(PathBuf::from(common_x86).join("CLAP"));
42 }
43 if let Ok(local_app_data) = std::env::var("LOCALAPPDATA") {
44 roots.push(PathBuf::from(local_app_data).join(r"Programs\Common\CLAP"));
45 }
46}
47
48#[cfg(test)]
49mod tests {
50 use super::*;
51 use std::sync::{LazyLock, Mutex};
52
53 static ENV_GUARD: LazyLock<Mutex<()>> = LazyLock::new(|| Mutex::new(()));
54
55 #[test]
56 fn home_dir_prefers_home_over_userprofile() {
57 let _guard = ENV_GUARD.lock().expect("lock env guard");
58 let old_home = std::env::var("HOME").ok();
59 let old_userprofile = std::env::var("USERPROFILE").ok();
60
61 unsafe {
62 std::env::set_var("HOME", "/home/tester");
63 std::env::set_var("USERPROFILE", "C:/Users/tester");
64 }
65
66 let home = home_dir();
67
68 if let Some(value) = old_home {
69 unsafe { std::env::set_var("HOME", value) };
70 } else {
71 unsafe { std::env::remove_var("HOME") };
72 }
73 if let Some(value) = old_userprofile {
74 unsafe { std::env::set_var("USERPROFILE", value) };
75 } else {
76 unsafe { std::env::remove_var("USERPROFILE") };
77 }
78
79 assert_eq!(home, "/home/tester");
80 }
81
82 #[test]
83 fn push_unix_plugin_roots_adds_system_and_user_locations() {
84 let _guard = ENV_GUARD.lock().expect("lock env guard");
85 let old_home = std::env::var("HOME").ok();
86 unsafe {
87 std::env::set_var("HOME", "/home/tester");
88 }
89
90 let mut roots = Vec::new();
91 push_unix_plugin_roots(&mut roots, "clap");
92
93 if let Some(value) = old_home {
94 unsafe { std::env::set_var("HOME", value) };
95 } else {
96 unsafe { std::env::remove_var("HOME") };
97 }
98
99 assert_eq!(
100 roots,
101 vec![
102 PathBuf::from("/usr/lib/clap"),
103 PathBuf::from("/usr/lib64/clap"),
104 PathBuf::from("/usr/local/lib/clap"),
105 PathBuf::from("/usr/local/lib64/clap"),
106 PathBuf::from("/home/tester/.clap"),
107 PathBuf::from("/home/tester/.local/lib/clap"),
108 ]
109 );
110 }
111
112 #[test]
113 fn push_windows_vst3_roots_adds_standard_locations() {
114 let mut roots = Vec::new();
115
116 push_windows_vst3_roots(&mut roots);
117
118 assert_eq!(
119 roots,
120 vec![
121 PathBuf::from(r"C:\Program Files\Common Files\VST3"),
122 PathBuf::from(r"C:\Program Files (x86)\Common Files\VST3"),
123 ]
124 );
125 }
126
127 #[test]
128 fn push_windows_clap_roots_adds_standard_locations() {
129 let _guard = ENV_GUARD.lock().expect("lock env guard");
130 let old_common = std::env::var("COMMONPROGRAMFILES").ok();
131 let old_common_x86 = std::env::var("COMMONPROGRAMFILES(X86)").ok();
132 let old_local_app_data = std::env::var("LOCALAPPDATA").ok();
133
134 unsafe {
135 std::env::set_var("COMMONPROGRAMFILES", r"C:\Program Files\Common Files");
136 std::env::set_var(
137 "COMMONPROGRAMFILES(X86)",
138 r"C:\Program Files (x86)\Common Files",
139 );
140 std::env::set_var("LOCALAPPDATA", r"C:\Users\tester\AppData\Local");
141 }
142
143 let mut roots = Vec::new();
144 push_windows_clap_roots(&mut roots);
145
146 if let Some(value) = old_common {
147 unsafe { std::env::set_var("COMMONPROGRAMFILES", value) };
148 } else {
149 unsafe { std::env::remove_var("COMMONPROGRAMFILES") };
150 }
151 if let Some(value) = old_common_x86 {
152 unsafe { std::env::set_var("COMMONPROGRAMFILES(X86)", value) };
153 } else {
154 unsafe { std::env::remove_var("COMMONPROGRAMFILES(X86)") };
155 }
156 if let Some(value) = old_local_app_data {
157 unsafe { std::env::set_var("LOCALAPPDATA", value) };
158 } else {
159 unsafe { std::env::remove_var("LOCALAPPDATA") };
160 }
161
162 assert_eq!(
163 roots,
164 vec![
165 PathBuf::from(r"C:\Program Files\Common Files").join("CLAP"),
166 PathBuf::from(r"C:\Program Files (x86)\Common Files").join("CLAP"),
167 PathBuf::from(r"C:\Users\tester\AppData\Local").join(r"Programs\Common\CLAP"),
168 ]
169 );
170 }
171}