diff --git a/Cargo.lock b/Cargo.lock index acee78131..b2eca9cef 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1250,6 +1250,7 @@ dependencies = [ "percent-encoding", "prost", "prost-build", + "rand 0.7.3", "serde", "serde_json", "structopt", diff --git a/http/Cargo.toml b/http/Cargo.toml index 6335079cb..41430de88 100644 --- a/http/Cargo.toml +++ b/http/Cargo.toml @@ -40,4 +40,5 @@ warp = { default-features = false, version = "0.2" } [dev-dependencies] hex-literal = { default-features = false, version = "0.3" } +rand = { default-features = false, version = "0.7" } tempfile = { default-features = false, version = "3.1" } diff --git a/http/src/v0/root_files/add.rs b/http/src/v0/root_files/add.rs index 0c53d3533..16c6cc9ec 100644 --- a/http/src/v0/root_files/add.rs +++ b/http/src/v0/root_files/add.rs @@ -143,15 +143,7 @@ where let content_type = field.content_type().map_err(AddError::Header)?; let next = match content_type { - "application/octet-stream" => { - - // files are of the form "file-{1,2,3,..}" - let _ = if field_name != "file" && !field_name.starts_with("file-") { - Err(AddError::UnsupportedField(field_name.to_string())) - } else { - Ok(()) - }?; - + "application/octet-stream" | "text/plain" => { let mut adder = FileAdder::default(); // how many bytes we have stored as blocks let mut total_written = 0u64; @@ -376,10 +368,14 @@ impl serde::Serialize for Quoted { #[cfg(test)] mod tests { use crate::v0::root_files::add; + use ipfs::Node; + use rand::distributions::Alphanumeric; + use rand::Rng; + use std::iter; #[tokio::test(max_threads = 1)] async fn add_single_block_file() { - let ipfs = tokio_ipfs().await; + let ipfs = Node::new("0").await; // this is from interface-ipfs-core, pretty much simplest add a buffer test case // but the body content is from the pubsub test case I copied this from @@ -408,15 +404,37 @@ mod tests { ); } - async fn tokio_ipfs() -> ipfs::Ipfs { - let options = ipfs::IpfsOptions::inmemory_with_generated_keys(); - let (ipfs, fut) = ipfs::UninitializedIpfs::new(options, None) - .await - .start() - .await - .unwrap(); + // copied from js-ipfs/packages/ipfs/test/http-api/inject/files.js + #[tokio::test(max_threads = 1)] + async fn js_multipart_test() { + let ipfs = Node::new("0").await; + let mut rng = rand::thread_rng(); + + let response = warp::test::request() + .path("/add") + .header( + "Content-Type", + "multipart/form-data; boundary=----------287032381131322", + ) + .body( + format!( + "\r\n\ + ------------287032381131322\r\n\ + Content-Disposition: form-data; name=\"test\"; filename=\"test.txt\"\r\n\ + Content-Type: text/plain\r\n\ + \r\n\ + {}\r\n\ + ------------287032381131322--", + iter::repeat(()) + .map(|_| rng.sample(Alphanumeric)) + .take(1024 * 1024 * 2) + .collect::() + ) + .into_bytes(), + ) + .reply(&add(&ipfs)) + .await; - tokio::spawn(fut); - ipfs + assert_eq!(response.status(), 200); } }