Spaces:
Runtime error
:zap: perf: several optimizations for improving the performance of the engine (#540)
Browse files* :recycle: refactor: initialize & store the config & cache structs as a constant (#486)
- initializes & stores the config & cache structs as a static constant.
- Pass the config & cache structs as a static reference to all the
functions handling their respective route.
* :zap: perf: replace hashmaps with vectors for fetching & aggregating results (#486)
- replace hashmaps with vectors for fetching, collecting & aggregating results as it tends to be contigous & cache efficient data structure.
- refactor & redesign algorithms for fetching & aggregating results
centered around vectors in aggregate function.
* :heavy_plus_sign: build: add the future crate (#486)
* :zap: perf: use `futureunordered` for collecting results fetched from the tokio spawn tasks (#486)
- using the `futureunordered` instead of vector for collecting results
reduces the time it takes to fetch the results as the results do not
need to come in specific order so any result that gets fetched first
gets collected in the `futureunordered` type.
Co-authored-by: Spencerjibz <spencernajib2@gmail.com>
* :zap: perf: initialize new async connections parallely using tokio spawn tasks (#486)
* :zap: perf: initialize redis pipeline struct once with the default size of 3 (#486)
* :zap: perf: reduce branch predictions by reducing conditional code branches (#486)
* :white_check_mark: test(unit): provide unit test for the `get_safesearch_level` function (#486)
* :zap: perf: reduce clones & use index based loop to improve search results filtering performance (#486)
* π¨ fix(clippy): make clippy/format checks happy (#486)
* π¨ fix(build): make the cargo build check happy (#486)
* :zap: perf: reduce the amount of clones, to_owneds & to_strings (#486)
* :zap: perf: use async crates & methods & make functions async (#486)
* :bookmark: chore(release): bump the app version (#486)
---------
Co-authored-by: Spencerjibz <spencernajib2@gmail.com>
- Cargo.lock +305 -310
- Cargo.toml +6 -6
- src/bin/websurfx.rs +8 -5
- src/cache/cacher.rs +40 -28
- src/cache/redis_cacher.rs +27 -10
- src/config/parser.rs +0 -1
- src/engines/bing.rs +1 -1
- src/engines/brave.rs +1 -1
- src/engines/duckduckgo.rs +1 -1
- src/engines/librex.rs +1 -1
- src/engines/mojeek.rs +18 -3
- src/engines/search_result_parser.rs +1 -2
- src/engines/searx.rs +15 -6
- src/engines/startpage.rs +1 -1
- src/lib.rs +17 -12
- src/models/aggregation_models.rs +2 -2
- src/models/engine_models.rs +2 -2
- src/models/parser_models.rs +1 -3
- src/results/aggregator.rs +105 -86
- src/server/router.rs +10 -6
- src/server/routes/search.rs +108 -36
- src/templates/partials/settings_tabs/engines.rs +2 -2
- src/templates/partials/settings_tabs/user_interface.rs +5 -3
- src/templates/views/search.rs +1 -1
- tests/index.rs +6 -3
@@ -4,17 +4,17 @@ version = 3
|
|
4 |
|
5 |
[[package]]
|
6 |
name = "actix-codec"
|
7 |
-
version = "0.5.
|
8 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
9 |
-
checksum = "
|
10 |
dependencies = [
|
11 |
-
"bitflags
|
12 |
"bytes 1.5.0",
|
13 |
"futures-core",
|
14 |
"futures-sink",
|
15 |
"memchr",
|
16 |
"pin-project-lite",
|
17 |
-
"tokio 1.
|
18 |
"tokio-util",
|
19 |
"tracing",
|
20 |
]
|
@@ -44,7 +44,7 @@ dependencies = [
|
|
44 |
"actix-service",
|
45 |
"actix-utils",
|
46 |
"actix-web",
|
47 |
-
"bitflags 2.4.
|
48 |
"bytes 1.5.0",
|
49 |
"derive_more",
|
50 |
"futures-core",
|
@@ -71,24 +71,24 @@ dependencies = [
|
|
71 |
|
72 |
[[package]]
|
73 |
name = "actix-http"
|
74 |
-
version = "3.
|
75 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
76 |
-
checksum = "
|
77 |
dependencies = [
|
78 |
"actix-codec",
|
79 |
"actix-rt",
|
80 |
"actix-service",
|
81 |
"actix-utils",
|
82 |
-
"ahash
|
83 |
-
"base64 0.21.
|
84 |
-
"bitflags 2.4.
|
85 |
"brotli",
|
86 |
"bytes 1.5.0",
|
87 |
"bytestring",
|
88 |
"derive_more",
|
89 |
"encoding_rs",
|
90 |
"futures-core",
|
91 |
-
"http 0.2.
|
92 |
"httparse",
|
93 |
"httpdate",
|
94 |
"itoa 1.0.10",
|
@@ -100,7 +100,7 @@ dependencies = [
|
|
100 |
"rand 0.8.5",
|
101 |
"sha1",
|
102 |
"smallvec 1.13.1",
|
103 |
-
"tokio 1.
|
104 |
"tokio-util",
|
105 |
"tracing",
|
106 |
]
|
@@ -112,7 +112,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|
112 |
checksum = "e01ed3140b2f8d422c68afa1ed2e85d996ea619c988ac834d255db32138655cb"
|
113 |
dependencies = [
|
114 |
"quote 1.0.35",
|
115 |
-
"syn 2.0.
|
116 |
]
|
117 |
|
118 |
[[package]]
|
@@ -122,7 +122,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|
122 |
checksum = "d22475596539443685426b6bdadb926ad0ecaefdfc5fb05e5e3441f15463c511"
|
123 |
dependencies = [
|
124 |
"bytestring",
|
125 |
-
"http 0.2.
|
126 |
"regex",
|
127 |
"serde",
|
128 |
"tracing",
|
@@ -135,7 +135,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|
135 |
checksum = "28f32d40287d3f402ae0028a9d54bef51af15c8769492826a69d28f81893151d"
|
136 |
dependencies = [
|
137 |
"futures-core",
|
138 |
-
"tokio 1.
|
139 |
]
|
140 |
|
141 |
[[package]]
|
@@ -149,9 +149,9 @@ dependencies = [
|
|
149 |
"actix-utils",
|
150 |
"futures-core",
|
151 |
"futures-util",
|
152 |
-
"mio 0.8.
|
153 |
"socket2",
|
154 |
-
"tokio 1.
|
155 |
"tracing",
|
156 |
]
|
157 |
|
@@ -178,9 +178,9 @@ dependencies = [
|
|
178 |
|
179 |
[[package]]
|
180 |
name = "actix-web"
|
181 |
-
version = "4.
|
182 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
183 |
-
checksum = "
|
184 |
dependencies = [
|
185 |
"actix-codec",
|
186 |
"actix-http",
|
@@ -191,7 +191,7 @@ dependencies = [
|
|
191 |
"actix-service",
|
192 |
"actix-utils",
|
193 |
"actix-web-codegen",
|
194 |
-
"ahash
|
195 |
"bytes 1.5.0",
|
196 |
"bytestring",
|
197 |
"cfg-if 1.0.0",
|
@@ -212,7 +212,7 @@ dependencies = [
|
|
212 |
"serde_urlencoded 0.7.1",
|
213 |
"smallvec 1.13.1",
|
214 |
"socket2",
|
215 |
-
"time 0.3.
|
216 |
"url 2.5.0",
|
217 |
]
|
218 |
|
@@ -225,7 +225,7 @@ dependencies = [
|
|
225 |
"actix-router",
|
226 |
"proc-macro2 1.0.78",
|
227 |
"quote 1.0.35",
|
228 |
-
"syn 2.0.
|
229 |
]
|
230 |
|
231 |
[[package]]
|
@@ -255,20 +255,9 @@ dependencies = [
|
|
255 |
|
256 |
[[package]]
|
257 |
name = "ahash"
|
258 |
-
version = "0.
|
259 |
-
source = "registry+https://github.com/rust-lang/crates.io-index"
|
260 |
-
checksum = "5a824f2aa7e75a0c98c5a504fceb80649e9c35265d44525b5f94de4771a395cd"
|
261 |
-
dependencies = [
|
262 |
-
"getrandom",
|
263 |
-
"once_cell",
|
264 |
-
"version_check",
|
265 |
-
]
|
266 |
-
|
267 |
-
[[package]]
|
268 |
-
name = "ahash"
|
269 |
-
version = "0.8.7"
|
270 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
271 |
-
checksum = "
|
272 |
dependencies = [
|
273 |
"cfg-if 1.0.0",
|
274 |
"getrandom",
|
@@ -318,21 +307,21 @@ checksum = "4b46cbb362ab8752921c97e041f5e366ee6297bd428a31275b9fcf1e380f7299"
|
|
318 |
|
319 |
[[package]]
|
320 |
name = "anstyle"
|
321 |
-
version = "1.0.
|
322 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
323 |
-
checksum = "
|
324 |
|
325 |
[[package]]
|
326 |
name = "anyhow"
|
327 |
-
version = "1.0.
|
328 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
329 |
-
checksum = "
|
330 |
|
331 |
[[package]]
|
332 |
name = "arc-swap"
|
333 |
-
version = "1.
|
334 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
335 |
-
checksum = "
|
336 |
|
337 |
[[package]]
|
338 |
name = "arrayref"
|
@@ -348,16 +337,16 @@ checksum = "96d30a06541fbafbc7f82ed10c06164cfbd2c401138f6addd8404629c4b16711"
|
|
348 |
|
349 |
[[package]]
|
350 |
name = "async-compression"
|
351 |
-
version = "0.4.
|
352 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
353 |
-
checksum = "
|
354 |
dependencies = [
|
355 |
"brotli",
|
356 |
"flate2",
|
357 |
"futures-core",
|
358 |
"memchr",
|
359 |
"pin-project-lite",
|
360 |
-
"tokio 1.
|
361 |
]
|
362 |
|
363 |
[[package]]
|
@@ -368,13 +357,13 @@ checksum = "9338790e78aa95a416786ec8389546c4b6a1dfc3dc36071ed9518a9413a542eb"
|
|
368 |
|
369 |
[[package]]
|
370 |
name = "async-trait"
|
371 |
-
version = "0.1.
|
372 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
373 |
-
checksum = "
|
374 |
dependencies = [
|
375 |
"proc-macro2 1.0.78",
|
376 |
"quote 1.0.35",
|
377 |
-
"syn 2.0.
|
378 |
]
|
379 |
|
380 |
[[package]]
|
@@ -418,9 +407,9 @@ dependencies = [
|
|
418 |
|
419 |
[[package]]
|
420 |
name = "base64"
|
421 |
-
version = "0.21.
|
422 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
423 |
-
checksum = "
|
424 |
|
425 |
[[package]]
|
426 |
name = "bit-set"
|
@@ -445,9 +434,9 @@ checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a"
|
|
445 |
|
446 |
[[package]]
|
447 |
name = "bitflags"
|
448 |
-
version = "2.4.
|
449 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
450 |
-
checksum = "
|
451 |
|
452 |
[[package]]
|
453 |
name = "blake3"
|
@@ -494,9 +483,9 @@ dependencies = [
|
|
494 |
|
495 |
[[package]]
|
496 |
name = "bstr"
|
497 |
-
version = "1.9.
|
498 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
499 |
-
checksum = "
|
500 |
dependencies = [
|
501 |
"memchr",
|
502 |
"serde",
|
@@ -504,9 +493,9 @@ dependencies = [
|
|
504 |
|
505 |
[[package]]
|
506 |
name = "bumpalo"
|
507 |
-
version = "3.
|
508 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
509 |
-
checksum = "
|
510 |
|
511 |
[[package]]
|
512 |
name = "bytecount"
|
@@ -557,9 +546,9 @@ dependencies = [
|
|
557 |
|
558 |
[[package]]
|
559 |
name = "cargo-platform"
|
560 |
-
version = "0.1.
|
561 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
562 |
-
checksum = "
|
563 |
dependencies = [
|
564 |
"serde",
|
565 |
]
|
@@ -572,7 +561,7 @@ checksum = "4acbb09d9ee8e23699b9634375c72795d095bf268439da88562cf9b501f181fa"
|
|
572 |
dependencies = [
|
573 |
"camino",
|
574 |
"cargo-platform",
|
575 |
-
"semver 1.0.
|
576 |
"serde",
|
577 |
"serde_json",
|
578 |
]
|
@@ -585,12 +574,9 @@ checksum = "37b2a672a2cb129a2e41c10b1224bb368f9f37a2b16b612598138befd7b37eb5"
|
|
585 |
|
586 |
[[package]]
|
587 |
name = "cc"
|
588 |
-
version = "1.0.
|
589 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
590 |
-
checksum = "
|
591 |
-
dependencies = [
|
592 |
-
"libc",
|
593 |
-
]
|
594 |
|
595 |
[[package]]
|
596 |
name = "cfg-if"
|
@@ -639,9 +625,9 @@ dependencies = [
|
|
639 |
|
640 |
[[package]]
|
641 |
name = "ciborium"
|
642 |
-
version = "0.2.
|
643 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
644 |
-
checksum = "
|
645 |
dependencies = [
|
646 |
"ciborium-io",
|
647 |
"ciborium-ll",
|
@@ -650,15 +636,15 @@ dependencies = [
|
|
650 |
|
651 |
[[package]]
|
652 |
name = "ciborium-io"
|
653 |
-
version = "0.2.
|
654 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
655 |
-
checksum = "
|
656 |
|
657 |
[[package]]
|
658 |
name = "ciborium-ll"
|
659 |
-
version = "0.2.
|
660 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
661 |
-
checksum = "
|
662 |
dependencies = [
|
663 |
"ciborium-io",
|
664 |
"half",
|
@@ -677,18 +663,18 @@ dependencies = [
|
|
677 |
|
678 |
[[package]]
|
679 |
name = "clap"
|
680 |
-
version = "4.
|
681 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
682 |
-
checksum = "
|
683 |
dependencies = [
|
684 |
"clap_builder",
|
685 |
]
|
686 |
|
687 |
[[package]]
|
688 |
name = "clap_builder"
|
689 |
-
version = "4.
|
690 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
691 |
-
checksum = "
|
692 |
dependencies = [
|
693 |
"anstyle",
|
694 |
"clap_lex",
|
@@ -696,9 +682,9 @@ dependencies = [
|
|
696 |
|
697 |
[[package]]
|
698 |
name = "clap_lex"
|
699 |
-
version = "0.
|
700 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
701 |
-
checksum = "
|
702 |
|
703 |
[[package]]
|
704 |
name = "cloudabi"
|
@@ -719,7 +705,7 @@ dependencies = [
|
|
719 |
"futures-core",
|
720 |
"memchr",
|
721 |
"pin-project-lite",
|
722 |
-
"tokio 1.
|
723 |
"tokio-util",
|
724 |
]
|
725 |
|
@@ -772,7 +758,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|
772 |
checksum = "e859cd57d0710d9e06c381b550c06e76992472a8c6d527aecd2fc673dcc231fb"
|
773 |
dependencies = [
|
774 |
"percent-encoding 2.3.1",
|
775 |
-
"time 0.3.
|
776 |
"version_check",
|
777 |
]
|
778 |
|
@@ -812,18 +798,18 @@ checksum = "06ea2b9bc92be3c2baa9334a323ebca2d6f074ff852cd1d7b11064035cd3868f"
|
|
812 |
|
813 |
[[package]]
|
814 |
name = "cpufeatures"
|
815 |
-
version = "0.2.
|
816 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
817 |
-
checksum = "
|
818 |
dependencies = [
|
819 |
"libc",
|
820 |
]
|
821 |
|
822 |
[[package]]
|
823 |
name = "crc32fast"
|
824 |
-
version = "1.
|
825 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
826 |
-
checksum = "
|
827 |
dependencies = [
|
828 |
"cfg-if 1.0.0",
|
829 |
]
|
@@ -864,12 +850,11 @@ dependencies = [
|
|
864 |
|
865 |
[[package]]
|
866 |
name = "crossbeam-channel"
|
867 |
-
version = "0.5.
|
868 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
869 |
-
checksum = "
|
870 |
dependencies = [
|
871 |
-
"
|
872 |
-
"crossbeam-utils 0.8.18",
|
873 |
]
|
874 |
|
875 |
[[package]]
|
@@ -922,12 +907,15 @@ dependencies = [
|
|
922 |
|
923 |
[[package]]
|
924 |
name = "crossbeam-utils"
|
925 |
-
version = "0.8.
|
926 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
927 |
-
checksum = "
|
928 |
-
|
929 |
-
|
930 |
-
|
|
|
|
|
|
|
931 |
|
932 |
[[package]]
|
933 |
name = "crypto-common"
|
@@ -982,7 +970,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|
982 |
checksum = "13b588ba4ac1a99f7f2964d24b3d896ddc6bf847ee3855dbd4366f058cfcd331"
|
983 |
dependencies = [
|
984 |
"quote 1.0.35",
|
985 |
-
"syn 2.0.
|
986 |
]
|
987 |
|
988 |
[[package]]
|
@@ -1006,9 +994,9 @@ checksum = "7e962a19be5cfc3f3bf6dd8f61eb50107f356ad6270fbb3ed41476571db78be5"
|
|
1006 |
|
1007 |
[[package]]
|
1008 |
name = "deranged"
|
1009 |
-
version = "0.3.
|
1010 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1011 |
-
checksum = "
|
1012 |
dependencies = [
|
1013 |
"powerfmt",
|
1014 |
]
|
@@ -1081,9 +1069,9 @@ checksum = "3a68a4904193147e0a8dec3314640e6db742afd5f6e634f428a6af230d9b3591"
|
|
1081 |
|
1082 |
[[package]]
|
1083 |
name = "either"
|
1084 |
-
version = "1.
|
1085 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1086 |
-
checksum = "
|
1087 |
|
1088 |
[[package]]
|
1089 |
name = "encoding_rs"
|
@@ -1105,9 +1093,9 @@ dependencies = [
|
|
1105 |
|
1106 |
[[package]]
|
1107 |
name = "env_logger"
|
1108 |
-
version = "0.11.
|
1109 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1110 |
-
checksum = "
|
1111 |
dependencies = [
|
1112 |
"env_filter",
|
1113 |
"log",
|
@@ -1347,7 +1335,7 @@ checksum = "87750cf4b7a4c0625b1529e4c543c2182106e4dedc60a2a6455e00d212c489ac"
|
|
1347 |
dependencies = [
|
1348 |
"proc-macro2 1.0.78",
|
1349 |
"quote 1.0.35",
|
1350 |
-
"syn 2.0.
|
1351 |
]
|
1352 |
|
1353 |
[[package]]
|
@@ -1364,9 +1352,9 @@ checksum = "38d84fa142264698cdce1a9f9172cf383a0c82de1bddcf3092901442c4097004"
|
|
1364 |
|
1365 |
[[package]]
|
1366 |
name = "futures-timer"
|
1367 |
-
version = "3.0.
|
1368 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1369 |
-
checksum = "
|
1370 |
|
1371 |
[[package]]
|
1372 |
name = "futures-util"
|
@@ -1416,9 +1404,9 @@ dependencies = [
|
|
1416 |
|
1417 |
[[package]]
|
1418 |
name = "getrandom"
|
1419 |
-
version = "0.2.
|
1420 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1421 |
-
checksum = "
|
1422 |
dependencies = [
|
1423 |
"cfg-if 1.0.0",
|
1424 |
"libc",
|
@@ -1439,9 +1427,9 @@ checksum = "d2fabcfbdc87f4758337ca535fb41a6d701b65693ce38287d856d1674551ec9b"
|
|
1439 |
|
1440 |
[[package]]
|
1441 |
name = "governor"
|
1442 |
-
version = "0.6.
|
1443 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1444 |
-
checksum = "
|
1445 |
dependencies = [
|
1446 |
"cfg-if 1.0.0",
|
1447 |
"dashmap",
|
@@ -1450,9 +1438,11 @@ dependencies = [
|
|
1450 |
"no-std-compat",
|
1451 |
"nonzero_ext",
|
1452 |
"parking_lot 0.12.1",
|
|
|
1453 |
"quanta",
|
1454 |
"rand 0.8.5",
|
1455 |
"smallvec 1.13.1",
|
|
|
1456 |
]
|
1457 |
|
1458 |
[[package]]
|
@@ -1475,28 +1465,32 @@ dependencies = [
|
|
1475 |
|
1476 |
[[package]]
|
1477 |
name = "h2"
|
1478 |
-
version = "0.3.
|
1479 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1480 |
-
checksum = "
|
1481 |
dependencies = [
|
1482 |
"bytes 1.5.0",
|
1483 |
"fnv",
|
1484 |
"futures-core",
|
1485 |
"futures-sink",
|
1486 |
"futures-util",
|
1487 |
-
"http 0.2.
|
1488 |
-
"indexmap 2.
|
1489 |
"slab",
|
1490 |
-
"tokio 1.
|
1491 |
"tokio-util",
|
1492 |
"tracing",
|
1493 |
]
|
1494 |
|
1495 |
[[package]]
|
1496 |
name = "half"
|
1497 |
-
version = "
|
1498 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1499 |
-
checksum = "
|
|
|
|
|
|
|
|
|
1500 |
|
1501 |
[[package]]
|
1502 |
name = "hashbrown"
|
@@ -1510,7 +1504,7 @@ version = "0.13.2"
|
|
1510 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1511 |
checksum = "43a3c133739dddd0d2990f9a4bdf8eb4b21ef50e4851ca85ab661199821d510e"
|
1512 |
dependencies = [
|
1513 |
-
"ahash
|
1514 |
"bumpalo",
|
1515 |
]
|
1516 |
|
@@ -1522,9 +1516,9 @@ checksum = "290f1a1d9242c78d09ce40a5e87e7554ee637af1351968159f4952f028f75604"
|
|
1522 |
|
1523 |
[[package]]
|
1524 |
name = "hermit-abi"
|
1525 |
-
version = "0.3.
|
1526 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1527 |
-
checksum = "
|
1528 |
|
1529 |
[[package]]
|
1530 |
name = "home"
|
@@ -1576,9 +1570,9 @@ dependencies = [
|
|
1576 |
|
1577 |
[[package]]
|
1578 |
name = "http"
|
1579 |
-
version = "0.2.
|
1580 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1581 |
-
checksum = "
|
1582 |
dependencies = [
|
1583 |
"bytes 1.5.0",
|
1584 |
"fnv",
|
@@ -1604,7 +1598,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|
1604 |
checksum = "7ceab25649e9960c0311ea418d17bee82c0dcec1bd053b5f9a66e265a693bed2"
|
1605 |
dependencies = [
|
1606 |
"bytes 1.5.0",
|
1607 |
-
"http 0.2.
|
1608 |
"pin-project-lite",
|
1609 |
]
|
1610 |
|
@@ -1666,15 +1660,15 @@ dependencies = [
|
|
1666 |
"futures-channel",
|
1667 |
"futures-core",
|
1668 |
"futures-util",
|
1669 |
-
"h2 0.3.
|
1670 |
-
"http 0.2.
|
1671 |
"http-body 0.4.6",
|
1672 |
"httparse",
|
1673 |
"httpdate",
|
1674 |
"itoa 1.0.10",
|
1675 |
"pin-project-lite",
|
1676 |
"socket2",
|
1677 |
-
"tokio 1.
|
1678 |
"tower-service",
|
1679 |
"tracing",
|
1680 |
"want 0.3.1",
|
@@ -1687,10 +1681,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|
1687 |
checksum = "ec3efd23720e2049821a693cbc7e65ea87c72f1c58ff2f9522ff332b1491e590"
|
1688 |
dependencies = [
|
1689 |
"futures-util",
|
1690 |
-
"http 0.2.
|
1691 |
"hyper 0.14.28",
|
1692 |
"rustls",
|
1693 |
-
"tokio 1.
|
1694 |
"tokio-rustls",
|
1695 |
]
|
1696 |
|
@@ -1751,9 +1745,9 @@ dependencies = [
|
|
1751 |
|
1752 |
[[package]]
|
1753 |
name = "indexmap"
|
1754 |
-
version = "2.
|
1755 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1756 |
-
checksum = "
|
1757 |
dependencies = [
|
1758 |
"equivalent",
|
1759 |
"hashbrown 0.14.3",
|
@@ -1785,12 +1779,12 @@ checksum = "8f518f335dce6725a761382244631d86cf0ccb2863413590b31338feb467f9c3"
|
|
1785 |
|
1786 |
[[package]]
|
1787 |
name = "is-terminal"
|
1788 |
-
version = "0.4.
|
1789 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1790 |
-
checksum = "
|
1791 |
dependencies = [
|
1792 |
"hermit-abi",
|
1793 |
-
"
|
1794 |
"windows-sys 0.52.0",
|
1795 |
]
|
1796 |
|
@@ -1817,9 +1811,9 @@ checksum = "b1a46d1a171d865aa5f83f92695765caa047a9b4cbae2cbf37dbd613a793fd4c"
|
|
1817 |
|
1818 |
[[package]]
|
1819 |
name = "js-sys"
|
1820 |
-
version = "0.3.
|
1821 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1822 |
-
checksum = "
|
1823 |
dependencies = [
|
1824 |
"wasm-bindgen",
|
1825 |
]
|
@@ -1864,16 +1858,17 @@ dependencies = [
|
|
1864 |
|
1865 |
[[package]]
|
1866 |
name = "lightningcss"
|
1867 |
-
version = "1.0.0-alpha.
|
1868 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1869 |
-
checksum = "
|
1870 |
dependencies = [
|
1871 |
-
"ahash
|
1872 |
-
"bitflags 2.4.
|
1873 |
"const-str",
|
1874 |
"cssparser 0.33.0",
|
1875 |
"cssparser-color",
|
1876 |
"data-encoding",
|
|
|
1877 |
"itertools",
|
1878 |
"lazy_static",
|
1879 |
"parcel_selectors",
|
@@ -1884,9 +1879,9 @@ dependencies = [
|
|
1884 |
|
1885 |
[[package]]
|
1886 |
name = "linux-raw-sys"
|
1887 |
-
version = "0.4.
|
1888 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1889 |
-
checksum = "
|
1890 |
|
1891 |
[[package]]
|
1892 |
name = "local-channel"
|
@@ -1941,9 +1936,9 @@ dependencies = [
|
|
1941 |
|
1942 |
[[package]]
|
1943 |
name = "luajit-src"
|
1944 |
-
version = "210.5.
|
1945 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1946 |
-
checksum = "
|
1947 |
dependencies = [
|
1948 |
"cc",
|
1949 |
"which",
|
@@ -1955,15 +1950,6 @@ version = "0.1.1"
|
|
1955 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1956 |
checksum = "c41e0c4fef86961ac6d6f8a82609f55f31b05e4fce149ac5710e439df7619ba4"
|
1957 |
|
1958 |
-
[[package]]
|
1959 |
-
name = "mach2"
|
1960 |
-
version = "0.4.2"
|
1961 |
-
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1962 |
-
checksum = "19b955cdeb2a02b9117f121ce63aa52d08ade45de53e48fe6a38b39c10f6f709"
|
1963 |
-
dependencies = [
|
1964 |
-
"libc",
|
1965 |
-
]
|
1966 |
-
|
1967 |
[[package]]
|
1968 |
name = "markup5ever"
|
1969 |
version = "0.8.1"
|
@@ -2073,12 +2059,12 @@ dependencies = [
|
|
2073 |
|
2074 |
[[package]]
|
2075 |
name = "mini-moka"
|
2076 |
-
version = "0.10.
|
2077 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2078 |
-
checksum = "
|
2079 |
dependencies = [
|
2080 |
"crossbeam-channel",
|
2081 |
-
"crossbeam-utils 0.8.
|
2082 |
"dashmap",
|
2083 |
"skeptic",
|
2084 |
"smallvec 1.13.1",
|
@@ -2099,22 +2085,18 @@ dependencies = [
|
|
2099 |
|
2100 |
[[package]]
|
2101 |
name = "miniz_oxide"
|
2102 |
-
version = "0.7.
|
2103 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2104 |
-
checksum = "
|
2105 |
dependencies = [
|
2106 |
"adler",
|
2107 |
]
|
2108 |
|
2109 |
[[package]]
|
2110 |
name = "mintex"
|
2111 |
-
version = "0.1.
|
2112 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2113 |
-
checksum = "
|
2114 |
-
dependencies = [
|
2115 |
-
"once_cell",
|
2116 |
-
"sys-info",
|
2117 |
-
]
|
2118 |
|
2119 |
[[package]]
|
2120 |
name = "mio"
|
@@ -2137,9 +2119,9 @@ dependencies = [
|
|
2137 |
|
2138 |
[[package]]
|
2139 |
name = "mio"
|
2140 |
-
version = "0.8.
|
2141 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2142 |
-
checksum = "
|
2143 |
dependencies = [
|
2144 |
"libc",
|
2145 |
"log",
|
@@ -2161,9 +2143,9 @@ dependencies = [
|
|
2161 |
|
2162 |
[[package]]
|
2163 |
name = "mlua"
|
2164 |
-
version = "0.9.
|
2165 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2166 |
-
checksum = "
|
2167 |
dependencies = [
|
2168 |
"bstr",
|
2169 |
"mlua-sys",
|
@@ -2174,9 +2156,9 @@ dependencies = [
|
|
2174 |
|
2175 |
[[package]]
|
2176 |
name = "mlua-sys"
|
2177 |
-
version = "0.
|
2178 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2179 |
-
checksum = "
|
2180 |
dependencies = [
|
2181 |
"cc",
|
2182 |
"cfg-if 1.0.0",
|
@@ -2238,11 +2220,17 @@ version = "0.3.0"
|
|
2238 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2239 |
checksum = "38bf9645c8b145698bb0b18a4637dcacbc421ea49bef2317e4fd8065a387cf21"
|
2240 |
|
|
|
|
|
|
|
|
|
|
|
|
|
2241 |
[[package]]
|
2242 |
name = "num-traits"
|
2243 |
-
version = "0.2.
|
2244 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2245 |
-
checksum = "
|
2246 |
dependencies = [
|
2247 |
"autocfg 1.1.0",
|
2248 |
]
|
@@ -2280,17 +2268,17 @@ checksum = "0ab1bc2a289d34bd04a330323ac98a1b4bc82c9d9fcb1e66b63caa84da26b575"
|
|
2280 |
|
2281 |
[[package]]
|
2282 |
name = "opaque-debug"
|
2283 |
-
version = "0.3.
|
2284 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2285 |
-
checksum = "
|
2286 |
|
2287 |
[[package]]
|
2288 |
name = "openssl"
|
2289 |
-
version = "0.10.
|
2290 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2291 |
-
checksum = "
|
2292 |
dependencies = [
|
2293 |
-
"bitflags 2.4.
|
2294 |
"cfg-if 1.0.0",
|
2295 |
"foreign-types",
|
2296 |
"libc",
|
@@ -2307,7 +2295,7 @@ checksum = "a948666b637a0f465e8564c73e89d4dde00d72d4d473cc972f390fc3dcee7d9c"
|
|
2307 |
dependencies = [
|
2308 |
"proc-macro2 1.0.78",
|
2309 |
"quote 1.0.35",
|
2310 |
-
"syn 2.0.
|
2311 |
]
|
2312 |
|
2313 |
[[package]]
|
@@ -2318,9 +2306,9 @@ checksum = "ff011a302c396a5197692431fc1948019154afc178baf7d8e37367442a4601cf"
|
|
2318 |
|
2319 |
[[package]]
|
2320 |
name = "openssl-sys"
|
2321 |
-
version = "0.9.
|
2322 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2323 |
-
checksum = "
|
2324 |
dependencies = [
|
2325 |
"cc",
|
2326 |
"libc",
|
@@ -2334,7 +2322,7 @@ version = "0.26.4"
|
|
2334 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2335 |
checksum = "05d74befe2d076330d9a58bf9ca2da424568724ab278adf15fb5718253133887"
|
2336 |
dependencies = [
|
2337 |
-
"bitflags 2.4.
|
2338 |
"cssparser 0.33.0",
|
2339 |
"fxhash",
|
2340 |
"log",
|
@@ -2518,7 +2506,7 @@ dependencies = [
|
|
2518 |
"phf_shared 0.11.2",
|
2519 |
"proc-macro2 1.0.78",
|
2520 |
"quote 1.0.35",
|
2521 |
-
"syn 2.0.
|
2522 |
]
|
2523 |
|
2524 |
[[package]]
|
@@ -2550,22 +2538,22 @@ dependencies = [
|
|
2550 |
|
2551 |
[[package]]
|
2552 |
name = "pin-project"
|
2553 |
-
version = "1.1.
|
2554 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2555 |
-
checksum = "
|
2556 |
dependencies = [
|
2557 |
"pin-project-internal",
|
2558 |
]
|
2559 |
|
2560 |
[[package]]
|
2561 |
name = "pin-project-internal"
|
2562 |
-
version = "1.1.
|
2563 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2564 |
-
checksum = "
|
2565 |
dependencies = [
|
2566 |
"proc-macro2 1.0.78",
|
2567 |
"quote 1.0.35",
|
2568 |
-
"syn 2.0.
|
2569 |
]
|
2570 |
|
2571 |
[[package]]
|
@@ -2582,9 +2570,9 @@ checksum = "8b870d8c151b6f2fb93e84a13146138f05d02ed11c7e7c54f8826aaaf7c9f184"
|
|
2582 |
|
2583 |
[[package]]
|
2584 |
name = "pkg-config"
|
2585 |
-
version = "0.3.
|
2586 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2587 |
-
checksum = "
|
2588 |
|
2589 |
[[package]]
|
2590 |
name = "poly1305"
|
@@ -2597,6 +2585,12 @@ dependencies = [
|
|
2597 |
"universal-hash",
|
2598 |
]
|
2599 |
|
|
|
|
|
|
|
|
|
|
|
|
|
2600 |
[[package]]
|
2601 |
name = "powerfmt"
|
2602 |
version = "0.2.0"
|
@@ -2669,24 +2663,23 @@ dependencies = [
|
|
2669 |
|
2670 |
[[package]]
|
2671 |
name = "pulldown-cmark"
|
2672 |
-
version = "0.9.
|
2673 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2674 |
-
checksum = "
|
2675 |
dependencies = [
|
2676 |
-
"bitflags
|
2677 |
"memchr",
|
2678 |
"unicase",
|
2679 |
]
|
2680 |
|
2681 |
[[package]]
|
2682 |
name = "quanta"
|
2683 |
-
version = "0.
|
2684 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2685 |
-
checksum = "
|
2686 |
dependencies = [
|
2687 |
-
"crossbeam-utils 0.8.
|
2688 |
"libc",
|
2689 |
-
"mach2",
|
2690 |
"once_cell",
|
2691 |
"raw-cpuid",
|
2692 |
"wasi 0.11.0+wasi-snapshot-preview1",
|
@@ -2850,11 +2843,11 @@ dependencies = [
|
|
2850 |
|
2851 |
[[package]]
|
2852 |
name = "raw-cpuid"
|
2853 |
-
version = "
|
2854 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2855 |
-
checksum = "
|
2856 |
dependencies = [
|
2857 |
-
"bitflags
|
2858 |
]
|
2859 |
|
2860 |
[[package]]
|
@@ -2882,7 +2875,7 @@ dependencies = [
|
|
2882 |
"percent-encoding 2.3.1",
|
2883 |
"pin-project-lite",
|
2884 |
"ryu",
|
2885 |
-
"tokio 1.
|
2886 |
"tokio-retry",
|
2887 |
"tokio-util",
|
2888 |
"url 2.5.0",
|
@@ -2905,9 +2898,9 @@ dependencies = [
|
|
2905 |
|
2906 |
[[package]]
|
2907 |
name = "regex"
|
2908 |
-
version = "1.10.
|
2909 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2910 |
-
checksum = "
|
2911 |
dependencies = [
|
2912 |
"aho-corasick 1.1.2",
|
2913 |
"memchr",
|
@@ -2917,9 +2910,9 @@ dependencies = [
|
|
2917 |
|
2918 |
[[package]]
|
2919 |
name = "regex-automata"
|
2920 |
-
version = "0.4.
|
2921 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2922 |
-
checksum = "
|
2923 |
dependencies = [
|
2924 |
"aho-corasick 1.1.2",
|
2925 |
"memchr",
|
@@ -2968,18 +2961,18 @@ dependencies = [
|
|
2968 |
|
2969 |
[[package]]
|
2970 |
name = "reqwest"
|
2971 |
-
version = "0.11.
|
2972 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2973 |
-
checksum = "
|
2974 |
dependencies = [
|
2975 |
"async-compression",
|
2976 |
-
"base64 0.21.
|
2977 |
"bytes 1.5.0",
|
2978 |
"encoding_rs",
|
2979 |
"futures-core",
|
2980 |
"futures-util",
|
2981 |
-
"h2 0.3.
|
2982 |
-
"http 0.2.
|
2983 |
"http-body 0.4.6",
|
2984 |
"hyper 0.14.28",
|
2985 |
"hyper-rustls",
|
@@ -2997,7 +2990,7 @@ dependencies = [
|
|
2997 |
"serde_urlencoded 0.7.1",
|
2998 |
"sync_wrapper",
|
2999 |
"system-configuration",
|
3000 |
-
"tokio 1.
|
3001 |
"tokio-rustls",
|
3002 |
"tokio-util",
|
3003 |
"tower-service",
|
@@ -3011,16 +3004,17 @@ dependencies = [
|
|
3011 |
|
3012 |
[[package]]
|
3013 |
name = "ring"
|
3014 |
-
version = "0.17.
|
3015 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3016 |
-
checksum = "
|
3017 |
dependencies = [
|
3018 |
"cc",
|
|
|
3019 |
"getrandom",
|
3020 |
"libc",
|
3021 |
"spin",
|
3022 |
"untrusted",
|
3023 |
-
"windows-sys 0.
|
3024 |
]
|
3025 |
|
3026 |
[[package]]
|
@@ -3050,7 +3044,7 @@ version = "0.4.0"
|
|
3050 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3051 |
checksum = "bfa0f585226d2e68097d4f95d113b15b83a82e819ab25717ec0590d9584ef366"
|
3052 |
dependencies = [
|
3053 |
-
"semver 1.0.
|
3054 |
]
|
3055 |
|
3056 |
[[package]]
|
@@ -3059,7 +3053,7 @@ version = "0.38.31"
|
|
3059 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3060 |
checksum = "6ea3e1a662af26cd7a3ba09c0297a31af215563ecf42817c98df621387f4e949"
|
3061 |
dependencies = [
|
3062 |
-
"bitflags 2.4.
|
3063 |
"errno",
|
3064 |
"libc",
|
3065 |
"linux-raw-sys",
|
@@ -3084,7 +3078,7 @@ version = "1.0.4"
|
|
3084 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3085 |
checksum = "1c74cae0a4cf6ccbbf5f359f08efdf8ee7e1dc532573bf0db71968cb56b1448c"
|
3086 |
dependencies = [
|
3087 |
-
"base64 0.21.
|
3088 |
]
|
3089 |
|
3090 |
[[package]]
|
@@ -3111,9 +3105,9 @@ dependencies = [
|
|
3111 |
|
3112 |
[[package]]
|
3113 |
name = "ryu"
|
3114 |
-
version = "1.0.
|
3115 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3116 |
-
checksum = "
|
3117 |
|
3118 |
[[package]]
|
3119 |
name = "same-file"
|
@@ -3145,7 +3139,7 @@ version = "0.18.1"
|
|
3145 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3146 |
checksum = "585480e3719b311b78a573db1c9d9c4c1f8010c2dee4cc59c2efe58ea4dbc3e1"
|
3147 |
dependencies = [
|
3148 |
-
"ahash
|
3149 |
"cssparser 0.31.2",
|
3150 |
"ego-tree",
|
3151 |
"html5ever 0.26.0",
|
@@ -3203,7 +3197,7 @@ version = "0.25.0"
|
|
3203 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3204 |
checksum = "4eb30575f3638fc8f6815f448d50cb1a2e255b0897985c8c59f4d37b72a07b06"
|
3205 |
dependencies = [
|
3206 |
-
"bitflags 2.4.
|
3207 |
"cssparser 0.31.2",
|
3208 |
"derive_more",
|
3209 |
"fxhash",
|
@@ -3227,9 +3221,9 @@ dependencies = [
|
|
3227 |
|
3228 |
[[package]]
|
3229 |
name = "semver"
|
3230 |
-
version = "1.0.
|
3231 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3232 |
-
checksum = "
|
3233 |
dependencies = [
|
3234 |
"serde",
|
3235 |
]
|
@@ -3242,29 +3236,29 @@ checksum = "388a1df253eca08550bef6c72392cfe7c30914bf41df5269b68cbd6ff8f570a3"
|
|
3242 |
|
3243 |
[[package]]
|
3244 |
name = "serde"
|
3245 |
-
version = "1.0.
|
3246 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3247 |
-
checksum = "
|
3248 |
dependencies = [
|
3249 |
"serde_derive",
|
3250 |
]
|
3251 |
|
3252 |
[[package]]
|
3253 |
name = "serde_derive"
|
3254 |
-
version = "1.0.
|
3255 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3256 |
-
checksum = "
|
3257 |
dependencies = [
|
3258 |
"proc-macro2 1.0.78",
|
3259 |
"quote 1.0.35",
|
3260 |
-
"syn 2.0.
|
3261 |
]
|
3262 |
|
3263 |
[[package]]
|
3264 |
name = "serde_json"
|
3265 |
-
version = "1.0.
|
3266 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3267 |
-
checksum = "
|
3268 |
dependencies = [
|
3269 |
"itoa 1.0.10",
|
3270 |
"ryu",
|
@@ -3380,12 +3374,12 @@ dependencies = [
|
|
3380 |
|
3381 |
[[package]]
|
3382 |
name = "socket2"
|
3383 |
-
version = "0.5.
|
3384 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3385 |
-
checksum = "
|
3386 |
dependencies = [
|
3387 |
"libc",
|
3388 |
-
"windows-sys 0.
|
3389 |
]
|
3390 |
|
3391 |
[[package]]
|
@@ -3394,6 +3388,15 @@ version = "0.9.8"
|
|
3394 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3395 |
checksum = "6980e8d7511241f8acf4aebddbb1ff938df5eebe98691418c4468d0b72a96a67"
|
3396 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
3397 |
[[package]]
|
3398 |
name = "stable_deref_trait"
|
3399 |
version = "1.2.0"
|
@@ -3499,9 +3502,9 @@ dependencies = [
|
|
3499 |
|
3500 |
[[package]]
|
3501 |
name = "syn"
|
3502 |
-
version = "2.0.
|
3503 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3504 |
-
checksum = "
|
3505 |
dependencies = [
|
3506 |
"proc-macro2 1.0.78",
|
3507 |
"quote 1.0.35",
|
@@ -3526,32 +3529,22 @@ dependencies = [
|
|
3526 |
"unicode-xid 0.2.4",
|
3527 |
]
|
3528 |
|
3529 |
-
[[package]]
|
3530 |
-
name = "sys-info"
|
3531 |
-
version = "0.9.1"
|
3532 |
-
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3533 |
-
checksum = "0b3a0d0aba8bf96a0e1ddfdc352fc53b3df7f39318c71854910c3c4b024ae52c"
|
3534 |
-
dependencies = [
|
3535 |
-
"cc",
|
3536 |
-
"libc",
|
3537 |
-
]
|
3538 |
-
|
3539 |
[[package]]
|
3540 |
name = "system-configuration"
|
3541 |
-
version = "0.
|
3542 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3543 |
-
checksum = "
|
3544 |
dependencies = [
|
3545 |
-
"bitflags
|
3546 |
"core-foundation",
|
3547 |
"system-configuration-sys",
|
3548 |
]
|
3549 |
|
3550 |
[[package]]
|
3551 |
name = "system-configuration-sys"
|
3552 |
-
version = "0.
|
3553 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3554 |
-
checksum = "
|
3555 |
dependencies = [
|
3556 |
"core-foundation-sys",
|
3557 |
"libc",
|
@@ -3605,12 +3598,13 @@ dependencies = [
|
|
3605 |
|
3606 |
[[package]]
|
3607 |
name = "time"
|
3608 |
-
version = "0.3.
|
3609 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3610 |
-
checksum = "
|
3611 |
dependencies = [
|
3612 |
"deranged",
|
3613 |
"itoa 1.0.10",
|
|
|
3614 |
"powerfmt",
|
3615 |
"serde",
|
3616 |
"time-core",
|
@@ -3625,10 +3619,11 @@ checksum = "ef927ca75afb808a4d64dd374f00a2adf8d0fcff8e7b184af886c3c87ec4a3f3"
|
|
3625 |
|
3626 |
[[package]]
|
3627 |
name = "time-macros"
|
3628 |
-
version = "0.2.
|
3629 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3630 |
-
checksum = "
|
3631 |
dependencies = [
|
|
|
3632 |
"time-core",
|
3633 |
]
|
3634 |
|
@@ -3678,14 +3673,14 @@ dependencies = [
|
|
3678 |
|
3679 |
[[package]]
|
3680 |
name = "tokio"
|
3681 |
-
version = "1.
|
3682 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3683 |
-
checksum = "
|
3684 |
dependencies = [
|
3685 |
"backtrace",
|
3686 |
"bytes 1.5.0",
|
3687 |
"libc",
|
3688 |
-
"mio 0.8.
|
3689 |
"num_cpus",
|
3690 |
"parking_lot 0.12.1",
|
3691 |
"pin-project-lite",
|
@@ -3745,7 +3740,7 @@ checksum = "5b8a1e28f2deaa14e508979454cb3a223b10b938b45af148bc0986de36f1923b"
|
|
3745 |
dependencies = [
|
3746 |
"proc-macro2 1.0.78",
|
3747 |
"quote 1.0.35",
|
3748 |
-
"syn 2.0.
|
3749 |
]
|
3750 |
|
3751 |
[[package]]
|
@@ -3775,7 +3770,7 @@ checksum = "7f57eb36ecbe0fc510036adff84824dd3c24bb781e21bfa67b69d556aa85214f"
|
|
3775 |
dependencies = [
|
3776 |
"pin-project",
|
3777 |
"rand 0.8.5",
|
3778 |
-
"tokio 1.
|
3779 |
]
|
3780 |
|
3781 |
[[package]]
|
@@ -3785,7 +3780,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
|
3785 |
checksum = "c28327cf380ac148141087fbfb9de9d7bd4e84ab5d2c28fbc911d753de8a7081"
|
3786 |
dependencies = [
|
3787 |
"rustls",
|
3788 |
-
"tokio 1.
|
3789 |
]
|
3790 |
|
3791 |
[[package]]
|
@@ -3851,7 +3846,7 @@ dependencies = [
|
|
3851 |
"futures-core",
|
3852 |
"futures-sink",
|
3853 |
"pin-project-lite",
|
3854 |
-
"tokio 1.
|
3855 |
"tracing",
|
3856 |
]
|
3857 |
|
@@ -3928,9 +3923,9 @@ dependencies = [
|
|
3928 |
|
3929 |
[[package]]
|
3930 |
name = "unicode-bidi"
|
3931 |
-
version = "0.3.
|
3932 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3933 |
-
checksum = "
|
3934 |
|
3935 |
[[package]]
|
3936 |
name = "unicode-ident"
|
@@ -3940,9 +3935,9 @@ checksum = "3354b9ac3fae1ff6755cb6db53683adb661634f67557942dea4facebec0fee4b"
|
|
3940 |
|
3941 |
[[package]]
|
3942 |
name = "unicode-normalization"
|
3943 |
-
version = "0.1.
|
3944 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3945 |
-
checksum = "
|
3946 |
dependencies = [
|
3947 |
"tinyvec",
|
3948 |
]
|
@@ -4038,9 +4033,9 @@ checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f"
|
|
4038 |
|
4039 |
[[package]]
|
4040 |
name = "walkdir"
|
4041 |
-
version = "2.
|
4042 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4043 |
-
checksum = "
|
4044 |
dependencies = [
|
4045 |
"same-file",
|
4046 |
"winapi-util",
|
@@ -4080,9 +4075,9 @@ checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423"
|
|
4080 |
|
4081 |
[[package]]
|
4082 |
name = "wasm-bindgen"
|
4083 |
-
version = "0.2.
|
4084 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4085 |
-
checksum = "
|
4086 |
dependencies = [
|
4087 |
"cfg-if 1.0.0",
|
4088 |
"wasm-bindgen-macro",
|
@@ -4090,24 +4085,24 @@ dependencies = [
|
|
4090 |
|
4091 |
[[package]]
|
4092 |
name = "wasm-bindgen-backend"
|
4093 |
-
version = "0.2.
|
4094 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4095 |
-
checksum = "
|
4096 |
dependencies = [
|
4097 |
"bumpalo",
|
4098 |
"log",
|
4099 |
"once_cell",
|
4100 |
"proc-macro2 1.0.78",
|
4101 |
"quote 1.0.35",
|
4102 |
-
"syn 2.0.
|
4103 |
"wasm-bindgen-shared",
|
4104 |
]
|
4105 |
|
4106 |
[[package]]
|
4107 |
name = "wasm-bindgen-futures"
|
4108 |
-
version = "0.4.
|
4109 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4110 |
-
checksum = "
|
4111 |
dependencies = [
|
4112 |
"cfg-if 1.0.0",
|
4113 |
"js-sys",
|
@@ -4117,9 +4112,9 @@ dependencies = [
|
|
4117 |
|
4118 |
[[package]]
|
4119 |
name = "wasm-bindgen-macro"
|
4120 |
-
version = "0.2.
|
4121 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4122 |
-
checksum = "
|
4123 |
dependencies = [
|
4124 |
"quote 1.0.35",
|
4125 |
"wasm-bindgen-macro-support",
|
@@ -4127,28 +4122,28 @@ dependencies = [
|
|
4127 |
|
4128 |
[[package]]
|
4129 |
name = "wasm-bindgen-macro-support"
|
4130 |
-
version = "0.2.
|
4131 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4132 |
-
checksum = "
|
4133 |
dependencies = [
|
4134 |
"proc-macro2 1.0.78",
|
4135 |
"quote 1.0.35",
|
4136 |
-
"syn 2.0.
|
4137 |
"wasm-bindgen-backend",
|
4138 |
"wasm-bindgen-shared",
|
4139 |
]
|
4140 |
|
4141 |
[[package]]
|
4142 |
name = "wasm-bindgen-shared"
|
4143 |
-
version = "0.2.
|
4144 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4145 |
-
checksum = "
|
4146 |
|
4147 |
[[package]]
|
4148 |
name = "web-sys"
|
4149 |
-
version = "0.3.
|
4150 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4151 |
-
checksum = "
|
4152 |
dependencies = [
|
4153 |
"js-sys",
|
4154 |
"wasm-bindgen",
|
@@ -4156,23 +4151,23 @@ dependencies = [
|
|
4156 |
|
4157 |
[[package]]
|
4158 |
name = "webpki-roots"
|
4159 |
-
version = "0.25.
|
4160 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4161 |
-
checksum = "
|
4162 |
|
4163 |
[[package]]
|
4164 |
name = "websurfx"
|
4165 |
-
version = "1.9
|
4166 |
dependencies = [
|
4167 |
"actix-cors",
|
4168 |
"actix-files",
|
4169 |
"actix-governor",
|
4170 |
"actix-web",
|
|
|
4171 |
"async-once-cell",
|
4172 |
"async-trait",
|
4173 |
-
"base64 0.21.
|
4174 |
"blake3",
|
4175 |
-
"brotli",
|
4176 |
"cfg-if 1.0.0",
|
4177 |
"chacha20",
|
4178 |
"chacha20poly1305",
|
@@ -4191,27 +4186,27 @@ dependencies = [
|
|
4191 |
"mlua",
|
4192 |
"redis",
|
4193 |
"regex",
|
4194 |
-
"reqwest 0.11.
|
4195 |
"rusty-hook",
|
4196 |
"scraper",
|
4197 |
"serde",
|
4198 |
"serde_json",
|
4199 |
"smallvec 1.13.1",
|
4200 |
"tempfile",
|
4201 |
-
"tokio 1.
|
4202 |
]
|
4203 |
|
4204 |
[[package]]
|
4205 |
name = "which"
|
4206 |
-
version = "
|
4207 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4208 |
-
checksum = "
|
4209 |
dependencies = [
|
4210 |
"either",
|
4211 |
"home",
|
4212 |
"once_cell",
|
4213 |
"rustix",
|
4214 |
-
"windows-sys 0.
|
4215 |
]
|
4216 |
|
4217 |
[[package]]
|
@@ -4272,7 +4267,7 @@ version = "0.52.0"
|
|
4272 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4273 |
checksum = "282be5f36a8ce781fad8c8ae18fa3f9beff57ec1b52cb3de0789201425d9a33d"
|
4274 |
dependencies = [
|
4275 |
-
"windows-targets 0.52.
|
4276 |
]
|
4277 |
|
4278 |
[[package]]
|
@@ -4292,17 +4287,17 @@ dependencies = [
|
|
4292 |
|
4293 |
[[package]]
|
4294 |
name = "windows-targets"
|
4295 |
-
version = "0.52.
|
4296 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4297 |
-
checksum = "
|
4298 |
dependencies = [
|
4299 |
-
"windows_aarch64_gnullvm 0.52.
|
4300 |
-
"windows_aarch64_msvc 0.52.
|
4301 |
-
"windows_i686_gnu 0.52.
|
4302 |
-
"windows_i686_msvc 0.52.
|
4303 |
-
"windows_x86_64_gnu 0.52.
|
4304 |
-
"windows_x86_64_gnullvm 0.52.
|
4305 |
-
"windows_x86_64_msvc 0.52.
|
4306 |
]
|
4307 |
|
4308 |
[[package]]
|
@@ -4313,9 +4308,9 @@ checksum = "2b38e32f0abccf9987a4e3079dfb67dcd799fb61361e53e2882c3cbaf0d905d8"
|
|
4313 |
|
4314 |
[[package]]
|
4315 |
name = "windows_aarch64_gnullvm"
|
4316 |
-
version = "0.52.
|
4317 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4318 |
-
checksum = "
|
4319 |
|
4320 |
[[package]]
|
4321 |
name = "windows_aarch64_msvc"
|
@@ -4325,9 +4320,9 @@ checksum = "dc35310971f3b2dbbf3f0690a219f40e2d9afcf64f9ab7cc1be722937c26b4bc"
|
|
4325 |
|
4326 |
[[package]]
|
4327 |
name = "windows_aarch64_msvc"
|
4328 |
-
version = "0.52.
|
4329 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4330 |
-
checksum = "
|
4331 |
|
4332 |
[[package]]
|
4333 |
name = "windows_i686_gnu"
|
@@ -4337,9 +4332,9 @@ checksum = "a75915e7def60c94dcef72200b9a8e58e5091744960da64ec734a6c6e9b3743e"
|
|
4337 |
|
4338 |
[[package]]
|
4339 |
name = "windows_i686_gnu"
|
4340 |
-
version = "0.52.
|
4341 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4342 |
-
checksum = "
|
4343 |
|
4344 |
[[package]]
|
4345 |
name = "windows_i686_msvc"
|
@@ -4349,9 +4344,9 @@ checksum = "8f55c233f70c4b27f66c523580f78f1004e8b5a8b659e05a4eb49d4166cca406"
|
|
4349 |
|
4350 |
[[package]]
|
4351 |
name = "windows_i686_msvc"
|
4352 |
-
version = "0.52.
|
4353 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4354 |
-
checksum = "
|
4355 |
|
4356 |
[[package]]
|
4357 |
name = "windows_x86_64_gnu"
|
@@ -4361,9 +4356,9 @@ checksum = "53d40abd2583d23e4718fddf1ebec84dbff8381c07cae67ff7768bbf19c6718e"
|
|
4361 |
|
4362 |
[[package]]
|
4363 |
name = "windows_x86_64_gnu"
|
4364 |
-
version = "0.52.
|
4365 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4366 |
-
checksum = "
|
4367 |
|
4368 |
[[package]]
|
4369 |
name = "windows_x86_64_gnullvm"
|
@@ -4373,9 +4368,9 @@ checksum = "0b7b52767868a23d5bab768e390dc5f5c55825b6d30b86c844ff2dc7414044cc"
|
|
4373 |
|
4374 |
[[package]]
|
4375 |
name = "windows_x86_64_gnullvm"
|
4376 |
-
version = "0.52.
|
4377 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4378 |
-
checksum = "
|
4379 |
|
4380 |
[[package]]
|
4381 |
name = "windows_x86_64_msvc"
|
@@ -4385,9 +4380,9 @@ checksum = "ed94fce61571a4006852b7389a063ab983c02eb1bb37b47f8272ce92d06d9538"
|
|
4385 |
|
4386 |
[[package]]
|
4387 |
name = "windows_x86_64_msvc"
|
4388 |
-
version = "0.52.
|
4389 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4390 |
-
checksum = "
|
4391 |
|
4392 |
[[package]]
|
4393 |
name = "winreg"
|
@@ -4435,7 +4430,7 @@ checksum = "9ce1b18ccd8e73a9321186f97e46f9f04b778851177567b1975109d26a08d2a6"
|
|
4435 |
dependencies = [
|
4436 |
"proc-macro2 1.0.78",
|
4437 |
"quote 1.0.35",
|
4438 |
-
"syn 2.0.
|
4439 |
]
|
4440 |
|
4441 |
[[package]]
|
|
|
4 |
|
5 |
[[package]]
|
6 |
name = "actix-codec"
|
7 |
+
version = "0.5.2"
|
8 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
9 |
+
checksum = "5f7b0a21988c1bf877cf4759ef5ddaac04c1c9fe808c9142ecb78ba97d97a28a"
|
10 |
dependencies = [
|
11 |
+
"bitflags 2.4.2",
|
12 |
"bytes 1.5.0",
|
13 |
"futures-core",
|
14 |
"futures-sink",
|
15 |
"memchr",
|
16 |
"pin-project-lite",
|
17 |
+
"tokio 1.36.0",
|
18 |
"tokio-util",
|
19 |
"tracing",
|
20 |
]
|
|
|
44 |
"actix-service",
|
45 |
"actix-utils",
|
46 |
"actix-web",
|
47 |
+
"bitflags 2.4.2",
|
48 |
"bytes 1.5.0",
|
49 |
"derive_more",
|
50 |
"futures-core",
|
|
|
71 |
|
72 |
[[package]]
|
73 |
name = "actix-http"
|
74 |
+
version = "3.6.0"
|
75 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
76 |
+
checksum = "d223b13fd481fc0d1f83bb12659ae774d9e3601814c68a0bc539731698cca743"
|
77 |
dependencies = [
|
78 |
"actix-codec",
|
79 |
"actix-rt",
|
80 |
"actix-service",
|
81 |
"actix-utils",
|
82 |
+
"ahash",
|
83 |
+
"base64 0.21.7",
|
84 |
+
"bitflags 2.4.2",
|
85 |
"brotli",
|
86 |
"bytes 1.5.0",
|
87 |
"bytestring",
|
88 |
"derive_more",
|
89 |
"encoding_rs",
|
90 |
"futures-core",
|
91 |
+
"http 0.2.12",
|
92 |
"httparse",
|
93 |
"httpdate",
|
94 |
"itoa 1.0.10",
|
|
|
100 |
"rand 0.8.5",
|
101 |
"sha1",
|
102 |
"smallvec 1.13.1",
|
103 |
+
"tokio 1.36.0",
|
104 |
"tokio-util",
|
105 |
"tracing",
|
106 |
]
|
|
|
112 |
checksum = "e01ed3140b2f8d422c68afa1ed2e85d996ea619c988ac834d255db32138655cb"
|
113 |
dependencies = [
|
114 |
"quote 1.0.35",
|
115 |
+
"syn 2.0.52",
|
116 |
]
|
117 |
|
118 |
[[package]]
|
|
|
122 |
checksum = "d22475596539443685426b6bdadb926ad0ecaefdfc5fb05e5e3441f15463c511"
|
123 |
dependencies = [
|
124 |
"bytestring",
|
125 |
+
"http 0.2.12",
|
126 |
"regex",
|
127 |
"serde",
|
128 |
"tracing",
|
|
|
135 |
checksum = "28f32d40287d3f402ae0028a9d54bef51af15c8769492826a69d28f81893151d"
|
136 |
dependencies = [
|
137 |
"futures-core",
|
138 |
+
"tokio 1.36.0",
|
139 |
]
|
140 |
|
141 |
[[package]]
|
|
|
149 |
"actix-utils",
|
150 |
"futures-core",
|
151 |
"futures-util",
|
152 |
+
"mio 0.8.11",
|
153 |
"socket2",
|
154 |
+
"tokio 1.36.0",
|
155 |
"tracing",
|
156 |
]
|
157 |
|
|
|
178 |
|
179 |
[[package]]
|
180 |
name = "actix-web"
|
181 |
+
version = "4.5.1"
|
182 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
183 |
+
checksum = "43a6556ddebb638c2358714d853257ed226ece6023ef9364f23f0c70737ea984"
|
184 |
dependencies = [
|
185 |
"actix-codec",
|
186 |
"actix-http",
|
|
|
191 |
"actix-service",
|
192 |
"actix-utils",
|
193 |
"actix-web-codegen",
|
194 |
+
"ahash",
|
195 |
"bytes 1.5.0",
|
196 |
"bytestring",
|
197 |
"cfg-if 1.0.0",
|
|
|
212 |
"serde_urlencoded 0.7.1",
|
213 |
"smallvec 1.13.1",
|
214 |
"socket2",
|
215 |
+
"time 0.3.34",
|
216 |
"url 2.5.0",
|
217 |
]
|
218 |
|
|
|
225 |
"actix-router",
|
226 |
"proc-macro2 1.0.78",
|
227 |
"quote 1.0.35",
|
228 |
+
"syn 2.0.52",
|
229 |
]
|
230 |
|
231 |
[[package]]
|
|
|
255 |
|
256 |
[[package]]
|
257 |
name = "ahash"
|
258 |
+
version = "0.8.11"
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
259 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
260 |
+
checksum = "e89da841a80418a9b391ebaea17f5c112ffaaa96f621d2c285b5174da76b9011"
|
261 |
dependencies = [
|
262 |
"cfg-if 1.0.0",
|
263 |
"getrandom",
|
|
|
307 |
|
308 |
[[package]]
|
309 |
name = "anstyle"
|
310 |
+
version = "1.0.6"
|
311 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
312 |
+
checksum = "8901269c6307e8d93993578286ac0edf7f195079ffff5ebdeea6a59ffb7e36bc"
|
313 |
|
314 |
[[package]]
|
315 |
name = "anyhow"
|
316 |
+
version = "1.0.80"
|
317 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
318 |
+
checksum = "5ad32ce52e4161730f7098c077cd2ed6229b5804ccf99e5366be1ab72a98b4e1"
|
319 |
|
320 |
[[package]]
|
321 |
name = "arc-swap"
|
322 |
+
version = "1.7.0"
|
323 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
324 |
+
checksum = "7b3d0060af21e8d11a926981cc00c6c1541aa91dd64b9f881985c3da1094425f"
|
325 |
|
326 |
[[package]]
|
327 |
name = "arrayref"
|
|
|
337 |
|
338 |
[[package]]
|
339 |
name = "async-compression"
|
340 |
+
version = "0.4.6"
|
341 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
342 |
+
checksum = "a116f46a969224200a0a97f29cfd4c50e7534e4b4826bd23ea2c3c533039c82c"
|
343 |
dependencies = [
|
344 |
"brotli",
|
345 |
"flate2",
|
346 |
"futures-core",
|
347 |
"memchr",
|
348 |
"pin-project-lite",
|
349 |
+
"tokio 1.36.0",
|
350 |
]
|
351 |
|
352 |
[[package]]
|
|
|
357 |
|
358 |
[[package]]
|
359 |
name = "async-trait"
|
360 |
+
version = "0.1.77"
|
361 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
362 |
+
checksum = "c980ee35e870bd1a4d2c8294d4c04d0499e67bca1e4b5cefcc693c2fa00caea9"
|
363 |
dependencies = [
|
364 |
"proc-macro2 1.0.78",
|
365 |
"quote 1.0.35",
|
366 |
+
"syn 2.0.52",
|
367 |
]
|
368 |
|
369 |
[[package]]
|
|
|
407 |
|
408 |
[[package]]
|
409 |
name = "base64"
|
410 |
+
version = "0.21.7"
|
411 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
412 |
+
checksum = "9d297deb1925b89f2ccc13d7635fa0714f12c87adce1c75356b39ca9b7178567"
|
413 |
|
414 |
[[package]]
|
415 |
name = "bit-set"
|
|
|
434 |
|
435 |
[[package]]
|
436 |
name = "bitflags"
|
437 |
+
version = "2.4.2"
|
438 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
439 |
+
checksum = "ed570934406eb16438a4e976b1b4500774099c13b8cb96eec99f620f05090ddf"
|
440 |
|
441 |
[[package]]
|
442 |
name = "blake3"
|
|
|
483 |
|
484 |
[[package]]
|
485 |
name = "bstr"
|
486 |
+
version = "1.9.1"
|
487 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
488 |
+
checksum = "05efc5cfd9110c8416e471df0e96702d58690178e206e61b7173706673c93706"
|
489 |
dependencies = [
|
490 |
"memchr",
|
491 |
"serde",
|
|
|
493 |
|
494 |
[[package]]
|
495 |
name = "bumpalo"
|
496 |
+
version = "3.15.4"
|
497 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
498 |
+
checksum = "7ff69b9dd49fd426c69a0db9fc04dd934cdb6645ff000864d98f7e2af8830eaa"
|
499 |
|
500 |
[[package]]
|
501 |
name = "bytecount"
|
|
|
546 |
|
547 |
[[package]]
|
548 |
name = "cargo-platform"
|
549 |
+
version = "0.1.7"
|
550 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
551 |
+
checksum = "694c8807f2ae16faecc43dc17d74b3eb042482789fd0eb64b39a2e04e087053f"
|
552 |
dependencies = [
|
553 |
"serde",
|
554 |
]
|
|
|
561 |
dependencies = [
|
562 |
"camino",
|
563 |
"cargo-platform",
|
564 |
+
"semver 1.0.22",
|
565 |
"serde",
|
566 |
"serde_json",
|
567 |
]
|
|
|
574 |
|
575 |
[[package]]
|
576 |
name = "cc"
|
577 |
+
version = "1.0.90"
|
578 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
579 |
+
checksum = "8cd6604a82acf3039f1144f54b8eb34e91ffba622051189e71b781822d5ee1f5"
|
|
|
|
|
|
|
580 |
|
581 |
[[package]]
|
582 |
name = "cfg-if"
|
|
|
625 |
|
626 |
[[package]]
|
627 |
name = "ciborium"
|
628 |
+
version = "0.2.2"
|
629 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
630 |
+
checksum = "42e69ffd6f0917f5c029256a24d0161db17cea3997d185db0d35926308770f0e"
|
631 |
dependencies = [
|
632 |
"ciborium-io",
|
633 |
"ciborium-ll",
|
|
|
636 |
|
637 |
[[package]]
|
638 |
name = "ciborium-io"
|
639 |
+
version = "0.2.2"
|
640 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
641 |
+
checksum = "05afea1e0a06c9be33d539b876f1ce3692f4afea2cb41f740e7743225ed1c757"
|
642 |
|
643 |
[[package]]
|
644 |
name = "ciborium-ll"
|
645 |
+
version = "0.2.2"
|
646 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
647 |
+
checksum = "57663b653d948a338bfb3eeba9bb2fd5fcfaecb9e199e87e1eda4d9e8b240fd9"
|
648 |
dependencies = [
|
649 |
"ciborium-io",
|
650 |
"half",
|
|
|
663 |
|
664 |
[[package]]
|
665 |
name = "clap"
|
666 |
+
version = "4.5.2"
|
667 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
668 |
+
checksum = "b230ab84b0ffdf890d5a10abdbc8b83ae1c4918275daea1ab8801f71536b2651"
|
669 |
dependencies = [
|
670 |
"clap_builder",
|
671 |
]
|
672 |
|
673 |
[[package]]
|
674 |
name = "clap_builder"
|
675 |
+
version = "4.5.2"
|
676 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
677 |
+
checksum = "ae129e2e766ae0ec03484e609954119f123cc1fe650337e155d03b022f24f7b4"
|
678 |
dependencies = [
|
679 |
"anstyle",
|
680 |
"clap_lex",
|
|
|
682 |
|
683 |
[[package]]
|
684 |
name = "clap_lex"
|
685 |
+
version = "0.7.0"
|
686 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
687 |
+
checksum = "98cc8fbded0c607b7ba9dd60cd98df59af97e84d24e49c8557331cfc26d301ce"
|
688 |
|
689 |
[[package]]
|
690 |
name = "cloudabi"
|
|
|
705 |
"futures-core",
|
706 |
"memchr",
|
707 |
"pin-project-lite",
|
708 |
+
"tokio 1.36.0",
|
709 |
"tokio-util",
|
710 |
]
|
711 |
|
|
|
758 |
checksum = "e859cd57d0710d9e06c381b550c06e76992472a8c6d527aecd2fc673dcc231fb"
|
759 |
dependencies = [
|
760 |
"percent-encoding 2.3.1",
|
761 |
+
"time 0.3.34",
|
762 |
"version_check",
|
763 |
]
|
764 |
|
|
|
798 |
|
799 |
[[package]]
|
800 |
name = "cpufeatures"
|
801 |
+
version = "0.2.12"
|
802 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
803 |
+
checksum = "53fe5e26ff1b7aef8bca9c6080520cfb8d9333c7568e1829cef191a9723e5504"
|
804 |
dependencies = [
|
805 |
"libc",
|
806 |
]
|
807 |
|
808 |
[[package]]
|
809 |
name = "crc32fast"
|
810 |
+
version = "1.4.0"
|
811 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
812 |
+
checksum = "b3855a8a784b474f333699ef2bbca9db2c4a1f6d9088a90a2d25b1eb53111eaa"
|
813 |
dependencies = [
|
814 |
"cfg-if 1.0.0",
|
815 |
]
|
|
|
850 |
|
851 |
[[package]]
|
852 |
name = "crossbeam-channel"
|
853 |
+
version = "0.5.12"
|
854 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
855 |
+
checksum = "ab3db02a9c5b5121e1e42fbdb1aeb65f5e02624cc58c43f2884c6ccac0b82f95"
|
856 |
dependencies = [
|
857 |
+
"crossbeam-utils 0.8.19",
|
|
|
858 |
]
|
859 |
|
860 |
[[package]]
|
|
|
907 |
|
908 |
[[package]]
|
909 |
name = "crossbeam-utils"
|
910 |
+
version = "0.8.19"
|
911 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
912 |
+
checksum = "248e3bacc7dc6baa3b21e405ee045c3047101a49145e7e9eca583ab4c2ca5345"
|
913 |
+
|
914 |
+
[[package]]
|
915 |
+
name = "crunchy"
|
916 |
+
version = "0.2.2"
|
917 |
+
source = "registry+https://github.com/rust-lang/crates.io-index"
|
918 |
+
checksum = "7a81dae078cea95a014a339291cec439d2f232ebe854a9d672b796c6afafa9b7"
|
919 |
|
920 |
[[package]]
|
921 |
name = "crypto-common"
|
|
|
970 |
checksum = "13b588ba4ac1a99f7f2964d24b3d896ddc6bf847ee3855dbd4366f058cfcd331"
|
971 |
dependencies = [
|
972 |
"quote 1.0.35",
|
973 |
+
"syn 2.0.52",
|
974 |
]
|
975 |
|
976 |
[[package]]
|
|
|
994 |
|
995 |
[[package]]
|
996 |
name = "deranged"
|
997 |
+
version = "0.3.11"
|
998 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
999 |
+
checksum = "b42b6fa04a440b495c8b04d0e71b707c585f83cb9cb28cf8cd0d976c315e31b4"
|
1000 |
dependencies = [
|
1001 |
"powerfmt",
|
1002 |
]
|
|
|
1069 |
|
1070 |
[[package]]
|
1071 |
name = "either"
|
1072 |
+
version = "1.10.0"
|
1073 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1074 |
+
checksum = "11157ac094ffbdde99aa67b23417ebdd801842852b500e395a45a9c0aac03e4a"
|
1075 |
|
1076 |
[[package]]
|
1077 |
name = "encoding_rs"
|
|
|
1093 |
|
1094 |
[[package]]
|
1095 |
name = "env_logger"
|
1096 |
+
version = "0.11.3"
|
1097 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1098 |
+
checksum = "38b35839ba51819680ba087cd351788c9a3c476841207e0b8cee0b04722343b9"
|
1099 |
dependencies = [
|
1100 |
"env_filter",
|
1101 |
"log",
|
|
|
1335 |
dependencies = [
|
1336 |
"proc-macro2 1.0.78",
|
1337 |
"quote 1.0.35",
|
1338 |
+
"syn 2.0.52",
|
1339 |
]
|
1340 |
|
1341 |
[[package]]
|
|
|
1352 |
|
1353 |
[[package]]
|
1354 |
name = "futures-timer"
|
1355 |
+
version = "3.0.3"
|
1356 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1357 |
+
checksum = "f288b0a4f20f9a56b5d1da57e2227c661b7b16168e2f72365f57b63326e29b24"
|
1358 |
|
1359 |
[[package]]
|
1360 |
name = "futures-util"
|
|
|
1404 |
|
1405 |
[[package]]
|
1406 |
name = "getrandom"
|
1407 |
+
version = "0.2.12"
|
1408 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1409 |
+
checksum = "190092ea657667030ac6a35e305e62fc4dd69fd98ac98631e5d3a2b1575a12b5"
|
1410 |
dependencies = [
|
1411 |
"cfg-if 1.0.0",
|
1412 |
"libc",
|
|
|
1427 |
|
1428 |
[[package]]
|
1429 |
name = "governor"
|
1430 |
+
version = "0.6.3"
|
1431 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1432 |
+
checksum = "68a7f542ee6b35af73b06abc0dad1c1bae89964e4e253bc4b587b91c9637867b"
|
1433 |
dependencies = [
|
1434 |
"cfg-if 1.0.0",
|
1435 |
"dashmap",
|
|
|
1438 |
"no-std-compat",
|
1439 |
"nonzero_ext",
|
1440 |
"parking_lot 0.12.1",
|
1441 |
+
"portable-atomic",
|
1442 |
"quanta",
|
1443 |
"rand 0.8.5",
|
1444 |
"smallvec 1.13.1",
|
1445 |
+
"spinning_top",
|
1446 |
]
|
1447 |
|
1448 |
[[package]]
|
|
|
1465 |
|
1466 |
[[package]]
|
1467 |
name = "h2"
|
1468 |
+
version = "0.3.24"
|
1469 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1470 |
+
checksum = "bb2c4422095b67ee78da96fbb51a4cc413b3b25883c7717ff7ca1ab31022c9c9"
|
1471 |
dependencies = [
|
1472 |
"bytes 1.5.0",
|
1473 |
"fnv",
|
1474 |
"futures-core",
|
1475 |
"futures-sink",
|
1476 |
"futures-util",
|
1477 |
+
"http 0.2.12",
|
1478 |
+
"indexmap 2.2.5",
|
1479 |
"slab",
|
1480 |
+
"tokio 1.36.0",
|
1481 |
"tokio-util",
|
1482 |
"tracing",
|
1483 |
]
|
1484 |
|
1485 |
[[package]]
|
1486 |
name = "half"
|
1487 |
+
version = "2.4.0"
|
1488 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1489 |
+
checksum = "b5eceaaeec696539ddaf7b333340f1af35a5aa87ae3e4f3ead0532f72affab2e"
|
1490 |
+
dependencies = [
|
1491 |
+
"cfg-if 1.0.0",
|
1492 |
+
"crunchy",
|
1493 |
+
]
|
1494 |
|
1495 |
[[package]]
|
1496 |
name = "hashbrown"
|
|
|
1504 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1505 |
checksum = "43a3c133739dddd0d2990f9a4bdf8eb4b21ef50e4851ca85ab661199821d510e"
|
1506 |
dependencies = [
|
1507 |
+
"ahash",
|
1508 |
"bumpalo",
|
1509 |
]
|
1510 |
|
|
|
1516 |
|
1517 |
[[package]]
|
1518 |
name = "hermit-abi"
|
1519 |
+
version = "0.3.9"
|
1520 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1521 |
+
checksum = "d231dfb89cfffdbc30e7fc41579ed6066ad03abda9e567ccafae602b97ec5024"
|
1522 |
|
1523 |
[[package]]
|
1524 |
name = "home"
|
|
|
1570 |
|
1571 |
[[package]]
|
1572 |
name = "http"
|
1573 |
+
version = "0.2.12"
|
1574 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1575 |
+
checksum = "601cbb57e577e2f5ef5be8e7b83f0f63994f25aa94d673e54a92d5c516d101f1"
|
1576 |
dependencies = [
|
1577 |
"bytes 1.5.0",
|
1578 |
"fnv",
|
|
|
1598 |
checksum = "7ceab25649e9960c0311ea418d17bee82c0dcec1bd053b5f9a66e265a693bed2"
|
1599 |
dependencies = [
|
1600 |
"bytes 1.5.0",
|
1601 |
+
"http 0.2.12",
|
1602 |
"pin-project-lite",
|
1603 |
]
|
1604 |
|
|
|
1660 |
"futures-channel",
|
1661 |
"futures-core",
|
1662 |
"futures-util",
|
1663 |
+
"h2 0.3.24",
|
1664 |
+
"http 0.2.12",
|
1665 |
"http-body 0.4.6",
|
1666 |
"httparse",
|
1667 |
"httpdate",
|
1668 |
"itoa 1.0.10",
|
1669 |
"pin-project-lite",
|
1670 |
"socket2",
|
1671 |
+
"tokio 1.36.0",
|
1672 |
"tower-service",
|
1673 |
"tracing",
|
1674 |
"want 0.3.1",
|
|
|
1681 |
checksum = "ec3efd23720e2049821a693cbc7e65ea87c72f1c58ff2f9522ff332b1491e590"
|
1682 |
dependencies = [
|
1683 |
"futures-util",
|
1684 |
+
"http 0.2.12",
|
1685 |
"hyper 0.14.28",
|
1686 |
"rustls",
|
1687 |
+
"tokio 1.36.0",
|
1688 |
"tokio-rustls",
|
1689 |
]
|
1690 |
|
|
|
1745 |
|
1746 |
[[package]]
|
1747 |
name = "indexmap"
|
1748 |
+
version = "2.2.5"
|
1749 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1750 |
+
checksum = "7b0b929d511467233429c45a44ac1dcaa21ba0f5ba11e4879e6ed28ddb4f9df4"
|
1751 |
dependencies = [
|
1752 |
"equivalent",
|
1753 |
"hashbrown 0.14.3",
|
|
|
1779 |
|
1780 |
[[package]]
|
1781 |
name = "is-terminal"
|
1782 |
+
version = "0.4.12"
|
1783 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1784 |
+
checksum = "f23ff5ef2b80d608d61efee834934d862cd92461afc0560dedf493e4c033738b"
|
1785 |
dependencies = [
|
1786 |
"hermit-abi",
|
1787 |
+
"libc",
|
1788 |
"windows-sys 0.52.0",
|
1789 |
]
|
1790 |
|
|
|
1811 |
|
1812 |
[[package]]
|
1813 |
name = "js-sys"
|
1814 |
+
version = "0.3.69"
|
1815 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1816 |
+
checksum = "29c15563dc2726973df627357ce0c9ddddbea194836909d655df6a75d2cf296d"
|
1817 |
dependencies = [
|
1818 |
"wasm-bindgen",
|
1819 |
]
|
|
|
1858 |
|
1859 |
[[package]]
|
1860 |
name = "lightningcss"
|
1861 |
+
version = "1.0.0-alpha.54"
|
1862 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1863 |
+
checksum = "07d306844e5af1753490c420c0d6ae3d814b00725092d106332762827ca8f0fe"
|
1864 |
dependencies = [
|
1865 |
+
"ahash",
|
1866 |
+
"bitflags 2.4.2",
|
1867 |
"const-str",
|
1868 |
"cssparser 0.33.0",
|
1869 |
"cssparser-color",
|
1870 |
"data-encoding",
|
1871 |
+
"getrandom",
|
1872 |
"itertools",
|
1873 |
"lazy_static",
|
1874 |
"parcel_selectors",
|
|
|
1879 |
|
1880 |
[[package]]
|
1881 |
name = "linux-raw-sys"
|
1882 |
+
version = "0.4.13"
|
1883 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1884 |
+
checksum = "01cda141df6706de531b6c46c3a33ecca755538219bd484262fa09410c13539c"
|
1885 |
|
1886 |
[[package]]
|
1887 |
name = "local-channel"
|
|
|
1936 |
|
1937 |
[[package]]
|
1938 |
name = "luajit-src"
|
1939 |
+
version = "210.5.6+9cc2e42"
|
1940 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1941 |
+
checksum = "23b365d859c9ffc187f48bb3e25ec80c3b40cf3f68f53544f4adeaee70554157"
|
1942 |
dependencies = [
|
1943 |
"cc",
|
1944 |
"which",
|
|
|
1950 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
1951 |
checksum = "c41e0c4fef86961ac6d6f8a82609f55f31b05e4fce149ac5710e439df7619ba4"
|
1952 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1953 |
[[package]]
|
1954 |
name = "markup5ever"
|
1955 |
version = "0.8.1"
|
|
|
2059 |
|
2060 |
[[package]]
|
2061 |
name = "mini-moka"
|
2062 |
+
version = "0.10.3"
|
2063 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2064 |
+
checksum = "c325dfab65f261f386debee8b0969da215b3fa0037e74c8a1234db7ba986d803"
|
2065 |
dependencies = [
|
2066 |
"crossbeam-channel",
|
2067 |
+
"crossbeam-utils 0.8.19",
|
2068 |
"dashmap",
|
2069 |
"skeptic",
|
2070 |
"smallvec 1.13.1",
|
|
|
2085 |
|
2086 |
[[package]]
|
2087 |
name = "miniz_oxide"
|
2088 |
+
version = "0.7.2"
|
2089 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2090 |
+
checksum = "9d811f3e15f28568be3407c8e7fdb6514c1cda3cb30683f15b6a1a1dc4ea14a7"
|
2091 |
dependencies = [
|
2092 |
"adler",
|
2093 |
]
|
2094 |
|
2095 |
[[package]]
|
2096 |
name = "mintex"
|
2097 |
+
version = "0.1.3"
|
2098 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2099 |
+
checksum = "9bec4598fddb13cc7b528819e697852653252b760f1228b7642679bf2ff2cd07"
|
|
|
|
|
|
|
|
|
2100 |
|
2101 |
[[package]]
|
2102 |
name = "mio"
|
|
|
2119 |
|
2120 |
[[package]]
|
2121 |
name = "mio"
|
2122 |
+
version = "0.8.11"
|
2123 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2124 |
+
checksum = "a4a650543ca06a924e8b371db273b2756685faae30f8487da1b56505a8f78b0c"
|
2125 |
dependencies = [
|
2126 |
"libc",
|
2127 |
"log",
|
|
|
2143 |
|
2144 |
[[package]]
|
2145 |
name = "mlua"
|
2146 |
+
version = "0.9.6"
|
2147 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2148 |
+
checksum = "868d02cb5eb97761bbf6bd6922c1c7a88b8ea252bbf43bd8350a0bf8497a1fc0"
|
2149 |
dependencies = [
|
2150 |
"bstr",
|
2151 |
"mlua-sys",
|
|
|
2156 |
|
2157 |
[[package]]
|
2158 |
name = "mlua-sys"
|
2159 |
+
version = "0.5.1"
|
2160 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2161 |
+
checksum = "2847b42764435201d8cbee1f517edb79c4cca4181877b90047587c89e1b7bce4"
|
2162 |
dependencies = [
|
2163 |
"cc",
|
2164 |
"cfg-if 1.0.0",
|
|
|
2220 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2221 |
checksum = "38bf9645c8b145698bb0b18a4637dcacbc421ea49bef2317e4fd8065a387cf21"
|
2222 |
|
2223 |
+
[[package]]
|
2224 |
+
name = "num-conv"
|
2225 |
+
version = "0.1.0"
|
2226 |
+
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2227 |
+
checksum = "51d515d32fb182ee37cda2ccdcb92950d6a3c2893aa280e540671c2cd0f3b1d9"
|
2228 |
+
|
2229 |
[[package]]
|
2230 |
name = "num-traits"
|
2231 |
+
version = "0.2.18"
|
2232 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2233 |
+
checksum = "da0df0e5185db44f69b44f26786fe401b6c293d1907744beaa7fa62b2e5a517a"
|
2234 |
dependencies = [
|
2235 |
"autocfg 1.1.0",
|
2236 |
]
|
|
|
2268 |
|
2269 |
[[package]]
|
2270 |
name = "opaque-debug"
|
2271 |
+
version = "0.3.1"
|
2272 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2273 |
+
checksum = "c08d65885ee38876c4f86fa503fb49d7b507c2b62552df7c70b2fce627e06381"
|
2274 |
|
2275 |
[[package]]
|
2276 |
name = "openssl"
|
2277 |
+
version = "0.10.64"
|
2278 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2279 |
+
checksum = "95a0481286a310808298130d22dd1fef0fa571e05a8f44ec801801e84b216b1f"
|
2280 |
dependencies = [
|
2281 |
+
"bitflags 2.4.2",
|
2282 |
"cfg-if 1.0.0",
|
2283 |
"foreign-types",
|
2284 |
"libc",
|
|
|
2295 |
dependencies = [
|
2296 |
"proc-macro2 1.0.78",
|
2297 |
"quote 1.0.35",
|
2298 |
+
"syn 2.0.52",
|
2299 |
]
|
2300 |
|
2301 |
[[package]]
|
|
|
2306 |
|
2307 |
[[package]]
|
2308 |
name = "openssl-sys"
|
2309 |
+
version = "0.9.101"
|
2310 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2311 |
+
checksum = "dda2b0f344e78efc2facf7d195d098df0dd72151b26ab98da807afc26c198dff"
|
2312 |
dependencies = [
|
2313 |
"cc",
|
2314 |
"libc",
|
|
|
2322 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2323 |
checksum = "05d74befe2d076330d9a58bf9ca2da424568724ab278adf15fb5718253133887"
|
2324 |
dependencies = [
|
2325 |
+
"bitflags 2.4.2",
|
2326 |
"cssparser 0.33.0",
|
2327 |
"fxhash",
|
2328 |
"log",
|
|
|
2506 |
"phf_shared 0.11.2",
|
2507 |
"proc-macro2 1.0.78",
|
2508 |
"quote 1.0.35",
|
2509 |
+
"syn 2.0.52",
|
2510 |
]
|
2511 |
|
2512 |
[[package]]
|
|
|
2538 |
|
2539 |
[[package]]
|
2540 |
name = "pin-project"
|
2541 |
+
version = "1.1.5"
|
2542 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2543 |
+
checksum = "b6bf43b791c5b9e34c3d182969b4abb522f9343702850a2e57f460d00d09b4b3"
|
2544 |
dependencies = [
|
2545 |
"pin-project-internal",
|
2546 |
]
|
2547 |
|
2548 |
[[package]]
|
2549 |
name = "pin-project-internal"
|
2550 |
+
version = "1.1.5"
|
2551 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2552 |
+
checksum = "2f38a4412a78282e09a2cf38d195ea5420d15ba0602cb375210efbc877243965"
|
2553 |
dependencies = [
|
2554 |
"proc-macro2 1.0.78",
|
2555 |
"quote 1.0.35",
|
2556 |
+
"syn 2.0.52",
|
2557 |
]
|
2558 |
|
2559 |
[[package]]
|
|
|
2570 |
|
2571 |
[[package]]
|
2572 |
name = "pkg-config"
|
2573 |
+
version = "0.3.30"
|
2574 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2575 |
+
checksum = "d231b230927b5e4ad203db57bbcbee2802f6bce620b1e4a9024a07d94e2907ec"
|
2576 |
|
2577 |
[[package]]
|
2578 |
name = "poly1305"
|
|
|
2585 |
"universal-hash",
|
2586 |
]
|
2587 |
|
2588 |
+
[[package]]
|
2589 |
+
name = "portable-atomic"
|
2590 |
+
version = "1.6.0"
|
2591 |
+
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2592 |
+
checksum = "7170ef9988bc169ba16dd36a7fa041e5c4cbeb6a35b76d4c03daded371eae7c0"
|
2593 |
+
|
2594 |
[[package]]
|
2595 |
name = "powerfmt"
|
2596 |
version = "0.2.0"
|
|
|
2663 |
|
2664 |
[[package]]
|
2665 |
name = "pulldown-cmark"
|
2666 |
+
version = "0.9.6"
|
2667 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2668 |
+
checksum = "57206b407293d2bcd3af849ce869d52068623f19e1b5ff8e8778e3309439682b"
|
2669 |
dependencies = [
|
2670 |
+
"bitflags 2.4.2",
|
2671 |
"memchr",
|
2672 |
"unicase",
|
2673 |
]
|
2674 |
|
2675 |
[[package]]
|
2676 |
name = "quanta"
|
2677 |
+
version = "0.12.2"
|
2678 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2679 |
+
checksum = "9ca0b7bac0b97248c40bb77288fc52029cf1459c0461ea1b05ee32ccf011de2c"
|
2680 |
dependencies = [
|
2681 |
+
"crossbeam-utils 0.8.19",
|
2682 |
"libc",
|
|
|
2683 |
"once_cell",
|
2684 |
"raw-cpuid",
|
2685 |
"wasi 0.11.0+wasi-snapshot-preview1",
|
|
|
2843 |
|
2844 |
[[package]]
|
2845 |
name = "raw-cpuid"
|
2846 |
+
version = "11.0.1"
|
2847 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2848 |
+
checksum = "9d86a7c4638d42c44551f4791a20e687dbb4c3de1f33c43dd71e355cd429def1"
|
2849 |
dependencies = [
|
2850 |
+
"bitflags 2.4.2",
|
2851 |
]
|
2852 |
|
2853 |
[[package]]
|
|
|
2875 |
"percent-encoding 2.3.1",
|
2876 |
"pin-project-lite",
|
2877 |
"ryu",
|
2878 |
+
"tokio 1.36.0",
|
2879 |
"tokio-retry",
|
2880 |
"tokio-util",
|
2881 |
"url 2.5.0",
|
|
|
2898 |
|
2899 |
[[package]]
|
2900 |
name = "regex"
|
2901 |
+
version = "1.10.3"
|
2902 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2903 |
+
checksum = "b62dbe01f0b06f9d8dc7d49e05a0785f153b00b2c227856282f671e0318c9b15"
|
2904 |
dependencies = [
|
2905 |
"aho-corasick 1.1.2",
|
2906 |
"memchr",
|
|
|
2910 |
|
2911 |
[[package]]
|
2912 |
name = "regex-automata"
|
2913 |
+
version = "0.4.6"
|
2914 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2915 |
+
checksum = "86b83b8b9847f9bf95ef68afb0b8e6cdb80f498442f5179a29fad448fcc1eaea"
|
2916 |
dependencies = [
|
2917 |
"aho-corasick 1.1.2",
|
2918 |
"memchr",
|
|
|
2961 |
|
2962 |
[[package]]
|
2963 |
name = "reqwest"
|
2964 |
+
version = "0.11.25"
|
2965 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
2966 |
+
checksum = "0eea5a9eb898d3783f17c6407670e3592fd174cb81a10e51d4c37f49450b9946"
|
2967 |
dependencies = [
|
2968 |
"async-compression",
|
2969 |
+
"base64 0.21.7",
|
2970 |
"bytes 1.5.0",
|
2971 |
"encoding_rs",
|
2972 |
"futures-core",
|
2973 |
"futures-util",
|
2974 |
+
"h2 0.3.24",
|
2975 |
+
"http 0.2.12",
|
2976 |
"http-body 0.4.6",
|
2977 |
"hyper 0.14.28",
|
2978 |
"hyper-rustls",
|
|
|
2990 |
"serde_urlencoded 0.7.1",
|
2991 |
"sync_wrapper",
|
2992 |
"system-configuration",
|
2993 |
+
"tokio 1.36.0",
|
2994 |
"tokio-rustls",
|
2995 |
"tokio-util",
|
2996 |
"tower-service",
|
|
|
3004 |
|
3005 |
[[package]]
|
3006 |
name = "ring"
|
3007 |
+
version = "0.17.8"
|
3008 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3009 |
+
checksum = "c17fa4cb658e3583423e915b9f3acc01cceaee1860e33d59ebae66adc3a2dc0d"
|
3010 |
dependencies = [
|
3011 |
"cc",
|
3012 |
+
"cfg-if 1.0.0",
|
3013 |
"getrandom",
|
3014 |
"libc",
|
3015 |
"spin",
|
3016 |
"untrusted",
|
3017 |
+
"windows-sys 0.52.0",
|
3018 |
]
|
3019 |
|
3020 |
[[package]]
|
|
|
3044 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3045 |
checksum = "bfa0f585226d2e68097d4f95d113b15b83a82e819ab25717ec0590d9584ef366"
|
3046 |
dependencies = [
|
3047 |
+
"semver 1.0.22",
|
3048 |
]
|
3049 |
|
3050 |
[[package]]
|
|
|
3053 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3054 |
checksum = "6ea3e1a662af26cd7a3ba09c0297a31af215563ecf42817c98df621387f4e949"
|
3055 |
dependencies = [
|
3056 |
+
"bitflags 2.4.2",
|
3057 |
"errno",
|
3058 |
"libc",
|
3059 |
"linux-raw-sys",
|
|
|
3078 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3079 |
checksum = "1c74cae0a4cf6ccbbf5f359f08efdf8ee7e1dc532573bf0db71968cb56b1448c"
|
3080 |
dependencies = [
|
3081 |
+
"base64 0.21.7",
|
3082 |
]
|
3083 |
|
3084 |
[[package]]
|
|
|
3105 |
|
3106 |
[[package]]
|
3107 |
name = "ryu"
|
3108 |
+
version = "1.0.17"
|
3109 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3110 |
+
checksum = "e86697c916019a8588c99b5fac3cead74ec0b4b819707a682fd4d23fa0ce1ba1"
|
3111 |
|
3112 |
[[package]]
|
3113 |
name = "same-file"
|
|
|
3139 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3140 |
checksum = "585480e3719b311b78a573db1c9d9c4c1f8010c2dee4cc59c2efe58ea4dbc3e1"
|
3141 |
dependencies = [
|
3142 |
+
"ahash",
|
3143 |
"cssparser 0.31.2",
|
3144 |
"ego-tree",
|
3145 |
"html5ever 0.26.0",
|
|
|
3197 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3198 |
checksum = "4eb30575f3638fc8f6815f448d50cb1a2e255b0897985c8c59f4d37b72a07b06"
|
3199 |
dependencies = [
|
3200 |
+
"bitflags 2.4.2",
|
3201 |
"cssparser 0.31.2",
|
3202 |
"derive_more",
|
3203 |
"fxhash",
|
|
|
3221 |
|
3222 |
[[package]]
|
3223 |
name = "semver"
|
3224 |
+
version = "1.0.22"
|
3225 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3226 |
+
checksum = "92d43fe69e652f3df9bdc2b85b2854a0825b86e4fb76bc44d945137d053639ca"
|
3227 |
dependencies = [
|
3228 |
"serde",
|
3229 |
]
|
|
|
3236 |
|
3237 |
[[package]]
|
3238 |
name = "serde"
|
3239 |
+
version = "1.0.197"
|
3240 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3241 |
+
checksum = "3fb1c873e1b9b056a4dc4c0c198b24c3ffa059243875552b2bd0933b1aee4ce2"
|
3242 |
dependencies = [
|
3243 |
"serde_derive",
|
3244 |
]
|
3245 |
|
3246 |
[[package]]
|
3247 |
name = "serde_derive"
|
3248 |
+
version = "1.0.197"
|
3249 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3250 |
+
checksum = "7eb0b34b42edc17f6b7cac84a52a1c5f0e1bb2227e997ca9011ea3dd34e8610b"
|
3251 |
dependencies = [
|
3252 |
"proc-macro2 1.0.78",
|
3253 |
"quote 1.0.35",
|
3254 |
+
"syn 2.0.52",
|
3255 |
]
|
3256 |
|
3257 |
[[package]]
|
3258 |
name = "serde_json"
|
3259 |
+
version = "1.0.114"
|
3260 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3261 |
+
checksum = "c5f09b1bd632ef549eaa9f60a1f8de742bdbc698e6cee2095fc84dde5f549ae0"
|
3262 |
dependencies = [
|
3263 |
"itoa 1.0.10",
|
3264 |
"ryu",
|
|
|
3374 |
|
3375 |
[[package]]
|
3376 |
name = "socket2"
|
3377 |
+
version = "0.5.6"
|
3378 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3379 |
+
checksum = "05ffd9c0a93b7543e062e759284fcf5f5e3b098501104bfbdde4d404db792871"
|
3380 |
dependencies = [
|
3381 |
"libc",
|
3382 |
+
"windows-sys 0.52.0",
|
3383 |
]
|
3384 |
|
3385 |
[[package]]
|
|
|
3388 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3389 |
checksum = "6980e8d7511241f8acf4aebddbb1ff938df5eebe98691418c4468d0b72a96a67"
|
3390 |
|
3391 |
+
[[package]]
|
3392 |
+
name = "spinning_top"
|
3393 |
+
version = "0.3.0"
|
3394 |
+
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3395 |
+
checksum = "d96d2d1d716fb500937168cc09353ffdc7a012be8475ac7308e1bdf0e3923300"
|
3396 |
+
dependencies = [
|
3397 |
+
"lock_api 0.4.11",
|
3398 |
+
]
|
3399 |
+
|
3400 |
[[package]]
|
3401 |
name = "stable_deref_trait"
|
3402 |
version = "1.2.0"
|
|
|
3502 |
|
3503 |
[[package]]
|
3504 |
name = "syn"
|
3505 |
+
version = "2.0.52"
|
3506 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3507 |
+
checksum = "b699d15b36d1f02c3e7c69f8ffef53de37aefae075d8488d4ba1a7788d574a07"
|
3508 |
dependencies = [
|
3509 |
"proc-macro2 1.0.78",
|
3510 |
"quote 1.0.35",
|
|
|
3529 |
"unicode-xid 0.2.4",
|
3530 |
]
|
3531 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
3532 |
[[package]]
|
3533 |
name = "system-configuration"
|
3534 |
+
version = "0.6.0"
|
3535 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3536 |
+
checksum = "658bc6ee10a9b4fcf576e9b0819d95ec16f4d2c02d39fd83ac1c8789785c4a42"
|
3537 |
dependencies = [
|
3538 |
+
"bitflags 2.4.2",
|
3539 |
"core-foundation",
|
3540 |
"system-configuration-sys",
|
3541 |
]
|
3542 |
|
3543 |
[[package]]
|
3544 |
name = "system-configuration-sys"
|
3545 |
+
version = "0.6.0"
|
3546 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3547 |
+
checksum = "8e1d1b10ced5ca923a1fcb8d03e96b8d3268065d724548c0211415ff6ac6bac4"
|
3548 |
dependencies = [
|
3549 |
"core-foundation-sys",
|
3550 |
"libc",
|
|
|
3598 |
|
3599 |
[[package]]
|
3600 |
name = "time"
|
3601 |
+
version = "0.3.34"
|
3602 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3603 |
+
checksum = "c8248b6521bb14bc45b4067159b9b6ad792e2d6d754d6c41fb50e29fefe38749"
|
3604 |
dependencies = [
|
3605 |
"deranged",
|
3606 |
"itoa 1.0.10",
|
3607 |
+
"num-conv",
|
3608 |
"powerfmt",
|
3609 |
"serde",
|
3610 |
"time-core",
|
|
|
3619 |
|
3620 |
[[package]]
|
3621 |
name = "time-macros"
|
3622 |
+
version = "0.2.17"
|
3623 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3624 |
+
checksum = "7ba3a3ef41e6672a2f0f001392bb5dcd3ff0a9992d618ca761a11c3121547774"
|
3625 |
dependencies = [
|
3626 |
+
"num-conv",
|
3627 |
"time-core",
|
3628 |
]
|
3629 |
|
|
|
3673 |
|
3674 |
[[package]]
|
3675 |
name = "tokio"
|
3676 |
+
version = "1.36.0"
|
3677 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3678 |
+
checksum = "61285f6515fa018fb2d1e46eb21223fff441ee8db5d0f1435e8ab4f5cdb80931"
|
3679 |
dependencies = [
|
3680 |
"backtrace",
|
3681 |
"bytes 1.5.0",
|
3682 |
"libc",
|
3683 |
+
"mio 0.8.11",
|
3684 |
"num_cpus",
|
3685 |
"parking_lot 0.12.1",
|
3686 |
"pin-project-lite",
|
|
|
3740 |
dependencies = [
|
3741 |
"proc-macro2 1.0.78",
|
3742 |
"quote 1.0.35",
|
3743 |
+
"syn 2.0.52",
|
3744 |
]
|
3745 |
|
3746 |
[[package]]
|
|
|
3770 |
dependencies = [
|
3771 |
"pin-project",
|
3772 |
"rand 0.8.5",
|
3773 |
+
"tokio 1.36.0",
|
3774 |
]
|
3775 |
|
3776 |
[[package]]
|
|
|
3780 |
checksum = "c28327cf380ac148141087fbfb9de9d7bd4e84ab5d2c28fbc911d753de8a7081"
|
3781 |
dependencies = [
|
3782 |
"rustls",
|
3783 |
+
"tokio 1.36.0",
|
3784 |
]
|
3785 |
|
3786 |
[[package]]
|
|
|
3846 |
"futures-core",
|
3847 |
"futures-sink",
|
3848 |
"pin-project-lite",
|
3849 |
+
"tokio 1.36.0",
|
3850 |
"tracing",
|
3851 |
]
|
3852 |
|
|
|
3923 |
|
3924 |
[[package]]
|
3925 |
name = "unicode-bidi"
|
3926 |
+
version = "0.3.15"
|
3927 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3928 |
+
checksum = "08f95100a766bf4f8f28f90d77e0a5461bbdb219042e7679bebe79004fed8d75"
|
3929 |
|
3930 |
[[package]]
|
3931 |
name = "unicode-ident"
|
|
|
3935 |
|
3936 |
[[package]]
|
3937 |
name = "unicode-normalization"
|
3938 |
+
version = "0.1.23"
|
3939 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
3940 |
+
checksum = "a56d1686db2308d901306f92a263857ef59ea39678a5458e7cb17f01415101f5"
|
3941 |
dependencies = [
|
3942 |
"tinyvec",
|
3943 |
]
|
|
|
4033 |
|
4034 |
[[package]]
|
4035 |
name = "walkdir"
|
4036 |
+
version = "2.5.0"
|
4037 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4038 |
+
checksum = "29790946404f91d9c5d06f9874efddea1dc06c5efe94541a7d6863108e3a5e4b"
|
4039 |
dependencies = [
|
4040 |
"same-file",
|
4041 |
"winapi-util",
|
|
|
4075 |
|
4076 |
[[package]]
|
4077 |
name = "wasm-bindgen"
|
4078 |
+
version = "0.2.92"
|
4079 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4080 |
+
checksum = "4be2531df63900aeb2bca0daaaddec08491ee64ceecbee5076636a3b026795a8"
|
4081 |
dependencies = [
|
4082 |
"cfg-if 1.0.0",
|
4083 |
"wasm-bindgen-macro",
|
|
|
4085 |
|
4086 |
[[package]]
|
4087 |
name = "wasm-bindgen-backend"
|
4088 |
+
version = "0.2.92"
|
4089 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4090 |
+
checksum = "614d787b966d3989fa7bb98a654e369c762374fd3213d212cfc0251257e747da"
|
4091 |
dependencies = [
|
4092 |
"bumpalo",
|
4093 |
"log",
|
4094 |
"once_cell",
|
4095 |
"proc-macro2 1.0.78",
|
4096 |
"quote 1.0.35",
|
4097 |
+
"syn 2.0.52",
|
4098 |
"wasm-bindgen-shared",
|
4099 |
]
|
4100 |
|
4101 |
[[package]]
|
4102 |
name = "wasm-bindgen-futures"
|
4103 |
+
version = "0.4.42"
|
4104 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4105 |
+
checksum = "76bc14366121efc8dbb487ab05bcc9d346b3b5ec0eaa76e46594cabbe51762c0"
|
4106 |
dependencies = [
|
4107 |
"cfg-if 1.0.0",
|
4108 |
"js-sys",
|
|
|
4112 |
|
4113 |
[[package]]
|
4114 |
name = "wasm-bindgen-macro"
|
4115 |
+
version = "0.2.92"
|
4116 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4117 |
+
checksum = "a1f8823de937b71b9460c0c34e25f3da88250760bec0ebac694b49997550d726"
|
4118 |
dependencies = [
|
4119 |
"quote 1.0.35",
|
4120 |
"wasm-bindgen-macro-support",
|
|
|
4122 |
|
4123 |
[[package]]
|
4124 |
name = "wasm-bindgen-macro-support"
|
4125 |
+
version = "0.2.92"
|
4126 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4127 |
+
checksum = "e94f17b526d0a461a191c78ea52bbce64071ed5c04c9ffe424dcb38f74171bb7"
|
4128 |
dependencies = [
|
4129 |
"proc-macro2 1.0.78",
|
4130 |
"quote 1.0.35",
|
4131 |
+
"syn 2.0.52",
|
4132 |
"wasm-bindgen-backend",
|
4133 |
"wasm-bindgen-shared",
|
4134 |
]
|
4135 |
|
4136 |
[[package]]
|
4137 |
name = "wasm-bindgen-shared"
|
4138 |
+
version = "0.2.92"
|
4139 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4140 |
+
checksum = "af190c94f2773fdb3729c55b007a722abb5384da03bc0986df4c289bf5567e96"
|
4141 |
|
4142 |
[[package]]
|
4143 |
name = "web-sys"
|
4144 |
+
version = "0.3.69"
|
4145 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4146 |
+
checksum = "77afa9a11836342370f4817622a2f0f418b134426d91a82dfb48f532d2ec13ef"
|
4147 |
dependencies = [
|
4148 |
"js-sys",
|
4149 |
"wasm-bindgen",
|
|
|
4151 |
|
4152 |
[[package]]
|
4153 |
name = "webpki-roots"
|
4154 |
+
version = "0.25.4"
|
4155 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4156 |
+
checksum = "5f20c57d8d7db6d3b86154206ae5d8fba62dd39573114de97c2cb0578251f8e1"
|
4157 |
|
4158 |
[[package]]
|
4159 |
name = "websurfx"
|
4160 |
+
version = "1.10.9"
|
4161 |
dependencies = [
|
4162 |
"actix-cors",
|
4163 |
"actix-files",
|
4164 |
"actix-governor",
|
4165 |
"actix-web",
|
4166 |
+
"async-compression",
|
4167 |
"async-once-cell",
|
4168 |
"async-trait",
|
4169 |
+
"base64 0.21.7",
|
4170 |
"blake3",
|
|
|
4171 |
"cfg-if 1.0.0",
|
4172 |
"chacha20",
|
4173 |
"chacha20poly1305",
|
|
|
4186 |
"mlua",
|
4187 |
"redis",
|
4188 |
"regex",
|
4189 |
+
"reqwest 0.11.25",
|
4190 |
"rusty-hook",
|
4191 |
"scraper",
|
4192 |
"serde",
|
4193 |
"serde_json",
|
4194 |
"smallvec 1.13.1",
|
4195 |
"tempfile",
|
4196 |
+
"tokio 1.36.0",
|
4197 |
]
|
4198 |
|
4199 |
[[package]]
|
4200 |
name = "which"
|
4201 |
+
version = "6.0.0"
|
4202 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4203 |
+
checksum = "7fa5e0c10bf77f44aac573e498d1a82d5fbd5e91f6fc0a99e7be4b38e85e101c"
|
4204 |
dependencies = [
|
4205 |
"either",
|
4206 |
"home",
|
4207 |
"once_cell",
|
4208 |
"rustix",
|
4209 |
+
"windows-sys 0.52.0",
|
4210 |
]
|
4211 |
|
4212 |
[[package]]
|
|
|
4267 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4268 |
checksum = "282be5f36a8ce781fad8c8ae18fa3f9beff57ec1b52cb3de0789201425d9a33d"
|
4269 |
dependencies = [
|
4270 |
+
"windows-targets 0.52.4",
|
4271 |
]
|
4272 |
|
4273 |
[[package]]
|
|
|
4287 |
|
4288 |
[[package]]
|
4289 |
name = "windows-targets"
|
4290 |
+
version = "0.52.4"
|
4291 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4292 |
+
checksum = "7dd37b7e5ab9018759f893a1952c9420d060016fc19a472b4bb20d1bdd694d1b"
|
4293 |
dependencies = [
|
4294 |
+
"windows_aarch64_gnullvm 0.52.4",
|
4295 |
+
"windows_aarch64_msvc 0.52.4",
|
4296 |
+
"windows_i686_gnu 0.52.4",
|
4297 |
+
"windows_i686_msvc 0.52.4",
|
4298 |
+
"windows_x86_64_gnu 0.52.4",
|
4299 |
+
"windows_x86_64_gnullvm 0.52.4",
|
4300 |
+
"windows_x86_64_msvc 0.52.4",
|
4301 |
]
|
4302 |
|
4303 |
[[package]]
|
|
|
4308 |
|
4309 |
[[package]]
|
4310 |
name = "windows_aarch64_gnullvm"
|
4311 |
+
version = "0.52.4"
|
4312 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4313 |
+
checksum = "bcf46cf4c365c6f2d1cc93ce535f2c8b244591df96ceee75d8e83deb70a9cac9"
|
4314 |
|
4315 |
[[package]]
|
4316 |
name = "windows_aarch64_msvc"
|
|
|
4320 |
|
4321 |
[[package]]
|
4322 |
name = "windows_aarch64_msvc"
|
4323 |
+
version = "0.52.4"
|
4324 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4325 |
+
checksum = "da9f259dd3bcf6990b55bffd094c4f7235817ba4ceebde8e6d11cd0c5633b675"
|
4326 |
|
4327 |
[[package]]
|
4328 |
name = "windows_i686_gnu"
|
|
|
4332 |
|
4333 |
[[package]]
|
4334 |
name = "windows_i686_gnu"
|
4335 |
+
version = "0.52.4"
|
4336 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4337 |
+
checksum = "b474d8268f99e0995f25b9f095bc7434632601028cf86590aea5c8a5cb7801d3"
|
4338 |
|
4339 |
[[package]]
|
4340 |
name = "windows_i686_msvc"
|
|
|
4344 |
|
4345 |
[[package]]
|
4346 |
name = "windows_i686_msvc"
|
4347 |
+
version = "0.52.4"
|
4348 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4349 |
+
checksum = "1515e9a29e5bed743cb4415a9ecf5dfca648ce85ee42e15873c3cd8610ff8e02"
|
4350 |
|
4351 |
[[package]]
|
4352 |
name = "windows_x86_64_gnu"
|
|
|
4356 |
|
4357 |
[[package]]
|
4358 |
name = "windows_x86_64_gnu"
|
4359 |
+
version = "0.52.4"
|
4360 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4361 |
+
checksum = "5eee091590e89cc02ad514ffe3ead9eb6b660aedca2183455434b93546371a03"
|
4362 |
|
4363 |
[[package]]
|
4364 |
name = "windows_x86_64_gnullvm"
|
|
|
4368 |
|
4369 |
[[package]]
|
4370 |
name = "windows_x86_64_gnullvm"
|
4371 |
+
version = "0.52.4"
|
4372 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4373 |
+
checksum = "77ca79f2451b49fa9e2af39f0747fe999fcda4f5e241b2898624dca97a1f2177"
|
4374 |
|
4375 |
[[package]]
|
4376 |
name = "windows_x86_64_msvc"
|
|
|
4380 |
|
4381 |
[[package]]
|
4382 |
name = "windows_x86_64_msvc"
|
4383 |
+
version = "0.52.4"
|
4384 |
source = "registry+https://github.com/rust-lang/crates.io-index"
|
4385 |
+
checksum = "32b752e52a2da0ddfbdbcc6fceadfeede4c939ed16d13e648833a61dfb611ed8"
|
4386 |
|
4387 |
[[package]]
|
4388 |
name = "winreg"
|
|
|
4430 |
dependencies = [
|
4431 |
"proc-macro2 1.0.78",
|
4432 |
"quote 1.0.35",
|
4433 |
+
"syn 2.0.52",
|
4434 |
]
|
4435 |
|
4436 |
[[package]]
|
@@ -1,6 +1,6 @@
|
|
1 |
[package]
|
2 |
name = "websurfx"
|
3 |
-
version = "1.9
|
4 |
edition = "2021"
|
5 |
description = "An open-source alternative to Searx that provides clean, ad-free, and organic results with incredible speed while keeping privacy and security in mind."
|
6 |
repository = "https://github.com/neon-mmd/websurfx"
|
@@ -14,7 +14,7 @@ path = "src/bin/websurfx.rs"
|
|
14 |
|
15 |
[dependencies]
|
16 |
reqwest = {version="0.11.24", default-features=false, features=["rustls-tls","brotli", "gzip"]}
|
17 |
-
tokio = {version="1.32.0",features=["rt-multi-thread","macros"], default-features = false}
|
18 |
serde = {version="1.0.196", default-features=false, features=["derive"]}
|
19 |
serde_json = {version="1.0.109", default-features=false}
|
20 |
maud = {version="0.25.0", default-features=false, features=["actix-web"]}
|
@@ -32,13 +32,13 @@ error-stack = {version="0.4.0", default-features=false, features=["std"]}
|
|
32 |
async-trait = {version="0.1.76", default-features=false}
|
33 |
regex = {version="1.9.4", features=["perf"], default-features = false}
|
34 |
smallvec = {version="1.13.1", features=["union", "serde"], default-features=false}
|
35 |
-
futures = {version="0.3.
|
36 |
-
dhat = {version="0.3.
|
37 |
mimalloc = { version = "0.1.38", default-features = false }
|
38 |
async-once-cell = {version="0.5.3", default-features=false}
|
39 |
actix-governor = {version="0.5.0", default-features=false}
|
40 |
mini-moka = { version="0.10", optional = true, default-features=false, features=["sync"]}
|
41 |
-
|
42 |
chacha20poly1305={version="0.10.1", default-features=false, features=["alloc","getrandom"], optional=true}
|
43 |
chacha20 = {version="0.9.1", default-features=false, optional=true}
|
44 |
base64 = {version="0.21.5", default-features=false, features=["std"], optional=true}
|
@@ -84,7 +84,7 @@ default = ["memory-cache"]
|
|
84 |
dhat-heap = ["dep:dhat"]
|
85 |
memory-cache = ["dep:mini-moka"]
|
86 |
redis-cache = ["dep:redis","dep:base64"]
|
87 |
-
compress-cache-results = ["dep:
|
88 |
encrypt-cache-results = ["dep:chacha20poly1305","dep:chacha20"]
|
89 |
cec-cache-results = ["compress-cache-results","encrypt-cache-results"]
|
90 |
|
|
|
1 |
[package]
|
2 |
name = "websurfx"
|
3 |
+
version = "1.10.9"
|
4 |
edition = "2021"
|
5 |
description = "An open-source alternative to Searx that provides clean, ad-free, and organic results with incredible speed while keeping privacy and security in mind."
|
6 |
repository = "https://github.com/neon-mmd/websurfx"
|
|
|
14 |
|
15 |
[dependencies]
|
16 |
reqwest = {version="0.11.24", default-features=false, features=["rustls-tls","brotli", "gzip"]}
|
17 |
+
tokio = {version="1.32.0",features=["rt-multi-thread","macros", "fs", "io-util"], default-features = false}
|
18 |
serde = {version="1.0.196", default-features=false, features=["derive"]}
|
19 |
serde_json = {version="1.0.109", default-features=false}
|
20 |
maud = {version="0.25.0", default-features=false, features=["actix-web"]}
|
|
|
32 |
async-trait = {version="0.1.76", default-features=false}
|
33 |
regex = {version="1.9.4", features=["perf"], default-features = false}
|
34 |
smallvec = {version="1.13.1", features=["union", "serde"], default-features=false}
|
35 |
+
futures = {version="0.3.30", default-features=false, features=["alloc"]}
|
36 |
+
dhat = {version="0.3.2", optional = true, default-features=false}
|
37 |
mimalloc = { version = "0.1.38", default-features = false }
|
38 |
async-once-cell = {version="0.5.3", default-features=false}
|
39 |
actix-governor = {version="0.5.0", default-features=false}
|
40 |
mini-moka = { version="0.10", optional = true, default-features=false, features=["sync"]}
|
41 |
+
async-compression = { version = "0.4.6", default-features = false, features=["brotli","tokio"], optional=true}
|
42 |
chacha20poly1305={version="0.10.1", default-features=false, features=["alloc","getrandom"], optional=true}
|
43 |
chacha20 = {version="0.9.1", default-features=false, optional=true}
|
44 |
base64 = {version="0.21.5", default-features=false, features=["std"], optional=true}
|
|
|
84 |
dhat-heap = ["dep:dhat"]
|
85 |
memory-cache = ["dep:mini-moka"]
|
86 |
redis-cache = ["dep:redis","dep:base64"]
|
87 |
+
compress-cache-results = ["dep:async-compression","dep:cfg-if"]
|
88 |
encrypt-cache-results = ["dep:chacha20poly1305","dep:chacha20"]
|
89 |
cec-cache-results = ["compress-cache-results","encrypt-cache-results"]
|
90 |
|
@@ -5,7 +5,7 @@
|
|
5 |
#[cfg(not(feature = "dhat-heap"))]
|
6 |
use mimalloc::MiMalloc;
|
7 |
|
8 |
-
use std::net::TcpListener;
|
9 |
use websurfx::{cache::cacher::create_cache, config::parser::Config, run};
|
10 |
|
11 |
/// A dhat heap memory profiler
|
@@ -17,6 +17,9 @@ static ALLOC: dhat::Alloc = dhat::Alloc;
|
|
17 |
#[global_allocator]
|
18 |
static GLOBAL: MiMalloc = MiMalloc;
|
19 |
|
|
|
|
|
|
|
20 |
/// The function that launches the main server and registers all the routes of the website.
|
21 |
///
|
22 |
/// # Error
|
@@ -29,10 +32,10 @@ async fn main() -> std::io::Result<()> {
|
|
29 |
#[cfg(feature = "dhat-heap")]
|
30 |
let _profiler = dhat::Profiler::new_heap();
|
31 |
|
32 |
-
// Initialize the parsed config
|
33 |
-
let config = Config::parse(false).unwrap();
|
34 |
|
35 |
-
let cache = create_cache(
|
36 |
|
37 |
log::info!(
|
38 |
"started server on port {} and IP {}",
|
@@ -45,7 +48,7 @@ async fn main() -> std::io::Result<()> {
|
|
45 |
config.port,
|
46 |
);
|
47 |
|
48 |
-
let listener = TcpListener::bind((config.binding_ip.
|
49 |
|
50 |
run(listener, config, cache)?.await
|
51 |
}
|
|
|
5 |
#[cfg(not(feature = "dhat-heap"))]
|
6 |
use mimalloc::MiMalloc;
|
7 |
|
8 |
+
use std::{net::TcpListener, sync::OnceLock};
|
9 |
use websurfx::{cache::cacher::create_cache, config::parser::Config, run};
|
10 |
|
11 |
/// A dhat heap memory profiler
|
|
|
17 |
#[global_allocator]
|
18 |
static GLOBAL: MiMalloc = MiMalloc;
|
19 |
|
20 |
+
/// A static constant for holding the parsed config.
|
21 |
+
static CONFIG: OnceLock<Config> = OnceLock::new();
|
22 |
+
|
23 |
/// The function that launches the main server and registers all the routes of the website.
|
24 |
///
|
25 |
/// # Error
|
|
|
32 |
#[cfg(feature = "dhat-heap")]
|
33 |
let _profiler = dhat::Profiler::new_heap();
|
34 |
|
35 |
+
// Initialize the parsed config globally.
|
36 |
+
let config = CONFIG.get_or_init(|| Config::parse(false).unwrap());
|
37 |
|
38 |
+
let cache = create_cache(config).await;
|
39 |
|
40 |
log::info!(
|
41 |
"started server on port {} and IP {}",
|
|
|
48 |
config.port,
|
49 |
);
|
50 |
|
51 |
+
let listener = TcpListener::bind((config.binding_ip.as_str(), config.port))?;
|
52 |
|
53 |
run(listener, config, cache)?.await
|
54 |
}
|
@@ -93,7 +93,7 @@ pub trait Cacher: Send + Sync {
|
|
93 |
feature = "encrypt-cache-results",
|
94 |
feature = "cec-cache-results"
|
95 |
))]
|
96 |
-
fn encrypt_or_decrypt_results(
|
97 |
&mut self,
|
98 |
mut bytes: Vec<u8>,
|
99 |
encrypt: bool,
|
@@ -137,11 +137,19 @@ pub trait Cacher: Send + Sync {
|
|
137 |
/// Returns the compressed bytes on success otherwise it returns a CacheError
|
138 |
/// on failure.
|
139 |
#[cfg(any(feature = "compress-cache-results", feature = "cec-cache-results"))]
|
140 |
-
fn compress_results(
|
141 |
-
|
142 |
-
|
|
|
|
|
|
|
143 |
writer
|
144 |
.write_all(&bytes)
|
|
|
|
|
|
|
|
|
|
|
145 |
.map_err(|_| CacheError::CompressionError)?;
|
146 |
bytes = writer.into_inner();
|
147 |
Ok(bytes)
|
@@ -159,17 +167,17 @@ pub trait Cacher: Send + Sync {
|
|
159 |
/// Returns the compressed and encrypted bytes on success otherwise it returns a CacheError
|
160 |
/// on failure.
|
161 |
#[cfg(feature = "cec-cache-results")]
|
162 |
-
fn compress_encrypt_compress_results(
|
163 |
&mut self,
|
164 |
mut bytes: Vec<u8>,
|
165 |
) -> Result<Vec<u8>, Report<CacheError>> {
|
166 |
// compress first
|
167 |
-
bytes = self.compress_results(bytes)?;
|
168 |
// encrypt
|
169 |
-
bytes = self.encrypt_or_decrypt_results(bytes, true)?;
|
170 |
|
171 |
// compress again;
|
172 |
-
bytes = self.compress_results(bytes)?;
|
173 |
|
174 |
Ok(bytes)
|
175 |
}
|
@@ -187,11 +195,11 @@ pub trait Cacher: Send + Sync {
|
|
187 |
/// on failure.
|
188 |
|
189 |
#[cfg(any(feature = "compress-cache-results", feature = "cec-cache-results"))]
|
190 |
-
fn decompress_results(&mut self, bytes: &[u8]) -> Result<Vec<u8>, Report<CacheError>> {
|
191 |
cfg_if::cfg_if! {
|
192 |
if #[cfg(feature = "compress-cache-results")]
|
193 |
{
|
194 |
-
decompress_util(bytes)
|
195 |
|
196 |
}
|
197 |
else if #[cfg(feature = "cec-cache-results")]
|
@@ -199,7 +207,7 @@ pub trait Cacher: Send + Sync {
|
|
199 |
let decompressed = decompress_util(bytes)?;
|
200 |
let decrypted = self.encrypt_or_decrypt_results(decompressed, false)?;
|
201 |
|
202 |
-
decompress_util(&decrypted)
|
203 |
|
204 |
}
|
205 |
}
|
@@ -216,7 +224,7 @@ pub trait Cacher: Send + Sync {
|
|
216 |
/// # Error
|
217 |
/// Returns a Vec of compressed or encrypted bytes on success otherwise it returns a CacheError
|
218 |
/// on failure.
|
219 |
-
fn pre_process_search_results(
|
220 |
&mut self,
|
221 |
search_results: &SearchResults,
|
222 |
) -> Result<Vec<u8>, Report<CacheError>> {
|
@@ -224,19 +232,20 @@ pub trait Cacher: Send + Sync {
|
|
224 |
let mut bytes: Vec<u8> = search_results.try_into()?;
|
225 |
#[cfg(feature = "compress-cache-results")]
|
226 |
{
|
227 |
-
let compressed = self.compress_results(bytes)?;
|
228 |
bytes = compressed;
|
229 |
}
|
230 |
|
231 |
#[cfg(feature = "encrypt-cache-results")]
|
232 |
{
|
233 |
-
let encrypted = self.encrypt_or_decrypt_results(bytes, true)?;
|
234 |
bytes = encrypted;
|
235 |
}
|
236 |
|
237 |
#[cfg(feature = "cec-cache-results")]
|
238 |
{
|
239 |
-
let compressed_encrypted_compressed =
|
|
|
240 |
bytes = compressed_encrypted_compressed;
|
241 |
}
|
242 |
|
@@ -256,25 +265,25 @@ pub trait Cacher: Send + Sync {
|
|
256 |
/// on failure.
|
257 |
|
258 |
#[allow(unused_mut)] // needs to be mutable when any of the features is enabled
|
259 |
-
fn post_process_search_results(
|
260 |
&mut self,
|
261 |
mut bytes: Vec<u8>,
|
262 |
) -> Result<SearchResults, Report<CacheError>> {
|
263 |
#[cfg(feature = "compress-cache-results")]
|
264 |
{
|
265 |
-
let decompressed = self.decompress_results(&bytes)?;
|
266 |
bytes = decompressed
|
267 |
}
|
268 |
|
269 |
#[cfg(feature = "encrypt-cache-results")]
|
270 |
{
|
271 |
-
let decrypted = self.encrypt_or_decrypt_results(bytes, false)?;
|
272 |
bytes = decrypted
|
273 |
}
|
274 |
|
275 |
#[cfg(feature = "cec-cache-results")]
|
276 |
{
|
277 |
-
let decompressed_decrypted = self.decompress_results(&bytes)?;
|
278 |
bytes = decompressed_decrypted;
|
279 |
}
|
280 |
|
@@ -295,16 +304,19 @@ pub trait Cacher: Send + Sync {
|
|
295 |
/// on failure.
|
296 |
|
297 |
#[cfg(any(feature = "compress-cache-results", feature = "cec-cache-results"))]
|
298 |
-
fn decompress_util(input: &[u8]) -> Result<Vec<u8>, Report<CacheError>> {
|
299 |
-
use
|
300 |
-
let mut writer =
|
301 |
|
302 |
writer
|
303 |
.write_all(input)
|
|
|
304 |
.map_err(|_| CacheError::CompressionError)?;
|
305 |
-
|
306 |
-
.
|
|
|
307 |
.map_err(|_| CacheError::CompressionError)?;
|
|
|
308 |
Ok(bytes)
|
309 |
}
|
310 |
|
@@ -329,7 +341,7 @@ impl Cacher for RedisCache {
|
|
329 |
let bytes = base64::engine::general_purpose::STANDARD_NO_PAD
|
330 |
.decode(base64_string)
|
331 |
.map_err(|_| CacheError::Base64DecodingOrEncodingError)?;
|
332 |
-
self.post_process_search_results(bytes)
|
333 |
}
|
334 |
|
335 |
async fn cache_results(
|
@@ -345,7 +357,7 @@ impl Cacher for RedisCache {
|
|
345 |
let mut bytes = Vec::with_capacity(search_results_len);
|
346 |
|
347 |
for result in search_results {
|
348 |
-
let processed = self.pre_process_search_results(result)?;
|
349 |
bytes.push(processed);
|
350 |
}
|
351 |
|
@@ -405,7 +417,7 @@ impl Cacher for InMemoryCache {
|
|
405 |
async fn cached_results(&mut self, url: &str) -> Result<SearchResults, Report<CacheError>> {
|
406 |
let hashed_url_string = self.hash_url(url);
|
407 |
match self.cache.get(&hashed_url_string) {
|
408 |
-
Some(res) => self.post_process_search_results(res),
|
409 |
None => Err(Report::new(CacheError::MissingValue)),
|
410 |
}
|
411 |
}
|
@@ -417,7 +429,7 @@ impl Cacher for InMemoryCache {
|
|
417 |
) -> Result<(), Report<CacheError>> {
|
418 |
for (url, search_result) in urls.iter().zip(search_results.iter()) {
|
419 |
let hashed_url_string = self.hash_url(url);
|
420 |
-
let bytes = self.pre_process_search_results(search_result)?;
|
421 |
self.cache.insert(hashed_url_string, bytes);
|
422 |
}
|
423 |
|
|
|
93 |
feature = "encrypt-cache-results",
|
94 |
feature = "cec-cache-results"
|
95 |
))]
|
96 |
+
async fn encrypt_or_decrypt_results(
|
97 |
&mut self,
|
98 |
mut bytes: Vec<u8>,
|
99 |
encrypt: bool,
|
|
|
137 |
/// Returns the compressed bytes on success otherwise it returns a CacheError
|
138 |
/// on failure.
|
139 |
#[cfg(any(feature = "compress-cache-results", feature = "cec-cache-results"))]
|
140 |
+
async fn compress_results(
|
141 |
+
&mut self,
|
142 |
+
mut bytes: Vec<u8>,
|
143 |
+
) -> Result<Vec<u8>, Report<CacheError>> {
|
144 |
+
use tokio::io::AsyncWriteExt;
|
145 |
+
let mut writer = async_compression::tokio::write::BrotliEncoder::new(Vec::new());
|
146 |
writer
|
147 |
.write_all(&bytes)
|
148 |
+
.await
|
149 |
+
.map_err(|_| CacheError::CompressionError)?;
|
150 |
+
writer
|
151 |
+
.shutdown()
|
152 |
+
.await
|
153 |
.map_err(|_| CacheError::CompressionError)?;
|
154 |
bytes = writer.into_inner();
|
155 |
Ok(bytes)
|
|
|
167 |
/// Returns the compressed and encrypted bytes on success otherwise it returns a CacheError
|
168 |
/// on failure.
|
169 |
#[cfg(feature = "cec-cache-results")]
|
170 |
+
async fn compress_encrypt_compress_results(
|
171 |
&mut self,
|
172 |
mut bytes: Vec<u8>,
|
173 |
) -> Result<Vec<u8>, Report<CacheError>> {
|
174 |
// compress first
|
175 |
+
bytes = self.compress_results(bytes).await?;
|
176 |
// encrypt
|
177 |
+
bytes = self.encrypt_or_decrypt_results(bytes, true).await?;
|
178 |
|
179 |
// compress again;
|
180 |
+
bytes = self.compress_results(bytes).await?;
|
181 |
|
182 |
Ok(bytes)
|
183 |
}
|
|
|
195 |
/// on failure.
|
196 |
|
197 |
#[cfg(any(feature = "compress-cache-results", feature = "cec-cache-results"))]
|
198 |
+
async fn decompress_results(&mut self, bytes: &[u8]) -> Result<Vec<u8>, Report<CacheError>> {
|
199 |
cfg_if::cfg_if! {
|
200 |
if #[cfg(feature = "compress-cache-results")]
|
201 |
{
|
202 |
+
decompress_util(bytes).await
|
203 |
|
204 |
}
|
205 |
else if #[cfg(feature = "cec-cache-results")]
|
|
|
207 |
let decompressed = decompress_util(bytes)?;
|
208 |
let decrypted = self.encrypt_or_decrypt_results(decompressed, false)?;
|
209 |
|
210 |
+
decompress_util(&decrypted).await
|
211 |
|
212 |
}
|
213 |
}
|
|
|
224 |
/// # Error
|
225 |
/// Returns a Vec of compressed or encrypted bytes on success otherwise it returns a CacheError
|
226 |
/// on failure.
|
227 |
+
async fn pre_process_search_results(
|
228 |
&mut self,
|
229 |
search_results: &SearchResults,
|
230 |
) -> Result<Vec<u8>, Report<CacheError>> {
|
|
|
232 |
let mut bytes: Vec<u8> = search_results.try_into()?;
|
233 |
#[cfg(feature = "compress-cache-results")]
|
234 |
{
|
235 |
+
let compressed = self.compress_results(bytes).await?;
|
236 |
bytes = compressed;
|
237 |
}
|
238 |
|
239 |
#[cfg(feature = "encrypt-cache-results")]
|
240 |
{
|
241 |
+
let encrypted = self.encrypt_or_decrypt_results(bytes, true).await?;
|
242 |
bytes = encrypted;
|
243 |
}
|
244 |
|
245 |
#[cfg(feature = "cec-cache-results")]
|
246 |
{
|
247 |
+
let compressed_encrypted_compressed =
|
248 |
+
self.compress_encrypt_compress_results(bytes).await?;
|
249 |
bytes = compressed_encrypted_compressed;
|
250 |
}
|
251 |
|
|
|
265 |
/// on failure.
|
266 |
|
267 |
#[allow(unused_mut)] // needs to be mutable when any of the features is enabled
|
268 |
+
async fn post_process_search_results(
|
269 |
&mut self,
|
270 |
mut bytes: Vec<u8>,
|
271 |
) -> Result<SearchResults, Report<CacheError>> {
|
272 |
#[cfg(feature = "compress-cache-results")]
|
273 |
{
|
274 |
+
let decompressed = self.decompress_results(&bytes).await?;
|
275 |
bytes = decompressed
|
276 |
}
|
277 |
|
278 |
#[cfg(feature = "encrypt-cache-results")]
|
279 |
{
|
280 |
+
let decrypted = self.encrypt_or_decrypt_results(bytes, false).await?;
|
281 |
bytes = decrypted
|
282 |
}
|
283 |
|
284 |
#[cfg(feature = "cec-cache-results")]
|
285 |
{
|
286 |
+
let decompressed_decrypted = self.decompress_results(&bytes).await?;
|
287 |
bytes = decompressed_decrypted;
|
288 |
}
|
289 |
|
|
|
304 |
/// on failure.
|
305 |
|
306 |
#[cfg(any(feature = "compress-cache-results", feature = "cec-cache-results"))]
|
307 |
+
async fn decompress_util(input: &[u8]) -> Result<Vec<u8>, Report<CacheError>> {
|
308 |
+
use tokio::io::AsyncWriteExt;
|
309 |
+
let mut writer = async_compression::tokio::write::BrotliDecoder::new(Vec::new());
|
310 |
|
311 |
writer
|
312 |
.write_all(input)
|
313 |
+
.await
|
314 |
.map_err(|_| CacheError::CompressionError)?;
|
315 |
+
writer
|
316 |
+
.shutdown()
|
317 |
+
.await
|
318 |
.map_err(|_| CacheError::CompressionError)?;
|
319 |
+
let bytes = writer.into_inner();
|
320 |
Ok(bytes)
|
321 |
}
|
322 |
|
|
|
341 |
let bytes = base64::engine::general_purpose::STANDARD_NO_PAD
|
342 |
.decode(base64_string)
|
343 |
.map_err(|_| CacheError::Base64DecodingOrEncodingError)?;
|
344 |
+
self.post_process_search_results(bytes).await
|
345 |
}
|
346 |
|
347 |
async fn cache_results(
|
|
|
357 |
let mut bytes = Vec::with_capacity(search_results_len);
|
358 |
|
359 |
for result in search_results {
|
360 |
+
let processed = self.pre_process_search_results(result).await?;
|
361 |
bytes.push(processed);
|
362 |
}
|
363 |
|
|
|
417 |
async fn cached_results(&mut self, url: &str) -> Result<SearchResults, Report<CacheError>> {
|
418 |
let hashed_url_string = self.hash_url(url);
|
419 |
match self.cache.get(&hashed_url_string) {
|
420 |
+
Some(res) => self.post_process_search_results(res).await,
|
421 |
None => Err(Report::new(CacheError::MissingValue)),
|
422 |
}
|
423 |
}
|
|
|
429 |
) -> Result<(), Report<CacheError>> {
|
430 |
for (url, search_result) in urls.iter().zip(search_results.iter()) {
|
431 |
let hashed_url_string = self.hash_url(url);
|
432 |
+
let bytes = self.pre_process_search_results(search_result).await?;
|
433 |
self.cache.insert(hashed_url_string, bytes);
|
434 |
}
|
435 |
|
@@ -1,15 +1,16 @@
|
|
1 |
//! This module provides the functionality to cache the aggregated results fetched and aggregated
|
2 |
//! from the upstream search engines in a json format.
|
3 |
|
|
|
4 |
use error_stack::Report;
|
5 |
-
use futures::
|
6 |
use redis::{aio::ConnectionManager, AsyncCommands, Client, RedisError};
|
7 |
|
8 |
-
|
|
|
9 |
|
10 |
/// A named struct which stores the redis Connection url address to which the client will
|
11 |
/// connect to.
|
12 |
-
#[derive(Clone)]
|
13 |
pub struct RedisCache {
|
14 |
/// It stores a pool of connections ready to be used.
|
15 |
connection_pool: Vec<ConnectionManager>,
|
@@ -20,6 +21,8 @@ pub struct RedisCache {
|
|
20 |
current_connection: u8,
|
21 |
/// It stores the max TTL for keys.
|
22 |
cache_ttl: u16,
|
|
|
|
|
23 |
}
|
24 |
|
25 |
impl RedisCache {
|
@@ -30,6 +33,8 @@ impl RedisCache {
|
|
30 |
/// * `redis_connection_url` - It takes the redis Connection url address.
|
31 |
/// * `pool_size` - It takes the size of the connection pool (in other words the number of
|
32 |
/// connections that should be stored in the pool).
|
|
|
|
|
33 |
///
|
34 |
/// # Error
|
35 |
///
|
@@ -41,18 +46,28 @@ impl RedisCache {
|
|
41 |
cache_ttl: u16,
|
42 |
) -> Result<Self, Box<dyn std::error::Error>> {
|
43 |
let client = Client::open(redis_connection_url)?;
|
44 |
-
let
|
45 |
|
46 |
for _ in 0..pool_size {
|
47 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
48 |
}
|
49 |
|
50 |
let redis_cache = RedisCache {
|
51 |
-
connection_pool:
|
52 |
pool_size,
|
53 |
current_connection: Default::default(),
|
54 |
cache_ttl,
|
|
|
55 |
};
|
|
|
56 |
Ok(redis_cache)
|
57 |
}
|
58 |
|
@@ -122,13 +137,14 @@ impl RedisCache {
|
|
122 |
keys: impl Iterator<Item = String>,
|
123 |
) -> Result<(), Report<CacheError>> {
|
124 |
self.current_connection = Default::default();
|
125 |
-
let mut pipeline = redis::Pipeline::with_capacity(3);
|
126 |
|
127 |
for (key, json_result) in keys.zip(json_results) {
|
128 |
-
|
|
|
129 |
}
|
130 |
|
131 |
-
let mut result: Result<(), RedisError> =
|
|
|
132 |
.query_async(&mut self.connection_pool[self.current_connection as usize])
|
133 |
.await;
|
134 |
|
@@ -149,7 +165,8 @@ impl RedisCache {
|
|
149 |
CacheError::PoolExhaustionWithConnectionDropError,
|
150 |
));
|
151 |
}
|
152 |
-
result =
|
|
|
153 |
.query_async(
|
154 |
&mut self.connection_pool[self.current_connection as usize],
|
155 |
)
|
|
|
1 |
//! This module provides the functionality to cache the aggregated results fetched and aggregated
|
2 |
//! from the upstream search engines in a json format.
|
3 |
|
4 |
+
use super::error::CacheError;
|
5 |
use error_stack::Report;
|
6 |
+
use futures::stream::FuturesUnordered;
|
7 |
use redis::{aio::ConnectionManager, AsyncCommands, Client, RedisError};
|
8 |
|
9 |
+
/// A constant holding the redis pipeline size.
|
10 |
+
const REDIS_PIPELINE_SIZE: usize = 3;
|
11 |
|
12 |
/// A named struct which stores the redis Connection url address to which the client will
|
13 |
/// connect to.
|
|
|
14 |
pub struct RedisCache {
|
15 |
/// It stores a pool of connections ready to be used.
|
16 |
connection_pool: Vec<ConnectionManager>,
|
|
|
21 |
current_connection: u8,
|
22 |
/// It stores the max TTL for keys.
|
23 |
cache_ttl: u16,
|
24 |
+
/// It stores the redis pipeline struct of size 3.
|
25 |
+
pipeline: redis::Pipeline,
|
26 |
}
|
27 |
|
28 |
impl RedisCache {
|
|
|
33 |
/// * `redis_connection_url` - It takes the redis Connection url address.
|
34 |
/// * `pool_size` - It takes the size of the connection pool (in other words the number of
|
35 |
/// connections that should be stored in the pool).
|
36 |
+
/// * `cache_ttl` - It takes the the time to live for cached results to live in the redis
|
37 |
+
/// server.
|
38 |
///
|
39 |
/// # Error
|
40 |
///
|
|
|
46 |
cache_ttl: u16,
|
47 |
) -> Result<Self, Box<dyn std::error::Error>> {
|
48 |
let client = Client::open(redis_connection_url)?;
|
49 |
+
let tasks: FuturesUnordered<_> = FuturesUnordered::new();
|
50 |
|
51 |
for _ in 0..pool_size {
|
52 |
+
let client_partially_cloned = client.clone();
|
53 |
+
tasks.push(tokio::spawn(async move {
|
54 |
+
client_partially_cloned.get_connection_manager().await
|
55 |
+
}));
|
56 |
+
}
|
57 |
+
|
58 |
+
let mut outputs = Vec::new();
|
59 |
+
for task in tasks {
|
60 |
+
outputs.push(task.await??);
|
61 |
}
|
62 |
|
63 |
let redis_cache = RedisCache {
|
64 |
+
connection_pool: outputs,
|
65 |
pool_size,
|
66 |
current_connection: Default::default(),
|
67 |
cache_ttl,
|
68 |
+
pipeline: redis::Pipeline::with_capacity(REDIS_PIPELINE_SIZE),
|
69 |
};
|
70 |
+
|
71 |
Ok(redis_cache)
|
72 |
}
|
73 |
|
|
|
137 |
keys: impl Iterator<Item = String>,
|
138 |
) -> Result<(), Report<CacheError>> {
|
139 |
self.current_connection = Default::default();
|
|
|
140 |
|
141 |
for (key, json_result) in keys.zip(json_results) {
|
142 |
+
self.pipeline
|
143 |
+
.set_ex(key, json_result, self.cache_ttl.into());
|
144 |
}
|
145 |
|
146 |
+
let mut result: Result<(), RedisError> = self
|
147 |
+
.pipeline
|
148 |
.query_async(&mut self.connection_pool[self.current_connection as usize])
|
149 |
.await;
|
150 |
|
|
|
165 |
CacheError::PoolExhaustionWithConnectionDropError,
|
166 |
));
|
167 |
}
|
168 |
+
result = self
|
169 |
+
.pipeline
|
170 |
.query_async(
|
171 |
&mut self.connection_pool[self.current_connection as usize],
|
172 |
)
|
@@ -9,7 +9,6 @@ use mlua::Lua;
|
|
9 |
use std::{collections::HashMap, fs, thread::available_parallelism};
|
10 |
|
11 |
/// A named struct which stores the parsed config file options.
|
12 |
-
#[derive(Clone)]
|
13 |
pub struct Config {
|
14 |
/// It stores the parsed port number option on which the server should launch.
|
15 |
pub port: u16,
|
|
|
9 |
use std::{collections::HashMap, fs, thread::available_parallelism};
|
10 |
|
11 |
/// A named struct which stores the parsed config file options.
|
|
|
12 |
pub struct Config {
|
13 |
/// It stores the parsed port number option on which the server should launch.
|
14 |
pub port: u16,
|
@@ -48,7 +48,7 @@ impl SearchEngine for Bing {
|
|
48 |
user_agent: &str,
|
49 |
client: &Client,
|
50 |
_safe_search: u8,
|
51 |
-
) -> Result<
|
52 |
// Bing uses `start results from this number` convention
|
53 |
// So, for 10 results per page, page 0 starts at 1, page 1
|
54 |
// starts at 11, and so on.
|
|
|
48 |
user_agent: &str,
|
49 |
client: &Client,
|
50 |
_safe_search: u8,
|
51 |
+
) -> Result<Vec<(String, SearchResult)>, EngineError> {
|
52 |
// Bing uses `start results from this number` convention
|
53 |
// So, for 10 results per page, page 0 starts at 1, page 1
|
54 |
// starts at 11, and so on.
|
@@ -44,7 +44,7 @@ impl SearchEngine for Brave {
|
|
44 |
user_agent: &str,
|
45 |
client: &Client,
|
46 |
safe_search: u8,
|
47 |
-
) -> Result<
|
48 |
let url = format!("https://search.brave.com/search?q={query}&offset={page}");
|
49 |
|
50 |
let safe_search_level = match safe_search {
|
|
|
44 |
user_agent: &str,
|
45 |
client: &Client,
|
46 |
safe_search: u8,
|
47 |
+
) -> Result<Vec<(String, SearchResult)>, EngineError> {
|
48 |
let url = format!("https://search.brave.com/search?q={query}&offset={page}");
|
49 |
|
50 |
let safe_search_level = match safe_search {
|
@@ -47,7 +47,7 @@ impl SearchEngine for DuckDuckGo {
|
|
47 |
user_agent: &str,
|
48 |
client: &Client,
|
49 |
_safe_search: u8,
|
50 |
-
) -> Result<
|
51 |
// Page number can be missing or empty string and so appropriate handling is required
|
52 |
// so that upstream server recieves valid page number.
|
53 |
let url: String = match page {
|
|
|
47 |
user_agent: &str,
|
48 |
client: &Client,
|
49 |
_safe_search: u8,
|
50 |
+
) -> Result<Vec<(String, SearchResult)>, EngineError> {
|
51 |
// Page number can be missing or empty string and so appropriate handling is required
|
52 |
// so that upstream server recieves valid page number.
|
53 |
let url: String = match page {
|
@@ -62,7 +62,7 @@ impl SearchEngine for LibreX {
|
|
62 |
user_agent: &str,
|
63 |
client: &Client,
|
64 |
_safe_search: u8,
|
65 |
-
) -> Result<
|
66 |
// Page number can be missing or empty string and so appropriate handling is required
|
67 |
// so that upstream server recieves valid page number.
|
68 |
let url: String = format!(
|
|
|
62 |
user_agent: &str,
|
63 |
client: &Client,
|
64 |
_safe_search: u8,
|
65 |
+
) -> Result<Vec<(String, SearchResult)>, EngineError> {
|
66 |
// Page number can be missing or empty string and so appropriate handling is required
|
67 |
// so that upstream server recieves valid page number.
|
68 |
let url: String = format!(
|
@@ -47,7 +47,7 @@ impl SearchEngine for Mojeek {
|
|
47 |
user_agent: &str,
|
48 |
client: &Client,
|
49 |
safe_search: u8,
|
50 |
-
) -> Result<
|
51 |
// Mojeek uses `start results from this number` convention
|
52 |
// So, for 10 results per page, page 0 starts at 1, page 1
|
53 |
// starts at 11, and so on.
|
@@ -72,8 +72,23 @@ impl SearchEngine for Mojeek {
|
|
72 |
"Yep",
|
73 |
"You",
|
74 |
];
|
|
|
75 |
let qss = search_engines.join("%2C");
|
76 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
77 |
|
78 |
// Mojeek detects automated requests, these are preferences that are
|
79 |
// able to circumvent the countermeasure. Some of these are
|
@@ -89,7 +104,7 @@ impl SearchEngine for Mojeek {
|
|
89 |
("hp", "minimal"),
|
90 |
("lb", "en"),
|
91 |
("qss", &qss),
|
92 |
-
("safe", safe),
|
93 |
];
|
94 |
|
95 |
let mut query_params_string = String::new();
|
|
|
47 |
user_agent: &str,
|
48 |
client: &Client,
|
49 |
safe_search: u8,
|
50 |
+
) -> Result<Vec<(String, SearchResult)>, EngineError> {
|
51 |
// Mojeek uses `start results from this number` convention
|
52 |
// So, for 10 results per page, page 0 starts at 1, page 1
|
53 |
// starts at 11, and so on.
|
|
|
72 |
"Yep",
|
73 |
"You",
|
74 |
];
|
75 |
+
|
76 |
let qss = search_engines.join("%2C");
|
77 |
+
|
78 |
+
// A branchless condition to check whether the `safe_search` parameter has the
|
79 |
+
// value 0 or not. If it is zero then it sets the value 0 otherwise it sets
|
80 |
+
// the value to 1 for all other values of `safe_search`
|
81 |
+
//
|
82 |
+
// Moreover, the below branchless code is equivalent to the following code below:
|
83 |
+
//
|
84 |
+
// ```rust
|
85 |
+
// let safe = if safe_search == 0 { 0 } else { 1 }.to_string();
|
86 |
+
// ```
|
87 |
+
//
|
88 |
+
// For more information on branchless programming. See:
|
89 |
+
//
|
90 |
+
// * https://piped.video/watch?v=bVJ-mWWL7cE
|
91 |
+
let safe = u8::from(safe_search != 0).to_string();
|
92 |
|
93 |
// Mojeek detects automated requests, these are preferences that are
|
94 |
// able to circumvent the countermeasure. Some of these are
|
|
|
104 |
("hp", "minimal"),
|
105 |
("lb", "en"),
|
106 |
("qss", &qss),
|
107 |
+
("safe", &safe),
|
108 |
];
|
109 |
|
110 |
let mut query_params_string = String::new();
|
@@ -1,5 +1,4 @@
|
|
1 |
//! This modules provides helper functionalities for parsing a html document into internal SearchResult.
|
2 |
-
use std::collections::HashMap;
|
3 |
|
4 |
use crate::models::{aggregation_models::SearchResult, engine_models::EngineError};
|
5 |
use error_stack::{Report, Result};
|
@@ -47,7 +46,7 @@ impl SearchResultParser {
|
|
47 |
&self,
|
48 |
document: &Html,
|
49 |
builder: impl Fn(&ElementRef<'_>, &ElementRef<'_>, &ElementRef<'_>) -> Option<SearchResult>,
|
50 |
-
) -> Result<
|
51 |
let res = document
|
52 |
.select(&self.results)
|
53 |
.filter_map(|result| {
|
|
|
1 |
//! This modules provides helper functionalities for parsing a html document into internal SearchResult.
|
|
|
2 |
|
3 |
use crate::models::{aggregation_models::SearchResult, engine_models::EngineError};
|
4 |
use error_stack::{Report, Result};
|
|
|
46 |
&self,
|
47 |
document: &Html,
|
48 |
builder: impl Fn(&ElementRef<'_>, &ElementRef<'_>, &ElementRef<'_>) -> Option<SearchResult>,
|
49 |
+
) -> Result<Vec<(String, SearchResult)>, EngineError> {
|
50 |
let res = document
|
51 |
.select(&self.results)
|
52 |
.filter_map(|result| {
|
@@ -43,12 +43,21 @@ impl SearchEngine for Searx {
|
|
43 |
user_agent: &str,
|
44 |
client: &Client,
|
45 |
mut safe_search: u8,
|
46 |
-
) -> Result<
|
47 |
-
//
|
48 |
-
//
|
49 |
-
|
50 |
-
|
51 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
52 |
|
53 |
let url: String = format!(
|
54 |
"https://searx.be/search?q={query}&pageno={}&safesearch={safe_search}",
|
|
|
43 |
user_agent: &str,
|
44 |
client: &Client,
|
45 |
mut safe_search: u8,
|
46 |
+
) -> Result<Vec<(String, SearchResult)>, EngineError> {
|
47 |
+
// A branchless condition to check whether the `safe_search` parameter has the
|
48 |
+
// value greater than equal to three or not. If it is, then it modifies the
|
49 |
+
// `safesearch` parameters value to 2.
|
50 |
+
//
|
51 |
+
// Moreover, the below branchless code is equivalent to the following code below:
|
52 |
+
//
|
53 |
+
// ```rust
|
54 |
+
// safe_search = u8::from(safe_search == 3) * 2;
|
55 |
+
// ```
|
56 |
+
//
|
57 |
+
// For more information on branchless programming. See:
|
58 |
+
//
|
59 |
+
// * https://piped.video/watch?v=bVJ-mWWL7cE
|
60 |
+
safe_search = u8::from(safe_search >= 3) * 2;
|
61 |
|
62 |
let url: String = format!(
|
63 |
"https://searx.be/search?q={query}&pageno={}&safesearch={safe_search}",
|
@@ -47,7 +47,7 @@ impl SearchEngine for Startpage {
|
|
47 |
user_agent: &str,
|
48 |
client: &Client,
|
49 |
_safe_search: u8,
|
50 |
-
) -> Result<
|
51 |
// Page number can be missing or empty string and so appropriate handling is required
|
52 |
// so that upstream server recieves valid page number.
|
53 |
let url: String = format!(
|
|
|
47 |
user_agent: &str,
|
48 |
client: &Client,
|
49 |
_safe_search: u8,
|
50 |
+
) -> Result<Vec<(String, SearchResult)>, EngineError> {
|
51 |
// Page number can be missing or empty string and so appropriate handling is required
|
52 |
// so that upstream server recieves valid page number.
|
53 |
let url: String = format!(
|
@@ -14,7 +14,7 @@ pub mod results;
|
|
14 |
pub mod server;
|
15 |
pub mod templates;
|
16 |
|
17 |
-
use std::net::TcpListener;
|
18 |
|
19 |
use crate::server::router;
|
20 |
|
@@ -31,6 +31,9 @@ use cache::cacher::{Cacher, SharedCache};
|
|
31 |
use config::parser::Config;
|
32 |
use handler::{file_path, FileType};
|
33 |
|
|
|
|
|
|
|
34 |
/// Runs the web server on the provided TCP listener and returns a `Server` instance.
|
35 |
///
|
36 |
/// # Arguments
|
@@ -44,27 +47,29 @@ use handler::{file_path, FileType};
|
|
44 |
/// # Example
|
45 |
///
|
46 |
/// ```rust
|
47 |
-
/// use std::net::TcpListener;
|
48 |
/// use websurfx::{config::parser::Config, run, cache::cacher::create_cache};
|
49 |
///
|
|
|
|
|
|
|
50 |
/// #[tokio::main]
|
51 |
/// async fn main(){
|
52 |
-
///
|
|
|
53 |
/// let listener = TcpListener::bind("127.0.0.1:8080").expect("Failed to bind address");
|
54 |
-
/// let cache = create_cache(
|
55 |
-
/// let server = run(listener
|
56 |
/// }
|
57 |
/// ```
|
58 |
pub fn run(
|
59 |
listener: TcpListener,
|
60 |
-
config: Config,
|
61 |
cache: impl Cacher + 'static,
|
62 |
) -> std::io::Result<Server> {
|
63 |
let public_folder_path: &str = file_path(FileType::Theme)?;
|
64 |
|
65 |
-
let
|
66 |
-
|
67 |
-
let cache = web::Data::new(SharedCache::new(cache));
|
68 |
|
69 |
let server = HttpServer::new(move || {
|
70 |
let cors: Cors = Cors::default()
|
@@ -81,8 +86,8 @@ pub fn run(
|
|
81 |
// Compress the responses provided by the server for the client requests.
|
82 |
.wrap(Compress::default())
|
83 |
.wrap(Logger::default()) // added logging middleware for logging.
|
84 |
-
.app_data(web::Data::new(config
|
85 |
-
.app_data(cache
|
86 |
.wrap(cors)
|
87 |
.wrap(Governor::new(
|
88 |
&GovernorConfigBuilder::default()
|
@@ -107,7 +112,7 @@ pub fn run(
|
|
107 |
.service(router::settings) // settings page
|
108 |
.default_service(web::route().to(router::not_found)) // error page
|
109 |
})
|
110 |
-
.workers(
|
111 |
// Start server on 127.0.0.1 with the user provided port number. for example 127.0.0.1:8080.
|
112 |
.listen(listener)?
|
113 |
.run();
|
|
|
14 |
pub mod server;
|
15 |
pub mod templates;
|
16 |
|
17 |
+
use std::{net::TcpListener, sync::OnceLock};
|
18 |
|
19 |
use crate::server::router;
|
20 |
|
|
|
31 |
use config::parser::Config;
|
32 |
use handler::{file_path, FileType};
|
33 |
|
34 |
+
/// A static constant for holding the cache struct.
|
35 |
+
static SHARED_CACHE: OnceLock<SharedCache> = OnceLock::new();
|
36 |
+
|
37 |
/// Runs the web server on the provided TCP listener and returns a `Server` instance.
|
38 |
///
|
39 |
/// # Arguments
|
|
|
47 |
/// # Example
|
48 |
///
|
49 |
/// ```rust
|
50 |
+
/// use std::{net::TcpListener, sync::OnceLock};
|
51 |
/// use websurfx::{config::parser::Config, run, cache::cacher::create_cache};
|
52 |
///
|
53 |
+
/// /// A static constant for holding the parsed config.
|
54 |
+
/// static CONFIG: OnceLock<Config> = OnceLock::new();
|
55 |
+
///
|
56 |
/// #[tokio::main]
|
57 |
/// async fn main(){
|
58 |
+
/// // Initialize the parsed config globally.
|
59 |
+
/// let config = CONFIG.get_or_init(|| Config::parse(true).unwrap());
|
60 |
/// let listener = TcpListener::bind("127.0.0.1:8080").expect("Failed to bind address");
|
61 |
+
/// let cache = create_cache(config).await;
|
62 |
+
/// let server = run(listener,&config,cache).expect("Failed to start server");
|
63 |
/// }
|
64 |
/// ```
|
65 |
pub fn run(
|
66 |
listener: TcpListener,
|
67 |
+
config: &'static Config,
|
68 |
cache: impl Cacher + 'static,
|
69 |
) -> std::io::Result<Server> {
|
70 |
let public_folder_path: &str = file_path(FileType::Theme)?;
|
71 |
|
72 |
+
let cache = SHARED_CACHE.get_or_init(|| SharedCache::new(cache));
|
|
|
|
|
73 |
|
74 |
let server = HttpServer::new(move || {
|
75 |
let cors: Cors = Cors::default()
|
|
|
86 |
// Compress the responses provided by the server for the client requests.
|
87 |
.wrap(Compress::default())
|
88 |
.wrap(Logger::default()) // added logging middleware for logging.
|
89 |
+
.app_data(web::Data::new(config))
|
90 |
+
.app_data(web::Data::new(cache))
|
91 |
.wrap(cors)
|
92 |
.wrap(Governor::new(
|
93 |
&GovernorConfigBuilder::default()
|
|
|
112 |
.service(router::settings) // settings page
|
113 |
.default_service(web::route().to(router::not_found)) // error page
|
114 |
})
|
115 |
+
.workers(config.threads as usize)
|
116 |
// Start server on 127.0.0.1 with the user provided port number. for example 127.0.0.1:8080.
|
117 |
.listen(listener)?
|
118 |
.run();
|
@@ -154,8 +154,8 @@ impl SearchResults {
|
|
154 |
}
|
155 |
|
156 |
/// A setter function that sets the filtered to true.
|
157 |
-
pub fn set_filtered(&mut self) {
|
158 |
-
self.filtered =
|
159 |
}
|
160 |
|
161 |
/// A getter function that gets the value of `engine_errors_info`.
|
|
|
154 |
}
|
155 |
|
156 |
/// A setter function that sets the filtered to true.
|
157 |
+
pub fn set_filtered(&mut self, filtered: bool) {
|
158 |
+
self.filtered = filtered;
|
159 |
}
|
160 |
|
161 |
/// A getter function that gets the value of `engine_errors_info`.
|
@@ -4,7 +4,7 @@
|
|
4 |
use super::aggregation_models::SearchResult;
|
5 |
use error_stack::{Report, Result, ResultExt};
|
6 |
use reqwest::Client;
|
7 |
-
use std::
|
8 |
|
9 |
/// A custom error type used for handle engine associated errors.
|
10 |
#[derive(Debug)]
|
@@ -147,7 +147,7 @@ pub trait SearchEngine: Sync + Send {
|
|
147 |
user_agent: &str,
|
148 |
client: &Client,
|
149 |
safe_search: u8,
|
150 |
-
) -> Result<
|
151 |
}
|
152 |
|
153 |
/// A named struct which stores the engine struct with the name of the associated engine.
|
|
|
4 |
use super::aggregation_models::SearchResult;
|
5 |
use error_stack::{Report, Result, ResultExt};
|
6 |
use reqwest::Client;
|
7 |
+
use std::fmt;
|
8 |
|
9 |
/// A custom error type used for handle engine associated errors.
|
10 |
#[derive(Debug)]
|
|
|
147 |
user_agent: &str,
|
148 |
client: &Client,
|
149 |
safe_search: u8,
|
150 |
+
) -> Result<Vec<(String, SearchResult)>, EngineError>;
|
151 |
}
|
152 |
|
153 |
/// A named struct which stores the engine struct with the name of the associated engine.
|
@@ -10,7 +10,7 @@
|
|
10 |
/// order to allow the deserializing the json back to struct in aggregate function in
|
11 |
/// aggregator.rs and create a new struct out of it and then serialize it back to json and pass
|
12 |
/// it to the template files.
|
13 |
-
#[derive(
|
14 |
pub struct Style {
|
15 |
/// It stores the parsed theme option used to set a theme for the website.
|
16 |
pub theme: String,
|
@@ -40,7 +40,6 @@ impl Style {
|
|
40 |
}
|
41 |
|
42 |
/// Configuration options for the aggregator.
|
43 |
-
#[derive(Clone)]
|
44 |
pub struct AggregatorConfig {
|
45 |
/// It stores the option to whether enable or disable random delays between
|
46 |
/// requests.
|
@@ -48,7 +47,6 @@ pub struct AggregatorConfig {
|
|
48 |
}
|
49 |
|
50 |
/// Configuration options for the rate limiter middleware.
|
51 |
-
#[derive(Clone)]
|
52 |
pub struct RateLimiter {
|
53 |
/// The number of request that are allowed within a provided time limit.
|
54 |
pub number_of_requests: u8,
|
|
|
10 |
/// order to allow the deserializing the json back to struct in aggregate function in
|
11 |
/// aggregator.rs and create a new struct out of it and then serialize it back to json and pass
|
12 |
/// it to the template files.
|
13 |
+
#[derive(Default)]
|
14 |
pub struct Style {
|
15 |
/// It stores the parsed theme option used to set a theme for the website.
|
16 |
pub theme: String,
|
|
|
40 |
}
|
41 |
|
42 |
/// Configuration options for the aggregator.
|
|
|
43 |
pub struct AggregatorConfig {
|
44 |
/// It stores the option to whether enable or disable random delays between
|
45 |
/// requests.
|
|
|
47 |
}
|
48 |
|
49 |
/// Configuration options for the rate limiter middleware.
|
|
|
50 |
pub struct RateLimiter {
|
51 |
/// The number of request that are allowed within a provided time limit.
|
52 |
pub number_of_requests: u8,
|
@@ -9,22 +9,25 @@ use crate::models::{
|
|
9 |
engine_models::{EngineError, EngineHandler},
|
10 |
};
|
11 |
use error_stack::Report;
|
|
|
12 |
use regex::Regex;
|
13 |
use reqwest::{Client, ClientBuilder};
|
|
|
14 |
use std::time::{SystemTime, UNIX_EPOCH};
|
15 |
-
use
|
16 |
-
|
17 |
-
io::{
|
|
|
18 |
time::Duration,
|
19 |
};
|
20 |
-
use std::{fs::File, io::BufRead};
|
21 |
-
use tokio::task::JoinHandle;
|
22 |
|
23 |
/// A constant for holding the prebuilt Client globally in the app.
|
24 |
static CLIENT: std::sync::OnceLock<Client> = std::sync::OnceLock::new();
|
25 |
|
26 |
/// Aliases for long type annotations
|
27 |
-
|
|
|
|
|
28 |
|
29 |
/// The function aggregates the scraped results from the user-selected upstream search engines.
|
30 |
/// These engines can be chosen either from the user interface (UI) or from the configuration file.
|
@@ -37,7 +40,7 @@ type FutureVec = Vec<JoinHandle<Result<HashMap<String, SearchResult>, Report<Eng
|
|
37 |
///
|
38 |
/// Additionally, the function eliminates duplicate results. If two results are identified as coming from
|
39 |
/// multiple engines, their names are combined to indicate that the results were fetched from these upstream
|
40 |
-
/// engines. After this, all the data in the `
|
41 |
/// the aggregated results in a vector. Furthermore, the query used is also added to the struct. This step is
|
42 |
/// necessary to ensure that the search bar in the search remains populated even when searched from the query URL.
|
43 |
///
|
@@ -94,15 +97,22 @@ pub async fn aggregate(
|
|
94 |
let mut names: Vec<&str> = Vec::with_capacity(0);
|
95 |
|
96 |
// create tasks for upstream result fetching
|
97 |
-
let
|
98 |
|
|
|
99 |
for engine_handler in upstream_search_engines {
|
100 |
-
let (name, search_engine) = engine_handler.
|
101 |
names.push(name);
|
102 |
-
let
|
103 |
tasks.push(tokio::spawn(async move {
|
104 |
search_engine
|
105 |
-
.results(
|
|
|
|
|
|
|
|
|
|
|
|
|
106 |
.await
|
107 |
}));
|
108 |
}
|
@@ -117,7 +127,7 @@ pub async fn aggregate(
|
|
117 |
}
|
118 |
|
119 |
// aggregate search results, removing duplicates and handling errors the upstream engines returned
|
120 |
-
let mut result_map:
|
121 |
let mut engine_errors_info: Vec<EngineErrorInfo> = Vec::new();
|
122 |
|
123 |
let mut handle_error = |error: &Report<EngineError>, engine_name: &'static str| {
|
@@ -134,51 +144,45 @@ pub async fn aggregate(
|
|
134 |
|
135 |
if result_map.is_empty() {
|
136 |
match response {
|
137 |
-
Ok(results) =>
|
138 |
-
|
139 |
-
|
140 |
-
Err(error) => {
|
141 |
-
handle_error(&error, engine);
|
142 |
-
}
|
143 |
-
}
|
144 |
continue;
|
145 |
}
|
146 |
|
147 |
match response {
|
148 |
Ok(result) => {
|
149 |
result.into_iter().for_each(|(key, value)| {
|
150 |
-
result_map
|
151 |
-
.
|
152 |
-
.
|
153 |
-
|
154 |
-
})
|
155 |
-
.or_insert_with(|| -> SearchResult { value });
|
156 |
});
|
157 |
}
|
158 |
-
Err(error) =>
|
159 |
-
|
160 |
-
}
|
161 |
-
}
|
162 |
}
|
163 |
|
164 |
if safe_search >= 3 {
|
165 |
-
let mut blacklist_map:
|
166 |
filter_with_lists(
|
167 |
&mut result_map,
|
168 |
&mut blacklist_map,
|
169 |
file_path(FileType::BlockList)?,
|
170 |
-
)
|
|
|
171 |
|
172 |
filter_with_lists(
|
173 |
&mut blacklist_map,
|
174 |
&mut result_map,
|
175 |
file_path(FileType::AllowList)?,
|
176 |
-
)
|
|
|
177 |
|
178 |
drop(blacklist_map);
|
179 |
}
|
180 |
|
181 |
-
let results: Vec<SearchResult> = result_map.
|
182 |
|
183 |
Ok(SearchResults::new(results, &engine_errors_info))
|
184 |
}
|
@@ -187,35 +191,41 @@ pub async fn aggregate(
|
|
187 |
///
|
188 |
/// # Arguments
|
189 |
///
|
190 |
-
/// * `map_to_be_filtered` - A mutable reference to a `
|
191 |
-
/// * `resultant_map` - A mutable reference to a `
|
192 |
/// * `file_path` - A `&str` representing the path to a file containing regex patterns to use for filtering.
|
193 |
///
|
194 |
/// # Errors
|
195 |
///
|
196 |
/// Returns an error if the file at `file_path` cannot be opened or read, or if a regex pattern is invalid.
|
197 |
-
pub fn filter_with_lists(
|
198 |
-
map_to_be_filtered: &mut
|
199 |
-
resultant_map: &mut
|
200 |
file_path: &str,
|
201 |
) -> Result<(), Box<dyn std::error::Error>> {
|
202 |
-
let
|
|
|
203 |
|
204 |
-
|
205 |
-
let re = Regex::new(line
|
206 |
|
|
|
|
|
207 |
// Iterate over each search result in the map and check if it matches the regex pattern
|
208 |
-
|
209 |
-
|
210 |
-
|
211 |
-
|
|
|
|
|
212 |
{
|
213 |
-
|
214 |
-
|
215 |
-
|
216 |
-
|
217 |
-
|
218 |
-
|
|
|
219 |
}
|
220 |
}
|
221 |
|
@@ -226,15 +236,14 @@ pub fn filter_with_lists(
|
|
226 |
mod tests {
|
227 |
use super::*;
|
228 |
use smallvec::smallvec;
|
229 |
-
use std::collections::HashMap;
|
230 |
use std::io::Write;
|
231 |
use tempfile::NamedTempFile;
|
232 |
|
233 |
-
#[test]
|
234 |
-
fn test_filter_with_lists() -> Result<(), Box<dyn std::error::Error>> {
|
235 |
// Create a map of search results to filter
|
236 |
-
let mut map_to_be_filtered =
|
237 |
-
map_to_be_filtered.
|
238 |
"https://www.example.com".to_owned(),
|
239 |
SearchResult {
|
240 |
title: "Example Domain".to_owned(),
|
@@ -243,15 +252,15 @@ mod tests {
|
|
243 |
.to_owned(),
|
244 |
engine: smallvec!["Google".to_owned(), "Bing".to_owned()],
|
245 |
},
|
246 |
-
);
|
247 |
-
map_to_be_filtered.
|
248 |
"https://www.rust-lang.org/".to_owned(),
|
249 |
SearchResult {
|
250 |
title: "Rust Programming Language".to_owned(),
|
251 |
url: "https://www.rust-lang.org/".to_owned(),
|
252 |
description: "A systems programming language that runs blazingly fast, prevents segfaults, and guarantees thread safety.".to_owned(),
|
253 |
engine: smallvec!["Google".to_owned(), "DuckDuckGo".to_owned()],
|
254 |
-
},
|
255 |
);
|
256 |
|
257 |
// Create a temporary file with regex patterns
|
@@ -260,25 +269,30 @@ mod tests {
|
|
260 |
writeln!(file, "rust")?;
|
261 |
file.flush()?;
|
262 |
|
263 |
-
let mut resultant_map =
|
264 |
filter_with_lists(
|
265 |
&mut map_to_be_filtered,
|
266 |
&mut resultant_map,
|
267 |
file.path().to_str().unwrap(),
|
268 |
-
)
|
|
|
269 |
|
270 |
assert_eq!(resultant_map.len(), 2);
|
271 |
-
assert!(resultant_map
|
272 |
-
|
|
|
|
|
|
|
|
|
273 |
assert_eq!(map_to_be_filtered.len(), 0);
|
274 |
|
275 |
Ok(())
|
276 |
}
|
277 |
|
278 |
-
#[test]
|
279 |
-
fn test_filter_with_lists_wildcard() -> Result<(), Box<dyn std::error::Error>> {
|
280 |
-
let mut map_to_be_filtered =
|
281 |
-
map_to_be_filtered.
|
282 |
"https://www.example.com".to_owned(),
|
283 |
SearchResult {
|
284 |
title: "Example Domain".to_owned(),
|
@@ -287,8 +301,8 @@ mod tests {
|
|
287 |
.to_owned(),
|
288 |
engine: smallvec!["Google".to_owned(), "Bing".to_owned()],
|
289 |
},
|
290 |
-
);
|
291 |
-
map_to_be_filtered.
|
292 |
"https://www.rust-lang.org/".to_owned(),
|
293 |
SearchResult {
|
294 |
title: "Rust Programming Language".to_owned(),
|
@@ -296,34 +310,39 @@ mod tests {
|
|
296 |
description: "A systems programming language that runs blazingly fast, prevents segfaults, and guarantees thread safety.".to_owned(),
|
297 |
engine: smallvec!["Google".to_owned(), "DuckDuckGo".to_owned()],
|
298 |
},
|
299 |
-
);
|
300 |
|
301 |
// Create a temporary file with a regex pattern containing a wildcard
|
302 |
let mut file = NamedTempFile::new()?;
|
303 |
writeln!(file, "ex.*le")?;
|
304 |
file.flush()?;
|
305 |
|
306 |
-
let mut resultant_map =
|
307 |
|
308 |
filter_with_lists(
|
309 |
&mut map_to_be_filtered,
|
310 |
&mut resultant_map,
|
311 |
file.path().to_str().unwrap(),
|
312 |
-
)
|
|
|
313 |
|
314 |
assert_eq!(resultant_map.len(), 1);
|
315 |
-
assert!(resultant_map
|
|
|
|
|
316 |
assert_eq!(map_to_be_filtered.len(), 1);
|
317 |
-
assert!(map_to_be_filtered
|
|
|
|
|
318 |
|
319 |
Ok(())
|
320 |
}
|
321 |
|
322 |
-
#[test]
|
323 |
-
fn test_filter_with_lists_file_not_found() {
|
324 |
-
let mut map_to_be_filtered =
|
325 |
|
326 |
-
let mut resultant_map =
|
327 |
|
328 |
// Call the `filter_with_lists` function with a non-existent file path
|
329 |
let result = filter_with_lists(
|
@@ -332,13 +351,13 @@ mod tests {
|
|
332 |
"non-existent-file.txt",
|
333 |
);
|
334 |
|
335 |
-
assert!(result.is_err());
|
336 |
}
|
337 |
|
338 |
-
#[test]
|
339 |
-
fn test_filter_with_lists_invalid_regex() {
|
340 |
-
let mut map_to_be_filtered =
|
341 |
-
map_to_be_filtered.
|
342 |
"https://www.example.com".to_owned(),
|
343 |
SearchResult {
|
344 |
title: "Example Domain".to_owned(),
|
@@ -347,9 +366,9 @@ mod tests {
|
|
347 |
.to_owned(),
|
348 |
engine: smallvec!["Google".to_owned(), "Bing".to_owned()],
|
349 |
},
|
350 |
-
);
|
351 |
|
352 |
-
let mut resultant_map =
|
353 |
|
354 |
// Create a temporary file with an invalid regex pattern
|
355 |
let mut file = NamedTempFile::new().unwrap();
|
@@ -362,6 +381,6 @@ mod tests {
|
|
362 |
file.path().to_str().unwrap(),
|
363 |
);
|
364 |
|
365 |
-
assert!(result.is_err());
|
366 |
}
|
367 |
}
|
|
|
9 |
engine_models::{EngineError, EngineHandler},
|
10 |
};
|
11 |
use error_stack::Report;
|
12 |
+
use futures::stream::FuturesUnordered;
|
13 |
use regex::Regex;
|
14 |
use reqwest::{Client, ClientBuilder};
|
15 |
+
use std::sync::Arc;
|
16 |
use std::time::{SystemTime, UNIX_EPOCH};
|
17 |
+
use tokio::{
|
18 |
+
fs::File,
|
19 |
+
io::{AsyncBufReadExt, BufReader},
|
20 |
+
task::JoinHandle,
|
21 |
time::Duration,
|
22 |
};
|
|
|
|
|
23 |
|
24 |
/// A constant for holding the prebuilt Client globally in the app.
|
25 |
static CLIENT: std::sync::OnceLock<Client> = std::sync::OnceLock::new();
|
26 |
|
27 |
/// Aliases for long type annotations
|
28 |
+
|
29 |
+
type FutureVec =
|
30 |
+
FuturesUnordered<JoinHandle<Result<Vec<(String, SearchResult)>, Report<EngineError>>>>;
|
31 |
|
32 |
/// The function aggregates the scraped results from the user-selected upstream search engines.
|
33 |
/// These engines can be chosen either from the user interface (UI) or from the configuration file.
|
|
|
40 |
///
|
41 |
/// Additionally, the function eliminates duplicate results. If two results are identified as coming from
|
42 |
/// multiple engines, their names are combined to indicate that the results were fetched from these upstream
|
43 |
+
/// engines. After this, all the data in the `Vec` is removed and placed into a struct that contains all
|
44 |
/// the aggregated results in a vector. Furthermore, the query used is also added to the struct. This step is
|
45 |
/// necessary to ensure that the search bar in the search remains populated even when searched from the query URL.
|
46 |
///
|
|
|
97 |
let mut names: Vec<&str> = Vec::with_capacity(0);
|
98 |
|
99 |
// create tasks for upstream result fetching
|
100 |
+
let tasks: FutureVec = FutureVec::new();
|
101 |
|
102 |
+
let query: Arc<String> = Arc::new(query.to_string());
|
103 |
for engine_handler in upstream_search_engines {
|
104 |
+
let (name, search_engine) = engine_handler.clone().into_name_engine();
|
105 |
names.push(name);
|
106 |
+
let query_partially_cloned = query.clone();
|
107 |
tasks.push(tokio::spawn(async move {
|
108 |
search_engine
|
109 |
+
.results(
|
110 |
+
&query_partially_cloned,
|
111 |
+
page,
|
112 |
+
user_agent,
|
113 |
+
client,
|
114 |
+
safe_search,
|
115 |
+
)
|
116 |
.await
|
117 |
}));
|
118 |
}
|
|
|
127 |
}
|
128 |
|
129 |
// aggregate search results, removing duplicates and handling errors the upstream engines returned
|
130 |
+
let mut result_map: Vec<(String, SearchResult)> = Vec::new();
|
131 |
let mut engine_errors_info: Vec<EngineErrorInfo> = Vec::new();
|
132 |
|
133 |
let mut handle_error = |error: &Report<EngineError>, engine_name: &'static str| {
|
|
|
144 |
|
145 |
if result_map.is_empty() {
|
146 |
match response {
|
147 |
+
Ok(results) => result_map = results,
|
148 |
+
Err(error) => handle_error(&error, engine),
|
149 |
+
};
|
|
|
|
|
|
|
|
|
150 |
continue;
|
151 |
}
|
152 |
|
153 |
match response {
|
154 |
Ok(result) => {
|
155 |
result.into_iter().for_each(|(key, value)| {
|
156 |
+
match result_map.iter().find(|(key_s, _)| key_s == &key) {
|
157 |
+
Some(value) => value.1.to_owned().add_engines(engine),
|
158 |
+
None => result_map.push((key, value)),
|
159 |
+
};
|
|
|
|
|
160 |
});
|
161 |
}
|
162 |
+
Err(error) => handle_error(&error, engine),
|
163 |
+
};
|
|
|
|
|
164 |
}
|
165 |
|
166 |
if safe_search >= 3 {
|
167 |
+
let mut blacklist_map: Vec<(String, SearchResult)> = Vec::new();
|
168 |
filter_with_lists(
|
169 |
&mut result_map,
|
170 |
&mut blacklist_map,
|
171 |
file_path(FileType::BlockList)?,
|
172 |
+
)
|
173 |
+
.await?;
|
174 |
|
175 |
filter_with_lists(
|
176 |
&mut blacklist_map,
|
177 |
&mut result_map,
|
178 |
file_path(FileType::AllowList)?,
|
179 |
+
)
|
180 |
+
.await?;
|
181 |
|
182 |
drop(blacklist_map);
|
183 |
}
|
184 |
|
185 |
+
let results: Vec<SearchResult> = result_map.iter().map(|(_, value)| value.clone()).collect();
|
186 |
|
187 |
Ok(SearchResults::new(results, &engine_errors_info))
|
188 |
}
|
|
|
191 |
///
|
192 |
/// # Arguments
|
193 |
///
|
194 |
+
/// * `map_to_be_filtered` - A mutable reference to a `Vec` of search results to filter, where the filtered results will be removed from.
|
195 |
+
/// * `resultant_map` - A mutable reference to a `Vec` to hold the filtered results.
|
196 |
/// * `file_path` - A `&str` representing the path to a file containing regex patterns to use for filtering.
|
197 |
///
|
198 |
/// # Errors
|
199 |
///
|
200 |
/// Returns an error if the file at `file_path` cannot be opened or read, or if a regex pattern is invalid.
|
201 |
+
pub async fn filter_with_lists(
|
202 |
+
map_to_be_filtered: &mut Vec<(String, SearchResult)>,
|
203 |
+
resultant_map: &mut Vec<(String, SearchResult)>,
|
204 |
file_path: &str,
|
205 |
) -> Result<(), Box<dyn std::error::Error>> {
|
206 |
+
let reader = BufReader::new(File::open(file_path).await?);
|
207 |
+
let mut lines = reader.lines();
|
208 |
|
209 |
+
while let Some(line) = lines.next_line().await? {
|
210 |
+
let re = Regex::new(line.trim())?;
|
211 |
|
212 |
+
let mut length = map_to_be_filtered.len();
|
213 |
+
let mut idx: usize = Default::default();
|
214 |
// Iterate over each search result in the map and check if it matches the regex pattern
|
215 |
+
while idx < length {
|
216 |
+
let ele = &map_to_be_filtered[idx];
|
217 |
+
let ele_inner = &ele.1;
|
218 |
+
match re.is_match(&ele.0.to_lowercase())
|
219 |
+
|| re.is_match(&ele_inner.title.to_lowercase())
|
220 |
+
|| re.is_match(&ele_inner.description.to_lowercase())
|
221 |
{
|
222 |
+
true => {
|
223 |
+
// If the search result matches the regex pattern, move it from the original map to the resultant map
|
224 |
+
resultant_map.push(map_to_be_filtered.swap_remove(idx));
|
225 |
+
length -= 1;
|
226 |
+
}
|
227 |
+
false => idx += 1,
|
228 |
+
};
|
229 |
}
|
230 |
}
|
231 |
|
|
|
236 |
mod tests {
|
237 |
use super::*;
|
238 |
use smallvec::smallvec;
|
|
|
239 |
use std::io::Write;
|
240 |
use tempfile::NamedTempFile;
|
241 |
|
242 |
+
#[tokio::test]
|
243 |
+
async fn test_filter_with_lists() -> Result<(), Box<dyn std::error::Error>> {
|
244 |
// Create a map of search results to filter
|
245 |
+
let mut map_to_be_filtered = Vec::new();
|
246 |
+
map_to_be_filtered.push((
|
247 |
"https://www.example.com".to_owned(),
|
248 |
SearchResult {
|
249 |
title: "Example Domain".to_owned(),
|
|
|
252 |
.to_owned(),
|
253 |
engine: smallvec!["Google".to_owned(), "Bing".to_owned()],
|
254 |
},
|
255 |
+
));
|
256 |
+
map_to_be_filtered.push((
|
257 |
"https://www.rust-lang.org/".to_owned(),
|
258 |
SearchResult {
|
259 |
title: "Rust Programming Language".to_owned(),
|
260 |
url: "https://www.rust-lang.org/".to_owned(),
|
261 |
description: "A systems programming language that runs blazingly fast, prevents segfaults, and guarantees thread safety.".to_owned(),
|
262 |
engine: smallvec!["Google".to_owned(), "DuckDuckGo".to_owned()],
|
263 |
+
},)
|
264 |
);
|
265 |
|
266 |
// Create a temporary file with regex patterns
|
|
|
269 |
writeln!(file, "rust")?;
|
270 |
file.flush()?;
|
271 |
|
272 |
+
let mut resultant_map = Vec::new();
|
273 |
filter_with_lists(
|
274 |
&mut map_to_be_filtered,
|
275 |
&mut resultant_map,
|
276 |
file.path().to_str().unwrap(),
|
277 |
+
)
|
278 |
+
.await?;
|
279 |
|
280 |
assert_eq!(resultant_map.len(), 2);
|
281 |
+
assert!(resultant_map
|
282 |
+
.iter()
|
283 |
+
.any(|(key, _)| key == "https://www.example.com"));
|
284 |
+
assert!(resultant_map
|
285 |
+
.iter()
|
286 |
+
.any(|(key, _)| key == "https://www.rust-lang.org/"));
|
287 |
assert_eq!(map_to_be_filtered.len(), 0);
|
288 |
|
289 |
Ok(())
|
290 |
}
|
291 |
|
292 |
+
#[tokio::test]
|
293 |
+
async fn test_filter_with_lists_wildcard() -> Result<(), Box<dyn std::error::Error>> {
|
294 |
+
let mut map_to_be_filtered = Vec::new();
|
295 |
+
map_to_be_filtered.push((
|
296 |
"https://www.example.com".to_owned(),
|
297 |
SearchResult {
|
298 |
title: "Example Domain".to_owned(),
|
|
|
301 |
.to_owned(),
|
302 |
engine: smallvec!["Google".to_owned(), "Bing".to_owned()],
|
303 |
},
|
304 |
+
));
|
305 |
+
map_to_be_filtered.push((
|
306 |
"https://www.rust-lang.org/".to_owned(),
|
307 |
SearchResult {
|
308 |
title: "Rust Programming Language".to_owned(),
|
|
|
310 |
description: "A systems programming language that runs blazingly fast, prevents segfaults, and guarantees thread safety.".to_owned(),
|
311 |
engine: smallvec!["Google".to_owned(), "DuckDuckGo".to_owned()],
|
312 |
},
|
313 |
+
));
|
314 |
|
315 |
// Create a temporary file with a regex pattern containing a wildcard
|
316 |
let mut file = NamedTempFile::new()?;
|
317 |
writeln!(file, "ex.*le")?;
|
318 |
file.flush()?;
|
319 |
|
320 |
+
let mut resultant_map = Vec::new();
|
321 |
|
322 |
filter_with_lists(
|
323 |
&mut map_to_be_filtered,
|
324 |
&mut resultant_map,
|
325 |
file.path().to_str().unwrap(),
|
326 |
+
)
|
327 |
+
.await?;
|
328 |
|
329 |
assert_eq!(resultant_map.len(), 1);
|
330 |
+
assert!(resultant_map
|
331 |
+
.iter()
|
332 |
+
.any(|(key, _)| key == "https://www.example.com"));
|
333 |
assert_eq!(map_to_be_filtered.len(), 1);
|
334 |
+
assert!(map_to_be_filtered
|
335 |
+
.iter()
|
336 |
+
.any(|(key, _)| key == "https://www.rust-lang.org/"));
|
337 |
|
338 |
Ok(())
|
339 |
}
|
340 |
|
341 |
+
#[tokio::test]
|
342 |
+
async fn test_filter_with_lists_file_not_found() {
|
343 |
+
let mut map_to_be_filtered = Vec::new();
|
344 |
|
345 |
+
let mut resultant_map = Vec::new();
|
346 |
|
347 |
// Call the `filter_with_lists` function with a non-existent file path
|
348 |
let result = filter_with_lists(
|
|
|
351 |
"non-existent-file.txt",
|
352 |
);
|
353 |
|
354 |
+
assert!(result.await.is_err());
|
355 |
}
|
356 |
|
357 |
+
#[tokio::test]
|
358 |
+
async fn test_filter_with_lists_invalid_regex() {
|
359 |
+
let mut map_to_be_filtered = Vec::new();
|
360 |
+
map_to_be_filtered.push((
|
361 |
"https://www.example.com".to_owned(),
|
362 |
SearchResult {
|
363 |
title: "Example Domain".to_owned(),
|
|
|
366 |
.to_owned(),
|
367 |
engine: smallvec!["Google".to_owned(), "Bing".to_owned()],
|
368 |
},
|
369 |
+
));
|
370 |
|
371 |
+
let mut resultant_map = Vec::new();
|
372 |
|
373 |
// Create a temporary file with an invalid regex pattern
|
374 |
let mut file = NamedTempFile::new().unwrap();
|
|
|
381 |
file.path().to_str().unwrap(),
|
382 |
);
|
383 |
|
384 |
+
assert!(result.await.is_err());
|
385 |
}
|
386 |
}
|
@@ -7,11 +7,13 @@ use crate::{
|
|
7 |
handler::{file_path, FileType},
|
8 |
};
|
9 |
use actix_web::{get, http::header::ContentType, web, HttpRequest, HttpResponse};
|
10 |
-
use
|
11 |
|
12 |
/// Handles the route of index page or main page of the `websurfx` meta search engine website.
|
13 |
#[get("/")]
|
14 |
-
pub async fn index(
|
|
|
|
|
15 |
Ok(HttpResponse::Ok().content_type(ContentType::html()).body(
|
16 |
crate::templates::views::index::index(
|
17 |
&config.style.colorscheme,
|
@@ -25,7 +27,7 @@ pub async fn index(config: web::Data<Config>) -> Result<HttpResponse, Box<dyn st
|
|
25 |
/// Handles the route of any other accessed route/page which is not provided by the
|
26 |
/// website essentially the 404 error page.
|
27 |
pub async fn not_found(
|
28 |
-
config: web::Data
|
29 |
) -> Result<HttpResponse, Box<dyn std::error::Error>> {
|
30 |
Ok(HttpResponse::Ok().content_type(ContentType::html()).body(
|
31 |
crate::templates::views::not_found::not_found(
|
@@ -41,7 +43,7 @@ pub async fn not_found(
|
|
41 |
#[get("/robots.txt")]
|
42 |
pub async fn robots_data(_req: HttpRequest) -> Result<HttpResponse, Box<dyn std::error::Error>> {
|
43 |
let page_content: String =
|
44 |
-
read_to_string(format!("{}/robots.txt", file_path(FileType::Theme)?))?;
|
45 |
Ok(HttpResponse::Ok()
|
46 |
.content_type(ContentType::plaintext())
|
47 |
.body(page_content))
|
@@ -49,7 +51,9 @@ pub async fn robots_data(_req: HttpRequest) -> Result<HttpResponse, Box<dyn std:
|
|
49 |
|
50 |
/// Handles the route of about page of the `websurfx` meta search engine website.
|
51 |
#[get("/about")]
|
52 |
-
pub async fn about(
|
|
|
|
|
53 |
Ok(HttpResponse::Ok().content_type(ContentType::html()).body(
|
54 |
crate::templates::views::about::about(
|
55 |
&config.style.colorscheme,
|
@@ -63,7 +67,7 @@ pub async fn about(config: web::Data<Config>) -> Result<HttpResponse, Box<dyn st
|
|
63 |
/// Handles the route of settings page of the `websurfx` meta search engine website.
|
64 |
#[get("/settings")]
|
65 |
pub async fn settings(
|
66 |
-
config: web::Data
|
67 |
) -> Result<HttpResponse, Box<dyn std::error::Error>> {
|
68 |
Ok(HttpResponse::Ok().content_type(ContentType::html()).body(
|
69 |
crate::templates::views::settings::settings(
|
|
|
7 |
handler::{file_path, FileType},
|
8 |
};
|
9 |
use actix_web::{get, http::header::ContentType, web, HttpRequest, HttpResponse};
|
10 |
+
use tokio::fs::read_to_string;
|
11 |
|
12 |
/// Handles the route of index page or main page of the `websurfx` meta search engine website.
|
13 |
#[get("/")]
|
14 |
+
pub async fn index(
|
15 |
+
config: web::Data<&'static Config>,
|
16 |
+
) -> Result<HttpResponse, Box<dyn std::error::Error>> {
|
17 |
Ok(HttpResponse::Ok().content_type(ContentType::html()).body(
|
18 |
crate::templates::views::index::index(
|
19 |
&config.style.colorscheme,
|
|
|
27 |
/// Handles the route of any other accessed route/page which is not provided by the
|
28 |
/// website essentially the 404 error page.
|
29 |
pub async fn not_found(
|
30 |
+
config: web::Data<&'static Config>,
|
31 |
) -> Result<HttpResponse, Box<dyn std::error::Error>> {
|
32 |
Ok(HttpResponse::Ok().content_type(ContentType::html()).body(
|
33 |
crate::templates::views::not_found::not_found(
|
|
|
43 |
#[get("/robots.txt")]
|
44 |
pub async fn robots_data(_req: HttpRequest) -> Result<HttpResponse, Box<dyn std::error::Error>> {
|
45 |
let page_content: String =
|
46 |
+
read_to_string(format!("{}/robots.txt", file_path(FileType::Theme)?)).await?;
|
47 |
Ok(HttpResponse::Ok()
|
48 |
.content_type(ContentType::plaintext())
|
49 |
.body(page_content))
|
|
|
51 |
|
52 |
/// Handles the route of about page of the `websurfx` meta search engine website.
|
53 |
#[get("/about")]
|
54 |
+
pub async fn about(
|
55 |
+
config: web::Data<&'static Config>,
|
56 |
+
) -> Result<HttpResponse, Box<dyn std::error::Error>> {
|
57 |
Ok(HttpResponse::Ok().content_type(ContentType::html()).body(
|
58 |
crate::templates::views::about::about(
|
59 |
&config.style.colorscheme,
|
|
|
67 |
/// Handles the route of settings page of the `websurfx` meta search engine website.
|
68 |
#[get("/settings")]
|
69 |
pub async fn settings(
|
70 |
+
config: web::Data<&'static Config>,
|
71 |
) -> Result<HttpResponse, Box<dyn std::error::Error>> {
|
72 |
Ok(HttpResponse::Ok().content_type(ContentType::html()).body(
|
73 |
crate::templates::views::settings::settings(
|
@@ -13,12 +13,12 @@ use crate::{
|
|
13 |
};
|
14 |
use actix_web::{get, http::header::ContentType, web, HttpRequest, HttpResponse};
|
15 |
use regex::Regex;
|
16 |
-
use std::
|
17 |
-
|
18 |
fs::File,
|
19 |
-
io::{
|
|
|
20 |
};
|
21 |
-
use tokio::join;
|
22 |
|
23 |
/// Handles the route of search page of the `websurfx` meta search engine website and it takes
|
24 |
/// two search url parameters `q` and `page` where `page` parameter is optional.
|
@@ -37,8 +37,8 @@ use tokio::join;
|
|
37 |
#[get("/search")]
|
38 |
pub async fn search(
|
39 |
req: HttpRequest,
|
40 |
-
config: web::Data
|
41 |
-
cache: web::Data
|
42 |
) -> Result<HttpResponse, Box<dyn std::error::Error>> {
|
43 |
use std::sync::Arc;
|
44 |
let params = web::Query::<SearchParams>::from_query(req.query_string())?;
|
@@ -70,8 +70,8 @@ pub async fn search(
|
|
70 |
});
|
71 |
|
72 |
search_settings.safe_search_level = get_safesearch_level(
|
73 |
-
|
74 |
-
|
75 |
config.safe_search,
|
76 |
);
|
77 |
|
@@ -158,8 +158,8 @@ pub async fn search(
|
|
158 |
/// It returns the `SearchResults` struct if the search results could be successfully fetched from
|
159 |
/// the cache or from the upstream search engines otherwise it returns an appropriate error.
|
160 |
async fn results(
|
161 |
-
config: &Config,
|
162 |
-
cache: &
|
163 |
query: &str,
|
164 |
page: u32,
|
165 |
search_settings: &server_models::Cookie<'_>,
|
@@ -188,7 +188,7 @@ async fn results(
|
|
188 |
let mut results: SearchResults = SearchResults::default();
|
189 |
|
190 |
let flag: bool =
|
191 |
-
!is_match_from_filter_list(file_path(FileType::BlockList)?, query)?;
|
192 |
// Return early when query contains disallowed words,
|
193 |
if flag {
|
194 |
results.set_disallowed();
|
@@ -225,12 +225,12 @@ async fn results(
|
|
225 |
search_results
|
226 |
}
|
227 |
};
|
228 |
-
|
229 |
-
|
230 |
-
|
231 |
-
|
232 |
-
|
233 |
-
|
234 |
cache
|
235 |
.cache_results(&[results.clone()], &[cache_key.clone()])
|
236 |
.await?;
|
@@ -252,13 +252,14 @@ async fn results(
|
|
252 |
///
|
253 |
/// Returns a bool indicating whether the results were found in the list or not on success
|
254 |
/// otherwise returns a standard error type on a failure.
|
255 |
-
fn is_match_from_filter_list(
|
256 |
file_path: &str,
|
257 |
query: &str,
|
258 |
) -> Result<bool, Box<dyn std::error::Error>> {
|
259 |
-
let
|
260 |
-
|
261 |
-
|
|
|
262 |
if re.is_match(query) {
|
263 |
return Ok(true);
|
264 |
}
|
@@ -267,24 +268,95 @@ fn is_match_from_filter_list(
|
|
267 |
Ok(false)
|
268 |
}
|
269 |
|
270 |
-
/// A helper function to
|
271 |
-
///
|
272 |
-
/// the default set by the server config if the cookie was missing.
|
273 |
///
|
274 |
/// # Argurments
|
275 |
///
|
276 |
-
/// * `
|
277 |
-
/// * `
|
278 |
-
/// * `
|
279 |
-
|
280 |
-
|
281 |
-
|
282 |
-
|
283 |
-
|
284 |
-
|
285 |
-
|
286 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
287 |
}
|
288 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
289 |
}
|
290 |
}
|
|
|
13 |
};
|
14 |
use actix_web::{get, http::header::ContentType, web, HttpRequest, HttpResponse};
|
15 |
use regex::Regex;
|
16 |
+
use std::borrow::Cow;
|
17 |
+
use tokio::{
|
18 |
fs::File,
|
19 |
+
io::{AsyncBufReadExt, BufReader},
|
20 |
+
join,
|
21 |
};
|
|
|
22 |
|
23 |
/// Handles the route of search page of the `websurfx` meta search engine website and it takes
|
24 |
/// two search url parameters `q` and `page` where `page` parameter is optional.
|
|
|
37 |
#[get("/search")]
|
38 |
pub async fn search(
|
39 |
req: HttpRequest,
|
40 |
+
config: web::Data<&'static Config>,
|
41 |
+
cache: web::Data<&'static SharedCache>,
|
42 |
) -> Result<HttpResponse, Box<dyn std::error::Error>> {
|
43 |
use std::sync::Arc;
|
44 |
let params = web::Query::<SearchParams>::from_query(req.query_string())?;
|
|
|
70 |
});
|
71 |
|
72 |
search_settings.safe_search_level = get_safesearch_level(
|
73 |
+
params.safesearch,
|
74 |
+
search_settings.safe_search_level,
|
75 |
config.safe_search,
|
76 |
);
|
77 |
|
|
|
158 |
/// It returns the `SearchResults` struct if the search results could be successfully fetched from
|
159 |
/// the cache or from the upstream search engines otherwise it returns an appropriate error.
|
160 |
async fn results(
|
161 |
+
config: &'static Config,
|
162 |
+
cache: &'static SharedCache,
|
163 |
query: &str,
|
164 |
page: u32,
|
165 |
search_settings: &server_models::Cookie<'_>,
|
|
|
188 |
let mut results: SearchResults = SearchResults::default();
|
189 |
|
190 |
let flag: bool =
|
191 |
+
!is_match_from_filter_list(file_path(FileType::BlockList)?, query).await?;
|
192 |
// Return early when query contains disallowed words,
|
193 |
if flag {
|
194 |
results.set_disallowed();
|
|
|
225 |
search_results
|
226 |
}
|
227 |
};
|
228 |
+
let (engine_errors_info, results_empty_check, no_engines_selected) = (
|
229 |
+
results.engine_errors_info().is_empty(),
|
230 |
+
results.results().is_empty(),
|
231 |
+
results.no_engines_selected(),
|
232 |
+
);
|
233 |
+
results.set_filtered(engine_errors_info & results_empty_check & !no_engines_selected);
|
234 |
cache
|
235 |
.cache_results(&[results.clone()], &[cache_key.clone()])
|
236 |
.await?;
|
|
|
252 |
///
|
253 |
/// Returns a bool indicating whether the results were found in the list or not on success
|
254 |
/// otherwise returns a standard error type on a failure.
|
255 |
+
async fn is_match_from_filter_list(
|
256 |
file_path: &str,
|
257 |
query: &str,
|
258 |
) -> Result<bool, Box<dyn std::error::Error>> {
|
259 |
+
let reader = BufReader::new(File::open(file_path).await?);
|
260 |
+
let mut lines = reader.lines();
|
261 |
+
while let Some(line) = lines.next_line().await? {
|
262 |
+
let re = Regex::new(&line)?;
|
263 |
if re.is_match(query) {
|
264 |
return Ok(true);
|
265 |
}
|
|
|
268 |
Ok(false)
|
269 |
}
|
270 |
|
271 |
+
/// A helper function to choose the safe search level value based on the URL parameters,
|
272 |
+
/// cookie value and config value.
|
|
|
273 |
///
|
274 |
/// # Argurments
|
275 |
///
|
276 |
+
/// * `safe_search_level_from_url` - Safe search level from the URL parameters.
|
277 |
+
/// * `cookie_safe_search_level` - Safe search level value from the cookie.
|
278 |
+
/// * `config_safe_search_level` - Safe search level value from the config file.
|
279 |
+
///
|
280 |
+
/// # Returns
|
281 |
+
///
|
282 |
+
/// Returns an appropriate safe search level value based on the safe search level values
|
283 |
+
/// from the URL parameters, cookie and the config file.
|
284 |
+
fn get_safesearch_level(
|
285 |
+
safe_search_level_from_url: Option<u8>,
|
286 |
+
cookie_safe_search_level: u8,
|
287 |
+
config_safe_search_level: u8,
|
288 |
+
) -> u8 {
|
289 |
+
(u8::from(safe_search_level_from_url.is_some())
|
290 |
+
* ((u8::from(config_safe_search_level >= 3) * config_safe_search_level)
|
291 |
+
+ (u8::from(config_safe_search_level < 3) * safe_search_level_from_url.unwrap_or(0))))
|
292 |
+
+ (u8::from(safe_search_level_from_url.is_none())
|
293 |
+
* ((u8::from(config_safe_search_level >= 3) * config_safe_search_level)
|
294 |
+
+ (u8::from(config_safe_search_level < 3) * cookie_safe_search_level)))
|
295 |
+
}
|
296 |
+
|
297 |
+
#[cfg(test)]
|
298 |
+
mod tests {
|
299 |
+
use std::time::{SystemTime, UNIX_EPOCH};
|
300 |
+
|
301 |
+
/// A helper function which creates a random mock safe search level value.
|
302 |
+
///
|
303 |
+
/// # Returns
|
304 |
+
///
|
305 |
+
/// Returns an optional u8 value.
|
306 |
+
fn mock_safe_search_level_value() -> Option<u8> {
|
307 |
+
let nanos = SystemTime::now()
|
308 |
+
.duration_since(UNIX_EPOCH)
|
309 |
+
.unwrap_or_default()
|
310 |
+
.subsec_nanos() as f32;
|
311 |
+
let delay = ((nanos / 1_0000_0000 as f32).floor() as i8) - 1;
|
312 |
+
|
313 |
+
match delay {
|
314 |
+
-1 => None,
|
315 |
+
some_num => Some(if some_num > 4 { some_num - 4 } else { some_num } as u8),
|
316 |
}
|
317 |
+
}
|
318 |
+
|
319 |
+
#[test]
|
320 |
+
/// A test function to test whether the output of the branchless and branched code
|
321 |
+
/// for the code to choose the appropriate safe search level is same or not.
|
322 |
+
fn get_safesearch_level_branched_branchless_code_test() {
|
323 |
+
// Get mock values for the safe search level values for URL parameters, cookie
|
324 |
+
// and config.
|
325 |
+
let safe_search_level_from_url = mock_safe_search_level_value();
|
326 |
+
let cookie_safe_search_level = mock_safe_search_level_value().unwrap_or(0);
|
327 |
+
let config_safe_search_level = mock_safe_search_level_value().unwrap_or(0);
|
328 |
+
|
329 |
+
// Branched code
|
330 |
+
let safe_search_level_value_from_branched_code = match safe_search_level_from_url {
|
331 |
+
Some(safe_search_level_from_url_parsed) => {
|
332 |
+
if config_safe_search_level >= 3 {
|
333 |
+
config_safe_search_level
|
334 |
+
} else {
|
335 |
+
safe_search_level_from_url_parsed
|
336 |
+
}
|
337 |
+
}
|
338 |
+
None => {
|
339 |
+
if config_safe_search_level >= 3 {
|
340 |
+
config_safe_search_level
|
341 |
+
} else {
|
342 |
+
cookie_safe_search_level
|
343 |
+
}
|
344 |
+
}
|
345 |
+
};
|
346 |
+
|
347 |
+
// branchless code
|
348 |
+
let safe_search_level_value_from_branchless_code =
|
349 |
+
(u8::from(safe_search_level_from_url.is_some())
|
350 |
+
* ((u8::from(config_safe_search_level >= 3) * config_safe_search_level)
|
351 |
+
+ (u8::from(config_safe_search_level < 3)
|
352 |
+
* safe_search_level_from_url.unwrap_or(0))))
|
353 |
+
+ (u8::from(safe_search_level_from_url.is_none())
|
354 |
+
* ((u8::from(config_safe_search_level >= 3) * config_safe_search_level)
|
355 |
+
+ (u8::from(config_safe_search_level < 3) * cookie_safe_search_level)));
|
356 |
+
|
357 |
+
assert_eq!(
|
358 |
+
safe_search_level_value_from_branched_code,
|
359 |
+
safe_search_level_value_from_branchless_code
|
360 |
+
);
|
361 |
}
|
362 |
}
|
@@ -55,7 +55,7 @@ pub fn engines(engine_names: &HashMap<String, bool>) -> Markup {
|
|
55 |
input type="checkbox" class="engine" checked;
|
56 |
span class="slider round"{}
|
57 |
}
|
58 |
-
(format!("{}{}"
|
59 |
}
|
60 |
}
|
61 |
@else {
|
@@ -64,7 +64,7 @@ pub fn engines(engine_names: &HashMap<String, bool>) -> Markup {
|
|
64 |
input type="checkbox" class="engine";
|
65 |
span class="slider round"{}
|
66 |
}
|
67 |
-
(format!("{}{}"
|
68 |
}
|
69 |
}
|
70 |
}
|
|
|
55 |
input type="checkbox" class="engine" checked;
|
56 |
span class="slider round"{}
|
57 |
}
|
58 |
+
(format!("{}{}",&engine_name[..1].to_uppercase(), &engine_name[1..]))
|
59 |
}
|
60 |
}
|
61 |
@else {
|
|
|
64 |
input type="checkbox" class="engine";
|
65 |
span class="slider round"{}
|
66 |
}
|
67 |
+
(format!("{}{}",&engine_name[..1], &engine_name[1..]))
|
68 |
}
|
69 |
}
|
70 |
}
|
@@ -36,7 +36,7 @@ fn style_option_list(
|
|
36 |
}
|
37 |
|
38 |
if style_type == "animations" {
|
39 |
-
style_option_names.push((
|
40 |
}
|
41 |
|
42 |
Ok(style_option_names)
|
@@ -83,9 +83,11 @@ pub fn user_interface(
|
|
83 |
"Select the animation for your theme to be used in user interface"
|
84 |
}
|
85 |
select name="animations"{
|
|
|
|
|
86 |
// Sets the user selected animation name from the config file as the first option in the selection list.
|
87 |
-
option value=(animation
|
88 |
-
@for (k,v) in style_option_list("animations", animation
|
89 |
option value=(k){(v)}
|
90 |
}
|
91 |
}
|
|
|
36 |
}
|
37 |
|
38 |
if style_type == "animations" {
|
39 |
+
style_option_names.push((String::default(), "none".to_owned()))
|
40 |
}
|
41 |
|
42 |
Ok(style_option_names)
|
|
|
83 |
"Select the animation for your theme to be used in user interface"
|
84 |
}
|
85 |
select name="animations"{
|
86 |
+
@let default_animation = &String::default();
|
87 |
+
@let animation = animation.as_ref().unwrap_or(default_animation);
|
88 |
// Sets the user selected animation name from the config file as the first option in the selection list.
|
89 |
+
option value=(animation){(animation.replace('-'," "))}
|
90 |
+
@for (k,v) in style_option_list("animations", animation)?{
|
91 |
option value=(k){(v)}
|
92 |
}
|
93 |
}
|
@@ -38,7 +38,7 @@ pub fn search(
|
|
38 |
small{(result.url)}
|
39 |
p{(PreEscaped(&result.description))}
|
40 |
.upstream_engines{
|
41 |
-
@for name in result.
|
42 |
span{(name)}
|
43 |
}
|
44 |
}
|
|
|
38 |
small{(result.url)}
|
39 |
p{(PreEscaped(&result.description))}
|
40 |
.upstream_engines{
|
41 |
+
@for name in &result.engine {
|
42 |
span{(name)}
|
43 |
}
|
44 |
}
|
@@ -1,14 +1,17 @@
|
|
1 |
-
use std::net::TcpListener;
|
2 |
|
3 |
use websurfx::{config::parser::Config, run, templates::views};
|
4 |
|
|
|
|
|
|
|
5 |
// Starts a new instance of the HTTP server, bound to a random available port
|
6 |
async fn spawn_app() -> String {
|
7 |
// Binding to port 0 will trigger the OS to assign a port for us.
|
8 |
let listener = TcpListener::bind("127.0.0.1:0").expect("Failed to bind random port");
|
9 |
let port = listener.local_addr().unwrap().port();
|
10 |
-
let config = Config::parse(false).unwrap();
|
11 |
-
let cache = websurfx::cache::cacher::create_cache(
|
12 |
let server = run(listener, config, cache).expect("Failed to bind address");
|
13 |
|
14 |
tokio::spawn(server);
|
|
|
1 |
+
use std::{net::TcpListener, sync::OnceLock};
|
2 |
|
3 |
use websurfx::{config::parser::Config, run, templates::views};
|
4 |
|
5 |
+
/// A static constant for holding the parsed config.
|
6 |
+
static CONFIG: OnceLock<Config> = OnceLock::new();
|
7 |
+
|
8 |
// Starts a new instance of the HTTP server, bound to a random available port
|
9 |
async fn spawn_app() -> String {
|
10 |
// Binding to port 0 will trigger the OS to assign a port for us.
|
11 |
let listener = TcpListener::bind("127.0.0.1:0").expect("Failed to bind random port");
|
12 |
let port = listener.local_addr().unwrap().port();
|
13 |
+
let config = CONFIG.get_or_init(|| Config::parse(false).unwrap());
|
14 |
+
let cache = websurfx::cache::cacher::create_cache(config).await;
|
15 |
let server = run(listener, config, cache).expect("Failed to bind address");
|
16 |
|
17 |
tokio::spawn(server);
|