fob_graph/memory/
queries.rs1use std::path::Path;
4
5use super::super::external_dep::ExternalDependency;
6use super::super::{Import, Module, ModuleId};
7use super::graph::ModuleGraph;
8use crate::Result;
9
10impl ModuleGraph {
11 pub fn module(&self, id: &ModuleId) -> Result<Option<Module>> {
26 let inner = self.inner.read();
27 Ok(inner.modules.get(id).map(|arc| (**arc).clone()))
28 }
29
30 pub fn module_by_path(&self, path: &Path) -> Result<Option<Module>> {
35 let inner = self.inner.read();
36 Ok(inner
37 .modules
38 .values()
39 .find(|module| module.path == path)
40 .map(|arc| (**arc).clone()))
41 }
42
43 pub fn modules(&self) -> Result<Vec<Module>> {
48 let inner = self.inner.read();
49 Ok(inner.modules.values().map(|arc| (**arc).clone()).collect())
50 }
51
52 pub fn dependencies(&self, id: &ModuleId) -> Result<Vec<ModuleId>> {
54 let inner = self.inner.read();
55 Ok(inner
56 .dependencies
57 .get(id)
58 .map(|set| set.iter().cloned().collect())
59 .unwrap_or_default())
60 }
61
62 pub fn dependents(&self, id: &ModuleId) -> Result<Vec<ModuleId>> {
64 let inner = self.inner.read();
65 Ok(inner
66 .dependents
67 .get(id)
68 .map(|set| set.iter().cloned().collect())
69 .unwrap_or_default())
70 }
71
72 pub fn contains(&self, id: &ModuleId) -> Result<bool> {
74 let inner = self.inner.read();
75 Ok(inner.modules.contains_key(id))
76 }
77
78 pub fn entry_points(&self) -> Result<Vec<ModuleId>> {
80 let inner = self.inner.read();
81 Ok(inner.entry_points.iter().cloned().collect())
82 }
83
84 pub fn len(&self) -> Result<usize> {
86 let inner = self.inner.read();
87 Ok(inner.modules.len())
88 }
89
90 pub fn is_empty(&self) -> Result<bool> {
92 let inner = self.inner.read();
93 Ok(inner.modules.is_empty())
94 }
95
96 pub fn imports_for_module(&self, id: &ModuleId) -> Result<Option<Vec<Import>>> {
98 let inner = self.inner.read();
99 Ok(inner.modules.get(id).map(|m| (*m.imports).clone()))
100 }
101
102 pub fn external_dependencies(&self) -> Result<Vec<ExternalDependency>> {
104 let inner = self.inner.read();
105 Ok(inner.external_deps.values().cloned().collect())
106 }
107
108 pub fn unreachable_modules(&self) -> Result<Vec<Module>> {
113 let inner = self.inner.read();
114 let mut unreachable = Vec::new();
115
116 for module in inner.modules.values() {
117 if module.is_entry || module.has_side_effects {
118 continue;
119 }
120
121 let has_dependents = inner
122 .dependents
123 .get(&module.id)
124 .map(|deps| !deps.is_empty())
125 .unwrap_or(false);
126
127 if !has_dependents {
128 unreachable.push((**module).clone());
129 }
130 }
131
132 Ok(unreachable)
133 }
134}