browser upload, multipart, ttl

This commit is contained in:
Paul Zinselmeyer 2023-10-20 13:58:44 +02:00
parent d9b512f8d8
commit 69d8bd1d8e
2 changed files with 26 additions and 9 deletions

View file

@ -15,7 +15,7 @@ After uploading data you can access it by accessing <bin_url> with an optional f
## Pipe into curl ## Pipe into curl
`$ tar -cz my-files | curl -H "Content-Type: application/gzip" -T - <bin_url>` `$ tar -cz my-files | curl -H "Content-Type: application/gzip" -T - <bin_url>`
## Enryption ## Encryption
``` ```
$ tar -cz my-files | gpg -co tmp.tar.gz $ tar -cz my-files | gpg -co tmp.tar.gz
$ curl -H "Content-Type: application/octet-stream" -T tmp.tar.gz <bin_url> $ curl -H "Content-Type: application/octet-stream" -T tmp.tar.gz <bin_url>

View file

@ -224,7 +224,7 @@ async fn post_item(
let mut writer = BufWriter::new(file); let mut writer = BufWriter::new(file);
let mut etag_hasher = Sha3_256::new(); let mut etag_hasher = Sha3_256::new();
let mut size = 0; let mut size: u64 = 0;
match data { match data {
MultipartOrStream::Stream(mut stream) => { MultipartOrStream::Stream(mut stream) => {
@ -235,6 +235,10 @@ async fn post_item(
cipher.apply_keystream(&mut buf); cipher.apply_keystream(&mut buf);
writer.write_all(&buf).await?; writer.write_all(&buf).await?;
} }
metadata.content_type = match content_type {
Some(content_type) => Some(content_type.to_string()),
None => Some("application/octet-stream".to_string()),
};
} }
MultipartOrStream::Multipart(mut multipart) => { MultipartOrStream::Multipart(mut multipart) => {
while let Some(mut field) = multipart while let Some(mut field) = multipart
@ -250,6 +254,13 @@ async fn post_item(
cipher.apply_keystream(&mut buf); cipher.apply_keystream(&mut buf);
writer.write_all(&buf).await?; writer.write_all(&buf).await?;
} }
metadata.content_type = Some(
field
.content_type()
.map(|x| x.to_string())
.unwrap_or("application/octet-stream".to_string()),
);
break;
} }
} }
} }
@ -259,16 +270,13 @@ async fn post_item(
let now = SystemTime::now().duration_since(UNIX_EPOCH)?.as_secs(); let now = SystemTime::now().duration_since(UNIX_EPOCH)?.as_secs();
let ttl = params.ttl.unwrap_or(24 * 3600); let ttl = params.ttl.unwrap_or(24 * 3600);
let expires_at = match u64::MAX - ttl > now { let expires_at = match u64::MAX - ttl > now {
true => u64::MAX, true => now + ttl,
false => now + ttl, false => u64::MAX,
}; };
metadata.etag = Some(hex::encode(etag_hasher.finalize())); metadata.etag = Some(hex::encode(etag_hasher.finalize()));
metadata.size = Some(size); metadata.size = Some(size);
metadata.content_type = match content_type {
Some(content_type) => Some(content_type.to_string()),
None => Some("application/octet-stream".to_string()),
};
metadata.expires_at = expires_at; metadata.expires_at = expires_at;
metadata.to_file(&metadata_path).await?; metadata.to_file(&metadata_path).await?;
@ -316,6 +324,11 @@ async fn get_item(
<body style={"font-family: monospace; background-color: black; color: white;"}> <body style={"font-family: monospace; background-color: black; color: white;"}>
<div style={"margin: auto; max-width: 80ch;"}> <div style={"margin: auto; max-width: 80ch;"}>
{raw!(body.as_str())} {raw!(body.as_str())}
<h2>{"Browser upload"}</h2>
<form method={"post"} enctype={"multipart/form-data"}>
<input type={"file"} name={"file"}>{}</input>
<button type={"submit"}>{"Upload"}</button>
</form>
</div> </div>
</body> </body>
</html> </html>
@ -371,7 +384,11 @@ where
let is_multipart = req let is_multipart = req
.headers() .headers()
.get(CONTENT_TYPE) .get(CONTENT_TYPE)
.map(|x| x == "multipart/form-data") .and_then(|x| {
x.to_str()
.ok()
.map(|y| y.starts_with("multipart/form-data"))
})
.unwrap_or_default(); .unwrap_or_default();
if is_multipart { if is_multipart {
Ok(Self::Multipart( Ok(Self::Multipart(