use anyhow::{Context, bail};
use std::process::Command;
use crate::plugin::{PluginKind, get_plugins};
pub trait EnwiroAdapterTrait {
fn get_active_environment_name(&self) -> anyhow::Result<String>;
fn activate(&self, name: &str) -> anyhow::Result<()>;
}
pub struct EnwiroAdapterExternal {
adapter_command: String,
}
impl EnwiroAdapterTrait for EnwiroAdapterExternal {
fn get_active_environment_name(&self) -> anyhow::Result<String> {
tracing::debug!("Querying adapter for active environment");
let output = Command::new(&self.adapter_command)
.arg("get-active-workspace-id")
.output()
.context("Adapter failed to determine active environment name")?;
if output.status.success() {
let stdout = String::from_utf8_lossy(&output.stdout);
Ok(stdout.trim().to_string())
} else {
let stderr = String::from_utf8_lossy(&output.stderr);
bail!("Error: {}", stderr);
}
}
fn activate(&self, name: &str) -> anyhow::Result<()> {
tracing::debug!(name = %name, "Activating workspace via adapter");
let output = Command::new(&self.adapter_command)
.arg("activate")
.arg(name)
.output()
.context("Adapter failed to activate workspace")?;
if output.status.success() {
Ok(())
} else {
let stderr = String::from_utf8_lossy(&output.stderr);
bail!("Error: {}", stderr);
}
}
}
impl EnwiroAdapterExternal {
pub fn new(adapter_name: &str) -> anyhow::Result<Self> {
let plugins = get_plugins(PluginKind::Adapter);
let plugin = plugins
.into_iter()
.find(|p| p.name == adapter_name)
.context(format!("Adapter '{}' not found", adapter_name))?;
Ok(Self {
adapter_command: plugin.executable,
})
}
}
pub struct EnwiroAdapterNone {}
impl EnwiroAdapterTrait for EnwiroAdapterNone {
fn get_active_environment_name(&self) -> anyhow::Result<String> {
bail!("Could not determine active environment because no adapter is configured.")
}
fn activate(&self, _name: &str) -> anyhow::Result<()> {
bail!("Could not activate workspace because no adapter is configured.")
}
}