1use crate::routing::Route;
2
3pub struct ModuleReloader {
4 cache: std::collections::HashMap<String, ModuleState>,
5}
6
7#[derive(Debug, Clone)]
8pub enum ModuleState {
9 Loaded,
10 Reloading,
11 Failed(String),
12}
13
14impl ModuleReloader {
15 pub fn new() -> Self {
16 Self {
17 cache: std::collections::HashMap::new(),
18 }
19 }
20
21 pub fn mark_loading(&mut self, module_path: &str) {
22 self.cache
23 .insert(module_path.to_string(), ModuleState::Reloading);
24 }
25
26 pub fn mark_loaded(&mut self, module_path: &str) {
27 self.cache
28 .insert(module_path.to_string(), ModuleState::Loaded);
29 }
30
31 pub fn mark_failed(&mut self, module_path: &str, error: String) {
32 self.cache
33 .insert(module_path.to_string(), ModuleState::Failed(error));
34 }
35
36 pub fn get_state(&self, module_path: &str) -> Option<&ModuleState> {
37 self.cache.get(module_path)
38 }
39}
40
41impl Default for ModuleReloader {
42 fn default() -> Self {
43 Self::new()
44 }
45}
46
47pub struct HotReloader {
48 #[allow(dead_code)]
49 reloader: ModuleReloader,
50 routes: Vec<Route>,
51}
52
53impl HotReloader {
54 pub fn new(routes: Vec<Route>) -> Self {
55 Self {
56 reloader: ModuleReloader::new(),
57 routes,
58 }
59 }
60
61 pub fn reload_page(&self, page_path: &str) -> anyhow::Result<String> {
62 let route = self.routes.iter().find(|r| r.path == page_path);
63
64 match route {
65 Some(route) => {
66 tracing::info!("Hot reloading page: {}", route.file_path);
67 Ok(format!("Reloaded: {}", route.file_path))
68 }
69 None => {
70 anyhow::bail!("Page not found: {}", page_path)
71 }
72 }
73 }
74
75 pub fn get_module_dependencies(&self, module_path: &str) -> Vec<String> {
76 let mut deps = Vec::new();
77
78 for route in &self.routes {
79 if route.file_path.contains(module_path) {
80 deps.push(route.file_path.clone());
81 }
82 }
83
84 deps
85 }
86
87 pub fn generate_vite_config(&self) -> String {
88 r#"
89import { defineConfig } from 'vite';
90import react from '@vitejs/plugin-react';
91import nestforgeWeb from 'nestforge-web/vite';
92
93export default defineConfig({
94 plugins: [
95 react(),
96 nestforgeWeb({
97 hotReload: true,
98 hmrPort: 3001,
99 }),
100 ],
101 server: {
102 port: 3000,
103 },
104});
105"#
106 .to_string()
107 }
108}