use std::{fmt, path::PathBuf, sync::Arc};
use reovim_arch::sync::RwLock;
use crate::{
core::{MarkBank, MotionEngine, OptionRegistry, TextObjectEngine},
ipc::EventBus,
};
use super::{buffer_manager::BufferManager, module::ModuleId, service::ServiceRegistry};
#[derive(Clone)]
pub struct KernelContext {
pub event_bus: Arc<EventBus>,
pub buffers: Arc<dyn BufferManager>,
pub motion: Arc<MotionEngine>,
pub text_objects: Arc<TextObjectEngine>,
pub global_marks: Arc<RwLock<MarkBank>>,
pub options: Arc<OptionRegistry>,
pub services: Arc<ServiceRegistry>,
}
impl KernelContext {
#[allow(clippy::too_many_arguments)]
pub fn new(
event_bus: Arc<EventBus>,
buffers: Arc<dyn BufferManager>,
motion: Arc<MotionEngine>,
text_objects: Arc<TextObjectEngine>,
global_marks: Arc<RwLock<MarkBank>>,
options: Arc<OptionRegistry>,
services: Arc<ServiceRegistry>,
) -> Self {
Self {
event_bus,
buffers,
motion,
text_objects,
global_marks,
options,
services,
}
}
}
impl fmt::Debug for KernelContext {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
f.debug_struct("KernelContext")
.field("event_bus", &"Arc<EventBus>")
.field("buffers", &"Arc<dyn BufferManager>")
.field("motion", &"Arc<MotionEngine>")
.field("text_objects", &"Arc<TextObjectEngine>")
.field("global_marks", &"Arc<RwLock<MarkBank>>")
.field("options", &"Arc<OptionRegistry>")
.field("services", &"Arc<ServiceRegistry>")
.finish()
}
}
#[derive(Clone)]
pub struct ModuleContext {
pub kernel: KernelContext,
pub services: Arc<ServiceRegistry>,
pub data_dir: PathBuf,
pub cache_dir: PathBuf,
loaded_optional_deps: Vec<ModuleId>,
}
impl ModuleContext {
#[must_use]
#[allow(clippy::missing_const_for_fn)] pub fn new(
kernel: KernelContext,
services: Arc<ServiceRegistry>,
data_dir: PathBuf,
cache_dir: PathBuf,
) -> Self {
Self {
kernel,
services,
data_dir,
cache_dir,
loaded_optional_deps: Vec::new(),
}
}
#[must_use]
#[allow(clippy::missing_const_for_fn)] pub fn with_optional_deps(
kernel: KernelContext,
services: Arc<ServiceRegistry>,
data_dir: PathBuf,
cache_dir: PathBuf,
loaded_optional_deps: Vec<ModuleId>,
) -> Self {
Self {
kernel,
services,
data_dir,
cache_dir,
loaded_optional_deps,
}
}
#[must_use]
pub fn has_optional_dep(&self, id: &ModuleId) -> bool {
self.loaded_optional_deps.iter().any(|dep| dep == id)
}
#[must_use]
pub fn optional_deps(&self) -> &[ModuleId] {
&self.loaded_optional_deps
}
}
impl fmt::Debug for ModuleContext {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
f.debug_struct("ModuleContext")
.field("kernel", &self.kernel)
.field("services", &self.services)
.field("data_dir", &self.data_dir)
.field("cache_dir", &self.cache_dir)
.field("loaded_optional_deps", &self.loaded_optional_deps)
.finish()
}
}
impl Default for ModuleContext {
fn default() -> Self {
Self {
kernel: KernelContext::default(),
services: Arc::new(ServiceRegistry::new()),
data_dir: PathBuf::from("/tmp/reovim-test/data"),
cache_dir: PathBuf::from("/tmp/reovim-test/cache"),
loaded_optional_deps: Vec::new(),
}
}
}
impl KernelContext {
#[must_use]
pub fn with_event_bus_and_services(
event_bus: Arc<EventBus>,
services: Arc<ServiceRegistry>,
) -> Self {
Self::with_event_bus_services_and_options(
event_bus,
services,
Arc::new(OptionRegistry::new()),
)
}
#[must_use]
pub fn with_event_bus_services_and_options(
event_bus: Arc<EventBus>,
services: Arc<ServiceRegistry>,
options: Arc<OptionRegistry>,
) -> Self {
use crate::core::{MarkBank, MotionEngine, TextObjectEngine};
Self {
event_bus,
buffers: Arc::new(StubBufferManager),
motion: Arc::new(MotionEngine),
text_objects: Arc::new(TextObjectEngine),
global_marks: Arc::new(RwLock::new(MarkBank::new())),
options,
services,
}
}
}
impl Default for KernelContext {
fn default() -> Self {
use crate::core::{MarkBank, MotionEngine, TextObjectEngine};
Self {
event_bus: Arc::new(crate::ipc::EventBus::new()),
buffers: Arc::new(StubBufferManager),
motion: Arc::new(MotionEngine),
text_objects: Arc::new(TextObjectEngine),
global_marks: Arc::new(RwLock::new(MarkBank::new())),
options: Arc::new(OptionRegistry::new()),
services: Arc::new(ServiceRegistry::new()),
}
}
}
pub struct StubBufferManager;
impl BufferManager for StubBufferManager {
fn get(
&self,
_id: crate::mm::BufferId,
) -> Option<Arc<reovim_arch::sync::RwLock<crate::mm::Buffer>>> {
None
}
fn create(&self) -> crate::mm::BufferId {
crate::mm::BufferId::new()
}
fn register(&self, _buffer: crate::mm::Buffer) -> crate::mm::BufferId {
crate::mm::BufferId::new()
}
fn unregister(
&self,
id: crate::mm::BufferId,
) -> Result<crate::mm::Buffer, super::buffer_manager::BufferError> {
Err(super::buffer_manager::BufferError::NotFound(id))
}
fn list(&self) -> Vec<crate::mm::BufferId> {
Vec::new()
}
fn count(&self) -> usize {
0
}
}