opendal/services/memory/
backend.rs1use std::fmt::Debug;
19use std::sync::Arc;
20
21use super::core::*;
22use super::delete::MemoryDeleter;
23use super::lister::MemoryLister;
24use super::writer::MemoryWriter;
25use super::DEFAULT_SCHEME;
26use crate::raw::oio;
27use crate::raw::*;
28use crate::services::MemoryConfig;
29use crate::*;
30impl Configurator for MemoryConfig {
31 type Builder = MemoryBuilder;
32 fn into_builder(self) -> Self::Builder {
33 MemoryBuilder { config: self }
34 }
35}
36
37#[doc = include_str!("docs.md")]
39#[derive(Default)]
40pub struct MemoryBuilder {
41 config: MemoryConfig,
42}
43
44impl MemoryBuilder {
45 pub fn root(mut self, path: &str) -> Self {
47 self.config.root = Some(path.into());
48 self
49 }
50}
51
52impl Builder for MemoryBuilder {
53 type Config = MemoryConfig;
54
55 fn build(self) -> Result<impl Access> {
56 let root = normalize_root(self.config.root.as_deref().unwrap_or("/"));
57
58 let core = MemoryCore::new();
59 Ok(MemoryAccessor::new(core).with_normalized_root(root))
60 }
61}
62
63#[derive(Debug, Clone)]
65pub struct MemoryAccessor {
66 core: Arc<MemoryCore>,
67 root: String,
68 info: Arc<AccessorInfo>,
69}
70
71impl MemoryAccessor {
72 fn new(core: MemoryCore) -> Self {
73 let info = AccessorInfo::default();
74 info.set_scheme(DEFAULT_SCHEME);
75 info.set_name(&format!("{:p}", Arc::as_ptr(&core.data)));
76 info.set_root("/");
77 info.set_native_capability(Capability {
78 read: true,
79 write: true,
80 write_can_empty: true,
81 write_with_cache_control: true,
82 write_with_content_type: true,
83 write_with_content_disposition: true,
84 write_with_content_encoding: true,
85 delete: true,
86 stat: true,
87 list: true,
88 list_with_recursive: true,
89 shared: false,
90 ..Default::default()
91 });
92
93 Self {
94 core: Arc::new(core),
95 root: "/".to_string(),
96 info: Arc::new(info),
97 }
98 }
99
100 fn with_normalized_root(mut self, root: String) -> Self {
101 self.info.set_root(&root);
102 self.root = root;
103 self
104 }
105}
106
107impl Access for MemoryAccessor {
108 type Reader = Buffer;
109 type Writer = MemoryWriter;
110 type Lister = oio::HierarchyLister<MemoryLister>;
111 type Deleter = oio::OneShotDeleter<MemoryDeleter>;
112
113 fn info(&self) -> Arc<AccessorInfo> {
114 self.info.clone()
115 }
116
117 async fn stat(&self, path: &str, _: OpStat) -> Result<RpStat> {
118 let p = build_abs_path(&self.root, path);
119
120 if p == build_abs_path(&self.root, "") {
121 Ok(RpStat::new(Metadata::new(EntryMode::DIR)))
122 } else {
123 match self.core.get(&p)? {
124 Some(value) => Ok(RpStat::new(value.metadata)),
125 None => Err(Error::new(
126 ErrorKind::NotFound,
127 "memory doesn't have this path",
128 )),
129 }
130 }
131 }
132
133 async fn read(&self, path: &str, args: OpRead) -> Result<(RpRead, Self::Reader)> {
134 let p = build_abs_path(&self.root, path);
135
136 let value = match self.core.get(&p)? {
137 Some(value) => value,
138 None => {
139 return Err(Error::new(
140 ErrorKind::NotFound,
141 "memory doesn't have this path",
142 ))
143 }
144 };
145
146 Ok((
147 RpRead::new(),
148 value.content.slice(args.range().to_range_as_usize()),
149 ))
150 }
151
152 async fn write(&self, path: &str, args: OpWrite) -> Result<(RpWrite, Self::Writer)> {
153 let p = build_abs_path(&self.root, path);
154 Ok((
155 RpWrite::new(),
156 MemoryWriter::new(self.core.clone(), p, args),
157 ))
158 }
159
160 async fn delete(&self) -> Result<(RpDelete, Self::Deleter)> {
161 Ok((
162 RpDelete::default(),
163 oio::OneShotDeleter::new(MemoryDeleter::new(self.core.clone(), self.root.clone())),
164 ))
165 }
166
167 async fn list(&self, path: &str, args: OpList) -> Result<(RpList, Self::Lister)> {
168 let p = build_abs_path(&self.root, path);
169 let keys = self.core.scan(&p)?;
170 let lister = MemoryLister::new(&self.root, keys);
171 let lister = oio::HierarchyLister::new(lister, path, args.recursive());
172
173 Ok((RpList::default(), lister))
174 }
175}
176
177#[cfg(test)]
178mod tests {
179 use super::*;
180
181 #[test]
182 fn test_accessor_metadata_name() {
183 let b1 = MemoryBuilder::default().build().unwrap();
184 assert_eq!(b1.info().name(), b1.info().name());
185
186 let b2 = MemoryBuilder::default().build().unwrap();
187 assert_ne!(b1.info().name(), b2.info().name())
188 }
189}