parent
6b60399c5f
commit
424af11918
@ -0,0 +1,139 @@
|
||||
use std::cmp;
|
||||
|
||||
use actix_web::web;
|
||||
use chrono::Duration;
|
||||
|
||||
use crate::config::Config;
|
||||
|
||||
const INDEX_HTML: &str = include_str!("../template/index.html");
|
||||
const AUTH_HIDE_JS: &str = include_str!("../template/auth-hide.js");
|
||||
const AUTH_SNIPPET_HTML: &str = include_str!("../snippet/auth.html.snippet");
|
||||
const MAX_SIZE_SNIPPET_HTML: &str = include_str!("../snippet/max_size.html.snippet");
|
||||
|
||||
pub async fn write_prefillable_templates(config: &Config) {
|
||||
let index_html = build_index_html(config);
|
||||
let auth_hide_js = build_auth_hide_js(config);
|
||||
let index_path = config.static_dir.join("index.html");
|
||||
let auth_hide_path = config.static_dir.join("auth-hide.js");
|
||||
|
||||
async_std::fs::write(index_path, index_html)
|
||||
.await
|
||||
.expect("could not write index.html to static folder");
|
||||
if let Some(auth_hide_js) = auth_hide_js {
|
||||
async_std::fs::write(auth_hide_path, auth_hide_js)
|
||||
.await
|
||||
.expect("could not write auth-hide.js to static folder");
|
||||
} else if auth_hide_path.exists().await {
|
||||
async_std::fs::remove_file(auth_hide_path)
|
||||
.await
|
||||
.expect("could not delete auth-hide.js from static folder");
|
||||
}
|
||||
}
|
||||
|
||||
fn build_index_html(config: &Config) -> String {
|
||||
let auth_snippet = config
|
||||
.no_auth_limits
|
||||
.as_ref()
|
||||
.map_or("", |_| AUTH_SNIPPET_HTML);
|
||||
let max_size_snippet = config
|
||||
.max_file_size
|
||||
.as_ref()
|
||||
.map_or("", |_| MAX_SIZE_SNIPPET_HTML);
|
||||
INDEX_HTML
|
||||
.replace("{max_size_snippet}", max_size_snippet)
|
||||
.replace(
|
||||
"{max_size}",
|
||||
&render_file_size(config.max_file_size.unwrap_or(0)),
|
||||
)
|
||||
.replace("{auth_snippet}", auth_snippet)
|
||||
.replace(
|
||||
"{auth_time}",
|
||||
&config
|
||||
.no_auth_limits
|
||||
.as_ref()
|
||||
.map(|limit| limit.max_time)
|
||||
.map_or("".into(), render_duration),
|
||||
)
|
||||
.replace(
|
||||
"{auth_large_time}",
|
||||
&config
|
||||
.no_auth_limits
|
||||
.as_ref()
|
||||
.map(|limit| limit.large_file_max_time)
|
||||
.map_or("".into(), render_duration),
|
||||
)
|
||||
.replace(
|
||||
"{auth_large_size}",
|
||||
&config
|
||||
.no_auth_limits
|
||||
.as_ref()
|
||||
.map(|limit| limit.large_file_size)
|
||||
.map_or("".into(), render_file_size),
|
||||
)
|
||||
}
|
||||
|
||||
fn render_file_size(size: u64) -> String {
|
||||
let magnitude = cmp::min((size as f64).log(1024.0) as u32, 5);
|
||||
let prefix = ["", "ki", "Mi", "Gi", "Ti", "Pi"][magnitude as usize];
|
||||
let value = size / (1024_u64.pow(magnitude));
|
||||
format!("{}{}B", value, prefix)
|
||||
}
|
||||
|
||||
fn render_duration(duration: Duration) -> String {
|
||||
let days = duration.num_days();
|
||||
let hours = duration.num_hours() % 24;
|
||||
let minutes = duration.num_minutes() % 60;
|
||||
let seconds = duration.num_seconds() % 60;
|
||||
let mut elements = vec![];
|
||||
if let Some(name) = pluralize(days, "tag", "e") {
|
||||
elements.push(name);
|
||||
}
|
||||
if let Some(name) = pluralize(hours, "stunde", "n") {
|
||||
elements.push(name);
|
||||
}
|
||||
if let Some(name) = pluralize(minutes, "minute", "n") {
|
||||
elements.push(name);
|
||||
}
|
||||
if let Some(name) = pluralize(seconds, "sekunde", "n") {
|
||||
elements.push(name);
|
||||
}
|
||||
elements.join("+")
|
||||
}
|
||||
|
||||
fn pluralize(number: i64, word: &str, suffix: &str) -> Option<String> {
|
||||
match number {
|
||||
0 => None,
|
||||
1 => Some(format!("{} {}", number, word)),
|
||||
_ => Some(format!("{} {}{}", number, word, suffix)),
|
||||
}
|
||||
}
|
||||
|
||||
fn build_auth_hide_js(config: &Config) -> Option<String> {
|
||||
if let Some(no_auth_limits) = &config.no_auth_limits {
|
||||
let auth_hide_js = AUTH_HIDE_JS
|
||||
.replace(
|
||||
"{no_auth_max_time}",
|
||||
&no_auth_limits.max_time.num_seconds().to_string(),
|
||||
)
|
||||
.replace(
|
||||
"{no_auth_large_file_max_time}",
|
||||
&no_auth_limits.large_file_max_time.num_seconds().to_string(),
|
||||
)
|
||||
.replace(
|
||||
"{no_auth_large_file_size}",
|
||||
&no_auth_limits.large_file_size.to_string(),
|
||||
);
|
||||
Some(auth_hide_js)
|
||||
// Ok(HttpResponse::Ok()
|
||||
// .content_type("application/javascript")
|
||||
// .body(auth_hide_js))
|
||||
} else {
|
||||
None
|
||||
// Err(error::ErrorNotFound("file not found"))
|
||||
}
|
||||
}
|
||||
|
||||
pub fn get_host_url(req: &web::HttpRequest) -> String {
|
||||
let conn = req.connection_info();
|
||||
format!("{}://{}", conn.scheme(), conn.host())
|
||||
}
|
@ -0,0 +1,73 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="de-DE">
|
||||
<head>
|
||||
<title>datatrash</title>
|
||||
<meta charset="utf-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
||||
<meta name="description" content="Temporärer Dateiaustausch" />
|
||||
<link href="/static/index.css" rel="stylesheet" />
|
||||
</head>
|
||||
<body>
|
||||
<main>
|
||||
<h1>datatrash</h1>
|
||||
<form action="/upload" method="POST" enctype="multipart/form-data">
|
||||
<label for="file-upload">datei (maximal 8MiB)
|
||||
</label>
|
||||
<br />
|
||||
<input id="file-upload" type="file" name="file" />
|
||||
<br />
|
||||
<label for="text-upload">oder asciitrash</label>
|
||||
<br />
|
||||
<textarea id="text-upload" name="text" cols="120"></textarea>
|
||||
<br />
|
||||
<label for="keep_for">gültig für</label>
|
||||
<select id="keep_for" name="keep_for">
|
||||
<option value="1800">30 minuten</option>
|
||||
<option value="3600">60 minuten</option>
|
||||
<option value="43200">12 stunden</option>
|
||||
<option value="86400">24 stunden</option>
|
||||
<option value="604800">eine woche</option>
|
||||
<option value="2678400">einen monat</option>
|
||||
</select>
|
||||
<br />
|
||||
<input
|
||||
id="delete_on_download"
|
||||
type="checkbox"
|
||||
name="delete_on_download"
|
||||
/>
|
||||
<label for="delete_on_download">nach einem download löschen</label>
|
||||
<br />
|
||||
<input class="main button" type="submit" value="hochladen" />
|
||||
</form>
|
||||
<details class="usage">
|
||||
<summary>nutzung als api</summary>
|
||||
<pre>
|
||||
datei hochladen
|
||||
curl -F 'file=@yourfile.rs' <domain>/upload
|
||||
|
||||
text hochladen
|
||||
curl -F 'text=your text' <domain>/upload
|
||||
|
||||
zeitbegrenzung setzen
|
||||
curl -F 'text=your text' -F 'keep_for=1800' <domain>/upload
|
||||
|
||||
nach einem download löschen
|
||||
curl -F 'text=your text' -F 'delete_on_download=true' <domain>/upload
|
||||
|
||||
authentifizieren
|
||||
curl -F 'text=your text' -F 'password=…' <domain>/upload</pre
|
||||
>
|
||||
</details>
|
||||
</main>
|
||||
<footer>
|
||||
<a
|
||||
class="repo"
|
||||
href="https://repos.ctdo.de/neri/datatrash"
|
||||
target="_blank"
|
||||
rel="noopener noreferrer"
|
||||
>
|
||||
repo
|
||||
</a>
|
||||
</footer>
|
||||
</body>
|
||||
</html>
|
Loading…
Reference in new issue