diff --git a/.github/workflows/deploy-docs.yaml b/.github/workflows/deploy-docs.yaml index 168a0c6b..a343f281 100644 --- a/.github/workflows/deploy-docs.yaml +++ b/.github/workflows/deploy-docs.yaml @@ -23,7 +23,7 @@ jobs: echo `pwd`/mdbook >> $GITHUB_PATH - name: Test and Build Book run: | - rustup default nightly-2024-09-01 + rustup default nightly-2024-10-13 cargo clean --target-dir mdbook-target cargo build --all-features --target-dir mdbook-target mdbook test -L mdbook-target/debug/deps wtx-docs && mdbook build wtx-docs diff --git a/.github/workflows/tests.yaml b/.github/workflows/tests.yaml index e60bab61..1594543f 100644 --- a/.github/workflows/tests.yaml +++ b/.github/workflows/tests.yaml @@ -13,7 +13,7 @@ jobs: with: override: true profile: minimal - toolchain: nightly-2024-09-01 + toolchain: nightly-2024-10-13 - uses: Swatinem/rust-cache@v2 - run: .scripts/autobahn-fuzzingclient.sh ci @@ -25,7 +25,7 @@ jobs: with: override: true profile: minimal - toolchain: nightly-2024-09-01 + toolchain: nightly-2024-10-13 - uses: Swatinem/rust-cache@v2 - run: .scripts/autobahn-fuzzingserver.sh ci @@ -37,7 +37,7 @@ jobs: with: override: true profile: minimal - toolchain: nightly-2024-09-01 + toolchain: nightly-2024-10-13 - uses: actions-rs/install@v0.1 with: crate: cargo-fuzz @@ -52,7 +52,7 @@ jobs: with: override: true profile: minimal - toolchain: nightly-2024-09-01 + toolchain: nightly-2024-10-13 - uses: Swatinem/rust-cache@v2 - run: .scripts/h2spec.sh high ci @@ -64,7 +64,7 @@ jobs: with: override: true profile: minimal - toolchain: nightly-2024-09-01 + toolchain: nightly-2024-10-13 - uses: Swatinem/rust-cache@v2 - run: .scripts/h2spec.sh low ci @@ -76,7 +76,7 @@ jobs: with: override: true profile: minimal - toolchain: nightly-2024-09-01 + toolchain: nightly-2024-10-13 - uses: Swatinem/rust-cache@v2 - run: sudo apt install docker-compose -y - run: docker-compose -f .test-utils/docker-compose.yml up -d @@ -97,7 +97,7 @@ jobs: components: clippy, rustfmt override: true profile: minimal - toolchain: nightly-2024-09-01 + toolchain: nightly-2024-10-13 - uses: Swatinem/rust-cache@v2 - run: .scripts/internal-tests-0.sh @@ -114,6 +114,6 @@ jobs: components: clippy, rustfmt override: true profile: minimal - toolchain: nightly-2024-09-01 + toolchain: nightly-2024-10-13 - uses: Swatinem/rust-cache@v2 - run: .scripts/internal-tests-1.sh diff --git a/.scripts/internal-tests-0.sh b/.scripts/internal-tests-0.sh index 2c0f07fd..b2aee8ca 100755 --- a/.scripts/internal-tests-0.sh +++ b/.scripts/internal-tests-0.sh @@ -3,7 +3,7 @@ . "$(dirname "$0")/common.sh" --source-only $rt rustfmt -$rt clippy -Aclippy::little-endian-bytes,-Aclippy::panic-in-result-fn +$rt clippy -Aclippy::little-endian-bytes,-Aclippy::panic-in-result-fn,-Aclippy::used_underscore_items cargo miri test --features http2,postgres,web-socket -p wtx two_sta @@ -13,6 +13,7 @@ $rt check-generic wtx $rt test-with-features wtx aes-gcm $rt test-with-features wtx arbitrary $rt test-with-features wtx argon2 +$rt test-with-features wtx aws-lc-rs,_hack $rt test-with-features wtx base64 $rt test-with-features wtx borsh $rt test-with-features wtx chrono @@ -22,6 +23,7 @@ $rt test-with-features wtx crypto-common $rt test-with-features wtx data-transformation $rt test-with-features wtx database $rt test-with-features wtx digest +$rt test-with-features wtx embassy-time $rt test-with-features wtx fastrand $rt test-with-features wtx flate2 $rt test-with-features wtx foldhash @@ -42,6 +44,7 @@ $rt test-with-features wtx quick-protobuf $rt test-with-features wtx rand_chacha $rt test-with-features wtx ring $rt test-with-features wtx rust_decimal +$rt test-with-features wtx rustls $rt test-with-features wtx schema-manager $rt test-with-features wtx schema-manager-dev $rt test-with-features wtx serde diff --git a/.scripts/internal-tests-1.sh b/.scripts/internal-tests-1.sh index c2585894..b98d70b2 100755 --- a/.scripts/internal-tests-1.sh +++ b/.scripts/internal-tests-1.sh @@ -6,7 +6,7 @@ cargo check --all-features --all-targets # WTX Docs -rustup default nightly-2024-09-01 +rustup default nightly-2024-10-13 cargo clean --target-dir mdbook-target cargo build --all-features --target-dir mdbook-target mdbook test -L mdbook-target/debug/deps wtx-docs \ No newline at end of file diff --git a/Cargo.lock b/Cargo.lock index 1ab5925d..cd218eee 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1,6 +1,6 @@ # This file is automatically @generated by Cargo. # It is not intended for manual editing. -version = 3 +version = 4 [[package]] name = "addr2line" @@ -181,6 +181,32 @@ version = "1.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ace50bade8e6234aa140d9a2f552bbee1db4d353f69b8217bc503490fc1a9f26" +[[package]] +name = "aws-lc-rs" +version = "1.11.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f47bb8cc16b669d267eeccf585aea077d0882f4777b1c1f740217885d6e6e5a3" +dependencies = [ + "aws-lc-sys", + "paste", + "zeroize", +] + +[[package]] +name = "aws-lc-sys" +version = "0.23.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a2101df3813227bbaaaa0b04cd61c534c7954b22bd68d399b440be937dc63ff7" +dependencies = [ + "bindgen", + "cc", + "cmake", + "dunce", + "fs_extra", + "libc", + "paste", +] + [[package]] name = "backtrace" version = "0.3.74" @@ -224,12 +250,41 @@ dependencies = [ "smallvec", ] +[[package]] +name = "bindgen" +version = "0.69.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "271383c67ccabffb7381723dea0672a673f292304fcb45c01cc648c7a8d58088" +dependencies = [ + "bitflags 2.6.0", + "cexpr", + "clang-sys", + "itertools", + "lazy_static", + "lazycell", + "log", + "prettyplease", + "proc-macro2", + "quote", + "regex", + "rustc-hash", + "shlex", + "syn 2.0.90", + "which", +] + [[package]] name = "bitflags" version = "1.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a" +[[package]] +name = "bitflags" +version = "2.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b048fb63fd8b5923fc5aa7b340d8e156aec7ec02f0c78fa8a6ddc2613f6f71de" + [[package]] name = "bitvec" version = "1.0.1" @@ -289,7 +344,7 @@ dependencies = [ "proc-macro-crate", "proc-macro2", "quote", - "syn 2.0.89", + "syn 2.0.90", ] [[package]] @@ -328,21 +383,30 @@ checksum = "1fd0f2584146f6f2ef48085050886acf353beff7305ebd1ae69500e27c67f64b" [[package]] name = "bytes" -version = "1.8.0" +version = "1.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9ac0150caa2ae65ca5bd83f25c7de183dea78d4d366469f148435e2acfbad0da" +checksum = "325918d6fe32f23b19878fe4b34794ae41fc19ddbe53b10571a4874d44ffd39b" [[package]] name = "cc" -version = "1.2.1" +version = "1.2.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fd9de9f2205d5ef3fd67e685b0df337994ddd4495e2a28d185500d0e1edfea47" +checksum = "f34d93e62b03caf570cccc334cbc6c2fceca82f39211051345108adcba3eebdc" dependencies = [ "jobserver", "libc", "shlex", ] +[[package]] +name = "cexpr" +version = "0.6.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6fac387a98bb7c37292057cffc56d62ecb629900026402633ae9160df93a8766" +dependencies = [ + "nom", +] + [[package]] name = "cfg-if" version = "1.0.0" @@ -398,11 +462,22 @@ dependencies = [ "tinyvec", ] +[[package]] +name = "clang-sys" +version = "1.8.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0b023947811758c97c59bf9d1c188fd619ad4718dcaa767947df1cadb14f39f4" +dependencies = [ + "glob", + "libc", + "libloading", +] + [[package]] name = "clap" -version = "4.5.21" +version = "4.5.23" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fb3b4b9e5a7c7514dfa52869339ee98b3156b0bfb4e8a77c4ff4babb64b1604f" +checksum = "3135e7ec2ef7b10c6ed8950f0f792ed96ee093fa088608f1c76e569722700c84" dependencies = [ "clap_builder", "clap_derive", @@ -410,9 +485,9 @@ dependencies = [ [[package]] name = "clap_builder" -version = "4.5.21" +version = "4.5.23" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b17a95aa67cc7b5ebd32aa5370189aa0d79069ef1c64ce893bd30fb24bff20ec" +checksum = "30582fc632330df2bd26877bde0c1f4470d57c582bbc070376afcd04d8cb4838" dependencies = [ "anstyle", "clap_lex", @@ -427,14 +502,23 @@ dependencies = [ "heck", "proc-macro2", "quote", - "syn 2.0.89", + "syn 2.0.90", ] [[package]] name = "clap_lex" -version = "0.7.3" +version = "0.7.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "afb84c814227b90d6895e01398aee0d8033c00e7466aca416fb6a8e0eb19d8a7" +checksum = "f46ad14479a25103f283c0f10005961cf086d8dc42205bb44c46ac563475dca6" + +[[package]] +name = "cmake" +version = "0.1.52" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c682c223677e0e5b6b7f63a64b9351844c3f1b1678a68b7ee617e30fb082620e" +dependencies = [ + "cc", +] [[package]] name = "const-oid" @@ -541,7 +625,7 @@ checksum = "30542c1ad912e0e3d22a1935c290e12e8a29d704a420177a31faad4a601a0800" dependencies = [ "proc-macro2", "quote", - "syn 2.0.89", + "syn 2.0.90", ] [[package]] @@ -570,6 +654,18 @@ version = "0.15.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "77c90badedccf4105eca100756a0b1289e191f6fcbdadd3cee1d2f614f97da8f" +[[package]] +name = "dunce" +version = "1.0.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "92773504d58c093f6de2459af4af33faa518c13451eb8f2b5698ed3d36e7c813" + +[[package]] +name = "either" +version = "1.13.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "60b1af1c220855b6ceac025d3f6ecdd2b7c4894bfe9cd9bda4fbb4bc7c0d4cf0" + [[package]] name = "elliptic-curve" version = "0.13.8" @@ -746,6 +842,16 @@ version = "1.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5443807d6dff69373d433ab9ef5378ad8df50ca6298caf15de6e52e24aaf54d5" +[[package]] +name = "errno" +version = "0.3.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "33d852cb9b869c2a9b3df2f71a3074817f01e1844f839a144f5fcef059a4eb5d" +dependencies = [ + "libc", + "windows-sys 0.59.0", +] + [[package]] name = "fastrand" version = "2.2.0" @@ -779,6 +885,12 @@ version = "0.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f81ec6369c545a7d40e4589b5597581fa1c441fe1cce96dd1de43159910a36a2" +[[package]] +name = "fs_extra" +version = "1.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "42703706b716c37f96a77aea830392ad231f44c9e9a67872fa5548707e11b11c" + [[package]] name = "funty" version = "2.0.0" @@ -962,12 +1074,6 @@ version = "0.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2304e00983f87ffb38b55b444b5e3b60a884b5d30c0fca7d82fe33449bbe55ea" -[[package]] -name = "hermit-abi" -version = "0.3.9" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d231dfb89cfffdbc30e7fc41579ed6066ad03abda9e567ccafae602b97ec5024" - [[package]] name = "hex" version = "0.4.3" @@ -992,6 +1098,15 @@ dependencies = [ "digest", ] +[[package]] +name = "home" +version = "0.5.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e3d1354bf6b7235cb4a0576c2619fd4ed18183f689b12b006a0ee7329eeff9a5" +dependencies = [ + "windows-sys 0.52.0", +] + [[package]] name = "httparse" version = "1.9.5" @@ -1032,9 +1147,9 @@ dependencies = [ [[package]] name = "indexmap" -version = "2.6.0" +version = "2.7.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "707907fe3c25f5424cce2cb7e1cbcafee6bdbe735ca90ef77c29e84591e5b9da" +checksum = "62f822373a4fe84d4bb149bf54e584a7f4abec90e072ed49cda0edea5b95471f" dependencies = [ "equivalent", "hashbrown 0.15.2", @@ -1059,6 +1174,15 @@ dependencies = [ "hybrid-array", ] +[[package]] +name = "itertools" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ba291022dbbd398a455acf126c1e341954079855bc60dfdda641363bd6922569" +dependencies = [ + "either", +] + [[package]] name = "itoa" version = "1.0.14" @@ -1076,10 +1200,11 @@ dependencies = [ [[package]] name = "js-sys" -version = "0.3.72" +version = "0.3.74" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6a88f1bda2bd75b0452a14784937d796722fdebfe50df998aeb3f0b7603019a9" +checksum = "a865e038f7f6ed956f788f0d7d60c541fff74c7bd74272c5d4cf15c63743e705" dependencies = [ + "once_cell", "wasm-bindgen", ] @@ -1089,11 +1214,17 @@ version = "1.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bbd2bcb4c963f2ddae06a2efc7e9f3591312473c50c6685e1f298068316e66fe" +[[package]] +name = "lazycell" +version = "1.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "830d08ce1d1d941e6b30645f1a0eb5643013d835ce3779a5fc208261dbe10f55" + [[package]] name = "libc" -version = "0.2.166" +version = "0.2.167" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c2ccc108bbc0b1331bd061864e7cd823c0cab660bbe6970e66e2c0614decde36" +checksum = "09d6582e104315a817dff97f75133544b2e094ee22447d2acf4a74e189ba06fc" [[package]] name = "libfuzzer-sys" @@ -1105,6 +1236,16 @@ dependencies = [ "cc", ] +[[package]] +name = "libloading" +version = "0.8.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fc2f4eb4bc735547cfed7c0a4922cbd04a4655978c09b54f1f7b228750664c34" +dependencies = [ + "cfg-if", + "windows-targets", +] + [[package]] name = "libz-rs-sys" version = "0.4.0" @@ -1114,6 +1255,12 @@ dependencies = [ "zlib-rs", ] +[[package]] +name = "linux-raw-sys" +version = "0.4.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "78b3ae25bc7c8c38cec158d1f2757ee79e9b3740fbc7ccf0e59e4b08d793fa89" + [[package]] name = "litrs" version = "0.4.1" @@ -1170,11 +1317,10 @@ dependencies = [ [[package]] name = "mio" -version = "1.0.2" +version = "1.0.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "80e04d1dcff3aae0704555fe5fee3bcfaf3d1fdf8a7e521d5b9d2b42acb52cec" +checksum = "2886843bf800fba2e3377cff24abf6379b4c4d5c6681eaf9ea5b0d15090450bd" dependencies = [ - "hermit-abi", "libc", "wasi", "windows-sys 0.52.0", @@ -1265,6 +1411,12 @@ dependencies = [ "subtle", ] +[[package]] +name = "paste" +version = "1.0.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "57c0d7b74b563b49d38dae00a0c37d4d6de9b432382b2892f0574ddcae73fd0a" + [[package]] name = "pb-rs" version = "0.10.0" @@ -1345,6 +1497,16 @@ dependencies = [ "zerocopy", ] +[[package]] +name = "prettyplease" +version = "0.2.25" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "64d1ec885c64d0457d564db4ec299b2dae3f9c02808b8ad9c3a089c591b18033" +dependencies = [ + "proc-macro2", + "syn 2.0.90", +] + [[package]] name = "primeorder" version = "0.13.6" @@ -1565,12 +1727,32 @@ version = "0.1.24" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "719b953e2095829ee67db738b3bfa9fa368c94900df327b3f07fe6e794d2fe1f" +[[package]] +name = "rustc-hash" +version = "1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "08d43f7aa6b08d49f382cde6a7982047c3426db949b1424bc4b7ec9ae12c6ce2" + +[[package]] +name = "rustix" +version = "0.38.41" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d7f649912bc1495e167a6edee79151c84b1bad49748cb4f1f1167f459f6224f6" +dependencies = [ + "bitflags 2.6.0", + "errno", + "libc", + "linux-raw-sys", + "windows-sys 0.52.0", +] + [[package]] name = "rustls" version = "0.23.19" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "934b404430bb06b3fae2cba809eb45a1ab1aecd64491213d7c3301b88393f8d1" dependencies = [ + "aws-lc-rs", "once_cell", "ring", "rustls-pki-types", @@ -1600,6 +1782,7 @@ version = "0.102.8" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "64ca1bc8749bd4cf37b5ce386cc146580777b4e8572c7b97baf22c83f444bee9" dependencies = [ + "aws-lc-rs", "ring", "rustls-pki-types", "untrusted", @@ -1647,7 +1830,7 @@ checksum = "ad1e866f866923f252f05c889987993144fb74e722403468a4ebd70c3cd756c0" dependencies = [ "proc-macro2", "quote", - "syn 2.0.89", + "syn 2.0.90", ] [[package]] @@ -1735,7 +1918,7 @@ version = "0.12.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "dad095989c1533c1c266d9b1e8d70a1329dd3723c3edac6d03bbd67e7bf6f4bb" dependencies = [ - "bitflags", + "bitflags 1.3.2", "byteorder", "cfg-if", "heapless 0.8.0", @@ -1793,9 +1976,9 @@ dependencies = [ [[package]] name = "syn" -version = "2.0.89" +version = "2.0.90" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "44d46482f1c1c87acd84dea20c1bf5ebff4c757009ed6bf19cfd36fb10e92c4e" +checksum = "919d3b74a5dd0ccd15aeb8f93e7006bd9e14c295087c9896a110f490752bcf31" dependencies = [ "proc-macro2", "quote", @@ -1840,7 +2023,7 @@ checksum = "4fee6c4efc90059e10f81e6d42c60a18f76588c3d74cb83a0b242a2b6c7504c1" dependencies = [ "proc-macro2", "quote", - "syn 2.0.89", + "syn 2.0.90", ] [[package]] @@ -1870,9 +2053,9 @@ checksum = "1f3ccbac311fea05f86f61904b462b55fb3df8837a366dfc601a0161d0532f20" [[package]] name = "tokio" -version = "1.41.1" +version = "1.42.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "22cfb5bee7a6a52939ca9224d6ac897bb669134078daa8735560897f69de4d33" +checksum = "5cec9b21b0450273377fc97bd4c33a8acffc8c996c987a7c5b319a0083707551" dependencies = [ "backtrace", "bytes", @@ -1892,17 +2075,16 @@ checksum = "693d596312e88961bc67d7f1f97af8a70227d9f90c31bba5806eec004978d752" dependencies = [ "proc-macro2", "quote", - "syn 2.0.89", + "syn 2.0.90", ] [[package]] name = "tokio-rustls" -version = "0.26.0" +version = "0.26.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0c7bc40d0e5a97695bb96e27995cd3a08538541b0a846f65bba7a359f36700d4" +checksum = "5f6d0975eaace0cf0fcadee4e4aaa5da15b5c079146f2cffb67c113be122bf37" dependencies = [ "rustls", - "rustls-pki-types", "tokio", ] @@ -1959,7 +2141,7 @@ checksum = "395ae124c09f9e6918a2310af6038fba074bcf474ac352496d5910dd59a2226d" dependencies = [ "proc-macro2", "quote", - "syn 2.0.89", + "syn 2.0.90", ] [[package]] @@ -1974,9 +2156,9 @@ dependencies = [ [[package]] name = "tracing-subscriber" -version = "0.3.18" +version = "0.3.19" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ad0f048c97dbd9faa9b7df56362b8ebcaa52adb06b498c050d2f4e32f90a7a8b" +checksum = "e8189decb5ac0fa7bc8b96b7cb9b2701d60d48805aca84a238004d665fcc4008" dependencies = [ "matchers", "once_cell", @@ -2083,9 +2265,9 @@ checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" [[package]] name = "wasm-bindgen" -version = "0.2.95" +version = "0.2.97" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "128d1e363af62632b8eb57219c8fd7877144af57558fb2ef0368d0087bddeb2e" +checksum = "d15e63b4482863c109d70a7b8706c1e364eb6ea449b201a76c5b89cedcec2d5c" dependencies = [ "cfg-if", "once_cell", @@ -2094,24 +2276,24 @@ dependencies = [ [[package]] name = "wasm-bindgen-backend" -version = "0.2.95" +version = "0.2.97" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cb6dd4d3ca0ddffd1dd1c9c04f94b868c37ff5fac97c30b97cff2d74fce3a358" +checksum = "8d36ef12e3aaca16ddd3f67922bc63e48e953f126de60bd33ccc0101ef9998cd" dependencies = [ "bumpalo", "log", "once_cell", "proc-macro2", "quote", - "syn 2.0.89", + "syn 2.0.90", "wasm-bindgen-shared", ] [[package]] name = "wasm-bindgen-macro" -version = "0.2.95" +version = "0.2.97" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e79384be7f8f5a9dd5d7167216f022090cf1f9ec128e6e6a482a2cb5c5422c56" +checksum = "705440e08b42d3e4b36de7d66c944be628d579796b8090bfa3471478a2260051" dependencies = [ "quote", "wasm-bindgen-macro-support", @@ -2119,22 +2301,22 @@ dependencies = [ [[package]] name = "wasm-bindgen-macro-support" -version = "0.2.95" +version = "0.2.97" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "26c6ab57572f7a24a4985830b120de1594465e5d500f24afe89e16b4e833ef68" +checksum = "98c9ae5a76e46f4deecd0f0255cc223cfa18dc9b261213b8aa0c7b36f61b3f1d" dependencies = [ "proc-macro2", "quote", - "syn 2.0.89", + "syn 2.0.90", "wasm-bindgen-backend", "wasm-bindgen-shared", ] [[package]] name = "wasm-bindgen-shared" -version = "0.2.95" +version = "0.2.97" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "65fc09f10666a9f147042251e0dda9c18f166ff7de300607007e96bdebc1068d" +checksum = "6ee99da9c5ba11bd675621338ef6fa52296b76b83305e9b6e5c77d4c286d6d49" [[package]] name = "webpki-roots" @@ -2145,6 +2327,18 @@ dependencies = [ "rustls-pki-types", ] +[[package]] +name = "which" +version = "4.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "87ba24419a2078cd2b0f2ede2691b6c66d8e47836da3b6db8265ebad47afbfc7" +dependencies = [ + "either", + "home", + "once_cell", + "rustix", +] + [[package]] name = "winapi-util" version = "0.1.9" @@ -2261,6 +2455,7 @@ dependencies = [ "aes-gcm 0.11.0-pre.2", "arbitrary", "argon2", + "aws-lc-rs", "base64", "borsh", "chrono", @@ -2268,6 +2463,7 @@ dependencies = [ "crypto-common 0.1.6", "digest", "embassy-net", + "embassy-time", "embedded-io-async", "embedded-tls", "fastrand", @@ -2285,6 +2481,7 @@ dependencies = [ "rand_core", "ring", "rust_decimal", + "rustls", "rustls-pemfile", "rustls-pki-types", "serde", @@ -2394,7 +2591,7 @@ checksum = "fa4f8080344d4671fb4e831a13ad1e68092748387dfc4f55e356242fae12ce3e" dependencies = [ "proc-macro2", "quote", - "syn 2.0.89", + "syn 2.0.90", ] [[package]] @@ -2414,7 +2611,7 @@ checksum = "ce36e65b0d2999d2aafac989fb249189a141aee1f53c612c1f37d72631959f69" dependencies = [ "proc-macro2", "quote", - "syn 2.0.89", + "syn 2.0.90", ] [[package]] diff --git a/README.md b/README.md index 8d5229a0..7c2c3711 100644 --- a/README.md +++ b/README.md @@ -4,9 +4,9 @@ [![crates.io](https://img.shields.io/crates/v/wtx.svg)](https://crates.io/crates/wtx) [![Documentation](https://docs.rs/wtx/badge.svg)](https://docs.rs/wtx) [![License](https://img.shields.io/badge/license-APACHE2-blue.svg)](https://github.com/c410-f3r/wtx/blob/main/LICENSE) -[![Rustc](https://img.shields.io/badge/rustc-1.82-lightgray")](https://blog.rust-lang.org/2024/10/17/Rust-1.82.0.html) +[![Rustc](https://img.shields.io/badge/rustc-1.83-lightgray")](https://blog.rust-lang.org/2024/11/28/Rust-1.83.0.html) -A collection of different transport implementations and related tools focused primarily on web technologies. Contains the implementations of 6 IETF RFCs ([6265](https://datatracker.ietf.org/doc/html/rfc6265), [6455](https://datatracker.ietf.org/doc/html/rfc6455), [7541](https://datatracker.ietf.org/doc/html/rfc7541), [7692](https://datatracker.ietf.org/doc/html/rfc7692), [8441](https://datatracker.ietf.org/doc/html/rfc8441), [9113](https://datatracker.ietf.org/doc/html/rfc9113)), 2 formal specifications ([gRPC](https://github.com/grpc/grpc/blob/master/doc/PROTOCOL-HTTP2.md), [PostgreSQL](https://www.postgresql.org/docs/current/protocol.html)) and several other invented ideas. +A collection of different transport implementations and related tools focused primarily on web technologies. Features the in-house development of 6 IETF RFCs ([6265](https://datatracker.ietf.org/doc/html/rfc6265), [6455](https://datatracker.ietf.org/doc/html/rfc6455), [7541](https://datatracker.ietf.org/doc/html/rfc7541), [7692](https://datatracker.ietf.org/doc/html/rfc7692), [8441](https://datatracker.ietf.org/doc/html/rfc8441), [9113](https://datatracker.ietf.org/doc/html/rfc9113)), 2 formal specifications ([gRPC](https://github.com/grpc/grpc/blob/master/doc/PROTOCOL-HTTP2.md), [PostgreSQL](https://www.postgresql.org/docs/current/protocol.html)) and several other invented ideas. 1. [Client API Framework](https://c410-f3r.github.io/wtx/client-api-framework/index.html) 2. [Database Client](https://c410-f3r.github.io/wtx/database-client/index.html) diff --git a/rust-toolchain b/rust-toolchain index 2f003195..e4bcfc46 100644 --- a/rust-toolchain +++ b/rust-toolchain @@ -1,4 +1,4 @@ [toolchain] -channel = "nightly-2024-09-01" +channel = "nightly-2024-10-13" components = ["clippy", "miri", "rustfmt", "rust-src"] profile = "minimal" diff --git a/wtx-docs/src/database-schema-manager/README.md b/wtx-docs/src/database-schema-manager/README.md index eca457f4..f59ac99d 100644 --- a/wtx-docs/src/database-schema-manager/README.md +++ b/wtx-docs/src/database-schema-manager/README.md @@ -123,7 +123,7 @@ extern crate wtx; // This is an example! The actual contents are filled by the `wtx-ui embed-migrations` binary call. mod embedded_migrations { - pub(crate) const GROUPS: wtx::database::schema_manager::EmbeddedMigrationsTy = &[]; + pub(crate) static GROUPS: wtx::database::schema_manager::EmbeddedMigrationsTy = &[]; } use wtx::database::schema_manager::Commands; diff --git a/wtx-instances/web-socket-examples/web-socket-concurrent-client.rs b/wtx-instances/web-socket-examples/web-socket-concurrent-client.rs index d23940ad..50e715ef 100644 --- a/wtx-instances/web-socket-examples/web-socket-concurrent-client.rs +++ b/wtx-instances/web-socket-examples/web-socket-concurrent-client.rs @@ -1,4 +1,4 @@ -//! WebSocket client that reads and writes frames in different tasks. +//! Encrypted WebSocket client that reads and writes frames in different tasks. extern crate tokio; extern crate wtx; diff --git a/wtx-macros/src/client_api_framework/api_params.rs b/wtx-macros/src/client_api_framework/api_params.rs index 4703c0ed..e8829503 100644 --- a/wtx-macros/src/client_api_framework/api_params.rs +++ b/wtx-macros/src/client_api_framework/api_params.rs @@ -5,9 +5,9 @@ use crate::{ misc::create_ident, }; use proc_macro2::{Ident, Span}; -use quote::ToTokens; +use quote::ToTokens as _; use syn::{ - parse_macro_input, punctuated::Punctuated, spanned::Spanned, AttributeArgs, Item, Path, + parse_macro_input, punctuated::Punctuated, spanned::Spanned as _, AttributeArgs, Item, Path, PathArguments, PathSegment, }; diff --git a/wtx-macros/src/client_api_framework/pkg.rs b/wtx-macros/src/client_api_framework/pkg.rs index 1397563e..1c356c4d 100644 --- a/wtx-macros/src/client_api_framework/pkg.rs +++ b/wtx-macros/src/client_api_framework/pkg.rs @@ -13,7 +13,7 @@ use fir::{ fir_req_item_values::FirReqItemValues, fir_res_item_values::FirResItemValues, }; use proc_macro2::{Ident, Span, TokenStream}; -use quote::ToTokens; +use quote::ToTokens as _; use sir::{sir_final_values::SirFinalValues, sir_pkg_attr::SirPkaAttr}; use syn::{ parse_macro_input, diff --git a/wtx-macros/src/client_api_framework/pkg/fir/fir_aux_field_attr.rs b/wtx-macros/src/client_api_framework/pkg/fir/fir_aux_field_attr.rs index 567f2c1b..22f467f5 100644 --- a/wtx-macros/src/client_api_framework/pkg/fir/fir_aux_field_attr.rs +++ b/wtx-macros/src/client_api_framework/pkg/fir/fir_aux_field_attr.rs @@ -1,7 +1,7 @@ use crate::client_api_framework::pkg::keywords; use syn::{ parse::{Parse, ParseStream}, - spanned::Spanned, + spanned::Spanned as _, }; #[derive(Debug)] diff --git a/wtx-macros/src/client_api_framework/pkg/fir/fir_custom_field_attr.rs b/wtx-macros/src/client_api_framework/pkg/fir/fir_custom_field_attr.rs index 9bff4d81..4639ee88 100644 --- a/wtx-macros/src/client_api_framework/pkg/fir/fir_custom_field_attr.rs +++ b/wtx-macros/src/client_api_framework/pkg/fir/fir_custom_field_attr.rs @@ -3,7 +3,7 @@ use crate::client_api_framework::pkg::{ }; use syn::{ parse::{Parse, ParseStream}, - spanned::Spanned, + spanned::Spanned as _, }; #[derive(Debug)] diff --git a/wtx-macros/src/client_api_framework/pkg/fir/fir_items_values.rs b/wtx-macros/src/client_api_framework/pkg/fir/fir_items_values.rs index b62f5c3d..c48eccc2 100644 --- a/wtx-macros/src/client_api_framework/pkg/fir/fir_items_values.rs +++ b/wtx-macros/src/client_api_framework/pkg/fir/fir_items_values.rs @@ -1,5 +1,5 @@ use crate::client_api_framework::{ - contained_attrs::ContainedAttrs, + contained_attrs::ContainedAttrs as _, item_with_attr_span::ItemWithAttrSpan, pkg::{ fir::fir_item_attr::{FirItemAttr, FirItemAttrTy}, diff --git a/wtx-macros/src/client_api_framework/pkg/misc.rs b/wtx-macros/src/client_api_framework/pkg/misc.rs index f51de553..f3a6a458 100644 --- a/wtx-macros/src/client_api_framework/pkg/misc.rs +++ b/wtx-macros/src/client_api_framework/pkg/misc.rs @@ -1,7 +1,7 @@ use proc_macro2::Span; -use quote::ToTokens; +use quote::ToTokens as _; use syn::{ - parse::Parse, punctuated::Punctuated, spanned::Spanned, token::Paren, + parse::Parse, punctuated::Punctuated, spanned::Spanned as _, token::Paren, AngleBracketedGenericArguments, Attribute, GenericArgument, GenericParam, Generics, PathArguments, PathSegment, Token, Type, TypePath, TypeTuple, WherePredicate, }; diff --git a/wtx-macros/src/client_api_framework/transport_group.rs b/wtx-macros/src/client_api_framework/transport_group.rs index 75a06512..2af9ad50 100644 --- a/wtx-macros/src/client_api_framework/transport_group.rs +++ b/wtx-macros/src/client_api_framework/transport_group.rs @@ -1,6 +1,6 @@ use crate::misc::single_elem; use proc_macro2::{Span, TokenStream}; -use quote::ToTokens; +use quote::ToTokens as _; use syn::{punctuated::Punctuated, Meta, NestedMeta, Path, PathSegment, Token}; #[derive(Debug)] diff --git a/wtx-ui/src/embed_migrations.rs b/wtx-ui/src/embed_migrations.rs index bd75939d..a5957ec3 100644 --- a/wtx-ui/src/embed_migrations.rs +++ b/wtx-ui/src/embed_migrations.rs @@ -10,7 +10,7 @@ pub(crate) async fn embed_migrations(elem: EmbedMigrations) -> wtx::Result<()> { migration_groups.sort(); buffer.push_str( - "#[rustfmt::skip]pub(crate) const GROUPS: wtx::database::schema_manager::EmbeddedMigrationsTy = &[", + "#[rustfmt::skip]pub(crate) static GROUPS: wtx::database::schema_manager::EmbeddedMigrationsTy = &[", ); for mg_path in migration_groups { diff --git a/wtx/Cargo.toml b/wtx/Cargo.toml index 045ac8cb..42365bc5 100644 --- a/wtx/Cargo.toml +++ b/wtx/Cargo.toml @@ -2,6 +2,7 @@ aes-gcm = { default-features = false, optional = true, version = "0.11.0-pre.2" } arbitrary = { default-features = false, features = ["derive_arbitrary"], optional = true, version = "1.0" } argon2 = { default-features = false, optional = true, version = "0.5" } +aws-lc-rs = { default-features = false, optional = true, version = "1.0" } base64 = { default-features = false, features = ["alloc"], optional = true, version = "0.22" } borsh = { default-features = false, features = ["derive"], optional = true, version = "1.0" } chrono = { default-features = false, optional = true, version = "0.4" } @@ -9,6 +10,7 @@ cl-aux = { default-features = false, optional = true, features = ["alloc"], vers crypto-common = { default-features = false, optional = true, version = "0.1" } digest = { default-features = false, features = ["mac"], optional = true, version = "0.10" } embassy-net = { default-features = false, features = ["tcp"], optional = true, version = "0.5" } +embassy-time = { default-features = false, optional = true, version = "0.3" } embedded-io-async = { default-features = false, optional = true, version = "0.6" } embedded-tls = { default-features = false, optional = true, version = "0.17" } fastrand = { default-features = false, optional = true, version = "2.0" } @@ -26,6 +28,7 @@ rand_chacha = { default-features = false, optional = true, version = "0.3" } rand_core = { default-features = false, optional = true, version = "0.6" } ring = { default-features = false, optional = true, version = "0.17" } rust_decimal = { default-features = false, features = ["maths"], optional = true, version = "1.0" } +rustls = { default-features = false, optional = true, version = "0.23" } rustls-pemfile = { default-features = false, optional = true, version = "2.0" } rustls-pki-types = { default-features = false, optional = true, version = "1.0" } serde = { default-features = false, features = ["alloc", "derive"], optional = true, version = "1.0" } @@ -43,26 +46,18 @@ x509-certificate = { default-features = false, optional = true, version = "0.24" [features] arbitrary = ["dep:arbitrary", "std"] -base64 = ["dep:base64"] +aws-lc-rs = ["dep:aws-lc-rs", "rustls?/aws-lc-rs"] borsh = ["dep:borsh", "std"] -chrono = ["dep:chrono"] -cl-aux = ["dep:cl-aux"] client-api-framework = ["data-transformation"] -crypto-common = ["dep:crypto-common"] data-transformation = [] database = [] default = [] -digest = ["dep:digest"] embedded-tls = ["embedded-io-async", "dep:embedded-tls"] executor = [] -fastrand = ["dep:fastrand"] -flate2 = ["dep:flate2"] foldhash = ["dep:foldhash", "hashbrown?/default-hasher"] grpc = ["data-transformation"] grpc-client = ["grpc", "http-client-framework"] grpc-server = ["grpc", "http-server-framework"] -hashbrown = ["dep:hashbrown"] -hmac = ["dep:hmac"] http = [] http-client-framework = ["http2", "pool", "std"] http-cookie = ["chrono/alloc", "http"] @@ -70,8 +65,6 @@ http-cookie-secure = ["aes-gcm/aes", "aes-gcm/alloc", "base64", "digest", "http- http-server-framework = ["http2"] http-session = ["chrono/serde", "http-cookie-secure", "serde_json"] http2 = ["foldhash", "hashbrown", "http"] -httparse = ["dep:httparse"] -memchr = ["dep:memchr"] nightly = [] #FIXME(STABLE): "hashbrown?/nightly" optimization = ["memchr", "simdutf8"] pool = [] @@ -79,15 +72,11 @@ portable-atomic-util = ["portable-atomic", "dep:portable-atomic-util"] postgres = ["base64", "crypto-common", "database", "digest", "foldhash", "hashbrown", "hmac", "sha2"] quick-protobuf = ["dep:quick-protobuf", "std"] rand_chacha = ["dep:rand_chacha", "dep:rand_core"] -ring = ["dep:ring"] -rust_decimal = ["dep:rust_decimal"] +rustls = ["dep:rustls", "rustls-pki-types"] schema-manager = ["database", "chrono"] schema-manager-dev = ["schema-manager"] serde = ["cl-aux?/serde", "dep:serde"] serde_json = ["serde", "dep:serde_json", "std"] -sha1 = ["dep:sha1"] -sha2 = ["dep:sha2"] -simdutf8 = ["dep:simdutf8"] std = [ "aes-gcm?/std", "argon2?/std", @@ -97,6 +86,7 @@ std = [ "cl-aux?/std", "crypto-common?/std", "digest?/std", + "embassy-time?/std", "embedded-io-async?/std", "embedded-tls?/std", "fastrand?/std", @@ -121,18 +111,15 @@ std = [ "tracing?/std", "tracing-subscriber?/std" ] +tls = [] tokio = ["std", "dep:tokio"] -tokio-rustls = ["ring", "dep:rustls-pemfile", "dep:rustls-pki-types", "tokio", "dep:tokio-rustls"] -tracing = ["dep:tracing"] -tracing-subscriber = ["dep:tracing-subscriber"] +tokio-rustls = ["ring", "rustls", "dep:rustls-pemfile", "rustls-pki-types", "tokio", "dep:tokio-rustls"] web-socket = ["http"] web-socket-handshake = ["base64", "httparse", "sha1", "web-socket"] -webpki-roots = ["dep:webpki-roots"] -x509-certificate = ["dep:x509-certificate"] _async-tests = ["tokio/macros", "tokio/net", "tokio/rt-multi-thread", "tokio/time"] _bench = [] -_hack = ["embassy-net?/medium-ip", "embassy-net?/proto-ipv4"] +_hack = ["aws-lc-rs?/aws-lc-sys", "embassy-net?/medium-ip", "embassy-net?/proto-ipv4"] # Crate must not decide for downstream users _integration-tests = ["serde_json?/raw_value"] _tracing-tree = ["tracing", "tracing-subscriber", "dep:tracing-tree"] @@ -152,7 +139,7 @@ license = "Apache-2.0" name = "wtx" readme = "README.md" repository = "https://github.com/c410-f3r/wtx" -rust-version = "1.82" +rust-version = "1.83" version = "0.25.0" [package.metadata.docs.rs] diff --git a/wtx/src/client_api_framework/misc.rs b/wtx/src/client_api_framework/misc.rs index af0ddb8d..7c23d6cc 100644 --- a/wtx/src/client_api_framework/misc.rs +++ b/wtx/src/client_api_framework/misc.rs @@ -22,7 +22,6 @@ pub use request_throttling::RequestThrottling; /// Used in all implementations of [`crate::Transport::send`] and/or /// [`crate::Transport::send_recv``]. -#[expect(clippy::needless_pass_by_value, reason = "borrow checker woes")] pub(crate) fn log_req( _pgk: &mut P, _pkgs_aux: &mut PkgsAux, diff --git a/wtx/src/data_transformation/format/misc.rs b/wtx/src/data_transformation/format/misc.rs index 06280a90..ae7bfdb4 100644 --- a/wtx/src/data_transformation/format/misc.rs +++ b/wtx/src/data_transformation/format/misc.rs @@ -19,7 +19,7 @@ mod serde_json { { struct Buffer<'any, T>(&'any mut Vector); - impl<'any, 'de, T> Visitor<'de> for Buffer<'any, T> + impl<'de, T> Visitor<'de> for Buffer<'_, T> where T: Deserialize<'de>, { diff --git a/wtx/src/database.rs b/wtx/src/database.rs index ef449647..d59aa884 100644 --- a/wtx/src/database.rs +++ b/wtx/src/database.rs @@ -77,7 +77,8 @@ impl Database for () { const TY: DatabaseTy = DatabaseTy::Unit; type DecodeValue<'exec> = (); - type EncodeValue<'buffer, 'tmp> = crate::misc::FilledBufferWriter<'buffer> + type EncodeValue<'buffer, 'tmp> + = crate::misc::FilledBufferWriter<'buffer> where 'buffer: 'tmp; type Error = crate::Error; diff --git a/wtx/src/database/client/postgres/decode_value.rs b/wtx/src/database/client/postgres/decode_value.rs index fb978e37..e9a4cd52 100644 --- a/wtx/src/database/client/postgres/decode_value.rs +++ b/wtx/src/database/client/postgres/decode_value.rs @@ -25,7 +25,7 @@ impl<'any> DecodeValue<'any> { } } -impl<'any> Default for DecodeValue<'any> { +impl Default for DecodeValue<'_> { #[inline] fn default() -> Self { Self { bytes: &[], ty: Ty::Any } diff --git a/wtx/src/database/client/postgres/encode_value.rs b/wtx/src/database/client/postgres/encode_value.rs index 3c70b414..5dd59202 100644 --- a/wtx/src/database/client/postgres/encode_value.rs +++ b/wtx/src/database/client/postgres/encode_value.rs @@ -19,14 +19,14 @@ impl<'buffer, 'tmp> EncodeValue<'buffer, 'tmp> { } } -impl<'buffer, 'tmp> Lease> for EncodeValue<'buffer, 'tmp> { +impl<'buffer> Lease> for EncodeValue<'buffer, '_> { #[inline] fn lease(&self) -> &FilledBufferWriter<'buffer> { self.fbw } } -impl<'buffer, 'tmp> LeaseMut> for EncodeValue<'buffer, 'tmp> { +impl<'buffer> LeaseMut> for EncodeValue<'buffer, '_> { #[inline] fn lease_mut(&mut self) -> &mut FilledBufferWriter<'buffer> { self.fbw diff --git a/wtx/src/database/client/postgres/record.rs b/wtx/src/database/client/postgres/record.rs index 4e89f61f..a1a62293 100644 --- a/wtx/src/database/client/postgres/record.rs +++ b/wtx/src/database/client/postgres/record.rs @@ -136,7 +136,7 @@ impl<'exec, E> ValueIdent> for str { } } -impl<'exec, E> PartialEq for Record<'exec, E> { +impl PartialEq for Record<'_, E> { #[inline] fn eq(&self, other: &Self) -> bool { self.bytes == other.bytes diff --git a/wtx/src/database/client/postgres/records.rs b/wtx/src/database/client/postgres/records.rs index 65c92f15..9e54250e 100644 --- a/wtx/src/database/client/postgres/records.rs +++ b/wtx/src/database/client/postgres/records.rs @@ -71,7 +71,7 @@ where } } -impl<'exec, E> Default for Records<'exec, E> { +impl Default for Records<'_, E> { #[inline] fn default() -> Self { Self { diff --git a/wtx/src/database/client/postgres/struct_encoder.rs b/wtx/src/database/client/postgres/struct_encoder.rs index d26b5a02..673325f0 100644 --- a/wtx/src/database/client/postgres/struct_encoder.rs +++ b/wtx/src/database/client/postgres/struct_encoder.rs @@ -56,7 +56,7 @@ where } } -impl<'buffer, 'fbw, 'vec, E> Drop for StructEncoder<'buffer, 'fbw, 'vec, E> { +impl Drop for StructEncoder<'_, '_, '_, E> { #[inline] fn drop(&mut self) { write_len(self.ev, self.start, self.len); diff --git a/wtx/src/database/decode.rs b/wtx/src/database/decode.rs index e24beb08..9b28c0ee 100644 --- a/wtx/src/database/decode.rs +++ b/wtx/src/database/decode.rs @@ -9,21 +9,21 @@ where fn decode(dv: &D::DecodeValue<'de>) -> Result; } -impl<'de> Decode<'de, ()> for &str { +impl Decode<'_, ()> for &str { #[inline] fn decode(_: &()) -> Result { Ok("") } } -impl<'de> Decode<'de, ()> for u32 { +impl Decode<'_, ()> for u32 { #[inline] fn decode(_: &()) -> Result { Ok(0) } } -impl<'de> Decode<'de, ()> for u64 { +impl Decode<'_, ()> for u64 { #[inline] fn decode(_: &()) -> Result { Ok(0) diff --git a/wtx/src/database/record.rs b/wtx/src/database/record.rs index 0857ab7b..2b593d0b 100644 --- a/wtx/src/database/record.rs +++ b/wtx/src/database/record.rs @@ -37,7 +37,7 @@ pub trait Record<'exec>: Sized { CI: ValueIdent; } -impl<'exec> Record<'exec> for () { +impl Record<'_> for () { type Database = (); #[inline] diff --git a/wtx/src/database/schema_manager/fixed_sql_commands/postgres.rs b/wtx/src/database/schema_manager/fixed_sql_commands/postgres.rs index 8da638e9..6f143ad3 100644 --- a/wtx/src/database/schema_manager/fixed_sql_commands/postgres.rs +++ b/wtx/src/database/schema_manager/fixed_sql_commands/postgres.rs @@ -5,7 +5,7 @@ use crate::{ use alloc::string::String; use core::fmt::Write; -pub(crate) const _CREATE_MIGRATION_TABLES: &str = concat!( +pub(crate) static _CREATE_MIGRATION_TABLES: &str = concat!( "CREATE SCHEMA IF NOT EXISTS _wtx; \ CREATE TABLE IF NOT EXISTS _wtx._wtx_migration_group (", _wtx_migration_group_columns!(), diff --git a/wtx/src/error.rs b/wtx/src/error.rs index 496c28af..e2597c82 100644 --- a/wtx/src/error.rs +++ b/wtx/src/error.rs @@ -40,6 +40,8 @@ pub enum Error { EmbassyNet(embassy_net::tcp::Error), #[cfg(feature = "base64")] EncodeSliceError(base64::EncodeSliceError), + #[cfg(feature = "embedded-tls")] + EmbassyTlsError(embedded_tls::TlsError), #[cfg(feature = "flate2")] Flate2CompressError(flate2::CompressError), #[cfg(feature = "flate2")] @@ -52,20 +54,20 @@ pub enum Error { MatchitInsertError(Box), #[cfg(feature = "digest")] MacError(digest::MacError), + #[cfg(feature = "rustls-pki-types")] + PemError(Box), #[cfg(feature = "postgres")] PostgresDbError(Box), #[cfg(feature = "quick-protobuf")] QuickProtobuf(Box), + #[cfg(feature = "rustls")] + RustlsError(Box), #[cfg(feature = "serde_json")] SerdeJson(serde_json::Error), #[cfg(feature = "http-session")] SessionError(crate::http::SessionError), - #[cfg(feature = "embedded-tls")] - TlsError(embedded_tls::TlsError), #[cfg(feature = "tokio")] TokioJoinError(Box), - #[cfg(feature = "tokio-rustls")] - TokioRustlsError(Box), #[cfg(feature = "tracing-subscriber")] TryInitError(tracing_subscriber::util::TryInitError), #[cfg(feature = "std")] @@ -156,6 +158,8 @@ pub enum Error { SchemaManagerError(crate::database::schema_manager::SchemaManagerError), #[cfg(feature = "http-server-framework")] ServerFrameworkError(crate::http::server_framework::ServerFrameworkError), + #[cfg(feature = "tls")] + TlsError(crate::tls::TlsError), VectorError(VectorError), #[cfg(feature = "web-socket")] WebSocketError(crate::web_socket::WebSocketError), @@ -262,6 +266,14 @@ impl From for Error { } } +#[cfg(feature = "embedded-tls")] +impl From for Error { + #[inline] + fn from(from: embedded_tls::TlsError) -> Self { + Self::EmbassyTlsError(from) + } +} + #[cfg(feature = "flate2")] impl From for Error { #[inline] @@ -350,6 +362,13 @@ impl From for Error { } } +#[cfg(feature = "rustls-pki-types")] +impl From for Error { + #[inline] + fn from(from: rustls_pki_types::pem::Error) -> Self { + Self::PemError(from.into()) + } +} #[cfg(feature = "postgres")] impl From for Error { #[inline] @@ -366,6 +385,14 @@ impl From for Error { } } +#[cfg(feature = "rustls")] +impl From for Error { + #[inline] + fn from(from: rustls::Error) -> Self { + Self::RustlsError(from.into()) + } +} + #[cfg(feature = "serde_json")] impl From for Error { #[inline] @@ -382,14 +409,6 @@ impl From for Error { } } -#[cfg(feature = "embedded-tls")] -impl From for Error { - #[inline] - fn from(from: embedded_tls::TlsError) -> Self { - Self::TlsError(from) - } -} - #[cfg(feature = "tokio")] impl From for Error { #[inline] @@ -398,14 +417,6 @@ impl From for Error { } } -#[cfg(feature = "tokio-rustls")] -impl From for Error { - #[inline] - fn from(from: tokio_rustls::rustls::Error) -> Self { - Self::TokioRustlsError(from.into()) - } -} - #[cfg(feature = "tracing-subscriber")] impl From for Error { #[inline] @@ -542,6 +553,14 @@ impl From for Error { } } +#[cfg(feature = "tls")] +impl From for Error { + #[inline] + fn from(from: crate::tls::TlsError) -> Self { + Self::TlsError(from) + } +} + impl From for Error { #[inline] fn from(from: VectorError) -> Self { diff --git a/wtx/src/http/headers.rs b/wtx/src/http/headers.rs index d95b266d..15b706fe 100644 --- a/wtx/src/http/headers.rs +++ b/wtx/src/http/headers.rs @@ -162,12 +162,12 @@ impl Headers { let header_begin = self.bytes.len(); #[cfg(feature = "std")] { - use std::io::Write; + use std::io::Write as _; self.bytes.write_fmt(format_args!("{}{}", header.name, header.value))?; } #[cfg(not(feature = "std"))] { - use core::fmt::Write; + use core::fmt::Write as _; self.bytes.write_fmt(format_args!("{}{}", header.name, header.value))?; } let prev_len = self.headers_parts.len(); diff --git a/wtx/src/http/server_framework/cors_middleware.rs b/wtx/src/http/server_framework/cors_middleware.rs index 7645593e..cb46ee1e 100644 --- a/wtx/src/http/server_framework/cors_middleware.rs +++ b/wtx/src/http/server_framework/cors_middleware.rs @@ -68,7 +68,7 @@ impl CorsMiddleware { Self { allow_credentials: true, allow_headers: (true, ArrayVector::new()), - allow_methods: (false, ArrayVector::from_array(Method::ALL.into())), + allow_methods: (false, ArrayVector::from_array(Method::ALL)), allow_origins: (true, ArrayVector::new()), expose_headers: (true, ArrayVector::new()), max_age: None, @@ -176,7 +176,7 @@ impl CorsMiddleware { } #[inline] - fn allowed_origin<'this>(&'this self, origin: &[u8]) -> Option<&'static str> { + fn allowed_origin(&self, origin: &[u8]) -> Option<&'static str> { self.allow_origins.1.iter().find(|el| el.as_bytes() == origin).copied() } @@ -317,13 +317,13 @@ impl CorsMiddleware { fn extract_origin<'any>( opt: Option>, ) -> crate::Result> { - Ok(opt.ok_or_else(|| HttpError::MissingHeader(KnownHeaderName::Origin))?) + Ok(opt.ok_or(HttpError::MissingHeader(KnownHeaderName::Origin))?) } #[inline] - fn manage_preflight_headers<'bytes>( + fn manage_preflight_headers( &self, - acrh: Header<'_, &'bytes [u8]>, + acrh: Header<'_, &[u8]>, body: &mut Vector, ) -> crate::Result<()> { if self.allow_headers.0 { @@ -341,7 +341,7 @@ impl CorsMiddleware { } } if matched_headers != uniques.len() { - return Err(crate::Error::from(ServerFrameworkError::ForbiddenCorsHeader).into()); + return Err(crate::Error::from(ServerFrameworkError::ForbiddenCorsHeader)); } let mut iter = uniques.iter(); if let Some(elem) = iter.next() { @@ -366,7 +366,7 @@ impl CorsMiddleware { || a.as_bytes() == acrm.value || b.as_bytes() == acrm.value }) { - return Err(crate::Error::from(ServerFrameworkError::ForbiddenCorsMethod).into()); + return Err(crate::Error::from(ServerFrameworkError::ForbiddenCorsMethod)); } Ok(()) } @@ -382,7 +382,7 @@ impl CorsMiddleware { } else if let Some(allowed_origin) = self.allowed_origin(origin.value) { allowed_origin.as_bytes() } else { - return Err(crate::Error::from(ServerFrameworkError::ForbiddenCorsOrigin).into()); + return Err(crate::Error::from(ServerFrameworkError::ForbiddenCorsOrigin)); }; body.extend_from_copyable_slice(actual_origin).map_err(crate::Error::from)?; Ok(()) diff --git a/wtx/src/http2/common_stream.rs b/wtx/src/http2/common_stream.rs index 8ea3c6ca..de0fd9bd 100644 --- a/wtx/src/http2/common_stream.rs +++ b/wtx/src/http2/common_stream.rs @@ -73,8 +73,8 @@ where let mut lock = lock_pin!(cx, self.hd, pin); let hdpm = lock.parts_mut(); let sorp = sorp_mut(&mut hdpm.hb.sorp, self.stream_id)?; - if let Some(elem) = status_recv(&self.is_conn_open, sorp, |local_sorp| { - check_content_length(&local_sorp)?; + if let Some(elem) = status_recv(self.is_conn_open, sorp, |local_sorp| { + check_content_length(local_sorp)?; Ok(mem::take(&mut local_sorp.rrb.body)) })? { return Poll::Ready(Ok(elem)); @@ -105,7 +105,7 @@ where let mut lock = lock_pin!(cx, self.hd, pin); let hdpm = lock.parts_mut(); let sorp = sorp_mut(&mut hdpm.hb.sorp, self.stream_id)?; - if let Some(elem) = status_recv(&self.is_conn_open, sorp, |local_sorp| { + if let Some(elem) = status_recv(self.is_conn_open, sorp, |local_sorp| { Ok(mem::take(&mut local_sorp.rrb.headers)) })? { return Poll::Ready(Ok(elem)); @@ -129,7 +129,7 @@ where let mut wp = WindowsPair::new(hdpm.windows, &mut elem.windows); wp.withdrawn_recv( hdpm.hp, - &self.is_conn_open, + self.is_conn_open, hdpm.stream_writer, self.stream_id, U31::from_u32(value), @@ -173,7 +173,7 @@ where let mut lock = lock_pin!(cx, self.hd, pin); let hdpm = lock.parts_mut(); let sorp = sorp_mut(&mut hdpm.hb.sorp, self.stream_id)?; - if let Some(elem) = status_send::(&self.is_conn_open, sorp) { + if let Some(elem) = status_send::(self.is_conn_open, sorp) { return Poll::Ready(Ok(elem)); } let mut wp = WindowsPair::new(hdpm.windows, &mut sorp.windows); @@ -187,7 +187,7 @@ where is_eos, &mut has_data, false, - &self.is_conn_open, + self.is_conn_open, hdpm.hps.max_frame_len, hdpm.stream_writer, self.stream_id, @@ -224,7 +224,7 @@ where let mut guard = self.hd.lock().await; let hdpm = guard.parts_mut(); let sorp = sorp_mut(&mut hdpm.hb.sorp, self.stream_id)?; - if let Some(elem) = status_send::(&self.is_conn_open, sorp) { + if let Some(elem) = status_send::(self.is_conn_open, sorp) { return Ok(elem); } let hsreh = HpackStaticResponseHeaders { status_code: Some(status_code) }; @@ -236,7 +236,7 @@ where let _ = write_standalone_headers::<_, IS_CLIENT>( &mut hdpm.hb.hpack_enc_buffer, (HpackStaticRequestHeaders::EMPTY, hsreh), - &self.is_conn_open, + self.is_conn_open, is_eos, hdpm.hps.max_frame_len, hdpm.stream_writer, @@ -274,13 +274,13 @@ where let mut lock = self.hd.lock().await; let hdpm = lock.parts_mut(); let sorp = sorp_mut(&mut hdpm.hb.sorp, self.stream_id)?; - if let Some(elem) = status_send::(&self.is_conn_open, sorp) { + if let Some(elem) = status_send::(self.is_conn_open, sorp) { return Ok(elem); } write_standalone_trailers( trailers, (&mut hdpm.hb.hpack_enc, &mut hdpm.hb.hpack_enc_buffer), - &self.is_conn_open, + self.is_conn_open, hdpm.hps.max_frame_len, hdpm.stream_writer, self.stream_id, diff --git a/wtx/src/http2/index_map.rs b/wtx/src/http2/index_map.rs index 926c30e8..7b2cb30c 100644 --- a/wtx/src/http2/index_map.rs +++ b/wtx/src/http2/index_map.rs @@ -52,7 +52,7 @@ where #[inline] pub(crate) fn push_back(&mut self, key: K, value: V) -> Option { - let prev_value = self.elements.insert(key.clone(), value); + let prev_value = self.elements.insert(key, value); if prev_value.is_none() { self.keys.push_back(key).ok()?; } diff --git a/wtx/src/http2/process_receipt_frame_ty.rs b/wtx/src/http2/process_receipt_frame_ty.rs index 46e6f2f1..043ad904 100644 --- a/wtx/src/http2/process_receipt_frame_ty.rs +++ b/wtx/src/http2/process_receipt_frame_ty.rs @@ -159,12 +159,7 @@ where &mut ish.rrb, self.stream_reader, self.uri_buffer, - |hf| { - Ok(( - hf.hsreqh().method.ok_or_else(|| HttpError::MissingRequestMethod)?, - hf.hsreqh().protocol, - )) - }, + |hf| Ok((hf.hsreqh().method.ok_or(HttpError::MissingRequestMethod)?, hf.hsreqh().protocol)), ) .await?; let (content_length, has_eos, (method, protocol)) = tuple; diff --git a/wtx/src/http2/send_data_mode.rs b/wtx/src/http2/send_data_mode.rs index 8e576dbf..ebd8c174 100644 --- a/wtx/src/http2/send_data_mode.rs +++ b/wtx/src/http2/send_data_mode.rs @@ -80,7 +80,7 @@ impl<'bytes, const IS_SCATTERED: bool> SendDataModeBytes<'bytes, IS_SCATTERED> 'first: 'rslt, 'this: 'rslt, { - [first, &self[0], &[]] + [first, self[0], &[]] } #[inline] @@ -105,7 +105,7 @@ impl<'bytes> SendDataModeBytes<'bytes, false> for [&'bytes [u8]; 2] { 'first: 'rslt, 'this: 'rslt, { - [first, &self[0], &self[1]] + [first, self[0], self[1]] } #[inline] diff --git a/wtx/src/lib.rs b/wtx/src/lib.rs index 895f0f7a..64c65a77 100644 --- a/wtx/src/lib.rs +++ b/wtx/src/lib.rs @@ -35,6 +35,8 @@ pub mod misc; pub mod pool; #[cfg(test)] mod tests; +#[cfg(feature = "tls")] +pub mod tls; #[cfg(feature = "web-socket")] pub mod web_socket; diff --git a/wtx/src/misc.rs b/wtx/src/misc.rs index 74d2829b..d7a74f70 100644 --- a/wtx/src/misc.rs +++ b/wtx/src/misc.rs @@ -49,7 +49,7 @@ pub use blocks_deque::{Block, BlocksDeque, BlocksDequeBuilder, BlocksDequeError} pub use buffer_mode::BufferMode; pub use bytes_fmt::BytesFmt; pub use connection_state::ConnectionState; -use core::{any::type_name, fmt::Write, ops::Range, time::Duration}; +use core::{any::type_name, fmt::Write as _, ops::Range, time::Duration}; pub use deque::{Deque, DequeueError}; pub use either::Either; pub use enum_var_strings::EnumVarStrings; @@ -57,7 +57,7 @@ pub use facades::arc::Arc; pub use filled_buffer_writer::FilledBufferWriter; pub use fn_fut::*; pub use from_radix_10::{FromRadix10, FromRadix10Error}; -pub use generic_time::GenericTime; +pub use generic_time::{GenericTime, GenericTimeProvider}; pub use incomplete_utf8_char::{CompletionErr, IncompleteUtf8Char}; pub use interspace::Intersperse; pub use iter_wrapper::IterWrapper; diff --git a/wtx/src/misc/array_string.rs b/wtx/src/misc/array_string.rs index 57f2a8d4..8885b324 100644 --- a/wtx/src/misc/array_string.rs +++ b/wtx/src/misc/array_string.rs @@ -327,7 +327,7 @@ mod serde { { struct ArrayStringVisitor(PhantomData<[u8; N]>); - impl<'de, const N: usize> Visitor<'de> for ArrayStringVisitor { + impl Visitor<'_> for ArrayStringVisitor { type Value = ArrayString; #[inline] diff --git a/wtx/src/misc/array_vector.rs b/wtx/src/misc/array_vector.rs index 6dff541a..27a2b82c 100644 --- a/wtx/src/misc/array_vector.rs +++ b/wtx/src/misc/array_vector.rs @@ -150,7 +150,7 @@ impl ArrayVector { /// Shortens the vector, removing the last element. #[inline] - pub fn pop(&mut self) -> Option { + pub const fn pop(&mut self) -> Option { if let Some(new_len) = self.len.checked_sub(1) { self.len = new_len; // SAFETY: `new_len` is within bounds @@ -194,12 +194,12 @@ impl ArrayVector { } #[inline] - fn as_ptr_mut(&mut self) -> *mut T { + const fn as_ptr_mut(&mut self) -> *mut T { self.data.as_mut_ptr().cast() } #[inline] - fn do_push(&mut self, value: T) -> Result<(), T> { + const fn do_push(&mut self, value: T) -> Result<(), T> { let len = self.len; if len >= Self::N_U32 { return Err(value); @@ -215,7 +215,7 @@ impl ArrayVector { } #[inline] - unsafe fn get_owned(&mut self, idx: u32) -> T { + const unsafe fn get_owned(&mut self, idx: u32) -> T { // SAFETY: It is up to the caller to provide a valid index let src = unsafe { self.data.as_ptr().add(Usize::from_u32(idx).into_usize()) }; // SAFETY: If the index is valid, then the element exists @@ -263,7 +263,7 @@ where /// Iterates over the slice `other`, copies each element and then appends /// it to this vector. The `other` slice is traversed in-order. #[inline] - pub fn extend_from_copyable_slice(&mut self, other: &[T]) -> Result<(), ArrayVectorError> { + pub const fn extend_from_copyable_slice(&mut self, other: &[T]) -> Result<(), ArrayVectorError> { let len = self.len; let other_len_usize = other.len(); let other_len_u32 = 'block: { @@ -283,15 +283,6 @@ where self.len = len.wrapping_add(other_len_u32); Ok(()) } - - /// Appends an copyable element to the back of the collection. - #[inline] - pub fn push_copyable(&mut self, value: T) -> Result<(), ArrayVectorError> { - if self.do_push(value).is_err() { - return Err(ArrayVectorError::PushOverflow); - } - Ok(()) - } } impl Clone for ArrayVector diff --git a/wtx/src/misc/blocks_deque/blocks_deque_builder.rs b/wtx/src/misc/blocks_deque/blocks_deque_builder.rs index b1e8963d..8063e1a9 100644 --- a/wtx/src/misc/blocks_deque/blocks_deque_builder.rs +++ b/wtx/src/misc/blocks_deque/blocks_deque_builder.rs @@ -77,7 +77,7 @@ impl<'db, D, M, const IS_BACK: bool> BlocksDequeBuilder<'db, D, M, IS_BACK> { // some_fallible_operation(...)?; // builder.build(); // ``` -impl<'db, D, M, const IS_BACK: bool> Drop for BlocksDequeBuilder<'db, D, M, IS_BACK> { +impl Drop for BlocksDequeBuilder<'_, D, M, IS_BACK> { #[inline] fn drop(&mut self) { if !self.was_built { diff --git a/wtx/src/misc/facades/arc.rs b/wtx/src/misc/facades/arc.rs index 65fea6ea..d9be5e61 100644 --- a/wtx/src/misc/facades/arc.rs +++ b/wtx/src/misc/facades/arc.rs @@ -31,9 +31,6 @@ impl Clone for Arc { } impl Deref for Arc { - #[cfg(feature = "portable-atomic-util")] - type Target = T; - #[cfg(not(feature = "portable-atomic-util"))] type Target = T; #[inline] @@ -42,8 +39,8 @@ impl Deref for Arc { } } -#[cfg(not(feature = "portable-atomic-util"))] -impl From> for alloc::sync::Arc { +#[cfg(feature = "portable-atomic-util")] +impl From> for portable_atomic_util::Arc { #[inline] fn from(from: Arc) -> Self { from.0 @@ -51,9 +48,25 @@ impl From> for alloc::sync::Arc { } #[cfg(feature = "portable-atomic-util")] -impl From> for portable_atomic_util::Arc { +impl From> for Arc { + #[inline] + fn from(from: portable_atomic_util::Arc) -> Self { + Self(from) + } +} + +#[cfg(not(feature = "portable-atomic-util"))] +impl From> for alloc::sync::Arc { #[inline] fn from(from: Arc) -> Self { from.0 } } + +#[cfg(not(feature = "portable-atomic-util"))] +impl From> for Arc { + #[inline] + fn from(from: alloc::sync::Arc) -> Self { + Self(from) + } +} diff --git a/wtx/src/misc/facades/atomic_u64.rs b/wtx/src/misc/facades/atomic_u64.rs index 4f1887df..bacaba3e 100644 --- a/wtx/src/misc/facades/atomic_u64.rs +++ b/wtx/src/misc/facades/atomic_u64.rs @@ -1,6 +1,6 @@ use core::ops::{Deref, DerefMut}; -/// A thread-safe reference-counting pointer. ‘Arc’ stands for ‘Atomically Reference Counted’. +/// An integer type which can be safely shared between threads. #[derive(Debug)] pub(crate) struct AtomicU64( #[cfg(feature = "portable-atomic")] portable_atomic::AtomicU64, diff --git a/wtx/src/misc/facades/atomic_usize.rs b/wtx/src/misc/facades/atomic_usize.rs index 2223fd84..3733b7a6 100644 --- a/wtx/src/misc/facades/atomic_usize.rs +++ b/wtx/src/misc/facades/atomic_usize.rs @@ -1,6 +1,6 @@ use core::ops::{Deref, DerefMut}; -/// A thread-safe reference-counting pointer. ‘Arc’ stands for ‘Atomically Reference Counted’. +/// An integer type which can be safely shared between threads. #[derive(Debug)] pub(crate) struct AtomicUsize( #[cfg(feature = "portable-atomic")] portable_atomic::AtomicUsize, diff --git a/wtx/src/misc/filled_buffer_writer.rs b/wtx/src/misc/filled_buffer_writer.rs index 40b21f4a..c2e5fcd5 100644 --- a/wtx/src/misc/filled_buffer_writer.rs +++ b/wtx/src/misc/filled_buffer_writer.rs @@ -105,7 +105,7 @@ impl<'vec> LeaseMut> for FilledBufferWriter<'vec> { } } -impl<'vec> Drop for FilledBufferWriter<'vec> { +impl Drop for FilledBufferWriter<'_> { #[inline] fn drop(&mut self) { self._vec._truncate(self._initial_idx); diff --git a/wtx/src/misc/generic_time.rs b/wtx/src/misc/generic_time.rs index e28183d3..1b3f56c7 100644 --- a/wtx/src/misc/generic_time.rs +++ b/wtx/src/misc/generic_time.rs @@ -3,12 +3,14 @@ use core::time::Duration; /// Tries to support different time machineries of different platforms. /// /// Currently only supports `std`. For anything else, methods return errors. -#[derive(Clone, Copy, Debug, Eq, Hash, Ord, PartialEq, PartialOrd)] +#[derive(Clone, Copy, Debug, Eq, Ord, PartialEq, PartialOrd)] #[cfg_attr(feature = "serde", derive(serde::Deserialize, serde::Serialize))] pub struct GenericTime { #[cfg(feature = "std")] - inner: std::time::SystemTime, - #[cfg(not(feature = "std"))] + _inner: std::time::SystemTime, + #[cfg(all(feature = "embassy-time", not(any(feature = "std"))))] + _inner: embassy_time::Instant, + #[cfg(not(any(feature = "std", feature = "embassy-time")))] _inner: (), } @@ -17,11 +19,11 @@ impl GenericTime { #[inline] pub fn now() -> Self { #[cfg(feature = "std")] - { - Self { inner: std::time::SystemTime::now() } - } - #[cfg(not(feature = "std"))] - Self { _inner: () } + return Self { _inner: std::time::SystemTime::now() }; + #[cfg(all(feature = "embassy-time", not(any(feature = "std"))))] + return Self { _inner: embassy_time::Instant::now() }; + #[cfg(not(any(feature = "std", feature = "embassy-time")))] + return Self { _inner: () }; } /// Returns `Some(t)` where `t` is the time `self + duration` if `t` can be represented as @@ -30,15 +32,18 @@ impl GenericTime { #[inline] pub fn checked_add(&self, _duration: Duration) -> crate::Result { #[cfg(feature = "std")] - { - Ok(Self { - inner: self.inner.checked_add(_duration).ok_or(crate::Error::InvalidHardwareTime)?, - }) - } - #[cfg(not(feature = "std"))] - { - Err(crate::Error::GenericTimeNeedsBackend) - } + return Ok(Self { + _inner: self._inner.checked_add(_duration).ok_or(crate::Error::InvalidHardwareTime)?, + }); + #[cfg(all(feature = "embassy-time", not(any(feature = "std"))))] + return Ok(Self { + _inner: self + ._inner + .checked_add(embassy_time::Duration::from_secs(_duration.as_secs())) + .ok_or(crate::Error::InvalidHardwareTime)?, + }); + #[cfg(not(any(feature = "std", feature = "embassy-time")))] + return Err(crate::Error::GenericTimeNeedsBackend); } /// Returns `Some(t)` where `t` is the time `self - duration` if `t` can be represented as @@ -47,15 +52,18 @@ impl GenericTime { #[inline] pub fn checked_sub(&self, _duration: Duration) -> crate::Result { #[cfg(feature = "std")] - { - Ok(Self { - inner: self.inner.checked_sub(_duration).ok_or(crate::Error::InvalidHardwareTime)?, - }) - } - #[cfg(not(feature = "std"))] - { - Err(crate::Error::GenericTimeNeedsBackend) - } + return Ok(Self { + _inner: self._inner.checked_sub(_duration).ok_or(crate::Error::InvalidHardwareTime)?, + }); + #[cfg(all(feature = "embassy-time", not(any(feature = "std"))))] + return Ok(Self { + _inner: self + ._inner + .checked_sub(embassy_time::Duration::from_secs(_duration.as_secs())) + .ok_or(crate::Error::InvalidHardwareTime)?, + }); + #[cfg(not(any(feature = "std", feature = "embassy-time")))] + return Err(crate::Error::GenericTimeNeedsBackend); } /// Returns the amount of time elapsed from another instant to this one, @@ -63,13 +71,20 @@ impl GenericTime { #[inline] pub fn duration_since(&self, _earlier: Self) -> crate::Result { #[cfg(feature = "std")] - { - self.inner.duration_since(_earlier.inner).map_err(|_err| crate::Error::InvalidHardwareTime) - } - #[cfg(not(feature = "std"))] - { - Err(crate::Error::GenericTimeNeedsBackend) - } + return self + ._inner + .duration_since(_earlier._inner) + .map_err(|_err| crate::Error::InvalidHardwareTime); + #[cfg(all(feature = "embassy-time", not(any(feature = "std"))))] + return Ok(Duration::from_micros( + self + ._inner + .checked_duration_since(_earlier._inner) + .ok_or(crate::Error::InvalidHardwareTime)? + .as_micros(), + )); + #[cfg(not(any(feature = "std", feature = "embassy-time")))] + return Err(crate::Error::GenericTimeNeedsBackend); } /// Returns the amount of time elapsed since this instant was created. @@ -82,12 +97,22 @@ impl GenericTime { #[inline] pub fn timestamp() -> crate::Result { #[cfg(feature = "std")] - { - Self::now().duration_since(Self { inner: std::time::UNIX_EPOCH }) - } - #[cfg(not(feature = "std"))] - { - Err(crate::Error::GenericTimeNeedsBackend) - } + return Self::now().duration_since(Self { _inner: std::time::UNIX_EPOCH }); + #[cfg(all(feature = "embassy-time", not(any(feature = "std"))))] + return Self::now().duration_since(Self { _inner: embassy_time::Instant::from_secs(0) }); + #[cfg(not(any(feature = "std", feature = "embassy-time")))] + return Err(crate::Error::GenericTimeNeedsBackend); + } +} + +/// Provides the current time +#[derive(Debug)] +pub struct GenericTimeProvider; + +#[cfg(feature = "rustls")] +impl rustls::time_provider::TimeProvider for GenericTimeProvider { + #[inline] + fn current_time(&self) -> Option { + Some(rustls_pki_types::UnixTime::since_unix_epoch(GenericTime::timestamp().ok()?)) } } diff --git a/wtx/src/misc/uri.rs b/wtx/src/misc/uri.rs index 0a4c3368..b6f71200 100644 --- a/wtx/src/misc/uri.rs +++ b/wtx/src/misc/uri.rs @@ -1,9 +1,9 @@ use crate::misc::{ - QueryWriter, _unlikely_dflt, bytes_pos1, bytes_rpos1, str_split_once1, ArrayString, FromRadix10, - Lease, + QueryWriter, _unlikely_dflt, bytes_pos1, bytes_rpos1, str_split_once1, ArrayString, + FromRadix10 as _, Lease, }; use alloc::string::String; -use core::fmt::{Arguments, Debug, Display, Formatter, Write}; +use core::fmt::{Arguments, Debug, Display, Formatter, Write as _}; /// [Uri] with an owned array. pub type UriArrayString = Uri>; diff --git a/wtx/src/pool/simple_pool.rs b/wtx/src/pool/simple_pool.rs index 92f59268..b5851f23 100644 --- a/wtx/src/pool/simple_pool.rs +++ b/wtx/src/pool/simple_pool.rs @@ -19,7 +19,6 @@ pub type SimplePoolTokio = #[derive(Debug)] pub struct SimplePool { available_idxs: Arc>>, - #[expect(clippy::rc_buffer, reason = "false-positive")] locks: Arc>, rm: Arc, waker: Arc>>, diff --git a/wtx/src/tls.rs b/wtx/src/tls.rs new file mode 100644 index 00000000..10a8e74b --- /dev/null +++ b/wtx/src/tls.rs @@ -0,0 +1,29 @@ +#![allow(dead_code, missing_docs, reason = "development")] + +mod acceptor; +mod connector; +mod handshake; +mod item; +mod state; +mod tls_error; +mod tls_stream; +mod trust_anchor; + +pub use acceptor::{acceptor_backend::AcceptorBackend, Acceptor}; +pub use connector::{connector_backend::ConnectorBackend, Connector}; +pub use tls_error::TlsError; +pub use tls_stream::TlsStream; +pub use trust_anchor::TrustAnchor; + +/// Marker used to indicate the operations with `rustls` +#[cfg(feature = "rustls")] +#[derive(Debug)] +pub struct Rustls; + +#[inline] +fn _invalid_input_err(err: E) -> std::io::Error +where + E: Into>, +{ + std::io::Error::new(std::io::ErrorKind::InvalidInput, err) +} diff --git a/wtx/src/tls/acceptor.rs b/wtx/src/tls/acceptor.rs new file mode 100644 index 00000000..efd845b0 --- /dev/null +++ b/wtx/src/tls/acceptor.rs @@ -0,0 +1,49 @@ +pub(crate) mod acceptor_backend; +#[cfg(feature = "rustls")] +mod rustls; + +/// TLS implementation responsable for accepting connections +#[derive(Debug)] +pub struct Acceptor +where + B: acceptor_backend::AcceptorBackend, +{ + backend: B, + backend_wca: B::WithoutClientAuth, + is_http2: bool, +} + +impl Acceptor +where + B: acceptor_backend::AcceptorBackend, +{ + #[inline] + pub fn without_client_auth(mut backend: B) -> Self { + let backend_wca = backend.without_client_auth(); + Self { backend, backend_wca, is_http2: false } + } + + /// Creates a [`tokio_rustls::TlsAcceptor`] with a single certificate chain and matching private + /// key. + #[inline] + pub fn build_with_cert_chain_and_priv_key( + self, + cert_chain: &[u8], + priv_key: &[u8], + ) -> crate::Result { + self.backend.build_with_cert_chain_and_priv_key( + self.backend_wca, + cert_chain, + self.is_http2, + priv_key, + ) + } + + /// Erases the set of ALPN protocols when building and then pushes the expected ALPN value for an + /// HTTP2 connection. + #[inline] + pub fn http2(mut self) -> Self { + self.is_http2 = true; + self + } +} diff --git a/wtx/src/tls/acceptor/acceptor_backend.rs b/wtx/src/tls/acceptor/acceptor_backend.rs new file mode 100644 index 00000000..c4680f52 --- /dev/null +++ b/wtx/src/tls/acceptor/acceptor_backend.rs @@ -0,0 +1,35 @@ +pub trait AcceptorBackend { + type Acceptor; + type WithoutClientAuth; + + fn without_client_auth(&mut self) -> Self::WithoutClientAuth; + + fn build_with_cert_chain_and_priv_key( + self, + wca: Self::WithoutClientAuth, + cert_chain: &[u8], + is_http2: bool, + priv_key: &[u8], + ) -> crate::Result; +} + +impl AcceptorBackend for () { + type Acceptor = (); + type WithoutClientAuth = (); + + #[inline] + fn without_client_auth(&mut self) -> Self { + () + } + + #[inline] + fn build_with_cert_chain_and_priv_key( + self, + _: Self::WithoutClientAuth, + _: &[u8], + _: bool, + _: &[u8], + ) -> crate::Result { + Ok(()) + } +} diff --git a/wtx/src/tls/acceptor/rustls.rs b/wtx/src/tls/acceptor/rustls.rs new file mode 100644 index 00000000..d9da1c45 --- /dev/null +++ b/wtx/src/tls/acceptor/rustls.rs @@ -0,0 +1,39 @@ +use crate::tls::{Acceptor, AcceptorBackend, Rustls, _invalid_input_err}; +use alloc::sync::Arc; +use rustls::{server::WantsServerCert, ConfigBuilder, ServerConfig}; +use tokio_rustls::TlsAcceptor; + +impl Acceptor { + pub fn without_client_auth_rustls() -> Self { + Self::without_client_auth(Rustls) + } +} + +impl AcceptorBackend for Rustls { + type Acceptor = TlsAcceptor; + type WithoutClientAuth = ConfigBuilder; + + #[inline] + fn without_client_auth(&mut self) -> Self::WithoutClientAuth { + ServerConfig::builder().with_no_client_auth() + } + + #[inline] + fn build_with_cert_chain_and_priv_key( + self, + wca: Self::WithoutClientAuth, + cert_chain: &[u8], + is_http2: bool, + priv_key: &[u8], + ) -> crate::Result { + let mut config = wca.with_single_cert( + rustls_pemfile::certs(&mut &*cert_chain).collect::>()?, + rustls_pemfile::private_key(&mut &*priv_key)?.ok_or_else(|| _invalid_input_err("No key"))?, + )?; + if is_http2 { + config.alpn_protocols.clear(); + config.alpn_protocols.push("h2".into()); + } + Ok(TlsAcceptor::from(Arc::new(config))) + } +} diff --git a/wtx/src/tls/connector.rs b/wtx/src/tls/connector.rs new file mode 100644 index 00000000..f96690c6 --- /dev/null +++ b/wtx/src/tls/connector.rs @@ -0,0 +1,94 @@ +pub(crate) mod connector_backend; +#[cfg(feature = "rustls")] +mod rustls; + +use crate::{ + misc::Stream, + tls::{TlsStream, TrustAnchor}, +}; +use alloc::vec::Vec; + +/// TLS client using `tokio-rustls` and associated crates. +#[derive(Debug)] +pub struct Connector +where + B: connector_backend::ConnectorBackend, +{ + alpn_protocols: Vec>, + backend: B, + backend_config: B::Config, +} + +impl Connector +where + B: connector_backend::ConnectorBackend, +{ + #[inline] + pub fn new(mut backend: B) -> Self { + let backend_config = backend.config(); + Self { alpn_protocols: Vec::new(), backend, backend_config } + } + + /// From the automatic selection of dependencies. + /// + /// An error will be returned if no dependency that provides CA certificates is selected. + #[inline] + pub fn from_auto(backend: B) -> crate::Result { + #[cfg(feature = "webpki-roots")] + { + let mut this = Self::new(backend); + this.backend.extend_from_trust_anchors( + &mut this.backend_config, + webpki_roots::TLS_SERVER_ROOTS.iter().map(|el| TrustAnchor { + name_constraints: el.name_constraints.as_ref().map(|der| der.as_ref()), + subject: el.subject.as_ref(), + subject_public_key_info: el.subject_public_key_info.as_ref(), + }), + )?; + Ok(this) + } + #[cfg(not(feature = "webpki-roots"))] + return Err(crate::Error::MissingCaProviders); + } + + /// Connects using a generic stream without client authentication. + #[inline] + pub async fn connect_without_client_auth( + self, + hostname: &str, + stream: S, + ) -> crate::Result> + where + S: Stream, + { + self.backend.connect_without_client_auth(self.backend_config, hostname, stream) + } + + /// Erases the current set of ALPN protocols and then pushes the expected ALPN value for a HTTP2 + /// connection. + #[inline] + pub fn http2(mut self) -> Self { + self.alpn_protocols.clear(); + self.alpn_protocols.push("h2".into()); + self + } + + /// Avoids additional round trips by specifying in advance which protocols should be used. + #[inline] + pub fn push_alpn_protocol(mut self, protocol: &[u8]) -> Self { + self.alpn_protocols.push(protocol.into()); + self + } + + #[inline] + pub fn push_der_cert(mut self, der_cert: &[u8]) -> crate::Result { + self.backend.push_der_cert(&mut self.backend_config, der_cert)?; + Ok(self) + } + + #[inline] + pub fn push_der_certs_from_pem(mut self, pem: &[u8]) -> crate::Result { + self.backend.push_der_cert(&mut self.backend_config, pem)?; + Ok(self) + } +} diff --git a/wtx/src/tls/connector/connector_backend.rs b/wtx/src/tls/connector/connector_backend.rs new file mode 100644 index 00000000..21b5b52c --- /dev/null +++ b/wtx/src/tls/connector/connector_backend.rs @@ -0,0 +1,74 @@ +use crate::{ + misc::Stream, + tls::{connector::TrustAnchor, TlsStream}, +}; + +/// TLS implementation responsable for initiating connections +pub trait ConnectorBackend { + type Config; + type StreamAux; + + fn config(&mut self) -> Self::Config; + + fn connect_without_client_auth( + self, + config: Self::Config, + hostname: &str, + stream: S, + ) -> crate::Result> + where + S: Stream; + + fn extend_from_trust_anchors( + &mut self, + config: &mut Self::Config, + trust_anchors: impl Iterator>, + ) -> crate::Result<()>; + + fn push_der_cert(&mut self, config: &mut Self::Config, der_cert: &[u8]) -> crate::Result<()>; + + fn push_der_certs_from_pem(&mut self, config: &mut Self::Config, pem: &[u8]) + -> crate::Result<()>; +} + +impl ConnectorBackend for () { + type Config = (); + type StreamAux = (); + + #[inline] + fn config(&mut self) -> Self::Config { + () + } + + #[inline] + fn connect_without_client_auth( + self, + _: Self::Config, + _: &str, + stream: S, + ) -> crate::Result> + where + S: Stream, + { + Ok(TlsStream::new((), stream)) + } + + #[inline] + fn extend_from_trust_anchors( + &mut self, + _: &mut Self::Config, + _: impl Iterator>, + ) -> crate::Result<()> { + Ok(()) + } + + #[inline] + fn push_der_cert(&mut self, _: &mut Self::Config, _: &[u8]) -> crate::Result<()> { + Ok(()) + } + + #[inline] + fn push_der_certs_from_pem(&mut self, _: &mut Self::Config, _: &[u8]) -> crate::Result<()> { + Ok(()) + } +} diff --git a/wtx/src/tls/connector/rustls.rs b/wtx/src/tls/connector/rustls.rs new file mode 100644 index 00000000..49f7d8b0 --- /dev/null +++ b/wtx/src/tls/connector/rustls.rs @@ -0,0 +1,88 @@ +use crate::{ + misc::{GenericTimeProvider, Stream}, + tls::{ + connector::TrustAnchor, item::Item, Connector, ConnectorBackend, Rustls, TlsStream, + _invalid_input_err, + }, +}; +use alloc::{string::String, sync::Arc}; +use rustls::{client::UnbufferedClientConnection, version::TLS13, ClientConfig, RootCertStore}; +use rustls_pki_types::{CertificateDer, Der, ServerName}; + +impl Connector { + pub fn rustls() -> Self { + Connector::new(Rustls) + } +} + +impl ConnectorBackend for Rustls { + type Config = RootCertStore; + type StreamAux = UnbufferedClientConnection; + + #[inline] + fn config(&mut self) -> Self::Config { + RootCertStore::empty() + } + + #[inline] + fn connect_without_client_auth( + self, + config: Self::Config, + hostname: &str, + stream: S, + ) -> crate::Result> + where + S: Stream, + { + #[cfg(feature = "aws-lc-rs")] + let provider = rustls::crypto::aws_lc_rs::default_provider(); + #[cfg(all(feature = "ring", not(any(feature = "aws-lc-rs"))))] + let provider = rustls::crypto::ring::default_provider(); + #[cfg(not(any(feature = "aws-lc-rs", feature = "ring")))] + return Err(crate::tls::TlsError::MissingProvider.into()); + + let time_provider = Arc::new(GenericTimeProvider); + let client_config = ClientConfig::builder_with_details(Arc::new(provider), time_provider) + .with_protocol_versions(&[&TLS13])? + .with_root_certificates(config) + .with_no_client_auth(); + let ucc = UnbufferedClientConnection::new( + Arc::new(client_config), + ServerName::try_from(String::from(hostname)).map_err(_invalid_input_err)?, + )?; + Ok(TlsStream::new(ucc, stream)) + } + + #[inline] + fn extend_from_trust_anchors( + &mut self, + config: &mut Self::Config, + trust_anchors: impl Iterator>, + ) -> crate::Result<()> { + config.extend(trust_anchors.map(|ta| rustls_pki_types::TrustAnchor { + subject: Der::from_slice(ta.subject), + subject_public_key_info: Der::from_slice(ta.subject_public_key_info), + name_constraints: ta.name_constraints.map(|el| Der::from_slice(el)), + })); + Ok(()) + } + + #[inline] + fn push_der_cert(&mut self, config: &mut Self::Config, der_cert: &[u8]) -> crate::Result<()> { + config.add(CertificateDer::from_slice(der_cert))?; + Ok(()) + } + + #[inline] + fn push_der_certs_from_pem( + &mut self, + config: &mut Self::Config, + pem: &[u8], + ) -> crate::Result<()> { + for rslt in Item::rustls_pki_types(pem) { + let Item::X509DerCertificate(der_cert) = rslt?; + config.add(der_cert.into())?; + } + Ok(()) + } +} diff --git a/wtx/src/tls/handshake.rs b/wtx/src/tls/handshake.rs new file mode 100644 index 00000000..eb349b02 --- /dev/null +++ b/wtx/src/tls/handshake.rs @@ -0,0 +1 @@ +pub(crate) struct Handshake {} diff --git a/wtx/src/tls/item.rs b/wtx/src/tls/item.rs new file mode 100644 index 00000000..54526e9f --- /dev/null +++ b/wtx/src/tls/item.rs @@ -0,0 +1,36 @@ +use alloc::vec::Vec; + +#[derive(Debug, PartialEq)] +pub(crate) enum Item { + X509DerCertificate(Vec), +} + +#[cfg(feature = "rustls-pki-types")] +mod rustls { + use crate::tls::item::Item; + use rustls_pki_types::pem::{PemObject, SectionKind}; + use std::vec::Vec; + + impl Item { + #[inline] + pub(crate) fn rustls_pki_types( + pem: &[u8], + ) -> impl Iterator> + use<'_> { + PemObject::pem_slice_iter(pem).filter_map(|rslt| { + let (sk, bytes) = match rslt { + Err(err) => return Some(Err(err)), + Ok(elem) => elem, + }; + Ok(Self::from_rustls_kind(bytes, sk)).transpose() + }) + } + + #[inline] + fn from_rustls_kind(bytes: Vec, sk: SectionKind) -> Option { + match sk { + SectionKind::Certificate => Some(Self::X509DerCertificate(bytes.into())), + _ => None, + } + } + } +} diff --git a/wtx/src/tls/state.rs b/wtx/src/tls/state.rs new file mode 100644 index 00000000..6e000f6f --- /dev/null +++ b/wtx/src/tls/state.rs @@ -0,0 +1,7 @@ +#[derive(Debug, Copy, Clone)] +pub(crate) enum State { + FullyShutdown, + ReadShutdown, + Stream, + WriteShutdown, +} diff --git a/wtx/src/tls/tls_error.rs b/wtx/src/tls/tls_error.rs new file mode 100644 index 00000000..806c010a --- /dev/null +++ b/wtx/src/tls/tls_error.rs @@ -0,0 +1,6 @@ +/// TLS errror +#[derive(Debug)] +pub enum TlsError { + /// It is necessary to provide a crypto provide using Cargo features + MissingProvider, +} diff --git a/wtx/src/tls/tls_stream.rs b/wtx/src/tls/tls_stream.rs new file mode 100644 index 00000000..1843d8e5 --- /dev/null +++ b/wtx/src/tls/tls_stream.rs @@ -0,0 +1,13 @@ +#[derive(Debug)] +pub struct TlsStream { + aux: A, + stream: S, +} + +impl TlsStream { + /// Creates a new instance with a stream that supposedly already performed a handshake. + #[inline] + pub fn new(aux: A, stream: S) -> Self { + Self { aux, stream } + } +} diff --git a/wtx/src/tls/trust_anchor.rs b/wtx/src/tls/trust_anchor.rs new file mode 100644 index 00000000..ed013a1a --- /dev/null +++ b/wtx/src/tls/trust_anchor.rs @@ -0,0 +1,6 @@ +#[derive(Debug)] +pub struct TrustAnchor<'bytes> { + pub(crate) name_constraints: Option<&'bytes [u8]>, + pub(crate) subject: &'bytes [u8], + pub(crate) subject_public_key_info: &'bytes [u8], +} diff --git a/wtx/src/web_socket/compression/flate2.rs b/wtx/src/web_socket/compression/flate2.rs index 7abd51b9..1e6d3185 100644 --- a/wtx/src/web_socket/compression/flate2.rs +++ b/wtx/src/web_socket/compression/flate2.rs @@ -132,7 +132,7 @@ impl NegotiatedCompression for NegotiatedFlate2 { let _ = this.compress.compress(local_input, output_butes, FlushCompress::Sync); Ok(()) }, - |a, b| Ok(rem_cb(a, b)?), + |a, b| rem_cb(a, b), |this| this.compress.reset(), |this| this.compress.total_in(), |this| this.compress.total_out(), diff --git a/wtx/src/web_socket/handshake.rs b/wtx/src/web_socket/handshake.rs index 51f7a0b6..76f93df3 100644 --- a/wtx/src/web_socket/handshake.rs +++ b/wtx/src/web_socket/handshake.rs @@ -262,15 +262,15 @@ where #[inline] fn check_header_value((name, value): (KnownHeaderName, Option<&[u8]>)) -> crate::Result<&[u8]> { let Some(elem) = value else { - return Err(crate::Error::from(HttpError::MissingHeader(name)).into()); + return Err(crate::Error::from(HttpError::MissingHeader(name))); }; Ok(elem) } #[inline] -fn check_headers<'header, 'headers, const N: usize>( +fn check_headers<'headers, const N: usize>( array: [(KnownHeaderName, Option<&[u8]>); N], - headers: &'headers [Header<'header>], + headers: &'headers [Header<'_>], ) -> crate::Result<[(KnownHeaderName, Option<&'headers [u8]>); N]> { let mut rslt = [(KnownHeaderName::Accept, None); N]; for header in headers { diff --git a/wtx/tests/embedded_migrations/mod.rs b/wtx/tests/embedded_migrations/mod.rs index 70477308..ab864df7 100644 --- a/wtx/tests/embedded_migrations/mod.rs +++ b/wtx/tests/embedded_migrations/mod.rs @@ -1,4 +1,4 @@ -#[rustfmt::skip]pub(crate) const GROUPS: wtx::database::schema_manager::EmbeddedMigrationsTy = &[{const INITIAL: &wtx::database::schema_manager::MigrationGroup<&'static str> = &wtx::database::schema_manager::MigrationGroup::new("INITIAL",1);const INITIAL_MIGRATIONS: &[wtx::database::schema_manager::UserMigrationRef<'static, 'static>] = &[wtx::database::schema_manager::UserMigrationRef::from_all_parts(7573493478190316387,&[],"create_author",None,"DROP TABLE author;","CREATE TABLE author ( +#[rustfmt::skip]pub(crate) static GROUPS: wtx::database::schema_manager::EmbeddedMigrationsTy = &[{const INITIAL: &wtx::database::schema_manager::MigrationGroup<&'static str> = &wtx::database::schema_manager::MigrationGroup::new("INITIAL",1);const INITIAL_MIGRATIONS: &[wtx::database::schema_manager::UserMigrationRef<'static, 'static>] = &[wtx::database::schema_manager::UserMigrationRef::from_all_parts(7573493478190316387,&[],"create_author",None,"DROP TABLE author;","CREATE TABLE author ( id INT NOT NULL PRIMARY KEY, first_name VARCHAR(50) NOT NULL, last_name VARCHAR(50) NOT NULL,