working(ish) upload
This commit is contained in:
2
.gitignore
vendored
2
.gitignore
vendored
@ -5,3 +5,5 @@
|
||||
|
||||
# These are backup files generated by rustfmt
|
||||
**/*.rs.bk
|
||||
serveurhttp
|
||||
test
|
||||
|
||||
273
Cargo.lock
generated
273
Cargo.lock
generated
@ -128,6 +128,28 @@ version = "1.5.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c08606f8c3cbf4ce6ec8e28fb0014a2c086708fe954eaa885384a6165172e7e8"
|
||||
|
||||
[[package]]
|
||||
name = "aws-lc-rs"
|
||||
version = "1.16.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a054912289d18629dc78375ba2c3726a3afe3ff71b4edba9dedfca0e3446d1fc"
|
||||
dependencies = [
|
||||
"aws-lc-sys",
|
||||
"zeroize",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "aws-lc-sys"
|
||||
version = "0.39.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1fa7e52a4c5c547c741610a2c6f123f3881e409b714cd27e6798ef020c514f0a"
|
||||
dependencies = [
|
||||
"cc",
|
||||
"cmake",
|
||||
"dunce",
|
||||
"fs_extra",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "axum"
|
||||
version = "0.8.8"
|
||||
@ -323,6 +345,8 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "aebf35691d1bfb0ac386a69bac2fde4dd276fb618cf8bf4f5318fe285e821bb2"
|
||||
dependencies = [
|
||||
"find-msvc-tools",
|
||||
"jobserver",
|
||||
"libc",
|
||||
"shlex",
|
||||
]
|
||||
|
||||
@ -415,6 +439,15 @@ dependencies = [
|
||||
"half",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "cmake"
|
||||
version = "0.1.57"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "75443c44cd6b379beb8c5b45d85d0773baf31cce901fe7bb252f4eff3008ef7d"
|
||||
dependencies = [
|
||||
"cc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "cocoa"
|
||||
version = "0.26.1"
|
||||
@ -887,6 +920,17 @@ dependencies = [
|
||||
"web-sys",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "dioxus-attributes"
|
||||
version = "0.1.0"
|
||||
source = "git+https://github.com/DioxusLabs/components#6ed7699b85fa4f4f50381138fc9d16e988768933"
|
||||
dependencies = [
|
||||
"dioxus-rsx",
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn 2.0.117",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "dioxus-cli-config"
|
||||
version = "0.7.3"
|
||||
@ -981,7 +1025,7 @@ dependencies = [
|
||||
"global-hotkey",
|
||||
"infer",
|
||||
"jni 0.21.1",
|
||||
"lazy-js-bundle",
|
||||
"lazy-js-bundle 0.7.3",
|
||||
"libc",
|
||||
"muda",
|
||||
"ndk",
|
||||
@ -1052,7 +1096,7 @@ dependencies = [
|
||||
"futures-channel",
|
||||
"futures-util",
|
||||
"generational-box",
|
||||
"lazy-js-bundle",
|
||||
"lazy-js-bundle 0.7.3",
|
||||
"serde",
|
||||
"serde_json",
|
||||
"tracing",
|
||||
@ -1098,7 +1142,7 @@ dependencies = [
|
||||
"js-sys",
|
||||
"mime",
|
||||
"pin-project",
|
||||
"reqwest",
|
||||
"reqwest 0.12.28",
|
||||
"rustversion",
|
||||
"send_wrapper",
|
||||
"serde",
|
||||
@ -1118,7 +1162,7 @@ dependencies = [
|
||||
"url",
|
||||
"wasm-bindgen",
|
||||
"wasm-bindgen-futures",
|
||||
"wasm-streams",
|
||||
"wasm-streams 0.4.2",
|
||||
"web-sys",
|
||||
"xxhash-rust",
|
||||
]
|
||||
@ -1210,7 +1254,7 @@ dependencies = [
|
||||
"futures-util",
|
||||
"generational-box",
|
||||
"keyboard-types",
|
||||
"lazy-js-bundle",
|
||||
"lazy-js-bundle 0.7.3",
|
||||
"rustversion",
|
||||
"serde",
|
||||
"serde_json",
|
||||
@ -1240,7 +1284,7 @@ dependencies = [
|
||||
"dioxus-core-types",
|
||||
"dioxus-html",
|
||||
"js-sys",
|
||||
"lazy-js-bundle",
|
||||
"lazy-js-bundle 0.7.3",
|
||||
"rustc-hash 2.1.1",
|
||||
"serde",
|
||||
"sledgehammer_bindgen",
|
||||
@ -1290,6 +1334,21 @@ dependencies = [
|
||||
"tracing-wasm",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "dioxus-primitives"
|
||||
version = "0.0.1"
|
||||
source = "git+https://github.com/DioxusLabs/components#6ed7699b85fa4f4f50381138fc9d16e988768933"
|
||||
dependencies = [
|
||||
"dioxus",
|
||||
"dioxus-attributes",
|
||||
"dioxus-sdk-time",
|
||||
"lazy-js-bundle 0.6.2",
|
||||
"num-integer",
|
||||
"serde",
|
||||
"time",
|
||||
"tracing",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "dioxus-router"
|
||||
version = "0.7.3"
|
||||
@ -1339,6 +1398,18 @@ dependencies = [
|
||||
"syn 2.0.117",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "dioxus-sdk-time"
|
||||
version = "0.7.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "80c25ae93a3f72e734873b97fbd09d9b1b6adff97205fb0ffd8543e3564fb78e"
|
||||
dependencies = [
|
||||
"dioxus",
|
||||
"futures",
|
||||
"gloo-timers",
|
||||
"tokio",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "dioxus-server"
|
||||
version = "0.7.3"
|
||||
@ -1470,7 +1541,7 @@ dependencies = [
|
||||
"generational-box",
|
||||
"gloo-timers",
|
||||
"js-sys",
|
||||
"lazy-js-bundle",
|
||||
"lazy-js-bundle 0.7.3",
|
||||
"rustc-hash 2.1.1",
|
||||
"send_wrapper",
|
||||
"serde",
|
||||
@ -1479,7 +1550,7 @@ dependencies = [
|
||||
"tracing",
|
||||
"wasm-bindgen",
|
||||
"wasm-bindgen-futures",
|
||||
"wasm-streams",
|
||||
"wasm-streams 0.4.2",
|
||||
"web-sys",
|
||||
]
|
||||
|
||||
@ -1642,6 +1713,15 @@ dependencies = [
|
||||
"serde",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "fastrand"
|
||||
version = "1.9.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e51093e27b0797c359783294ca4f0a911c270184cb10f85783b118614a1501be"
|
||||
dependencies = [
|
||||
"instant",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "fastrand"
|
||||
version = "2.3.0"
|
||||
@ -1752,6 +1832,12 @@ dependencies = [
|
||||
"percent-encoding",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "fs_extra"
|
||||
version = "1.3.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "42703706b716c37f96a77aea830392ad231f44c9e9a67872fa5548707e11b11c"
|
||||
|
||||
[[package]]
|
||||
name = "futf"
|
||||
version = "0.1.5"
|
||||
@ -2390,6 +2476,14 @@ name = "httpserver"
|
||||
version = "0.1.0"
|
||||
dependencies = [
|
||||
"dioxus",
|
||||
"dioxus-html",
|
||||
"dioxus-primitives",
|
||||
"futures",
|
||||
"random-string",
|
||||
"reqwest 0.13.2",
|
||||
"tracing",
|
||||
"wasm-bindgen",
|
||||
"web-sys",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@ -2617,6 +2711,15 @@ dependencies = [
|
||||
"cfb",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "instant"
|
||||
version = "0.1.13"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e0242819d153cba4b4b05a5a8f2a7e9bbf97b6055b2a002b395c96b5ff3c0222"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "inventory"
|
||||
version = "0.3.22"
|
||||
@ -2742,6 +2845,16 @@ dependencies = [
|
||||
"syn 2.0.117",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "jobserver"
|
||||
version = "0.1.34"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9afb3de4395d6b3e67a780b6de64b51c978ecf11cb9a462c66be7d4ca9039d33"
|
||||
dependencies = [
|
||||
"getrandom 0.3.4",
|
||||
"libc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "js-sys"
|
||||
version = "0.3.91"
|
||||
@ -2775,6 +2888,12 @@ dependencies = [
|
||||
"selectors",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "lazy-js-bundle"
|
||||
version = "0.6.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e49596223b9d9d4947a14a25c142a6e7d8ab3f27eb3ade269d238bb8b5c267e2"
|
||||
|
||||
[[package]]
|
||||
name = "lazy-js-bundle"
|
||||
version = "0.7.3"
|
||||
@ -3210,6 +3329,15 @@ version = "0.2.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "cf97ec579c3c42f953ef76dbf8d55ac91fb219dde70e49aa4a6b7d74e9919050"
|
||||
|
||||
[[package]]
|
||||
name = "num-integer"
|
||||
version = "0.1.46"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7969661fd2958a5cb096e56c8e1ad0444ac2bbcd0061bd28660485a44879858f"
|
||||
dependencies = [
|
||||
"num-traits",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "num-traits"
|
||||
version = "0.2.19"
|
||||
@ -3241,6 +3369,15 @@ dependencies = [
|
||||
"syn 2.0.117",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "num_threads"
|
||||
version = "0.1.7"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5c7398b9c8b70908f6371f47ed36737907c87c52af34c268fed0bf0ceb92ead9"
|
||||
dependencies = [
|
||||
"libc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "objc"
|
||||
version = "0.2.7"
|
||||
@ -3805,6 +3942,7 @@ version = "0.11.14"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "434b42fec591c96ef50e21e886936e66d3cc3f737104fdb9b737c40ffb94c098"
|
||||
dependencies = [
|
||||
"aws-lc-rs",
|
||||
"bytes",
|
||||
"getrandom 0.3.4",
|
||||
"lru-slab",
|
||||
@ -3965,6 +4103,15 @@ dependencies = [
|
||||
"rand_core 0.5.1",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "random-string"
|
||||
version = "1.1.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f70fd13c3024ae3f17381bb5c4d409c6dc9ea6895c08fa2147aba305bea3c4af"
|
||||
dependencies = [
|
||||
"fastrand 1.9.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "raw-window-handle"
|
||||
version = "0.5.2"
|
||||
@ -4053,11 +4200,52 @@ dependencies = [
|
||||
"url",
|
||||
"wasm-bindgen",
|
||||
"wasm-bindgen-futures",
|
||||
"wasm-streams",
|
||||
"wasm-streams 0.4.2",
|
||||
"web-sys",
|
||||
"webpki-roots",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "reqwest"
|
||||
version = "0.13.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ab3f43e3283ab1488b624b44b0e988d0acea0b3214e694730a055cb6b2efa801"
|
||||
dependencies = [
|
||||
"base64",
|
||||
"bytes",
|
||||
"encoding_rs",
|
||||
"futures-core",
|
||||
"futures-util",
|
||||
"h2",
|
||||
"http",
|
||||
"http-body",
|
||||
"http-body-util",
|
||||
"hyper",
|
||||
"hyper-rustls",
|
||||
"hyper-util",
|
||||
"js-sys",
|
||||
"log",
|
||||
"mime",
|
||||
"percent-encoding",
|
||||
"pin-project-lite",
|
||||
"quinn",
|
||||
"rustls",
|
||||
"rustls-pki-types",
|
||||
"rustls-platform-verifier",
|
||||
"sync_wrapper",
|
||||
"tokio",
|
||||
"tokio-rustls",
|
||||
"tokio-util",
|
||||
"tower",
|
||||
"tower-http",
|
||||
"tower-service",
|
||||
"url",
|
||||
"wasm-bindgen",
|
||||
"wasm-bindgen-futures",
|
||||
"wasm-streams 0.5.0",
|
||||
"web-sys",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rfd"
|
||||
version = "0.17.2"
|
||||
@ -4136,6 +4324,7 @@ version = "0.23.37"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "758025cb5fccfd3bc2fd74708fd4682be41d99e5dff73c377c0646c6012c73a4"
|
||||
dependencies = [
|
||||
"aws-lc-rs",
|
||||
"once_cell",
|
||||
"ring",
|
||||
"rustls-pki-types",
|
||||
@ -4144,6 +4333,18 @@ dependencies = [
|
||||
"zeroize",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rustls-native-certs"
|
||||
version = "0.8.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "612460d5f7bea540c490b2b6395d8e34a953e52b491accd6c86c8164c5932a63"
|
||||
dependencies = [
|
||||
"openssl-probe",
|
||||
"rustls-pki-types",
|
||||
"schannel",
|
||||
"security-framework",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rustls-pki-types"
|
||||
version = "1.14.0"
|
||||
@ -4154,12 +4355,40 @@ dependencies = [
|
||||
"zeroize",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rustls-platform-verifier"
|
||||
version = "0.6.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1d99feebc72bae7ab76ba994bb5e121b8d83d910ca40b36e0921f53becc41784"
|
||||
dependencies = [
|
||||
"core-foundation 0.10.1",
|
||||
"core-foundation-sys",
|
||||
"jni 0.21.1",
|
||||
"log",
|
||||
"once_cell",
|
||||
"rustls",
|
||||
"rustls-native-certs",
|
||||
"rustls-platform-verifier-android",
|
||||
"rustls-webpki",
|
||||
"security-framework",
|
||||
"security-framework-sys",
|
||||
"webpki-root-certs",
|
||||
"windows-sys 0.61.2",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rustls-platform-verifier-android"
|
||||
version = "0.1.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f87165f0995f63a9fbeea62b64d10b4d9d8e78ec6d7d51fb2125fda7bb36788f"
|
||||
|
||||
[[package]]
|
||||
name = "rustls-webpki"
|
||||
version = "0.103.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d7df23109aa6c1567d1c575b9952556388da57401e4ace1d15f79eedad0d8f53"
|
||||
dependencies = [
|
||||
"aws-lc-rs",
|
||||
"ring",
|
||||
"rustls-pki-types",
|
||||
"untrusted",
|
||||
@ -4762,7 +4991,7 @@ version = "3.26.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "82a72c767771b47409d2345987fda8628641887d5466101319899796367354a0"
|
||||
dependencies = [
|
||||
"fastrand",
|
||||
"fastrand 2.3.0",
|
||||
"getrandom 0.4.2",
|
||||
"once_cell",
|
||||
"rustix",
|
||||
@ -4837,7 +5066,9 @@ checksum = "743bd48c283afc0388f9b8827b976905fb217ad9e647fae3a379a9283c4def2c"
|
||||
dependencies = [
|
||||
"deranged",
|
||||
"itoa",
|
||||
"libc",
|
||||
"num-conv",
|
||||
"num_threads",
|
||||
"powerfmt",
|
||||
"serde_core",
|
||||
"time-core",
|
||||
@ -5487,6 +5718,19 @@ dependencies = [
|
||||
"web-sys",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "wasm-streams"
|
||||
version = "0.5.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9d1ec4f6517c9e11ae630e200b2b65d193279042e28edd4a2cda233e46670bbb"
|
||||
dependencies = [
|
||||
"futures-util",
|
||||
"js-sys",
|
||||
"wasm-bindgen",
|
||||
"wasm-bindgen-futures",
|
||||
"web-sys",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "wasmparser"
|
||||
version = "0.244.0"
|
||||
@ -5579,6 +5823,15 @@ dependencies = [
|
||||
"system-deps",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "webpki-root-certs"
|
||||
version = "1.0.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "804f18a4ac2676ffb4e8b5b5fa9ae38af06df08162314f96a68d2a363e21a8ca"
|
||||
dependencies = [
|
||||
"rustls-pki-types",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "webpki-roots"
|
||||
version = "1.0.6"
|
||||
|
||||
16
Cargo.toml
16
Cargo.toml
@ -8,6 +8,14 @@ edition = "2021"
|
||||
|
||||
[dependencies]
|
||||
dioxus = { version = "0.7.1", features = ["router", "fullstack"] }
|
||||
dioxus-html = "0.7.3"
|
||||
dioxus-primitives = { git = "https://github.com/DioxusLabs/components", version = "0.0.1", default-features = false }
|
||||
futures = "0.3.32"
|
||||
random-string = "1.1.0"
|
||||
reqwest = { version = "0.13.2", features = ["stream"] }
|
||||
tracing = "0.1.44"
|
||||
wasm-bindgen = "0.2.114"
|
||||
web-sys = { version = "0.3.91", features = ["XmlHttpRequest", "XmlHttpRequestUpload", "ProgressEvent" ] }
|
||||
|
||||
[features]
|
||||
default = ["web"]
|
||||
@ -19,3 +27,11 @@ desktop = ["dioxus/desktop"]
|
||||
mobile = ["dioxus/mobile"]
|
||||
# The feature that are only required for the server = ["dioxus/server"] build target should be optional and only enabled in the server = ["dioxus/server"] feature
|
||||
server = ["dioxus/server"]
|
||||
|
||||
[profile.release]
|
||||
opt-level = "z"
|
||||
debug = false
|
||||
lto = true
|
||||
codegen-units = 1
|
||||
panic = "abort"
|
||||
incremental = false
|
||||
|
||||
87
assets/dx-components-theme.css
Normal file
87
assets/dx-components-theme.css
Normal file
@ -0,0 +1,87 @@
|
||||
/* This file contains the global styles for the styled dioxus components. You only
|
||||
* need to import this file once in your project root.
|
||||
*/
|
||||
@import url("https://fonts.googleapis.com/css2?family=Inter:ital,opsz,wght@0,14..32,100..900;1,14..32,100..900&display=swap");
|
||||
|
||||
body {
|
||||
color: var(--secondary-color-4);
|
||||
font-family: Inter, sans-serif;
|
||||
font-optical-sizing: auto;
|
||||
font-style: normal;
|
||||
font-weight: 400;
|
||||
}
|
||||
|
||||
html[data-theme="dark"] {
|
||||
--dark: initial;
|
||||
--light: ;
|
||||
}
|
||||
|
||||
html[data-theme="light"] {
|
||||
--dark: ;
|
||||
--light: initial;
|
||||
}
|
||||
|
||||
@media (prefers-color-scheme: dark) {
|
||||
:root {
|
||||
--dark: initial;
|
||||
--light: ;
|
||||
}
|
||||
}
|
||||
|
||||
@media (prefers-color-scheme: light) {
|
||||
:root {
|
||||
--dark: ;
|
||||
--light: initial;
|
||||
}
|
||||
}
|
||||
|
||||
:root {
|
||||
/* Primary colors */
|
||||
--primary-color: var(--dark, #000) var(--light, #fff);
|
||||
--primary-color-1: var(--dark, #0e0e0e) var(--light, #fbfbfb);
|
||||
--primary-color-2: var(--dark, #0a0a0a) var(--light, #fff);
|
||||
--primary-color-3: var(--dark, #141313) var(--light, #f8f8f8);
|
||||
--primary-color-4: var(--dark, #1a1a1a) var(--light, #f8f8f8);
|
||||
--primary-color-5: var(--dark, #262626) var(--light, #f5f5f5);
|
||||
--primary-color-6: var(--dark, #232323) var(--light, #e5e5e5);
|
||||
--primary-color-7: var(--dark, #3e3e3e) var(--light, #b0b0b0);
|
||||
|
||||
/* Secondary colors */
|
||||
--secondary-color: var(--dark, #fff) var(--light, #000);
|
||||
--secondary-color-1: var(--dark, #fafafa) var(--light, #000);
|
||||
--secondary-color-2: var(--dark, #e6e6e6) var(--light, #0d0d0d);
|
||||
--secondary-color-3: var(--dark, #dcdcdc) var(--light, #2b2b2b);
|
||||
--secondary-color-4: var(--dark, #d4d4d4) var(--light, #111);
|
||||
--secondary-color-5: var(--dark, #a1a1a1) var(--light, #848484);
|
||||
--secondary-color-6: var(--dark, #5d5d5d) var(--light, #d0d0d0);
|
||||
|
||||
/* Highlight colors */
|
||||
--focused-border-color: var(--dark, #2b7fff) var(--light, #2b7fff);
|
||||
--primary-success-color: var(--dark, #02271c) var(--light, #ecfdf5);
|
||||
--secondary-success-color: var(--dark, #b6fae3) var(--light, #10b981);
|
||||
--primary-warning-color: var(--dark, #342203) var(--light, #fffbeb);
|
||||
--secondary-warning-color: var(--dark, #feeac7) var(--light, #f59e0b);
|
||||
--primary-error-color: var(--dark, #a22e2e) var(--light, #dc2626);
|
||||
--secondary-error-color: var(--dark, #9b1c1c) var(--light, #ef4444);
|
||||
--contrast-error-color: var(--dark, var(--secondary-color-3)) var(--light, var(--primary-color));
|
||||
--primary-info-color: var(--dark, var(--primary-color-5)) var(--light, var(--primary-color));
|
||||
--secondary-info-color: var(--dark, var(--primary-color-7)) var(--light, var(--secondary-color-3));
|
||||
}
|
||||
|
||||
/* Modern browsers with `scrollbar-*` support */
|
||||
@supports (scrollbar-width: auto) {
|
||||
:not(:hover) {
|
||||
scrollbar-color: rgb(0 0 0 / 0%) rgb(0 0 0 / 0%);
|
||||
}
|
||||
|
||||
:hover {
|
||||
scrollbar-color: var(--secondary-color-2) rgb(0 0 0 / 0%);
|
||||
}
|
||||
}
|
||||
|
||||
/* Legacy browsers with `::-webkit-scrollbar-*` support */
|
||||
@supports selector(::-webkit-scrollbar) {
|
||||
:root::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
}
|
||||
@ -1,8 +0,0 @@
|
||||
#blog {
|
||||
margin-top: 50px;
|
||||
}
|
||||
|
||||
#blog a {
|
||||
color: #ffffff;
|
||||
margin-top: 50px;
|
||||
}
|
||||
@ -1,34 +0,0 @@
|
||||
#echo {
|
||||
width: 360px;
|
||||
margin-left: auto;
|
||||
margin-right: auto;
|
||||
margin-top: 50px;
|
||||
background-color: #1e222d;
|
||||
padding: 20px;
|
||||
border-radius: 10px;
|
||||
}
|
||||
|
||||
#echo>h4 {
|
||||
margin: 0px 0px 15px 0px;
|
||||
}
|
||||
|
||||
|
||||
#echo>input {
|
||||
border: none;
|
||||
border-bottom: 1px white solid;
|
||||
background-color: transparent;
|
||||
color: #ffffff;
|
||||
transition: border-bottom-color 0.2s ease;
|
||||
outline: none;
|
||||
display: block;
|
||||
padding: 0px 0px 5px 0px;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
#echo>input:focus {
|
||||
border-bottom-color: #6d85c6;
|
||||
}
|
||||
|
||||
#echo>p {
|
||||
margin: 20px 0px 0px auto;
|
||||
}
|
||||
@ -1,42 +0,0 @@
|
||||
body {
|
||||
background-color: #0f1116;
|
||||
color: #ffffff;
|
||||
font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
|
||||
margin: 20px;
|
||||
}
|
||||
|
||||
#hero {
|
||||
margin: 0;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
#links {
|
||||
width: 400px;
|
||||
text-align: left;
|
||||
font-size: x-large;
|
||||
color: white;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
#links a {
|
||||
color: white;
|
||||
text-decoration: none;
|
||||
margin-top: 20px;
|
||||
margin: 10px 0px;
|
||||
border: white 1px solid;
|
||||
border-radius: 5px;
|
||||
padding: 10px;
|
||||
}
|
||||
|
||||
#links a:hover {
|
||||
background-color: #1f1f1f;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
#header {
|
||||
max-width: 1200px;
|
||||
}
|
||||
@ -1,16 +0,0 @@
|
||||
#navbar {
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
}
|
||||
|
||||
#navbar a {
|
||||
color: #ffffff;
|
||||
margin-right: 20px;
|
||||
text-decoration: none;
|
||||
transition: color 0.2s ease;
|
||||
}
|
||||
|
||||
#navbar a:hover {
|
||||
cursor: pointer;
|
||||
color: #91a4d2;
|
||||
}
|
||||
@ -7,6 +7,10 @@
|
||||
'Noto Color Emoji';
|
||||
--font-mono: ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, 'Liberation Mono', 'Courier New',
|
||||
monospace;
|
||||
--spacing: 0.25rem;
|
||||
--text-4xl: 2.25rem;
|
||||
--text-4xl--line-height: calc(2.5 / 2.25);
|
||||
--font-weight-bold: 700;
|
||||
--default-font-family: var(--font-sans);
|
||||
--default-mono-font-family: var(--font-mono);
|
||||
}
|
||||
@ -160,18 +164,41 @@
|
||||
.visible {
|
||||
visibility: visible;
|
||||
}
|
||||
.relative {
|
||||
position: relative;
|
||||
.m-0 {
|
||||
margin: calc(var(--spacing) * 0);
|
||||
}
|
||||
.block {
|
||||
display: block;
|
||||
.hidden {
|
||||
display: none;
|
||||
}
|
||||
.contents {
|
||||
display: contents;
|
||||
.table {
|
||||
display: table;
|
||||
}
|
||||
.w-1 {
|
||||
width: calc(var(--spacing) * 1);
|
||||
}
|
||||
.transform {
|
||||
transform: var(--tw-rotate-x,) var(--tw-rotate-y,) var(--tw-rotate-z,) var(--tw-skew-x,) var(--tw-skew-y,);
|
||||
}
|
||||
.p-1 {
|
||||
padding: calc(var(--spacing) * 1);
|
||||
}
|
||||
.p-2 {
|
||||
padding: calc(var(--spacing) * 2);
|
||||
}
|
||||
.px-2 {
|
||||
padding-inline: calc(var(--spacing) * 2);
|
||||
}
|
||||
.ps-6 {
|
||||
padding-inline-start: calc(var(--spacing) * 6);
|
||||
}
|
||||
.text-4xl {
|
||||
font-size: var(--text-4xl);
|
||||
line-height: var(--tw-leading, var(--text-4xl--line-height));
|
||||
}
|
||||
.font-bold {
|
||||
--tw-font-weight: var(--font-weight-bold);
|
||||
font-weight: var(--font-weight-bold);
|
||||
}
|
||||
}
|
||||
@property --tw-rotate-x {
|
||||
syntax: "*";
|
||||
@ -193,6 +220,10 @@
|
||||
syntax: "*";
|
||||
inherits: false;
|
||||
}
|
||||
@property --tw-font-weight {
|
||||
syntax: "*";
|
||||
inherits: false;
|
||||
}
|
||||
@layer properties {
|
||||
@supports ((-webkit-hyphens: none) and (not (margin-trim: inline))) or ((-moz-orient: inline) and (not (color:rgb(from red r g b)))) {
|
||||
*, ::before, ::after, ::backdrop {
|
||||
@ -201,6 +232,7 @@
|
||||
--tw-rotate-z: initial;
|
||||
--tw-skew-x: initial;
|
||||
--tw-skew-y: initial;
|
||||
--tw-font-weight: initial;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -5,6 +5,12 @@ pkgs.mkShell {
|
||||
];
|
||||
nativeBuildInputs = with pkgs;[
|
||||
openssl
|
||||
glib
|
||||
gdk-pixbuf
|
||||
pango
|
||||
atk
|
||||
xdo
|
||||
lld
|
||||
];
|
||||
PKG_CONFIG_PATH = "${pkgs.openssl.dev}/lib/pkgconfig";
|
||||
}
|
||||
|
||||
@ -1,13 +1,13 @@
|
||||
use dioxus::prelude::*;
|
||||
|
||||
const ECHO_CSS: Asset = asset!("/assets/styling/echo.css");
|
||||
//const ECHO_CSS: Asset = asset!("/assets/styling/echo.css");
|
||||
|
||||
#[component]
|
||||
pub fn Echo() -> Element {
|
||||
let mut response = use_signal(|| String::new());
|
||||
|
||||
rsx! {
|
||||
document::Link { rel: "stylesheet", href: ECHO_CSS }
|
||||
// document::Link { rel: "stylesheet", href: ECHO_CSS }
|
||||
|
||||
div {
|
||||
id: "echo",
|
||||
|
||||
@ -4,3 +4,4 @@ pub use hero::Hero;
|
||||
|
||||
mod echo;
|
||||
pub use echo::Echo;
|
||||
pub mod progress;
|
||||
|
||||
23
src/components/progress/component.rs
Normal file
23
src/components/progress/component.rs
Normal file
@ -0,0 +1,23 @@
|
||||
use dioxus::prelude::*;
|
||||
use dioxus_primitives::progress::{self, ProgressIndicatorProps, ProgressProps};
|
||||
|
||||
#[component]
|
||||
pub fn Progress(props: ProgressProps) -> Element {
|
||||
rsx! {
|
||||
document::Link { rel: "stylesheet", href: asset!("./style.css") }
|
||||
progress::Progress {
|
||||
class: "progress",
|
||||
value: props.value,
|
||||
max: props.max,
|
||||
attributes: props.attributes,
|
||||
{props.children}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[component]
|
||||
pub fn ProgressIndicator(props: ProgressIndicatorProps) -> Element {
|
||||
rsx! {
|
||||
progress::ProgressIndicator { class: "progress-indicator", attributes: props.attributes, {props.children} }
|
||||
}
|
||||
}
|
||||
2
src/components/progress/mod.rs
Normal file
2
src/components/progress/mod.rs
Normal file
@ -0,0 +1,2 @@
|
||||
mod component;
|
||||
pub use component::*;
|
||||
31
src/components/progress/style.css
Normal file
31
src/components/progress/style.css
Normal file
@ -0,0 +1,31 @@
|
||||
.progress {
|
||||
position: relative;
|
||||
overflow: hidden;
|
||||
width: 200px;
|
||||
height: .5rem;
|
||||
box-sizing: border-box;
|
||||
border-radius: 9999px;
|
||||
background: var(--primary-color-5);
|
||||
}
|
||||
|
||||
.progress[data-state='indeterminate'] .progress-indicator {
|
||||
width: 50%;
|
||||
animation: indeterminate 1s infinite linear;
|
||||
}
|
||||
|
||||
.progress-indicator {
|
||||
width: var(--progress-value, 0%);
|
||||
height: 100%;
|
||||
background-color: var(--secondary-color-1);
|
||||
transition: width 250ms ease;
|
||||
}
|
||||
|
||||
@keyframes indeterminate {
|
||||
0% {
|
||||
transform: translateX(-100%);
|
||||
}
|
||||
|
||||
100% {
|
||||
transform: translateX(200%);
|
||||
}
|
||||
}
|
||||
11
src/main.rs
11
src/main.rs
@ -1,7 +1,7 @@
|
||||
use dioxus::prelude::*;
|
||||
|
||||
|
||||
use views::{Blog, Home, Navbar};
|
||||
use views::{Blog, Home, Navbar, Upload};
|
||||
use tracing::Level;
|
||||
|
||||
mod components;
|
||||
mod views;
|
||||
@ -9,6 +9,8 @@ mod views;
|
||||
#[derive(Debug, Clone, Routable, PartialEq)]
|
||||
#[rustfmt::skip]
|
||||
enum Route {
|
||||
#[route("/upload")]
|
||||
Upload {},
|
||||
#[layout(Navbar)]
|
||||
#[route("/")]
|
||||
Home {},
|
||||
@ -17,10 +19,11 @@ enum Route {
|
||||
}
|
||||
|
||||
const FAVICON: Asset = asset!("/assets/favicon.ico");
|
||||
const MAIN_CSS: Asset = asset!("/assets/styling/main.css");
|
||||
//const MAIN_CSS: Asset = asset!("/assets/styling/main.css");
|
||||
const TAILWIND_CSS: Asset = asset!("/assets/tailwind.css");
|
||||
|
||||
fn main() {
|
||||
dioxus::logger::init(Level::INFO).expect("failed to init logger");
|
||||
dioxus::launch(App);
|
||||
}
|
||||
|
||||
@ -28,7 +31,7 @@ fn main() {
|
||||
fn App() -> Element {
|
||||
rsx! {
|
||||
document::Link { rel: "icon", href: FAVICON }
|
||||
document::Link { rel: "stylesheet", href: MAIN_CSS }
|
||||
// document::Link { rel: "stylesheet", href: MAIN_CSS }
|
||||
document::Link { rel: "stylesheet", href: TAILWIND_CSS }
|
||||
|
||||
Router::<Route> {}
|
||||
|
||||
@ -2,12 +2,12 @@ use crate::Route;
|
||||
use dioxus::prelude::*;
|
||||
use crate::components::{Hero};
|
||||
|
||||
const BLOG_CSS: Asset = asset!("/assets/styling/blog.css");
|
||||
//const BLOG_CSS: Asset = asset!("/assets/styling/blog.css");
|
||||
|
||||
#[component]
|
||||
pub fn Blog(id: i32) -> Element {
|
||||
rsx! {
|
||||
document::Link { rel: "stylesheet", href: BLOG_CSS }
|
||||
// document::Link { rel: "stylesheet", href: BLOG_CSS }
|
||||
|
||||
div {
|
||||
id: "blog",
|
||||
|
||||
@ -6,3 +6,6 @@ pub use blog::Blog;
|
||||
|
||||
mod navbar;
|
||||
pub use navbar::Navbar;
|
||||
|
||||
mod upload;
|
||||
pub use upload::Upload;
|
||||
|
||||
@ -1,12 +1,12 @@
|
||||
use crate::Route;
|
||||
use dioxus::prelude::*;
|
||||
|
||||
const NAVBAR_CSS: Asset = asset!("/assets/styling/navbar.css");
|
||||
//const NAVBAR_CSS: Asset = asset!("/assets/styling/navbar.css");
|
||||
|
||||
#[component]
|
||||
pub fn Navbar() -> Element {
|
||||
rsx! {
|
||||
document::Link { rel: "stylesheet", href: NAVBAR_CSS }
|
||||
// document::Link { rel: "stylesheet", href: NAVBAR_CSS }
|
||||
|
||||
div {
|
||||
id: "navbar",
|
||||
|
||||
154
src/views/upload.rs
Normal file
154
src/views/upload.rs
Normal file
@ -0,0 +1,154 @@
|
||||
use dioxus::{
|
||||
fullstack::{ByteStream, FileStream},
|
||||
prelude::*,
|
||||
};
|
||||
|
||||
use dioxus_html::{FileData, HasFileData};
|
||||
use futures::StreamExt;
|
||||
|
||||
use std::{ env, fs, io::Write };
|
||||
|
||||
|
||||
use random_string;
|
||||
|
||||
pub fn byte_to_human_size(size: u64) -> String {
|
||||
let sizes = vec!["B", "KB", "MB", "GB", "TB", "WTFAREYOUDOINGB"];
|
||||
let mut current = 0;
|
||||
|
||||
let mut res_size: f64 = size as f64;
|
||||
let mut res: String;
|
||||
|
||||
while (res_size >= 1000.0 && current < sizes.len()) {
|
||||
res_size /= 1000.0;
|
||||
current += 1;
|
||||
}
|
||||
|
||||
res = ((res_size * 100.0).round() / 100.0).to_string() + " " + sizes[current];
|
||||
res
|
||||
}
|
||||
|
||||
#[post("/api/upload")]
|
||||
async fn upload_file(mut upload: FileStream) -> Result<String, HttpError> {
|
||||
let UPLOAD_SIZE_LIMIT: u64 = 1024 * 1024 * 1024 * 1;
|
||||
let UPLOAD_FOLDER: String = match env::var("UPLOAD_FOLDER") {
|
||||
Ok(value) => { value },
|
||||
Err(_) => { return HttpError::internal_server_error("UPLOAD_FOLDER not set"); }
|
||||
};
|
||||
|
||||
let mut total_len: u64 = 0;
|
||||
let mut error: Option<&str> = None;
|
||||
|
||||
let filename: String = loop {
|
||||
let cur = random_string::generate(20, "ABCDEFGHIJKLMNOPQRTSTUVWXYZ0123456789");
|
||||
if (!fs::exists(UPLOAD_FOLDER.clone() + &cur).expect("can't check if file exists")) {
|
||||
break cur;
|
||||
}
|
||||
};
|
||||
|
||||
if upload.size().unwrap() > UPLOAD_SIZE_LIMIT {
|
||||
return HttpError::payload_too_large("this file is too large");
|
||||
}
|
||||
|
||||
|
||||
let mut file = match fs::File::create(UPLOAD_FOLDER.clone() + &filename) {
|
||||
Ok(val) => { val },
|
||||
Err(_) => { return HttpError::internal_server_error("failed to open the output file") }
|
||||
};
|
||||
|
||||
while let Some(chunk) = upload.next().await {
|
||||
match chunk {
|
||||
Ok(bytes) => {
|
||||
total_len += bytes.len() as u64;
|
||||
if total_len > UPLOAD_SIZE_LIMIT {
|
||||
error = Some("Uploaded file to large");
|
||||
break;
|
||||
}
|
||||
|
||||
if file.write(&bytes).is_err() { error == Some("failed write"); break; };
|
||||
},
|
||||
Err(_) => { error = Some("unknown"); break; }
|
||||
}
|
||||
}
|
||||
|
||||
match error {
|
||||
Some(err)=> {
|
||||
file.sync_data();
|
||||
fs::remove_file(UPLOAD_FOLDER.clone() + &filename);
|
||||
HttpError::internal_server_error(err)?
|
||||
}
|
||||
None => { Ok(filename) }
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
pub fn build_table(files: Vec<(String, String, Option<Result<String, HttpError>>)>) -> Element {
|
||||
rsx! {
|
||||
table {
|
||||
tr {
|
||||
th { "filename" }
|
||||
th { "size" }
|
||||
th { "url" }
|
||||
}
|
||||
|
||||
{ files.iter().map(|file| rsx! {
|
||||
tr {
|
||||
td { class: "px-2", "{file.0}" }
|
||||
td { class: "px-2", "{file.1}" }
|
||||
td { class: "px-2",
|
||||
match &file.2 {
|
||||
Some(res) => { match res {
|
||||
Ok(file_id) => { rsx! { input { type:"button" , "/upload/dl/{file_id}"} } },
|
||||
Err(e) => {
|
||||
let msg = e.message.clone().unwrap();
|
||||
rsx! { p { "Upload failed, reason : {msg}" } }
|
||||
}
|
||||
} }
|
||||
None => { rsx! { p { "Waiting for file to be uploaded" } } }
|
||||
}
|
||||
}
|
||||
}
|
||||
}) }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[component]
|
||||
pub fn Upload() -> Element {
|
||||
//TODO: global config struct
|
||||
let UPLOAD_SIZE_LIMIT: u64 = 1024 * 1024 * 1024 * 1;
|
||||
|
||||
let mut selected : Signal<Vec<(String, String, Option<Result<String, HttpError>>)>> = use_signal(|| vec![]);
|
||||
|
||||
rsx! {
|
||||
div { class : "p-2",
|
||||
p { class: "text-4xl font-bold p-1", "Upload a file" }
|
||||
|
||||
form {
|
||||
|
||||
label { for :"file", {
|
||||
if selected.len() == 0 {
|
||||
rsx! { "No file selected" }
|
||||
} else {
|
||||
build_table(selected())
|
||||
}
|
||||
} }
|
||||
|
||||
input { id: "file", r#type : "file" ,multiple: true, class : "hidden", oninput: move |e| async move {
|
||||
for file in e.files() {
|
||||
selected.with_mut(|files| {files.push((file.name(), byte_to_human_size(file.size()), None)); } );
|
||||
let idx = selected().len() - 1;
|
||||
|
||||
if (file.size() > UPLOAD_SIZE_LIMIT) {
|
||||
//messy but firefox can't handle when server returns early
|
||||
selected.with_mut(|files| { files[idx].2 = Some(HttpError::payload_too_large("This file is too large")) });
|
||||
continue;
|
||||
}
|
||||
|
||||
let res = upload_file(file.clone().into()).await;
|
||||
selected.with_mut(|files| { files[idx].2 = Some(res) });
|
||||
}
|
||||
}}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
12
todo
Normal file
12
todo
Normal file
@ -0,0 +1,12 @@
|
||||
|
||||
/upload
|
||||
- can upload up to 100GB
|
||||
- if video, set mime
|
||||
- deletion rules:
|
||||
- older than 1 month
|
||||
- more than 300GB used and more than 7 days old
|
||||
- show file deletion info
|
||||
|
||||
/status (check status of dependent devices, maybe useless)
|
||||
|
||||
/boot (later, previous program is bad)
|
||||
Reference in New Issue
Block a user