Skip to content

Commit d24244b

Browse files
committed
feat: implement copy from ipfs
Signed-off-by: ClSlaid <cailue@bupt.edu.cn>
1 parent 35c44d1 commit d24244b

File tree

7 files changed

+80
-3
lines changed

7 files changed

+80
-3
lines changed

Cargo.lock

Lines changed: 1 addition & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/common/storage/Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ edition = "2021"
88

99
[features]
1010
storage-hdfs = ["opendal/services-hdfs"]
11+
storage-ipfs = ["opendal/services-ipfs"]
1112

1213
[dependencies]
1314
common-base = { path = "../base" }

src/common/storage/src/config.rs

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,8 @@ pub enum StorageParams {
3939
#[cfg(feature = "storage-hdfs")]
4040
Hdfs(StorageHdfsConfig),
4141
Http(StorageHttpConfig),
42+
#[cfg(feature = "storage-ipfs")]
43+
Ipfs(StorageIpfsConfig),
4244
Memory,
4345
Obs(StorageObsConfig),
4446
S3(StorageS3Config),
@@ -72,6 +74,10 @@ impl Display for StorageParams {
7274
StorageParams::Http(v) => {
7375
write!(f, "http://endpoint={},paths={:?}", v.endpoint_url, v.paths)
7476
}
77+
#[cfg(feature = "storage-ipfs")]
78+
StorageParams::Ipfs(c) => {
79+
write!(f, "ipfs://endpoint={},root={}", c.endpoint_url, c.root)
80+
}
7581
StorageParams::Memory => write!(f, "memory://"),
7682
StorageParams::Obs(v) => write!(
7783
f,
@@ -100,6 +106,8 @@ impl StorageParams {
100106
#[cfg(feature = "storage-hdfs")]
101107
StorageParams::Hdfs(_) => false,
102108
StorageParams::Http(v) => v.endpoint_url.starts_with("https://"),
109+
#[cfg(feature = "storage-ipfs")]
110+
StorageParams::Ipfs(c) => c.endpoint_url.starts_with("https://"),
103111
StorageParams::Memory => false,
104112
StorageParams::Obs(v) => v.endpoint_url.starts_with("https://"),
105113
StorageParams::S3(v) => v.endpoint_url.starts_with("https://"),
@@ -254,6 +262,15 @@ pub struct StorageHttpConfig {
254262
pub paths: Vec<String>,
255263
}
256264

265+
#[cfg(feature = "storage-ipfs")]
266+
pub const STORAGE_IPFS_DEFAULT_ENDPOINT: &str = "https://ipfs.io";
267+
/// Config for IPFS storage backend
268+
#[derive(Clone, Debug, Default, PartialEq, Eq, Serialize, Deserialize)]
269+
pub struct StorageIpfsConfig {
270+
pub endpoint_url: String,
271+
pub root: String,
272+
}
273+
257274
/// Config for storage backend obs.
258275
#[derive(Clone, Default, PartialEq, Eq, Serialize, Deserialize)]
259276
pub struct StorageObsConfig {

src/common/storage/src/lib.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,10 +23,13 @@ pub use config::StorageFsConfig;
2323
pub use config::StorageGcsConfig;
2424
pub use config::StorageHdfsConfig;
2525
pub use config::StorageHttpConfig;
26+
pub use config::StorageIpfsConfig;
2627
pub use config::StorageObsConfig;
2728
pub use config::StorageParams;
2829
pub use config::StorageS3Config;
2930
pub use config::STORAGE_GCS_DEFAULT_ENDPOINT;
31+
#[cfg(feature = "storage-ipfs")]
32+
pub use config::STORAGE_IPFS_DEFAULT_ENDPOINT;
3033
pub use config::STORAGE_S3_DEFAULT_ENDPOINT;
3134

3235
mod operator;

src/common/storage/src/location.rs

Lines changed: 18 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -42,10 +42,10 @@ pub fn parse_uri_location(l: &UriLocation) -> Result<(StorageParams, String)> {
4242
// Path endswith `/` means it's a directory, otherwise it's a file.
4343
// If the path is a directory, we will use this path as root.
4444
// If the path is a file, we will use `/` as root (which is the default value)
45-
let (root, path) = if l.path.ends_with('/') {
46-
(l.path.as_str(), "/")
45+
let root = if l.path.ends_with('/') {
46+
l.path.as_str()
4747
} else {
48-
("/", l.path.as_str())
48+
"/"
4949
};
5050

5151
let protocol = l.protocol.parse::<Scheme>()?;
@@ -95,6 +95,15 @@ pub fn parse_uri_location(l: &UriLocation) -> Result<(StorageParams, String)> {
9595
.to_string(),
9696
root: root.to_string(),
9797
}),
98+
#[cfg(feature = "storage-ipfs")]
99+
Scheme::Ipfs => {
100+
use crate::config::StorageIpfsConfig;
101+
use crate::config::STORAGE_IPFS_DEFAULT_ENDPOINT;
102+
StorageParams::Ipfs(StorageIpfsConfig {
103+
endpoint_url: STORAGE_IPFS_DEFAULT_ENDPOINT.to_string(),
104+
root: "/ipfs/".to_string(),
105+
})
106+
}
98107
Scheme::S3 => StorageParams::S3(StorageS3Config {
99108
endpoint_url: l
100109
.connection
@@ -158,5 +167,11 @@ pub fn parse_uri_location(l: &UriLocation) -> Result<(StorageParams, String)> {
158167
}
159168
};
160169

170+
let path = if cfg!(feature = "storage-ipfs") {
171+
&l.name
172+
} else {
173+
"/"
174+
};
175+
161176
Ok((sp, path.to_string()))
162177
}

src/common/storage/src/operator.rs

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -53,6 +53,8 @@ pub fn init_operator(cfg: &StorageParams) -> Result<Operator> {
5353
#[cfg(feature = "storage-hdfs")]
5454
StorageParams::Hdfs(cfg) => init_hdfs_operator(cfg)?,
5555
StorageParams::Http(cfg) => init_http_operator(cfg)?,
56+
#[cfg(feature = "storage-ipfs")]
57+
StorageParams::Ipfs(cfg) => init_ipfs_operator(cfg)?,
5658
StorageParams::Memory => init_memory_operator()?,
5759
StorageParams::Obs(cfg) => init_obs_operator(cfg)?,
5860
StorageParams::S3(cfg) => init_s3_operator(cfg)?,
@@ -122,6 +124,18 @@ pub fn init_hdfs_operator(cfg: &super::StorageHdfsConfig) -> Result<Operator> {
122124
Ok(Operator::new(builder.build()?).layer(LoggingLayer))
123125
}
124126

127+
#[cfg(feature = "storage-ipfs")]
128+
pub fn init_ipfs_operator(cfg: &super::StorageIpfsConfig) -> Result<Operator> {
129+
use opendal::services::ipfs;
130+
131+
let mut builder = ipfs::Builder::default();
132+
133+
builder.root(&cfg.root);
134+
builder.endpoint(&cfg.endpoint_url);
135+
136+
Ok(Operator::new(builder.build()?).layer(LoggingLayer))
137+
}
138+
125139
pub fn init_http_operator(cfg: &StorageHttpConfig) -> Result<Operator> {
126140
let mut builder = http::Builder::default();
127141

src/common/storage/tests/location.rs

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -175,3 +175,29 @@ fn test_parse_uri_location() -> Result<()> {
175175

176176
Ok(())
177177
}
178+
179+
#[cfg(feature = "storage-ipfs")]
180+
#[test]
181+
fn test_parse_ipfs_uri_location() {
182+
use common_storage::StorageIpfsConfig;
183+
use common_storage::STORAGE_IPFS_DEFAULT_ENDPOINT;
184+
185+
let l = UriLocation {
186+
protocol: "ipfs".to_string(),
187+
name: "somename".to_string(),
188+
path: "/".to_string(),
189+
connection: BTreeMap::new(),
190+
};
191+
192+
let want_config = StorageParams::Ipfs(StorageIpfsConfig {
193+
endpoint_url: STORAGE_IPFS_DEFAULT_ENDPOINT.to_string(),
194+
root: "/ipfs/".to_string(),
195+
});
196+
let want_path = "somename".to_string();
197+
if let Ok((got_config, got_path)) = parse_uri_location(&l) {
198+
assert_eq!(want_path, got_path, "want:{}, got:{}", want_path, got_path);
199+
assert_eq!(want_config, got_config);
200+
} else {
201+
unreachable!()
202+
}
203+
}

0 commit comments

Comments
 (0)