darling_vscode/
lib.rs

1use darling_api as darling;
2
3pub static PACKAGE_MANAGER: VSCode = VSCode;
4
5pub struct VSCode;
6
7impl darling::PackageManager for VSCode {
8    fn name(&self) -> String {
9        "vscode".to_owned()
10    }
11
12    fn install(&self, _context: &darling::Context, package: &darling::InstallationEntry) -> anyhow::Result<()> {
13        std::process::Command::new(code_or_codium()?)
14            .arg("--install-extension")
15            .arg(&package.name)
16            .spawn()?
17            .wait()?;
18
19        Ok(())
20    }
21
22    fn uninstall(&self, _context: &darling::Context, package: &darling::InstallationEntry) -> anyhow::Result<()> {
23        std::process::Command::new(code_or_codium()?)
24            .arg("--uninstall-extension")
25            .arg(&package.name)
26            .spawn()?
27            .wait()?;
28        Ok(())
29    }
30
31    fn get_all_explicit(&self, _context: &darling::Context) -> anyhow::Result<Vec<(String, String)>> {
32        let extensions = String::from_utf8(
33            std::process::Command::new(code_or_codium()?)
34                .arg("--show-versions")
35                .arg("--list-extensions")
36                .output()?
37                .stdout,
38        )?;
39        let list = extensions.lines().filter(|line| !line.chars().all(|char| char.is_whitespace()));
40        Ok(list
41            .map(|line| {
42                let parts = line.split('@').collect::<Vec<_>>();
43                (parts[0].to_owned(), parts[1].to_owned())
44            })
45            .collect::<Vec<_>>())
46    }
47}
48
49fn code_or_codium() -> anyhow::Result<&'static str> {
50    if which::which("code").is_ok() {
51        return Ok("code");
52    }
53
54    if which::which("codium").is_ok() {
55        return Ok("codium");
56    }
57
58    Err(anyhow::anyhow!("No installation of VSCode or VSCodium found!"))
59}