├── .gitignore ├── API ├── Cargo.lock ├── Cargo.toml ├── Shuttle.toml ├── src │ └── main.rs └── static │ ├── assets │ ├── index-726b6ed3.js │ └── index-8cf6afb9.css │ ├── index.html │ └── vite.svg ├── README.md ├── Screenshot.png ├── index.html ├── package.json ├── postcss.config.cjs ├── public └── vite.svg ├── src ├── App.tsx ├── assets │ └── react.svg ├── components │ └── NamePrompt.tsx ├── index.css ├── main.tsx └── vite-env.d.ts ├── tailwind.config.cjs ├── tsconfig.json ├── tsconfig.node.json └── vite.config.ts /.gitignore: -------------------------------------------------------------------------------- 1 | # Logs 2 | logs 3 | *.log 4 | npm-debug.log* 5 | yarn-debug.log* 6 | yarn-error.log* 7 | pnpm-debug.log* 8 | lerna-debug.log* 9 | 10 | node_modules 11 | dist 12 | dist-ssr 13 | *.local 14 | 15 | # Editor directories and files 16 | .env 17 | .vscode/* 18 | !.vscode/extensions.json 19 | .idea 20 | .DS_Store 21 | *.suo 22 | *.ntvs* 23 | *.njsproj 24 | *.sln 25 | *.sw? 26 | 27 | 28 | # Added by cargo 29 | 30 | /target 31 | /Cargo.lock 32 | target 33 | 34 | # Added for project 35 | Secrets.toml 36 | -------------------------------------------------------------------------------- /API/Cargo.lock: -------------------------------------------------------------------------------- 1 | # This file is automatically @generated by Cargo. 2 | # It is not intended for manual editing. 3 | version = 3 4 | 5 | [[package]] 6 | name = "android_system_properties" 7 | version = "0.1.5" 8 | source = "registry+https://github.com/rust-lang/crates.io-index" 9 | checksum = "819e7219dbd41043ac279b19830f2efc897156490d7fd6ea916720117ee66311" 10 | dependencies = [ 11 | "libc", 12 | ] 13 | 14 | [[package]] 15 | name = "anyhow" 16 | version = "1.0.68" 17 | source = "registry+https://github.com/rust-lang/crates.io-index" 18 | checksum = "2cb2f989d18dd141ab8ae82f64d1a8cdd37e0840f73a406896cf5e99502fab61" 19 | 20 | [[package]] 21 | name = "async-trait" 22 | version = "0.1.61" 23 | source = "registry+https://github.com/rust-lang/crates.io-index" 24 | checksum = "705339e0e4a9690e2908d2b3d049d85682cf19fbd5782494498fbf7003a6a282" 25 | dependencies = [ 26 | "proc-macro2", 27 | "quote", 28 | "syn", 29 | ] 30 | 31 | [[package]] 32 | name = "autocfg" 33 | version = "1.1.0" 34 | source = "registry+https://github.com/rust-lang/crates.io-index" 35 | checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa" 36 | 37 | [[package]] 38 | name = "axum" 39 | version = "0.6.4" 40 | source = "registry+https://github.com/rust-lang/crates.io-index" 41 | checksum = "e5694b64066a2459918d8074c2ce0d5a88f409431994c2356617c8ae0c4721fc" 42 | dependencies = [ 43 | "async-trait", 44 | "axum-core", 45 | "base64 0.20.0", 46 | "bitflags", 47 | "bytes", 48 | "futures-util", 49 | "http", 50 | "http-body", 51 | "hyper", 52 | "itoa", 53 | "matchit", 54 | "memchr", 55 | "mime", 56 | "percent-encoding", 57 | "pin-project-lite", 58 | "rustversion", 59 | "serde", 60 | "serde_json", 61 | "serde_path_to_error", 62 | "serde_urlencoded", 63 | "sha1", 64 | "sync_wrapper", 65 | "tokio", 66 | "tokio-tungstenite", 67 | "tower", 68 | "tower-http", 69 | "tower-layer", 70 | "tower-service", 71 | ] 72 | 73 | [[package]] 74 | name = "axum-core" 75 | version = "0.3.2" 76 | source = "registry+https://github.com/rust-lang/crates.io-index" 77 | checksum = "1cae3e661676ffbacb30f1a824089a8c9150e71017f7e1e38f2aa32009188d34" 78 | dependencies = [ 79 | "async-trait", 80 | "bytes", 81 | "futures-util", 82 | "http", 83 | "http-body", 84 | "mime", 85 | "rustversion", 86 | "tower-layer", 87 | "tower-service", 88 | ] 89 | 90 | [[package]] 91 | name = "axum-extra" 92 | version = "0.4.2" 93 | source = "registry+https://github.com/rust-lang/crates.io-index" 94 | checksum = "f9a320103719de37b7b4da4c8eb629d4573f6bcfd3dfe80d3208806895ccf81d" 95 | dependencies = [ 96 | "axum", 97 | "bytes", 98 | "futures-util", 99 | "http", 100 | "mime", 101 | "pin-project-lite", 102 | "tokio", 103 | "tower", 104 | "tower-http", 105 | "tower-layer", 106 | "tower-service", 107 | ] 108 | 109 | [[package]] 110 | name = "base64" 111 | version = "0.13.1" 112 | source = "registry+https://github.com/rust-lang/crates.io-index" 113 | checksum = "9e1b586273c5702936fe7b7d6896644d8be71e6314cfe09d3167c95f712589e8" 114 | 115 | [[package]] 116 | name = "base64" 117 | version = "0.20.0" 118 | source = "registry+https://github.com/rust-lang/crates.io-index" 119 | checksum = "0ea22880d78093b0cbe17c89f64a7d457941e65759157ec6cb31a31d652b05e5" 120 | 121 | [[package]] 122 | name = "bitflags" 123 | version = "1.3.2" 124 | source = "registry+https://github.com/rust-lang/crates.io-index" 125 | checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a" 126 | 127 | [[package]] 128 | name = "block-buffer" 129 | version = "0.10.3" 130 | source = "registry+https://github.com/rust-lang/crates.io-index" 131 | checksum = "69cce20737498f97b993470a6e536b8523f0af7892a4f928cceb1ac5e52ebe7e" 132 | dependencies = [ 133 | "generic-array", 134 | ] 135 | 136 | [[package]] 137 | name = "bumpalo" 138 | version = "3.11.1" 139 | source = "registry+https://github.com/rust-lang/crates.io-index" 140 | checksum = "572f695136211188308f16ad2ca5c851a712c464060ae6974944458eb83880ba" 141 | 142 | [[package]] 143 | name = "byteorder" 144 | version = "1.4.3" 145 | source = "registry+https://github.com/rust-lang/crates.io-index" 146 | checksum = "14c189c53d098945499cdfa7ecc63567cf3886b3332b312a5b4585d8d3a6a610" 147 | 148 | [[package]] 149 | name = "bytes" 150 | version = "1.3.0" 151 | source = "registry+https://github.com/rust-lang/crates.io-index" 152 | checksum = "dfb24e866b15a1af2a1b663f10c6b6b8f397a84aadb828f12e5b289ec23a3a3c" 153 | 154 | [[package]] 155 | name = "camino" 156 | version = "1.1.2" 157 | source = "registry+https://github.com/rust-lang/crates.io-index" 158 | checksum = "c77df041dc383319cc661b428b6961a005db4d6808d5e12536931b1ca9556055" 159 | dependencies = [ 160 | "serde", 161 | ] 162 | 163 | [[package]] 164 | name = "cargo-platform" 165 | version = "0.1.2" 166 | source = "registry+https://github.com/rust-lang/crates.io-index" 167 | checksum = "cbdb825da8a5df079a43676dbe042702f1707b1109f713a01420fbb4cc71fa27" 168 | dependencies = [ 169 | "serde", 170 | ] 171 | 172 | [[package]] 173 | name = "cargo_metadata" 174 | version = "0.15.2" 175 | source = "registry+https://github.com/rust-lang/crates.io-index" 176 | checksum = "982a0cf6a99c350d7246035613882e376d58cebe571785abc5da4f648d53ac0a" 177 | dependencies = [ 178 | "camino", 179 | "cargo-platform", 180 | "semver", 181 | "serde", 182 | "serde_json", 183 | "thiserror", 184 | ] 185 | 186 | [[package]] 187 | name = "cc" 188 | version = "1.0.78" 189 | source = "registry+https://github.com/rust-lang/crates.io-index" 190 | checksum = "a20104e2335ce8a659d6dd92a51a767a0c062599c73b343fd152cb401e828c3d" 191 | 192 | [[package]] 193 | name = "cfg-if" 194 | version = "1.0.0" 195 | source = "registry+https://github.com/rust-lang/crates.io-index" 196 | checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" 197 | 198 | [[package]] 199 | name = "chrono" 200 | version = "0.4.23" 201 | source = "registry+https://github.com/rust-lang/crates.io-index" 202 | checksum = "16b0a3d9ed01224b22057780a37bb8c5dbfe1be8ba48678e7bf57ec4b385411f" 203 | dependencies = [ 204 | "iana-time-zone", 205 | "js-sys", 206 | "num-integer", 207 | "num-traits", 208 | "serde", 209 | "time", 210 | "wasm-bindgen", 211 | "winapi", 212 | ] 213 | 214 | [[package]] 215 | name = "codespan-reporting" 216 | version = "0.11.1" 217 | source = "registry+https://github.com/rust-lang/crates.io-index" 218 | checksum = "3538270d33cc669650c4b093848450d380def10c331d38c768e34cac80576e6e" 219 | dependencies = [ 220 | "termcolor", 221 | "unicode-width", 222 | ] 223 | 224 | [[package]] 225 | name = "core-foundation" 226 | version = "0.9.3" 227 | source = "registry+https://github.com/rust-lang/crates.io-index" 228 | checksum = "194a7a9e6de53fa55116934067c844d9d749312f75c6f6d0980e8c252f8c2146" 229 | dependencies = [ 230 | "core-foundation-sys", 231 | "libc", 232 | ] 233 | 234 | [[package]] 235 | name = "core-foundation-sys" 236 | version = "0.8.3" 237 | source = "registry+https://github.com/rust-lang/crates.io-index" 238 | checksum = "5827cebf4670468b8772dd191856768aedcb1b0278a04f989f7766351917b9dc" 239 | 240 | [[package]] 241 | name = "cpufeatures" 242 | version = "0.2.5" 243 | source = "registry+https://github.com/rust-lang/crates.io-index" 244 | checksum = "28d997bd5e24a5928dd43e46dc529867e207907fe0b239c3477d924f7f2ca320" 245 | dependencies = [ 246 | "libc", 247 | ] 248 | 249 | [[package]] 250 | name = "crossbeam-channel" 251 | version = "0.5.6" 252 | source = "registry+https://github.com/rust-lang/crates.io-index" 253 | checksum = "c2dd04ddaf88237dc3b8d8f9a3c1004b506b54b3313403944054d23c0870c521" 254 | dependencies = [ 255 | "cfg-if", 256 | "crossbeam-utils", 257 | ] 258 | 259 | [[package]] 260 | name = "crossbeam-utils" 261 | version = "0.8.14" 262 | source = "registry+https://github.com/rust-lang/crates.io-index" 263 | checksum = "4fb766fa798726286dbbb842f174001dab8abc7b627a1dd86e0b7222a95d929f" 264 | dependencies = [ 265 | "cfg-if", 266 | ] 267 | 268 | [[package]] 269 | name = "crypto-common" 270 | version = "0.1.6" 271 | source = "registry+https://github.com/rust-lang/crates.io-index" 272 | checksum = "1bfb12502f3fc46cca1bb51ac28df9d618d813cdc3d2f25b9fe775a34af26bb3" 273 | dependencies = [ 274 | "generic-array", 275 | "typenum", 276 | ] 277 | 278 | [[package]] 279 | name = "cxx" 280 | version = "1.0.86" 281 | source = "registry+https://github.com/rust-lang/crates.io-index" 282 | checksum = "51d1075c37807dcf850c379432f0df05ba52cc30f279c5cfc43cc221ce7f8579" 283 | dependencies = [ 284 | "cc", 285 | "cxxbridge-flags", 286 | "cxxbridge-macro", 287 | "link-cplusplus", 288 | ] 289 | 290 | [[package]] 291 | name = "cxx-build" 292 | version = "1.0.86" 293 | source = "registry+https://github.com/rust-lang/crates.io-index" 294 | checksum = "5044281f61b27bc598f2f6647d480aed48d2bf52d6eb0b627d84c0361b17aa70" 295 | dependencies = [ 296 | "cc", 297 | "codespan-reporting", 298 | "once_cell", 299 | "proc-macro2", 300 | "quote", 301 | "scratch", 302 | "syn", 303 | ] 304 | 305 | [[package]] 306 | name = "cxxbridge-flags" 307 | version = "1.0.86" 308 | source = "registry+https://github.com/rust-lang/crates.io-index" 309 | checksum = "61b50bc93ba22c27b0d31128d2d130a0a6b3d267ae27ef7e4fae2167dfe8781c" 310 | 311 | [[package]] 312 | name = "cxxbridge-macro" 313 | version = "1.0.86" 314 | source = "registry+https://github.com/rust-lang/crates.io-index" 315 | checksum = "39e61fda7e62115119469c7b3591fd913ecca96fb766cfd3f2e2502ab7bc87a5" 316 | dependencies = [ 317 | "proc-macro2", 318 | "quote", 319 | "syn", 320 | ] 321 | 322 | [[package]] 323 | name = "digest" 324 | version = "0.10.6" 325 | source = "registry+https://github.com/rust-lang/crates.io-index" 326 | checksum = "8168378f4e5023e7218c89c891c0fd8ecdb5e5e4f18cb78f38cf245dd021e76f" 327 | dependencies = [ 328 | "block-buffer", 329 | "crypto-common", 330 | ] 331 | 332 | [[package]] 333 | name = "doc-comment" 334 | version = "0.3.3" 335 | source = "registry+https://github.com/rust-lang/crates.io-index" 336 | checksum = "fea41bba32d969b513997752735605054bc0dfa92b4c56bf1189f2e174be7a10" 337 | 338 | [[package]] 339 | name = "either" 340 | version = "1.8.0" 341 | source = "registry+https://github.com/rust-lang/crates.io-index" 342 | checksum = "90e5c1c8368803113bf0c9584fc495a58b86dc8a29edbf8fe877d21d9507e797" 343 | 344 | [[package]] 345 | name = "fastrand" 346 | version = "1.8.0" 347 | source = "registry+https://github.com/rust-lang/crates.io-index" 348 | checksum = "a7a407cfaa3385c4ae6b23e84623d48c2798d06e3e6a1878f7f59f17b3f86499" 349 | dependencies = [ 350 | "instant", 351 | ] 352 | 353 | [[package]] 354 | name = "finl_unicode" 355 | version = "1.2.0" 356 | source = "registry+https://github.com/rust-lang/crates.io-index" 357 | checksum = "8fcfdc7a0362c9f4444381a9e697c79d435fe65b52a37466fc2c1184cee9edc6" 358 | 359 | [[package]] 360 | name = "fnv" 361 | version = "1.0.7" 362 | source = "registry+https://github.com/rust-lang/crates.io-index" 363 | checksum = "3f9eec918d3f24069decb9af1554cad7c880e2da24a9afd88aca000531ab82c1" 364 | 365 | [[package]] 366 | name = "foreign-types" 367 | version = "0.3.2" 368 | source = "registry+https://github.com/rust-lang/crates.io-index" 369 | checksum = "f6f339eb8adc052cd2ca78910fda869aefa38d22d5cb648e6485e4d3fc06f3b1" 370 | dependencies = [ 371 | "foreign-types-shared", 372 | ] 373 | 374 | [[package]] 375 | name = "foreign-types-shared" 376 | version = "0.1.1" 377 | source = "registry+https://github.com/rust-lang/crates.io-index" 378 | checksum = "00b0228411908ca8685dba7fc2cdd70ec9990a6e753e89b6ac91a84c40fbaf4b" 379 | 380 | [[package]] 381 | name = "form_urlencoded" 382 | version = "1.1.0" 383 | source = "registry+https://github.com/rust-lang/crates.io-index" 384 | checksum = "a9c384f161156f5260c24a097c56119f9be8c798586aecc13afbcbe7b7e26bf8" 385 | dependencies = [ 386 | "percent-encoding", 387 | ] 388 | 389 | [[package]] 390 | name = "futures" 391 | version = "0.3.25" 392 | source = "registry+https://github.com/rust-lang/crates.io-index" 393 | checksum = "38390104763dc37a5145a53c29c63c1290b5d316d6086ec32c293f6736051bb0" 394 | dependencies = [ 395 | "futures-channel", 396 | "futures-core", 397 | "futures-executor", 398 | "futures-io", 399 | "futures-sink", 400 | "futures-task", 401 | "futures-util", 402 | ] 403 | 404 | [[package]] 405 | name = "futures-channel" 406 | version = "0.3.25" 407 | source = "registry+https://github.com/rust-lang/crates.io-index" 408 | checksum = "52ba265a92256105f45b719605a571ffe2d1f0fea3807304b522c1d778f79eed" 409 | dependencies = [ 410 | "futures-core", 411 | "futures-sink", 412 | ] 413 | 414 | [[package]] 415 | name = "futures-core" 416 | version = "0.3.25" 417 | source = "registry+https://github.com/rust-lang/crates.io-index" 418 | checksum = "04909a7a7e4633ae6c4a9ab280aeb86da1236243a77b694a49eacd659a4bd3ac" 419 | 420 | [[package]] 421 | name = "futures-executor" 422 | version = "0.3.25" 423 | source = "registry+https://github.com/rust-lang/crates.io-index" 424 | checksum = "7acc85df6714c176ab5edf386123fafe217be88c0840ec11f199441134a074e2" 425 | dependencies = [ 426 | "futures-core", 427 | "futures-task", 428 | "futures-util", 429 | ] 430 | 431 | [[package]] 432 | name = "futures-io" 433 | version = "0.3.25" 434 | source = "registry+https://github.com/rust-lang/crates.io-index" 435 | checksum = "00f5fb52a06bdcadeb54e8d3671f8888a39697dcb0b81b23b55174030427f4eb" 436 | 437 | [[package]] 438 | name = "futures-macro" 439 | version = "0.3.25" 440 | source = "registry+https://github.com/rust-lang/crates.io-index" 441 | checksum = "bdfb8ce053d86b91919aad980c220b1fb8401a9394410e1c289ed7e66b61835d" 442 | dependencies = [ 443 | "proc-macro2", 444 | "quote", 445 | "syn", 446 | ] 447 | 448 | [[package]] 449 | name = "futures-sink" 450 | version = "0.3.25" 451 | source = "registry+https://github.com/rust-lang/crates.io-index" 452 | checksum = "39c15cf1a4aa79df40f1bb462fb39676d0ad9e366c2a33b590d7c66f4f81fcf9" 453 | 454 | [[package]] 455 | name = "futures-task" 456 | version = "0.3.25" 457 | source = "registry+https://github.com/rust-lang/crates.io-index" 458 | checksum = "2ffb393ac5d9a6eaa9d3fdf37ae2776656b706e200c8e16b1bdb227f5198e6ea" 459 | 460 | [[package]] 461 | name = "futures-util" 462 | version = "0.3.25" 463 | source = "registry+https://github.com/rust-lang/crates.io-index" 464 | checksum = "197676987abd2f9cadff84926f410af1c183608d36641465df73ae8211dc65d6" 465 | dependencies = [ 466 | "futures-channel", 467 | "futures-core", 468 | "futures-io", 469 | "futures-macro", 470 | "futures-sink", 471 | "futures-task", 472 | "memchr", 473 | "pin-project-lite", 474 | "pin-utils", 475 | "slab", 476 | ] 477 | 478 | [[package]] 479 | name = "generic-array" 480 | version = "0.14.6" 481 | source = "registry+https://github.com/rust-lang/crates.io-index" 482 | checksum = "bff49e947297f3312447abdca79f45f4738097cc82b06e72054d2223f601f1b9" 483 | dependencies = [ 484 | "typenum", 485 | "version_check", 486 | ] 487 | 488 | [[package]] 489 | name = "getrandom" 490 | version = "0.2.8" 491 | source = "registry+https://github.com/rust-lang/crates.io-index" 492 | checksum = "c05aeb6a22b8f62540c194aac980f2115af067bfe15a0734d7277a768d396b31" 493 | dependencies = [ 494 | "cfg-if", 495 | "libc", 496 | "wasi 0.11.0+wasi-snapshot-preview1", 497 | ] 498 | 499 | [[package]] 500 | name = "h2" 501 | version = "0.3.15" 502 | source = "registry+https://github.com/rust-lang/crates.io-index" 503 | checksum = "5f9f29bc9dda355256b2916cf526ab02ce0aeaaaf2bad60d65ef3f12f11dd0f4" 504 | dependencies = [ 505 | "bytes", 506 | "fnv", 507 | "futures-core", 508 | "futures-sink", 509 | "futures-util", 510 | "http", 511 | "indexmap", 512 | "slab", 513 | "tokio", 514 | "tokio-util", 515 | "tracing", 516 | ] 517 | 518 | [[package]] 519 | name = "hashbrown" 520 | version = "0.12.3" 521 | source = "registry+https://github.com/rust-lang/crates.io-index" 522 | checksum = "8a9ee70c43aaf417c914396645a0fa852624801b24ebb7ae78fe8272889ac888" 523 | 524 | [[package]] 525 | name = "heck" 526 | version = "0.4.0" 527 | source = "registry+https://github.com/rust-lang/crates.io-index" 528 | checksum = "2540771e65fc8cb83cd6e8a237f70c319bd5c29f78ed1084ba5d50eeac86f7f9" 529 | 530 | [[package]] 531 | name = "hermit-abi" 532 | version = "0.2.6" 533 | source = "registry+https://github.com/rust-lang/crates.io-index" 534 | checksum = "ee512640fe35acbfb4bb779db6f0d80704c2cacfa2e39b601ef3e3f47d1ae4c7" 535 | dependencies = [ 536 | "libc", 537 | ] 538 | 539 | [[package]] 540 | name = "http" 541 | version = "0.2.8" 542 | source = "registry+https://github.com/rust-lang/crates.io-index" 543 | checksum = "75f43d41e26995c17e71ee126451dd3941010b0514a81a9d11f3b341debc2399" 544 | dependencies = [ 545 | "bytes", 546 | "fnv", 547 | "itoa", 548 | ] 549 | 550 | [[package]] 551 | name = "http-body" 552 | version = "0.4.5" 553 | source = "registry+https://github.com/rust-lang/crates.io-index" 554 | checksum = "d5f38f16d184e36f2408a55281cd658ecbd3ca05cce6d6510a176eca393e26d1" 555 | dependencies = [ 556 | "bytes", 557 | "http", 558 | "pin-project-lite", 559 | ] 560 | 561 | [[package]] 562 | name = "http-range-header" 563 | version = "0.3.0" 564 | source = "registry+https://github.com/rust-lang/crates.io-index" 565 | checksum = "0bfe8eed0a9285ef776bb792479ea3834e8b94e13d615c2f66d03dd50a435a29" 566 | 567 | [[package]] 568 | name = "httparse" 569 | version = "1.8.0" 570 | source = "registry+https://github.com/rust-lang/crates.io-index" 571 | checksum = "d897f394bad6a705d5f4104762e116a75639e470d80901eed05a860a95cb1904" 572 | 573 | [[package]] 574 | name = "httpdate" 575 | version = "1.0.2" 576 | source = "registry+https://github.com/rust-lang/crates.io-index" 577 | checksum = "c4a1e36c821dbe04574f602848a19f742f4fb3c98d40449f11bcad18d6b17421" 578 | 579 | [[package]] 580 | name = "hyper" 581 | version = "0.14.23" 582 | source = "registry+https://github.com/rust-lang/crates.io-index" 583 | checksum = "034711faac9d2166cb1baf1a2fb0b60b1f277f8492fd72176c17f3515e1abd3c" 584 | dependencies = [ 585 | "bytes", 586 | "futures-channel", 587 | "futures-core", 588 | "futures-util", 589 | "h2", 590 | "http", 591 | "http-body", 592 | "httparse", 593 | "httpdate", 594 | "itoa", 595 | "pin-project-lite", 596 | "socket2", 597 | "tokio", 598 | "tower-service", 599 | "tracing", 600 | "want", 601 | ] 602 | 603 | [[package]] 604 | name = "hyper-tls" 605 | version = "0.5.0" 606 | source = "registry+https://github.com/rust-lang/crates.io-index" 607 | checksum = "d6183ddfa99b85da61a140bea0efc93fdf56ceaa041b37d553518030827f9905" 608 | dependencies = [ 609 | "bytes", 610 | "hyper", 611 | "native-tls", 612 | "tokio", 613 | "tokio-native-tls", 614 | ] 615 | 616 | [[package]] 617 | name = "iana-time-zone" 618 | version = "0.1.53" 619 | source = "registry+https://github.com/rust-lang/crates.io-index" 620 | checksum = "64c122667b287044802d6ce17ee2ddf13207ed924c712de9a66a5814d5b64765" 621 | dependencies = [ 622 | "android_system_properties", 623 | "core-foundation-sys", 624 | "iana-time-zone-haiku", 625 | "js-sys", 626 | "wasm-bindgen", 627 | "winapi", 628 | ] 629 | 630 | [[package]] 631 | name = "iana-time-zone-haiku" 632 | version = "0.1.1" 633 | source = "registry+https://github.com/rust-lang/crates.io-index" 634 | checksum = "0703ae284fc167426161c2e3f1da3ea71d94b21bedbcc9494e92b28e334e3dca" 635 | dependencies = [ 636 | "cxx", 637 | "cxx-build", 638 | ] 639 | 640 | [[package]] 641 | name = "idna" 642 | version = "0.3.0" 643 | source = "registry+https://github.com/rust-lang/crates.io-index" 644 | checksum = "e14ddfc70884202db2244c223200c204c2bda1bc6e0998d11b5e024d657209e6" 645 | dependencies = [ 646 | "unicode-bidi", 647 | "unicode-normalization", 648 | ] 649 | 650 | [[package]] 651 | name = "indexmap" 652 | version = "1.9.2" 653 | source = "registry+https://github.com/rust-lang/crates.io-index" 654 | checksum = "1885e79c1fc4b10f0e172c475f458b7f7b93061064d98c3293e98c5ba0c8b399" 655 | dependencies = [ 656 | "autocfg", 657 | "hashbrown", 658 | ] 659 | 660 | [[package]] 661 | name = "instant" 662 | version = "0.1.12" 663 | source = "registry+https://github.com/rust-lang/crates.io-index" 664 | checksum = "7a5bbe824c507c5da5956355e86a746d82e0e1464f65d862cc5e71da70e94b2c" 665 | dependencies = [ 666 | "cfg-if", 667 | ] 668 | 669 | [[package]] 670 | name = "itertools" 671 | version = "0.10.5" 672 | source = "registry+https://github.com/rust-lang/crates.io-index" 673 | checksum = "b0fd2260e829bddf4cb6ea802289de2f86d6a7a690192fbe91b3f46e0f2c8473" 674 | dependencies = [ 675 | "either", 676 | ] 677 | 678 | [[package]] 679 | name = "itoa" 680 | version = "1.0.5" 681 | source = "registry+https://github.com/rust-lang/crates.io-index" 682 | checksum = "fad582f4b9e86b6caa621cabeb0963332d92eea04729ab12892c2533951e6440" 683 | 684 | [[package]] 685 | name = "js-sys" 686 | version = "0.3.60" 687 | source = "registry+https://github.com/rust-lang/crates.io-index" 688 | checksum = "49409df3e3bf0856b916e2ceaca09ee28e6871cf7d9ce97a692cacfdb2a25a47" 689 | dependencies = [ 690 | "wasm-bindgen", 691 | ] 692 | 693 | [[package]] 694 | name = "lazy_static" 695 | version = "1.4.0" 696 | source = "registry+https://github.com/rust-lang/crates.io-index" 697 | checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646" 698 | 699 | [[package]] 700 | name = "libc" 701 | version = "0.2.139" 702 | source = "registry+https://github.com/rust-lang/crates.io-index" 703 | checksum = "201de327520df007757c1f0adce6e827fe8562fbc28bfd9c15571c66ca1f5f79" 704 | 705 | [[package]] 706 | name = "link-cplusplus" 707 | version = "1.0.8" 708 | source = "registry+https://github.com/rust-lang/crates.io-index" 709 | checksum = "ecd207c9c713c34f95a097a5b029ac2ce6010530c7b49d7fea24d977dede04f5" 710 | dependencies = [ 711 | "cc", 712 | ] 713 | 714 | [[package]] 715 | name = "lock_api" 716 | version = "0.4.9" 717 | source = "registry+https://github.com/rust-lang/crates.io-index" 718 | checksum = "435011366fe56583b16cf956f9df0095b405b82d76425bc8981c0e22e60ec4df" 719 | dependencies = [ 720 | "autocfg", 721 | "scopeguard", 722 | ] 723 | 724 | [[package]] 725 | name = "log" 726 | version = "0.4.17" 727 | source = "registry+https://github.com/rust-lang/crates.io-index" 728 | checksum = "abb12e687cfb44aa40f41fc3978ef76448f9b6038cad6aef4259d3c095a2382e" 729 | dependencies = [ 730 | "cfg-if", 731 | ] 732 | 733 | [[package]] 734 | name = "matchers" 735 | version = "0.1.0" 736 | source = "registry+https://github.com/rust-lang/crates.io-index" 737 | checksum = "8263075bb86c5a1b1427b5ae862e8889656f126e9f77c484496e8b47cf5c5558" 738 | dependencies = [ 739 | "regex-automata", 740 | ] 741 | 742 | [[package]] 743 | name = "matchit" 744 | version = "0.7.0" 745 | source = "registry+https://github.com/rust-lang/crates.io-index" 746 | checksum = "b87248edafb776e59e6ee64a79086f65890d3510f2c656c000bf2a7e8a0aea40" 747 | 748 | [[package]] 749 | name = "memchr" 750 | version = "2.5.0" 751 | source = "registry+https://github.com/rust-lang/crates.io-index" 752 | checksum = "2dffe52ecf27772e601905b7522cb4ef790d2cc203488bbd0e2fe85fcb74566d" 753 | 754 | [[package]] 755 | name = "mime" 756 | version = "0.3.16" 757 | source = "registry+https://github.com/rust-lang/crates.io-index" 758 | checksum = "2a60c7ce501c71e03a9c9c0d35b861413ae925bd979cc7a4e30d060069aaac8d" 759 | 760 | [[package]] 761 | name = "mime_guess" 762 | version = "2.0.4" 763 | source = "git+https://github.com/NathanSWard/mime_guess.git?branch=platform-path-separators#053d56adb207cb774080668c8f97193957efb87a" 764 | dependencies = [ 765 | "mime", 766 | "unicase", 767 | ] 768 | 769 | [[package]] 770 | name = "mio" 771 | version = "0.8.5" 772 | source = "registry+https://github.com/rust-lang/crates.io-index" 773 | checksum = "e5d732bc30207a6423068df043e3d02e0735b155ad7ce1a6f76fe2baa5b158de" 774 | dependencies = [ 775 | "libc", 776 | "log", 777 | "wasi 0.11.0+wasi-snapshot-preview1", 778 | "windows-sys", 779 | ] 780 | 781 | [[package]] 782 | name = "native-tls" 783 | version = "0.2.11" 784 | source = "registry+https://github.com/rust-lang/crates.io-index" 785 | checksum = "07226173c32f2926027b63cce4bcd8076c3552846cbe7925f3aaffeac0a3b92e" 786 | dependencies = [ 787 | "lazy_static", 788 | "libc", 789 | "log", 790 | "openssl", 791 | "openssl-probe", 792 | "openssl-sys", 793 | "schannel", 794 | "security-framework", 795 | "security-framework-sys", 796 | "tempfile", 797 | ] 798 | 799 | [[package]] 800 | name = "nu-ansi-term" 801 | version = "0.46.0" 802 | source = "registry+https://github.com/rust-lang/crates.io-index" 803 | checksum = "77a8165726e8236064dbb45459242600304b42a5ea24ee2948e18e023bf7ba84" 804 | dependencies = [ 805 | "overload", 806 | "winapi", 807 | ] 808 | 809 | [[package]] 810 | name = "num-integer" 811 | version = "0.1.45" 812 | source = "registry+https://github.com/rust-lang/crates.io-index" 813 | checksum = "225d3389fb3509a24c93f5c29eb6bde2586b98d9f016636dff58d7c6f7569cd9" 814 | dependencies = [ 815 | "autocfg", 816 | "num-traits", 817 | ] 818 | 819 | [[package]] 820 | name = "num-traits" 821 | version = "0.2.15" 822 | source = "registry+https://github.com/rust-lang/crates.io-index" 823 | checksum = "578ede34cf02f8924ab9447f50c28075b4d3e5b269972345e7e0372b38c6cdcd" 824 | dependencies = [ 825 | "autocfg", 826 | ] 827 | 828 | [[package]] 829 | name = "num_cpus" 830 | version = "1.15.0" 831 | source = "registry+https://github.com/rust-lang/crates.io-index" 832 | checksum = "0fac9e2da13b5eb447a6ce3d392f23a29d8694bff781bf03a16cd9ac8697593b" 833 | dependencies = [ 834 | "hermit-abi", 835 | "libc", 836 | ] 837 | 838 | [[package]] 839 | name = "once_cell" 840 | version = "1.17.0" 841 | source = "registry+https://github.com/rust-lang/crates.io-index" 842 | checksum = "6f61fba1741ea2b3d6a1e3178721804bb716a68a6aeba1149b5d52e3d464ea66" 843 | 844 | [[package]] 845 | name = "openssl" 846 | version = "0.10.45" 847 | source = "registry+https://github.com/rust-lang/crates.io-index" 848 | checksum = "b102428fd03bc5edf97f62620f7298614c45cedf287c271e7ed450bbaf83f2e1" 849 | dependencies = [ 850 | "bitflags", 851 | "cfg-if", 852 | "foreign-types", 853 | "libc", 854 | "once_cell", 855 | "openssl-macros", 856 | "openssl-sys", 857 | ] 858 | 859 | [[package]] 860 | name = "openssl-macros" 861 | version = "0.1.0" 862 | source = "registry+https://github.com/rust-lang/crates.io-index" 863 | checksum = "b501e44f11665960c7e7fcf062c7d96a14ade4aa98116c004b2e37b5be7d736c" 864 | dependencies = [ 865 | "proc-macro2", 866 | "quote", 867 | "syn", 868 | ] 869 | 870 | [[package]] 871 | name = "openssl-probe" 872 | version = "0.1.5" 873 | source = "registry+https://github.com/rust-lang/crates.io-index" 874 | checksum = "ff011a302c396a5197692431fc1948019154afc178baf7d8e37367442a4601cf" 875 | 876 | [[package]] 877 | name = "openssl-sys" 878 | version = "0.9.80" 879 | source = "registry+https://github.com/rust-lang/crates.io-index" 880 | checksum = "23bbbf7854cd45b83958ebe919f0e8e516793727652e27fda10a8384cfc790b7" 881 | dependencies = [ 882 | "autocfg", 883 | "cc", 884 | "libc", 885 | "pkg-config", 886 | "vcpkg", 887 | ] 888 | 889 | [[package]] 890 | name = "overload" 891 | version = "0.1.1" 892 | source = "registry+https://github.com/rust-lang/crates.io-index" 893 | checksum = "b15813163c1d831bf4a13c3610c05c0d03b39feb07f7e09fa234dac9b15aaf39" 894 | 895 | [[package]] 896 | name = "parking_lot" 897 | version = "0.12.1" 898 | source = "registry+https://github.com/rust-lang/crates.io-index" 899 | checksum = "3742b2c103b9f06bc9fff0a37ff4912935851bee6d36f3c02bcc755bcfec228f" 900 | dependencies = [ 901 | "lock_api", 902 | "parking_lot_core", 903 | ] 904 | 905 | [[package]] 906 | name = "parking_lot_core" 907 | version = "0.9.5" 908 | source = "registry+https://github.com/rust-lang/crates.io-index" 909 | checksum = "7ff9f3fef3968a3ec5945535ed654cb38ff72d7495a25619e2247fb15a2ed9ba" 910 | dependencies = [ 911 | "cfg-if", 912 | "libc", 913 | "redox_syscall", 914 | "smallvec", 915 | "windows-sys", 916 | ] 917 | 918 | [[package]] 919 | name = "percent-encoding" 920 | version = "2.2.0" 921 | source = "registry+https://github.com/rust-lang/crates.io-index" 922 | checksum = "478c572c3d73181ff3c2539045f6eb99e5491218eae919370993b890cdbdd98e" 923 | 924 | [[package]] 925 | name = "pin-project" 926 | version = "1.0.12" 927 | source = "registry+https://github.com/rust-lang/crates.io-index" 928 | checksum = "ad29a609b6bcd67fee905812e544992d216af9d755757c05ed2d0e15a74c6ecc" 929 | dependencies = [ 930 | "pin-project-internal", 931 | ] 932 | 933 | [[package]] 934 | name = "pin-project-internal" 935 | version = "1.0.12" 936 | source = "registry+https://github.com/rust-lang/crates.io-index" 937 | checksum = "069bdb1e05adc7a8990dce9cc75370895fbe4e3d58b9b73bf1aee56359344a55" 938 | dependencies = [ 939 | "proc-macro2", 940 | "quote", 941 | "syn", 942 | ] 943 | 944 | [[package]] 945 | name = "pin-project-lite" 946 | version = "0.2.9" 947 | source = "registry+https://github.com/rust-lang/crates.io-index" 948 | checksum = "e0a7ae3ac2f1173085d398531c705756c94a4c56843785df85a60c1a0afac116" 949 | 950 | [[package]] 951 | name = "pin-utils" 952 | version = "0.1.0" 953 | source = "registry+https://github.com/rust-lang/crates.io-index" 954 | checksum = "8b870d8c151b6f2fb93e84a13146138f05d02ed11c7e7c54f8826aaaf7c9f184" 955 | 956 | [[package]] 957 | name = "pipe" 958 | version = "0.4.0" 959 | source = "registry+https://github.com/rust-lang/crates.io-index" 960 | checksum = "1c7b8f27da217eb966df4c58d4159ea939431950ca03cf782c22bd7c5c1d8d75" 961 | dependencies = [ 962 | "crossbeam-channel", 963 | ] 964 | 965 | [[package]] 966 | name = "pkg-config" 967 | version = "0.3.26" 968 | source = "registry+https://github.com/rust-lang/crates.io-index" 969 | checksum = "6ac9a59f73473f1b8d852421e59e64809f025994837ef743615c6d0c5b305160" 970 | 971 | [[package]] 972 | name = "ppv-lite86" 973 | version = "0.2.17" 974 | source = "registry+https://github.com/rust-lang/crates.io-index" 975 | checksum = "5b40af805b3121feab8a3c29f04d8ad262fa8e0561883e7653e024ae4479e6de" 976 | 977 | [[package]] 978 | name = "proc-macro-error" 979 | version = "1.0.4" 980 | source = "registry+https://github.com/rust-lang/crates.io-index" 981 | checksum = "da25490ff9892aab3fcf7c36f08cfb902dd3e71ca0f9f9517bea02a73a5ce38c" 982 | dependencies = [ 983 | "proc-macro-error-attr", 984 | "proc-macro2", 985 | "quote", 986 | "syn", 987 | "version_check", 988 | ] 989 | 990 | [[package]] 991 | name = "proc-macro-error-attr" 992 | version = "1.0.4" 993 | source = "registry+https://github.com/rust-lang/crates.io-index" 994 | checksum = "a1be40180e52ecc98ad80b184934baf3d0d29f979574e439af5a55274b35f869" 995 | dependencies = [ 996 | "proc-macro2", 997 | "quote", 998 | "version_check", 999 | ] 1000 | 1001 | [[package]] 1002 | name = "proc-macro2" 1003 | version = "1.0.49" 1004 | source = "registry+https://github.com/rust-lang/crates.io-index" 1005 | checksum = "57a8eca9f9c4ffde41714334dee777596264c7825420f521abc92b5b5deb63a5" 1006 | dependencies = [ 1007 | "unicode-ident", 1008 | ] 1009 | 1010 | [[package]] 1011 | name = "quote" 1012 | version = "1.0.23" 1013 | source = "registry+https://github.com/rust-lang/crates.io-index" 1014 | checksum = "8856d8364d252a14d474036ea1358d63c9e6965c8e5c1885c18f73d70bff9c7b" 1015 | dependencies = [ 1016 | "proc-macro2", 1017 | ] 1018 | 1019 | [[package]] 1020 | name = "rand" 1021 | version = "0.8.5" 1022 | source = "registry+https://github.com/rust-lang/crates.io-index" 1023 | checksum = "34af8d1a0e25924bc5b7c43c079c942339d8f0a8b57c39049bef581b46327404" 1024 | dependencies = [ 1025 | "libc", 1026 | "rand_chacha", 1027 | "rand_core", 1028 | ] 1029 | 1030 | [[package]] 1031 | name = "rand_chacha" 1032 | version = "0.3.1" 1033 | source = "registry+https://github.com/rust-lang/crates.io-index" 1034 | checksum = "e6c10a63a0fa32252be49d21e7709d4d4baf8d231c2dbce1eaa8141b9b127d88" 1035 | dependencies = [ 1036 | "ppv-lite86", 1037 | "rand_core", 1038 | ] 1039 | 1040 | [[package]] 1041 | name = "rand_core" 1042 | version = "0.6.4" 1043 | source = "registry+https://github.com/rust-lang/crates.io-index" 1044 | checksum = "ec0be4795e2f6a28069bec0b5ff3e2ac9bafc99e6a9a7dc3547996c5c816922c" 1045 | dependencies = [ 1046 | "getrandom", 1047 | ] 1048 | 1049 | [[package]] 1050 | name = "redox_syscall" 1051 | version = "0.2.16" 1052 | source = "registry+https://github.com/rust-lang/crates.io-index" 1053 | checksum = "fb5a58c1855b4b6819d59012155603f0b22ad30cad752600aadfcb695265519a" 1054 | dependencies = [ 1055 | "bitflags", 1056 | ] 1057 | 1058 | [[package]] 1059 | name = "regex" 1060 | version = "1.7.1" 1061 | source = "registry+https://github.com/rust-lang/crates.io-index" 1062 | checksum = "48aaa5748ba571fb95cd2c85c09f629215d3a6ece942baa100950af03a34f733" 1063 | dependencies = [ 1064 | "regex-syntax", 1065 | ] 1066 | 1067 | [[package]] 1068 | name = "regex-automata" 1069 | version = "0.1.10" 1070 | source = "registry+https://github.com/rust-lang/crates.io-index" 1071 | checksum = "6c230d73fb8d8c1b9c0b3135c5142a8acee3a0558fb8db5cf1cb65f8d7862132" 1072 | dependencies = [ 1073 | "regex-syntax", 1074 | ] 1075 | 1076 | [[package]] 1077 | name = "regex-syntax" 1078 | version = "0.6.28" 1079 | source = "registry+https://github.com/rust-lang/crates.io-index" 1080 | checksum = "456c603be3e8d448b072f410900c09faf164fbce2d480456f50eea6e25f9c848" 1081 | 1082 | [[package]] 1083 | name = "remove_dir_all" 1084 | version = "0.5.3" 1085 | source = "registry+https://github.com/rust-lang/crates.io-index" 1086 | checksum = "3acd125665422973a33ac9d3dd2df85edad0f4ae9b00dafb1a05e43a9f5ef8e7" 1087 | dependencies = [ 1088 | "winapi", 1089 | ] 1090 | 1091 | [[package]] 1092 | name = "rustc-hash" 1093 | version = "1.1.0" 1094 | source = "registry+https://github.com/rust-lang/crates.io-index" 1095 | checksum = "08d43f7aa6b08d49f382cde6a7982047c3426db949b1424bc4b7ec9ae12c6ce2" 1096 | 1097 | [[package]] 1098 | name = "rustrict" 1099 | version = "0.5.10" 1100 | source = "registry+https://github.com/rust-lang/crates.io-index" 1101 | checksum = "bfae409fc123d1e857745e4d7a1899460e0ddcb7c1c4a5a03d9b7745256efb3a" 1102 | dependencies = [ 1103 | "bitflags", 1104 | "doc-comment", 1105 | "finl_unicode", 1106 | "itertools", 1107 | "lazy_static", 1108 | "rustc-hash", 1109 | "strsim", 1110 | "unicode-normalization", 1111 | ] 1112 | 1113 | [[package]] 1114 | name = "rustversion" 1115 | version = "1.0.11" 1116 | source = "registry+https://github.com/rust-lang/crates.io-index" 1117 | checksum = "5583e89e108996506031660fe09baa5011b9dd0341b89029313006d1fb508d70" 1118 | 1119 | [[package]] 1120 | name = "ryu" 1121 | version = "1.0.12" 1122 | source = "registry+https://github.com/rust-lang/crates.io-index" 1123 | checksum = "7b4b9743ed687d4b4bcedf9ff5eaa7398495ae14e61cba0a295704edbc7decde" 1124 | 1125 | [[package]] 1126 | name = "schannel" 1127 | version = "0.1.21" 1128 | source = "registry+https://github.com/rust-lang/crates.io-index" 1129 | checksum = "713cfb06c7059f3588fb8044c0fad1d09e3c01d225e25b9220dbfdcf16dbb1b3" 1130 | dependencies = [ 1131 | "windows-sys", 1132 | ] 1133 | 1134 | [[package]] 1135 | name = "scopeguard" 1136 | version = "1.1.0" 1137 | source = "registry+https://github.com/rust-lang/crates.io-index" 1138 | checksum = "d29ab0c6d3fc0ee92fe66e2d99f700eab17a8d57d1c1d3b748380fb20baa78cd" 1139 | 1140 | [[package]] 1141 | name = "scratch" 1142 | version = "1.0.3" 1143 | source = "registry+https://github.com/rust-lang/crates.io-index" 1144 | checksum = "ddccb15bcce173023b3fedd9436f882a0739b8dfb45e4f6b6002bee5929f61b2" 1145 | 1146 | [[package]] 1147 | name = "security-framework" 1148 | version = "2.7.0" 1149 | source = "registry+https://github.com/rust-lang/crates.io-index" 1150 | checksum = "2bc1bb97804af6631813c55739f771071e0f2ed33ee20b68c86ec505d906356c" 1151 | dependencies = [ 1152 | "bitflags", 1153 | "core-foundation", 1154 | "core-foundation-sys", 1155 | "libc", 1156 | "security-framework-sys", 1157 | ] 1158 | 1159 | [[package]] 1160 | name = "security-framework-sys" 1161 | version = "2.6.1" 1162 | source = "registry+https://github.com/rust-lang/crates.io-index" 1163 | checksum = "0160a13a177a45bfb43ce71c01580998474f556ad854dcbca936dd2841a5c556" 1164 | dependencies = [ 1165 | "core-foundation-sys", 1166 | "libc", 1167 | ] 1168 | 1169 | [[package]] 1170 | name = "semver" 1171 | version = "1.0.16" 1172 | source = "registry+https://github.com/rust-lang/crates.io-index" 1173 | checksum = "58bc9567378fc7690d6b2addae4e60ac2eeea07becb2c64b9f218b53865cba2a" 1174 | dependencies = [ 1175 | "serde", 1176 | ] 1177 | 1178 | [[package]] 1179 | name = "serde" 1180 | version = "1.0.152" 1181 | source = "registry+https://github.com/rust-lang/crates.io-index" 1182 | checksum = "bb7d1f0d3021d347a83e556fc4683dea2ea09d87bccdf88ff5c12545d89d5efb" 1183 | dependencies = [ 1184 | "serde_derive", 1185 | ] 1186 | 1187 | [[package]] 1188 | name = "serde_derive" 1189 | version = "1.0.152" 1190 | source = "registry+https://github.com/rust-lang/crates.io-index" 1191 | checksum = "af487d118eecd09402d70a5d72551860e788df87b464af30e5ea6a38c75c541e" 1192 | dependencies = [ 1193 | "proc-macro2", 1194 | "quote", 1195 | "syn", 1196 | ] 1197 | 1198 | [[package]] 1199 | name = "serde_json" 1200 | version = "1.0.91" 1201 | source = "registry+https://github.com/rust-lang/crates.io-index" 1202 | checksum = "877c235533714907a8c2464236f5c4b2a17262ef1bd71f38f35ea592c8da6883" 1203 | dependencies = [ 1204 | "itoa", 1205 | "ryu", 1206 | "serde", 1207 | ] 1208 | 1209 | [[package]] 1210 | name = "serde_path_to_error" 1211 | version = "0.1.9" 1212 | source = "registry+https://github.com/rust-lang/crates.io-index" 1213 | checksum = "26b04f22b563c91331a10074bda3dd5492e3cc39d56bd557e91c0af42b6c7341" 1214 | dependencies = [ 1215 | "serde", 1216 | ] 1217 | 1218 | [[package]] 1219 | name = "serde_urlencoded" 1220 | version = "0.7.1" 1221 | source = "registry+https://github.com/rust-lang/crates.io-index" 1222 | checksum = "d3491c14715ca2294c4d6a88f15e84739788c1d030eed8c110436aafdaa2f3fd" 1223 | dependencies = [ 1224 | "form_urlencoded", 1225 | "itoa", 1226 | "ryu", 1227 | "serde", 1228 | ] 1229 | 1230 | [[package]] 1231 | name = "sha1" 1232 | version = "0.10.5" 1233 | source = "registry+https://github.com/rust-lang/crates.io-index" 1234 | checksum = "f04293dc80c3993519f2d7f6f511707ee7094fe0c6d3406feb330cdb3540eba3" 1235 | dependencies = [ 1236 | "cfg-if", 1237 | "cpufeatures", 1238 | "digest", 1239 | ] 1240 | 1241 | [[package]] 1242 | name = "sharded-slab" 1243 | version = "0.1.4" 1244 | source = "registry+https://github.com/rust-lang/crates.io-index" 1245 | checksum = "900fba806f70c630b0a382d0d825e17a0f19fcd059a2ade1ff237bcddf446b31" 1246 | dependencies = [ 1247 | "lazy_static", 1248 | ] 1249 | 1250 | [[package]] 1251 | name = "shuttle-codegen" 1252 | version = "0.10.0" 1253 | source = "registry+https://github.com/rust-lang/crates.io-index" 1254 | checksum = "503f3b6c11c193c593394dab348003e4c5813f186f13d9aa7a8172bd636b2458" 1255 | dependencies = [ 1256 | "proc-macro-error", 1257 | "proc-macro2", 1258 | "quote", 1259 | "syn", 1260 | ] 1261 | 1262 | [[package]] 1263 | name = "shuttle-common" 1264 | version = "0.10.0" 1265 | source = "registry+https://github.com/rust-lang/crates.io-index" 1266 | checksum = "37b613601be7fc96760dcc91aae0b3a02d4130ed54384674eb0370e0c46de55c" 1267 | dependencies = [ 1268 | "chrono", 1269 | "once_cell", 1270 | "rustrict", 1271 | "serde", 1272 | "strum", 1273 | "tracing", 1274 | "uuid", 1275 | ] 1276 | 1277 | [[package]] 1278 | name = "shuttle-secrets" 1279 | version = "0.10.0" 1280 | source = "registry+https://github.com/rust-lang/crates.io-index" 1281 | checksum = "6d78194d634c98f98a689f3da0bf4b12bc96799a2a01a16347c06d6221950183" 1282 | dependencies = [ 1283 | "async-trait", 1284 | "shuttle-service", 1285 | "tokio", 1286 | ] 1287 | 1288 | [[package]] 1289 | name = "shuttle-service" 1290 | version = "0.10.0" 1291 | source = "registry+https://github.com/rust-lang/crates.io-index" 1292 | checksum = "8b71e368b655c6e4d2dba14f57f9a28cd1077a2a5182c773af0f3848c6a16629" 1293 | dependencies = [ 1294 | "anyhow", 1295 | "async-trait", 1296 | "axum", 1297 | "cargo_metadata", 1298 | "chrono", 1299 | "crossbeam-channel", 1300 | "futures", 1301 | "pipe", 1302 | "serde_json", 1303 | "shuttle-codegen", 1304 | "shuttle-common", 1305 | "strfmt", 1306 | "sync_wrapper", 1307 | "thiserror", 1308 | "tokio", 1309 | "tracing", 1310 | "tracing-subscriber", 1311 | "uuid", 1312 | ] 1313 | 1314 | [[package]] 1315 | name = "shuttle-static-folder" 1316 | version = "0.10.0" 1317 | source = "registry+https://github.com/rust-lang/crates.io-index" 1318 | checksum = "324c725102dd5d720d4e3c08bf2399092017ee58875f4aa0e9595815b73de91f" 1319 | dependencies = [ 1320 | "async-trait", 1321 | "shuttle-service", 1322 | "tokio", 1323 | ] 1324 | 1325 | [[package]] 1326 | name = "signal-hook-registry" 1327 | version = "1.4.0" 1328 | source = "registry+https://github.com/rust-lang/crates.io-index" 1329 | checksum = "e51e73328dc4ac0c7ccbda3a494dfa03df1de2f46018127f60c693f2648455b0" 1330 | dependencies = [ 1331 | "libc", 1332 | ] 1333 | 1334 | [[package]] 1335 | name = "slab" 1336 | version = "0.4.7" 1337 | source = "registry+https://github.com/rust-lang/crates.io-index" 1338 | checksum = "4614a76b2a8be0058caa9dbbaf66d988527d86d003c11a94fbd335d7661edcef" 1339 | dependencies = [ 1340 | "autocfg", 1341 | ] 1342 | 1343 | [[package]] 1344 | name = "smallvec" 1345 | version = "1.10.0" 1346 | source = "registry+https://github.com/rust-lang/crates.io-index" 1347 | checksum = "a507befe795404456341dfab10cef66ead4c041f62b8b11bbb92bffe5d0953e0" 1348 | 1349 | [[package]] 1350 | name = "socket2" 1351 | version = "0.4.7" 1352 | source = "registry+https://github.com/rust-lang/crates.io-index" 1353 | checksum = "02e2d2db9033d13a1567121ddd7a095ee144db4e1ca1b1bda3419bc0da294ebd" 1354 | dependencies = [ 1355 | "libc", 1356 | "winapi", 1357 | ] 1358 | 1359 | [[package]] 1360 | name = "strfmt" 1361 | version = "0.2.3" 1362 | source = "registry+https://github.com/rust-lang/crates.io-index" 1363 | checksum = "b73de159e5e71c4c7579ea3041d3e765f46790555790c24489195554210f1fb4" 1364 | 1365 | [[package]] 1366 | name = "strsim" 1367 | version = "0.10.0" 1368 | source = "registry+https://github.com/rust-lang/crates.io-index" 1369 | checksum = "73473c0e59e6d5812c5dfe2a064a6444949f089e20eec9a2e5506596494e4623" 1370 | 1371 | [[package]] 1372 | name = "strum" 1373 | version = "0.24.1" 1374 | source = "registry+https://github.com/rust-lang/crates.io-index" 1375 | checksum = "063e6045c0e62079840579a7e47a355ae92f60eb74daaf156fb1e84ba164e63f" 1376 | dependencies = [ 1377 | "strum_macros", 1378 | ] 1379 | 1380 | [[package]] 1381 | name = "strum_macros" 1382 | version = "0.24.3" 1383 | source = "registry+https://github.com/rust-lang/crates.io-index" 1384 | checksum = "1e385be0d24f186b4ce2f9982191e7101bb737312ad61c1f2f984f34bcf85d59" 1385 | dependencies = [ 1386 | "heck", 1387 | "proc-macro2", 1388 | "quote", 1389 | "rustversion", 1390 | "syn", 1391 | ] 1392 | 1393 | [[package]] 1394 | name = "syn" 1395 | version = "1.0.107" 1396 | source = "registry+https://github.com/rust-lang/crates.io-index" 1397 | checksum = "1f4064b5b16e03ae50984a5a8ed5d4f8803e6bc1fd170a3cda91a1be4b18e3f5" 1398 | dependencies = [ 1399 | "proc-macro2", 1400 | "quote", 1401 | "unicode-ident", 1402 | ] 1403 | 1404 | [[package]] 1405 | name = "sync_wrapper" 1406 | version = "0.1.1" 1407 | source = "registry+https://github.com/rust-lang/crates.io-index" 1408 | checksum = "20518fe4a4c9acf048008599e464deb21beeae3d3578418951a189c235a7a9a8" 1409 | 1410 | [[package]] 1411 | name = "tempfile" 1412 | version = "3.3.0" 1413 | source = "registry+https://github.com/rust-lang/crates.io-index" 1414 | checksum = "5cdb1ef4eaeeaddc8fbd371e5017057064af0911902ef36b39801f67cc6d79e4" 1415 | dependencies = [ 1416 | "cfg-if", 1417 | "fastrand", 1418 | "libc", 1419 | "redox_syscall", 1420 | "remove_dir_all", 1421 | "winapi", 1422 | ] 1423 | 1424 | [[package]] 1425 | name = "termcolor" 1426 | version = "1.1.3" 1427 | source = "registry+https://github.com/rust-lang/crates.io-index" 1428 | checksum = "bab24d30b911b2376f3a13cc2cd443142f0c81dda04c118693e35b3835757755" 1429 | dependencies = [ 1430 | "winapi-util", 1431 | ] 1432 | 1433 | [[package]] 1434 | name = "thiserror" 1435 | version = "1.0.38" 1436 | source = "registry+https://github.com/rust-lang/crates.io-index" 1437 | checksum = "6a9cd18aa97d5c45c6603caea1da6628790b37f7a34b6ca89522331c5180fed0" 1438 | dependencies = [ 1439 | "thiserror-impl", 1440 | ] 1441 | 1442 | [[package]] 1443 | name = "thiserror-impl" 1444 | version = "1.0.38" 1445 | source = "registry+https://github.com/rust-lang/crates.io-index" 1446 | checksum = "1fb327af4685e4d03fa8cbcf1716380da910eeb2bb8be417e7f9fd3fb164f36f" 1447 | dependencies = [ 1448 | "proc-macro2", 1449 | "quote", 1450 | "syn", 1451 | ] 1452 | 1453 | [[package]] 1454 | name = "thread_local" 1455 | version = "1.1.4" 1456 | source = "registry+https://github.com/rust-lang/crates.io-index" 1457 | checksum = "5516c27b78311c50bf42c071425c560ac799b11c30b31f87e3081965fe5e0180" 1458 | dependencies = [ 1459 | "once_cell", 1460 | ] 1461 | 1462 | [[package]] 1463 | name = "time" 1464 | version = "0.1.45" 1465 | source = "registry+https://github.com/rust-lang/crates.io-index" 1466 | checksum = "1b797afad3f312d1c66a56d11d0316f916356d11bd158fbc6ca6389ff6bf805a" 1467 | dependencies = [ 1468 | "libc", 1469 | "wasi 0.10.0+wasi-snapshot-preview1", 1470 | "winapi", 1471 | ] 1472 | 1473 | [[package]] 1474 | name = "tinyvec" 1475 | version = "1.6.0" 1476 | source = "registry+https://github.com/rust-lang/crates.io-index" 1477 | checksum = "87cc5ceb3875bb20c2890005a4e226a4651264a5c75edb2421b52861a0a0cb50" 1478 | dependencies = [ 1479 | "tinyvec_macros", 1480 | ] 1481 | 1482 | [[package]] 1483 | name = "tinyvec_macros" 1484 | version = "0.1.0" 1485 | source = "registry+https://github.com/rust-lang/crates.io-index" 1486 | checksum = "cda74da7e1a664f795bb1f8a87ec406fb89a02522cf6e50620d016add6dbbf5c" 1487 | 1488 | [[package]] 1489 | name = "tokio" 1490 | version = "1.22.0" 1491 | source = "registry+https://github.com/rust-lang/crates.io-index" 1492 | checksum = "d76ce4a75fb488c605c54bf610f221cea8b0dafb53333c1a67e8ee199dcd2ae3" 1493 | dependencies = [ 1494 | "autocfg", 1495 | "bytes", 1496 | "libc", 1497 | "memchr", 1498 | "mio", 1499 | "num_cpus", 1500 | "parking_lot", 1501 | "pin-project-lite", 1502 | "signal-hook-registry", 1503 | "socket2", 1504 | "tokio-macros", 1505 | "winapi", 1506 | ] 1507 | 1508 | [[package]] 1509 | name = "tokio-macros" 1510 | version = "1.8.2" 1511 | source = "registry+https://github.com/rust-lang/crates.io-index" 1512 | checksum = "d266c00fde287f55d3f1c3e96c500c362a2b8c695076ec180f27918820bc6df8" 1513 | dependencies = [ 1514 | "proc-macro2", 1515 | "quote", 1516 | "syn", 1517 | ] 1518 | 1519 | [[package]] 1520 | name = "tokio-native-tls" 1521 | version = "0.3.0" 1522 | source = "registry+https://github.com/rust-lang/crates.io-index" 1523 | checksum = "f7d995660bd2b7f8c1568414c1126076c13fbb725c40112dc0120b78eb9b717b" 1524 | dependencies = [ 1525 | "native-tls", 1526 | "tokio", 1527 | ] 1528 | 1529 | [[package]] 1530 | name = "tokio-tungstenite" 1531 | version = "0.18.0" 1532 | source = "registry+https://github.com/rust-lang/crates.io-index" 1533 | checksum = "54319c93411147bced34cb5609a80e0a8e44c5999c93903a81cd866630ec0bfd" 1534 | dependencies = [ 1535 | "futures-util", 1536 | "log", 1537 | "tokio", 1538 | "tungstenite", 1539 | ] 1540 | 1541 | [[package]] 1542 | name = "tokio-util" 1543 | version = "0.7.4" 1544 | source = "registry+https://github.com/rust-lang/crates.io-index" 1545 | checksum = "0bb2e075f03b3d66d8d8785356224ba688d2906a371015e225beeb65ca92c740" 1546 | dependencies = [ 1547 | "bytes", 1548 | "futures-core", 1549 | "futures-sink", 1550 | "pin-project-lite", 1551 | "tokio", 1552 | "tracing", 1553 | ] 1554 | 1555 | [[package]] 1556 | name = "tower" 1557 | version = "0.4.13" 1558 | source = "registry+https://github.com/rust-lang/crates.io-index" 1559 | checksum = "b8fa9be0de6cf49e536ce1851f987bd21a43b771b09473c3549a6c853db37c1c" 1560 | dependencies = [ 1561 | "futures-core", 1562 | "futures-util", 1563 | "pin-project", 1564 | "pin-project-lite", 1565 | "tokio", 1566 | "tower-layer", 1567 | "tower-service", 1568 | "tracing", 1569 | ] 1570 | 1571 | [[package]] 1572 | name = "tower-http" 1573 | version = "0.3.5" 1574 | source = "registry+https://github.com/rust-lang/crates.io-index" 1575 | checksum = "f873044bf02dd1e8239e9c1293ea39dad76dc594ec16185d0a1bf31d8dc8d858" 1576 | dependencies = [ 1577 | "base64 0.13.1", 1578 | "bitflags", 1579 | "bytes", 1580 | "futures-core", 1581 | "futures-util", 1582 | "http", 1583 | "http-body", 1584 | "http-range-header", 1585 | "httpdate", 1586 | "mime", 1587 | "mime_guess", 1588 | "percent-encoding", 1589 | "pin-project-lite", 1590 | "tokio", 1591 | "tokio-util", 1592 | "tower", 1593 | "tower-layer", 1594 | "tower-service", 1595 | ] 1596 | 1597 | [[package]] 1598 | name = "tower-layer" 1599 | version = "0.3.2" 1600 | source = "registry+https://github.com/rust-lang/crates.io-index" 1601 | checksum = "c20c8dbed6283a09604c3e69b4b7eeb54e298b8a600d4d5ecb5ad39de609f1d0" 1602 | 1603 | [[package]] 1604 | name = "tower-service" 1605 | version = "0.3.2" 1606 | source = "registry+https://github.com/rust-lang/crates.io-index" 1607 | checksum = "b6bc1c9ce2b5135ac7f93c72918fc37feb872bdc6a5533a8b85eb4b86bfdae52" 1608 | 1609 | [[package]] 1610 | name = "tracing" 1611 | version = "0.1.37" 1612 | source = "registry+https://github.com/rust-lang/crates.io-index" 1613 | checksum = "8ce8c33a8d48bd45d624a6e523445fd21ec13d3653cd51f681abf67418f54eb8" 1614 | dependencies = [ 1615 | "cfg-if", 1616 | "log", 1617 | "pin-project-lite", 1618 | "tracing-attributes", 1619 | "tracing-core", 1620 | ] 1621 | 1622 | [[package]] 1623 | name = "tracing-attributes" 1624 | version = "0.1.23" 1625 | source = "registry+https://github.com/rust-lang/crates.io-index" 1626 | checksum = "4017f8f45139870ca7e672686113917c71c7a6e02d4924eda67186083c03081a" 1627 | dependencies = [ 1628 | "proc-macro2", 1629 | "quote", 1630 | "syn", 1631 | ] 1632 | 1633 | [[package]] 1634 | name = "tracing-core" 1635 | version = "0.1.30" 1636 | source = "registry+https://github.com/rust-lang/crates.io-index" 1637 | checksum = "24eb03ba0eab1fd845050058ce5e616558e8f8d8fca633e6b163fe25c797213a" 1638 | dependencies = [ 1639 | "once_cell", 1640 | "valuable", 1641 | ] 1642 | 1643 | [[package]] 1644 | name = "tracing-log" 1645 | version = "0.1.3" 1646 | source = "registry+https://github.com/rust-lang/crates.io-index" 1647 | checksum = "78ddad33d2d10b1ed7eb9d1f518a5674713876e97e5bb9b7345a7984fbb4f922" 1648 | dependencies = [ 1649 | "lazy_static", 1650 | "log", 1651 | "tracing-core", 1652 | ] 1653 | 1654 | [[package]] 1655 | name = "tracing-subscriber" 1656 | version = "0.3.16" 1657 | source = "registry+https://github.com/rust-lang/crates.io-index" 1658 | checksum = "a6176eae26dd70d0c919749377897b54a9276bd7061339665dd68777926b5a70" 1659 | dependencies = [ 1660 | "matchers", 1661 | "nu-ansi-term", 1662 | "once_cell", 1663 | "regex", 1664 | "sharded-slab", 1665 | "smallvec", 1666 | "thread_local", 1667 | "tracing", 1668 | "tracing-core", 1669 | "tracing-log", 1670 | ] 1671 | 1672 | [[package]] 1673 | name = "try-lock" 1674 | version = "0.2.4" 1675 | source = "registry+https://github.com/rust-lang/crates.io-index" 1676 | checksum = "3528ecfd12c466c6f163363caf2d02a71161dd5e1cc6ae7b34207ea2d42d81ed" 1677 | 1678 | [[package]] 1679 | name = "tungstenite" 1680 | version = "0.18.0" 1681 | source = "registry+https://github.com/rust-lang/crates.io-index" 1682 | checksum = "30ee6ab729cd4cf0fd55218530c4522ed30b7b6081752839b68fcec8d0960788" 1683 | dependencies = [ 1684 | "base64 0.13.1", 1685 | "byteorder", 1686 | "bytes", 1687 | "http", 1688 | "httparse", 1689 | "log", 1690 | "rand", 1691 | "sha1", 1692 | "thiserror", 1693 | "url", 1694 | "utf-8", 1695 | ] 1696 | 1697 | [[package]] 1698 | name = "typenum" 1699 | version = "1.16.0" 1700 | source = "registry+https://github.com/rust-lang/crates.io-index" 1701 | checksum = "497961ef93d974e23eb6f433eb5fe1b7930b659f06d12dec6fc44a8f554c0bba" 1702 | 1703 | [[package]] 1704 | name = "unicase" 1705 | version = "2.6.0" 1706 | source = "registry+https://github.com/rust-lang/crates.io-index" 1707 | checksum = "50f37be617794602aabbeee0be4f259dc1778fabe05e2d67ee8f79326d5cb4f6" 1708 | dependencies = [ 1709 | "version_check", 1710 | ] 1711 | 1712 | [[package]] 1713 | name = "unicode-bidi" 1714 | version = "0.3.8" 1715 | source = "registry+https://github.com/rust-lang/crates.io-index" 1716 | checksum = "099b7128301d285f79ddd55b9a83d5e6b9e97c92e0ea0daebee7263e932de992" 1717 | 1718 | [[package]] 1719 | name = "unicode-ident" 1720 | version = "1.0.6" 1721 | source = "registry+https://github.com/rust-lang/crates.io-index" 1722 | checksum = "84a22b9f218b40614adcb3f4ff08b703773ad44fa9423e4e0d346d5db86e4ebc" 1723 | 1724 | [[package]] 1725 | name = "unicode-normalization" 1726 | version = "0.1.22" 1727 | source = "registry+https://github.com/rust-lang/crates.io-index" 1728 | checksum = "5c5713f0fc4b5db668a2ac63cdb7bb4469d8c9fed047b1d0292cc7b0ce2ba921" 1729 | dependencies = [ 1730 | "tinyvec", 1731 | ] 1732 | 1733 | [[package]] 1734 | name = "unicode-width" 1735 | version = "0.1.10" 1736 | source = "registry+https://github.com/rust-lang/crates.io-index" 1737 | checksum = "c0edd1e5b14653f783770bce4a4dabb4a5108a5370a5f5d8cfe8710c361f6c8b" 1738 | 1739 | [[package]] 1740 | name = "url" 1741 | version = "2.3.1" 1742 | source = "registry+https://github.com/rust-lang/crates.io-index" 1743 | checksum = "0d68c799ae75762b8c3fe375feb6600ef5602c883c5d21eb51c09f22b83c4643" 1744 | dependencies = [ 1745 | "form_urlencoded", 1746 | "idna", 1747 | "percent-encoding", 1748 | ] 1749 | 1750 | [[package]] 1751 | name = "utf-8" 1752 | version = "0.7.6" 1753 | source = "registry+https://github.com/rust-lang/crates.io-index" 1754 | checksum = "09cc8ee72d2a9becf2f2febe0205bbed8fc6615b7cb429ad062dc7b7ddd036a9" 1755 | 1756 | [[package]] 1757 | name = "uuid" 1758 | version = "1.2.2" 1759 | source = "registry+https://github.com/rust-lang/crates.io-index" 1760 | checksum = "422ee0de9031b5b948b97a8fc04e3aa35230001a722ddd27943e0be31564ce4c" 1761 | dependencies = [ 1762 | "getrandom", 1763 | "serde", 1764 | ] 1765 | 1766 | [[package]] 1767 | name = "valuable" 1768 | version = "0.1.0" 1769 | source = "registry+https://github.com/rust-lang/crates.io-index" 1770 | checksum = "830b7e5d4d90034032940e4ace0d9a9a057e7a45cd94e6c007832e39edb82f6d" 1771 | 1772 | [[package]] 1773 | name = "vcpkg" 1774 | version = "0.2.15" 1775 | source = "registry+https://github.com/rust-lang/crates.io-index" 1776 | checksum = "accd4ea62f7bb7a82fe23066fb0957d48ef677f6eeb8215f372f52e48bb32426" 1777 | 1778 | [[package]] 1779 | name = "version_check" 1780 | version = "0.9.4" 1781 | source = "registry+https://github.com/rust-lang/crates.io-index" 1782 | checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f" 1783 | 1784 | [[package]] 1785 | name = "want" 1786 | version = "0.3.0" 1787 | source = "registry+https://github.com/rust-lang/crates.io-index" 1788 | checksum = "1ce8a968cb1cd110d136ff8b819a556d6fb6d919363c61534f6860c7eb172ba0" 1789 | dependencies = [ 1790 | "log", 1791 | "try-lock", 1792 | ] 1793 | 1794 | [[package]] 1795 | name = "wasi" 1796 | version = "0.10.0+wasi-snapshot-preview1" 1797 | source = "registry+https://github.com/rust-lang/crates.io-index" 1798 | checksum = "1a143597ca7c7793eff794def352d41792a93c481eb1042423ff7ff72ba2c31f" 1799 | 1800 | [[package]] 1801 | name = "wasi" 1802 | version = "0.11.0+wasi-snapshot-preview1" 1803 | source = "registry+https://github.com/rust-lang/crates.io-index" 1804 | checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" 1805 | 1806 | [[package]] 1807 | name = "wasm-bindgen" 1808 | version = "0.2.83" 1809 | source = "registry+https://github.com/rust-lang/crates.io-index" 1810 | checksum = "eaf9f5aceeec8be17c128b2e93e031fb8a4d469bb9c4ae2d7dc1888b26887268" 1811 | dependencies = [ 1812 | "cfg-if", 1813 | "wasm-bindgen-macro", 1814 | ] 1815 | 1816 | [[package]] 1817 | name = "wasm-bindgen-backend" 1818 | version = "0.2.83" 1819 | source = "registry+https://github.com/rust-lang/crates.io-index" 1820 | checksum = "4c8ffb332579b0557b52d268b91feab8df3615f265d5270fec2a8c95b17c1142" 1821 | dependencies = [ 1822 | "bumpalo", 1823 | "log", 1824 | "once_cell", 1825 | "proc-macro2", 1826 | "quote", 1827 | "syn", 1828 | "wasm-bindgen-shared", 1829 | ] 1830 | 1831 | [[package]] 1832 | name = "wasm-bindgen-macro" 1833 | version = "0.2.83" 1834 | source = "registry+https://github.com/rust-lang/crates.io-index" 1835 | checksum = "052be0f94026e6cbc75cdefc9bae13fd6052cdcaf532fa6c45e7ae33a1e6c810" 1836 | dependencies = [ 1837 | "quote", 1838 | "wasm-bindgen-macro-support", 1839 | ] 1840 | 1841 | [[package]] 1842 | name = "wasm-bindgen-macro-support" 1843 | version = "0.2.83" 1844 | source = "registry+https://github.com/rust-lang/crates.io-index" 1845 | checksum = "07bc0c051dc5f23e307b13285f9d75df86bfdf816c5721e573dec1f9b8aa193c" 1846 | dependencies = [ 1847 | "proc-macro2", 1848 | "quote", 1849 | "syn", 1850 | "wasm-bindgen-backend", 1851 | "wasm-bindgen-shared", 1852 | ] 1853 | 1854 | [[package]] 1855 | name = "wasm-bindgen-shared" 1856 | version = "0.2.83" 1857 | source = "registry+https://github.com/rust-lang/crates.io-index" 1858 | checksum = "1c38c045535d93ec4f0b4defec448e4291638ee608530863b1e2ba115d4fff7f" 1859 | 1860 | [[package]] 1861 | name = "websocket-chat-react-rust-example" 1862 | version = "0.1.0" 1863 | dependencies = [ 1864 | "axum", 1865 | "axum-extra", 1866 | "chrono", 1867 | "futures", 1868 | "hyper", 1869 | "hyper-tls", 1870 | "serde", 1871 | "serde_json", 1872 | "shuttle-secrets", 1873 | "shuttle-service", 1874 | "shuttle-static-folder", 1875 | "sync_wrapper", 1876 | "tokio", 1877 | "tower-http", 1878 | ] 1879 | 1880 | [[package]] 1881 | name = "winapi" 1882 | version = "0.3.9" 1883 | source = "registry+https://github.com/rust-lang/crates.io-index" 1884 | checksum = "5c839a674fcd7a98952e593242ea400abe93992746761e38641405d28b00f419" 1885 | dependencies = [ 1886 | "winapi-i686-pc-windows-gnu", 1887 | "winapi-x86_64-pc-windows-gnu", 1888 | ] 1889 | 1890 | [[package]] 1891 | name = "winapi-i686-pc-windows-gnu" 1892 | version = "0.4.0" 1893 | source = "registry+https://github.com/rust-lang/crates.io-index" 1894 | checksum = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6" 1895 | 1896 | [[package]] 1897 | name = "winapi-util" 1898 | version = "0.1.5" 1899 | source = "registry+https://github.com/rust-lang/crates.io-index" 1900 | checksum = "70ec6ce85bb158151cae5e5c87f95a8e97d2c0c4b001223f33a334e3ce5de178" 1901 | dependencies = [ 1902 | "winapi", 1903 | ] 1904 | 1905 | [[package]] 1906 | name = "winapi-x86_64-pc-windows-gnu" 1907 | version = "0.4.0" 1908 | source = "registry+https://github.com/rust-lang/crates.io-index" 1909 | checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" 1910 | 1911 | [[package]] 1912 | name = "windows-sys" 1913 | version = "0.42.0" 1914 | source = "registry+https://github.com/rust-lang/crates.io-index" 1915 | checksum = "5a3e1820f08b8513f676f7ab6c1f99ff312fb97b553d30ff4dd86f9f15728aa7" 1916 | dependencies = [ 1917 | "windows_aarch64_gnullvm", 1918 | "windows_aarch64_msvc", 1919 | "windows_i686_gnu", 1920 | "windows_i686_msvc", 1921 | "windows_x86_64_gnu", 1922 | "windows_x86_64_gnullvm", 1923 | "windows_x86_64_msvc", 1924 | ] 1925 | 1926 | [[package]] 1927 | name = "windows_aarch64_gnullvm" 1928 | version = "0.42.0" 1929 | source = "registry+https://github.com/rust-lang/crates.io-index" 1930 | checksum = "41d2aa71f6f0cbe00ae5167d90ef3cfe66527d6f613ca78ac8024c3ccab9a19e" 1931 | 1932 | [[package]] 1933 | name = "windows_aarch64_msvc" 1934 | version = "0.42.0" 1935 | source = "registry+https://github.com/rust-lang/crates.io-index" 1936 | checksum = "dd0f252f5a35cac83d6311b2e795981f5ee6e67eb1f9a7f64eb4500fbc4dcdb4" 1937 | 1938 | [[package]] 1939 | name = "windows_i686_gnu" 1940 | version = "0.42.0" 1941 | source = "registry+https://github.com/rust-lang/crates.io-index" 1942 | checksum = "fbeae19f6716841636c28d695375df17562ca208b2b7d0dc47635a50ae6c5de7" 1943 | 1944 | [[package]] 1945 | name = "windows_i686_msvc" 1946 | version = "0.42.0" 1947 | source = "registry+https://github.com/rust-lang/crates.io-index" 1948 | checksum = "84c12f65daa39dd2babe6e442988fc329d6243fdce47d7d2d155b8d874862246" 1949 | 1950 | [[package]] 1951 | name = "windows_x86_64_gnu" 1952 | version = "0.42.0" 1953 | source = "registry+https://github.com/rust-lang/crates.io-index" 1954 | checksum = "bf7b1b21b5362cbc318f686150e5bcea75ecedc74dd157d874d754a2ca44b0ed" 1955 | 1956 | [[package]] 1957 | name = "windows_x86_64_gnullvm" 1958 | version = "0.42.0" 1959 | source = "registry+https://github.com/rust-lang/crates.io-index" 1960 | checksum = "09d525d2ba30eeb3297665bd434a54297e4170c7f1a44cad4ef58095b4cd2028" 1961 | 1962 | [[package]] 1963 | name = "windows_x86_64_msvc" 1964 | version = "0.42.0" 1965 | source = "registry+https://github.com/rust-lang/crates.io-index" 1966 | checksum = "f40009d85759725a34da6d89a94e63d7bdc50a862acf0dbc7c8e488f1edcb6f5" 1967 | -------------------------------------------------------------------------------- /API/Cargo.toml: -------------------------------------------------------------------------------- 1 | [package] 2 | name = "websocket-chat-react-rust-example" 3 | version = "0.1.0" 4 | edition = "2021" 5 | publish = false 6 | 7 | [lib] 8 | 9 | [dependencies] 10 | axum = { version = "0.6.4", features = ["ws"] } 11 | axum-extra = { version = "0.4.2", features = ["spa"] } 12 | chrono = { version = "0.4", features = ["serde"] } 13 | futures = "0.3" 14 | hyper = { version = "0.14", features = ["client", "http2"] } 15 | hyper-tls = "0.5" 16 | serde = { version = "1.0", features = ["derive"] } 17 | serde_json = "1.0" 18 | shuttle-secrets = "0.10.0" 19 | shuttle-service = { version = "0.10.0", features = ["web-axum"] } 20 | shuttle-static-folder = "0.10.0" 21 | sync_wrapper = "0.1" 22 | tokio = { version = "1", features = ["full"] } 23 | tower-http = { version = "0.3.5", features = ["fs", "auth"]} 24 | 25 | [patch.crates-io.mime_guess] 26 | git="https://github.com/NathanSWard/mime_guess.git" 27 | branch="platform-path-separators" 28 | -------------------------------------------------------------------------------- /API/Shuttle.toml: -------------------------------------------------------------------------------- 1 | name="websocket-chat-react-rust-example" -------------------------------------------------------------------------------- /API/src/main.rs: -------------------------------------------------------------------------------- 1 | // dependencies 2 | use axum::{ 3 | extract::{ 4 | ws::{Message, WebSocket}, 5 | Path, WebSocketUpgrade, 6 | }, 7 | http::StatusCode, 8 | response::IntoResponse, 9 | routing::get, 10 | Extension, Router, 11 | }; 12 | use std::{collections::HashMap, path::PathBuf, sync::Arc}; 13 | 14 | use axum_extra::routing::SpaRouter; 15 | use futures::{SinkExt, StreamExt}; 16 | use serde::{Deserialize, Serialize}; 17 | use shuttle_secrets::SecretStore; 18 | use tokio::sync::{ 19 | mpsc::{self, UnboundedReceiver, UnboundedSender}, 20 | RwLock, 21 | }; 22 | use tower_http::auth::RequireAuthorizationLayer; 23 | 24 | // The list of users needs to be a hashmap that can be shared safely across threads, hence an Arc with RwLock 25 | type Users = Arc>>>; 26 | static NEXT_USERID: std::sync::atomic::AtomicUsize = std::sync::atomic::AtomicUsize::new(1); 27 | 28 | #[derive(Serialize, Deserialize)] 29 | struct Msg { 30 | name: String, 31 | uid: Option, 32 | message: String, 33 | } 34 | 35 | #[shuttle_runtime::main] 36 | async fn axum( 37 | #[shuttle_secrets::Secrets] secrets: SecretStore, 38 | #[shuttle_static_folder::StaticFolder] static_folder: PathBuf, 39 | ) -> shuttle_axum::ShuttleAxum { 40 | // We use Secrets.toml to set the BEARER key, just like in a .env file and call it here 41 | let secret = secrets.get("BEARER").unwrap_or("Bear".to_string()); 42 | 43 | // set up router with Secrets & use syncwrapper to make the web service work 44 | let router = router(secret, static_folder); 45 | 46 | Ok(router.into()) 47 | } 48 | 49 | fn router(secret: String, static_folder: PathBuf) -> Router { 50 | // initialise the Users k/v store and allow the static files to be served 51 | let users = Users::default(); 52 | 53 | // make an admin route for kicking users 54 | let admin = Router::new() 55 | .route("/disconnect/:user_id", get(disconnect_user)) 56 | .layer(RequireAuthorizationLayer::bearer(&secret)); 57 | 58 | let static_assets = SpaRouter::new("/", static_folder).index_file("index.html"); 59 | // return a new router and nest the admin route into the websocket route 60 | Router::new() 61 | .route("/ws", get(ws_handler)) 62 | .nest("/admin", admin) 63 | .layer(Extension(users)) 64 | .merge(static_assets) 65 | } 66 | 67 | async fn ws_handler(ws: WebSocketUpgrade, Extension(state): Extension) -> impl IntoResponse { 68 | ws.on_upgrade(|socket| handle_socket(socket, state)) 69 | } 70 | 71 | async fn handle_socket(stream: WebSocket, state: Users) { 72 | // When a new user enters the chat (opens the websocket connection), assign them a user ID 73 | let my_id = NEXT_USERID.fetch_add(1, std::sync::atomic::Ordering::Relaxed); 74 | // By splitting the websocket into a receiver and sender, we can send and receive at the same time. 75 | let (mut sender, mut receiver) = stream.split(); 76 | 77 | // Create a new channel for async task management 78 | let (tx, mut rx): (UnboundedSender, UnboundedReceiver) = 79 | mpsc::unbounded_channel(); 80 | 81 | // If a message has been received, send the message (expect on error) 82 | tokio::spawn(async move { 83 | // If a message has been received, send a message 84 | while let Some(msg) = rx.recv().await { 85 | sender.send(msg).await.expect("Error while sending message"); 86 | } 87 | sender.close().await.unwrap(); 88 | }); 89 | 90 | // insert the message into the HashMap - locks the Arc value to allow writing 91 | state.write().await.insert(my_id, tx); 92 | 93 | // if there's a message and the message is OK, broadcast it along all available open websocket connections 94 | while let Some(Ok(result)) = receiver.next().await { 95 | println!("{:?}", result); 96 | if let Ok(result) = enrich_result(result, my_id) { 97 | broadcast_msg(result, &state).await; 98 | } 99 | } 100 | 101 | // This client disconnected 102 | disconnect(my_id, &state).await; 103 | } 104 | 105 | // If the message is a websocket message and no errors, return it - else, return Ok(result) 106 | // which is required by the server to be able to broadcast the message 107 | fn enrich_result(result: Message, id: usize) -> Result { 108 | match result { 109 | Message::Text(msg) => { 110 | let mut msg: Msg = serde_json::from_str(&msg)?; 111 | msg.uid = Some(id); 112 | let msg = serde_json::to_string(&msg)?; 113 | Ok(Message::Text(msg)) 114 | } 115 | _ => Ok(result), 116 | } 117 | } 118 | 119 | // Send received websocket message out to all open available WS connections 120 | async fn broadcast_msg(msg: Message, users: &Users) { 121 | if let Message::Text(msg) = msg { 122 | for (&_uid, tx) in users.read().await.iter() { 123 | tx.send(Message::Text(msg.clone())) 124 | .expect("Failed to send Message") 125 | } 126 | } 127 | } 128 | 129 | // Disconnect a user manually - this is for admin purposes, eg if someone is being offensive in the chat 130 | // you will want to be able to kick them out 131 | async fn disconnect_user( 132 | Path(user_id): Path, 133 | Extension(users): Extension, 134 | ) -> impl IntoResponse { 135 | disconnect(user_id, &users).await; 136 | "Done" 137 | } 138 | 139 | // triggered when any user disconnects 140 | async fn disconnect(my_id: usize, users: &Users) { 141 | println!("Good bye user {}", my_id); 142 | users.write().await.remove(&my_id); 143 | println!("Disconnected {my_id}"); 144 | } 145 | 146 | // handle internal server errors 147 | async fn handle_error(err: std::io::Error) -> impl IntoResponse { 148 | (StatusCode::INTERNAL_SERVER_ERROR, format!("{:?}", err)) 149 | } 150 | -------------------------------------------------------------------------------- /API/static/assets/index-8cf6afb9.css: -------------------------------------------------------------------------------- 1 | @import"https://fonts.googleapis.com/css2?family=Text+Me+One&display=swap";*,:before,:after{box-sizing:border-box;border-width:0;border-style:solid;border-color:#e5e7eb}:before,:after{--tw-content: ""}html{line-height:1.5;-webkit-text-size-adjust:100%;-moz-tab-size:4;-o-tab-size:4;tab-size:4;font-family:ui-sans-serif,system-ui,-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Helvetica Neue,Arial,Noto Sans,sans-serif,"Apple Color Emoji","Segoe UI Emoji",Segoe UI Symbol,"Noto Color Emoji";font-feature-settings:normal}body{margin:0;line-height:inherit}hr{height:0;color:inherit;border-top-width:1px}abbr:where([title]){-webkit-text-decoration:underline dotted;text-decoration:underline dotted}h1,h2,h3,h4,h5,h6{font-size:inherit;font-weight:inherit}a{color:inherit;text-decoration:inherit}b,strong{font-weight:bolder}code,kbd,samp,pre{font-family:ui-monospace,SFMono-Regular,Menlo,Monaco,Consolas,Liberation Mono,Courier New,monospace;font-size:1em}small{font-size:80%}sub,sup{font-size:75%;line-height:0;position:relative;vertical-align:baseline}sub{bottom:-.25em}sup{top:-.5em}table{text-indent:0;border-color:inherit;border-collapse:collapse}button,input,optgroup,select,textarea{font-family:inherit;font-size:100%;font-weight:inherit;line-height:inherit;color:inherit;margin:0;padding:0}button,select{text-transform:none}button,[type=button],[type=reset],[type=submit]{-webkit-appearance:button;background-color:transparent;background-image:none}:-moz-focusring{outline:auto}:-moz-ui-invalid{box-shadow:none}progress{vertical-align:baseline}::-webkit-inner-spin-button,::-webkit-outer-spin-button{height:auto}[type=search]{-webkit-appearance:textfield;outline-offset:-2px}::-webkit-search-decoration{-webkit-appearance:none}::-webkit-file-upload-button{-webkit-appearance:button;font:inherit}summary{display:list-item}blockquote,dl,dd,h1,h2,h3,h4,h5,h6,hr,figure,p,pre{margin:0}fieldset{margin:0;padding:0}legend{padding:0}ol,ul,menu{list-style:none;margin:0;padding:0}textarea{resize:vertical}input::-moz-placeholder,textarea::-moz-placeholder{opacity:1;color:#9ca3af}input::placeholder,textarea::placeholder{opacity:1;color:#9ca3af}button,[role=button]{cursor:pointer}:disabled{cursor:default}img,svg,video,canvas,audio,iframe,embed,object{display:block;vertical-align:middle}img,video{max-width:100%;height:auto}[hidden]{display:none}input,button{box-shadow:5px 5px #00000080}input:active,button:active{box-shadow:3px 3px #00000080}*,:before,:after{--tw-border-spacing-x: 0;--tw-border-spacing-y: 0;--tw-translate-x: 0;--tw-translate-y: 0;--tw-rotate: 0;--tw-skew-x: 0;--tw-skew-y: 0;--tw-scale-x: 1;--tw-scale-y: 1;--tw-pan-x: ;--tw-pan-y: ;--tw-pinch-zoom: ;--tw-scroll-snap-strictness: proximity;--tw-ordinal: ;--tw-slashed-zero: ;--tw-numeric-figure: ;--tw-numeric-spacing: ;--tw-numeric-fraction: ;--tw-ring-inset: ;--tw-ring-offset-width: 0px;--tw-ring-offset-color: #fff;--tw-ring-color: rgb(59 130 246 / .5);--tw-ring-offset-shadow: 0 0 #0000;--tw-ring-shadow: 0 0 #0000;--tw-shadow: 0 0 #0000;--tw-shadow-colored: 0 0 #0000;--tw-blur: ;--tw-brightness: ;--tw-contrast: ;--tw-grayscale: ;--tw-hue-rotate: ;--tw-invert: ;--tw-saturate: ;--tw-sepia: ;--tw-drop-shadow: ;--tw-backdrop-blur: ;--tw-backdrop-brightness: ;--tw-backdrop-contrast: ;--tw-backdrop-grayscale: ;--tw-backdrop-hue-rotate: ;--tw-backdrop-invert: ;--tw-backdrop-opacity: ;--tw-backdrop-saturate: ;--tw-backdrop-sepia: }::backdrop{--tw-border-spacing-x: 0;--tw-border-spacing-y: 0;--tw-translate-x: 0;--tw-translate-y: 0;--tw-rotate: 0;--tw-skew-x: 0;--tw-skew-y: 0;--tw-scale-x: 1;--tw-scale-y: 1;--tw-pan-x: ;--tw-pan-y: ;--tw-pinch-zoom: ;--tw-scroll-snap-strictness: proximity;--tw-ordinal: ;--tw-slashed-zero: ;--tw-numeric-figure: ;--tw-numeric-spacing: ;--tw-numeric-fraction: ;--tw-ring-inset: ;--tw-ring-offset-width: 0px;--tw-ring-offset-color: #fff;--tw-ring-color: rgb(59 130 246 / .5);--tw-ring-offset-shadow: 0 0 #0000;--tw-ring-shadow: 0 0 #0000;--tw-shadow: 0 0 #0000;--tw-shadow-colored: 0 0 #0000;--tw-blur: ;--tw-brightness: ;--tw-contrast: ;--tw-grayscale: ;--tw-hue-rotate: ;--tw-invert: ;--tw-saturate: ;--tw-sepia: ;--tw-drop-shadow: ;--tw-backdrop-blur: ;--tw-backdrop-brightness: ;--tw-backdrop-contrast: ;--tw-backdrop-grayscale: ;--tw-backdrop-hue-rotate: ;--tw-backdrop-invert: ;--tw-backdrop-opacity: ;--tw-backdrop-saturate: ;--tw-backdrop-sepia: }.fixed{position:fixed}.absolute{position:absolute}.bottom-0{bottom:0px}.z-40{z-index:40}.z-50{z-index:50}.mx-8{margin-left:2rem;margin-right:2rem}.mb-5{margin-bottom:1.25rem}.inline-block{display:inline-block}.flex{display:flex}.hidden{display:none}.h-10{height:2.5rem}.h-screen{height:100vh}.h-3\/5{height:60%}.min-h-screen{min-height:100vh}.w-full{width:100%}.w-fit{width:-moz-fit-content;width:fit-content}.w-screen{width:100vw}.w-4\/5{width:80%}.flex-row{flex-direction:row}.flex-col{flex-direction:column}.items-center{align-items:center}.justify-end{justify-content:flex-end}.justify-center{justify-content:center}.gap-4{gap:1rem}.break-all{word-break:break-all}.rounded-xl{border-radius:.75rem}.rounded-tl-xl{border-top-left-radius:.75rem}.rounded-bl-xl{border-bottom-left-radius:.75rem}.rounded-tr-xl{border-top-right-radius:.75rem}.rounded-br-xl{border-bottom-right-radius:.75rem}.bg-slate-700{--tw-bg-opacity: 1;background-color:rgb(51 65 85 / var(--tw-bg-opacity))}.bg-slate-600{--tw-bg-opacity: 1;background-color:rgb(71 85 105 / var(--tw-bg-opacity))}.bg-slate-400{--tw-bg-opacity: 1;background-color:rgb(148 163 184 / var(--tw-bg-opacity))}.bg-slate-300{--tw-bg-opacity: 1;background-color:rgb(203 213 225 / var(--tw-bg-opacity))}.bg-slate-500{--tw-bg-opacity: 1;background-color:rgb(100 116 139 / var(--tw-bg-opacity))}.px-5{padding-left:1.25rem;padding-right:1.25rem}.py-4{padding-top:1rem;padding-bottom:1rem}.py-2{padding-top:.5rem;padding-bottom:.5rem}.px-2{padding-left:.5rem;padding-right:.5rem}.pb-5{padding-bottom:1.25rem}.pb-20{padding-bottom:5rem}.text-sm{font-size:.875rem;line-height:1.25rem}.text-lg{font-size:1.125rem;line-height:1.75rem}.text-gray-100{--tw-text-opacity: 1;color:rgb(243 244 246 / var(--tw-text-opacity))}.text-gray-200{--tw-text-opacity: 1;color:rgb(229 231 235 / var(--tw-text-opacity))}.shadow-md{--tw-shadow: 0 4px 6px -1px rgb(0 0 0 / .1), 0 2px 4px -2px rgb(0 0 0 / .1);--tw-shadow-colored: 0 4px 6px -1px var(--tw-shadow-color), 0 2px 4px -2px var(--tw-shadow-color);box-shadow:var(--tw-ring-offset-shadow, 0 0 #0000),var(--tw-ring-shadow, 0 0 #0000),var(--tw-shadow)}.backdrop-blur-xl{--tw-backdrop-blur: blur(24px);-webkit-backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia);backdrop-filter:var(--tw-backdrop-blur) var(--tw-backdrop-brightness) var(--tw-backdrop-contrast) var(--tw-backdrop-grayscale) var(--tw-backdrop-hue-rotate) var(--tw-backdrop-invert) var(--tw-backdrop-opacity) var(--tw-backdrop-saturate) var(--tw-backdrop-sepia)}.transition-all{transition-property:all;transition-timing-function:cubic-bezier(.4,0,.2,1);transition-duration:.15s}body{font-family:Text Me One,"Sans Serif";padding:0;margin:0;background-color:#d6d3d1;box-sizing:box-border;overflow-x:hidden}.hover\:bg-slate-400:hover{--tw-bg-opacity: 1;background-color:rgb(148 163 184 / var(--tw-bg-opacity))}.hover\:text-black:hover{--tw-text-opacity: 1;color:rgb(0 0 0 / var(--tw-text-opacity))}.focus\:outline-0:focus{outline-width:0px}.active\:translate-y-0\.5:active{--tw-translate-y: .125rem;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skew(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.active\:translate-x-0\.5:active{--tw-translate-x: .125rem;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skew(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.active\:translate-y-0:active{--tw-translate-y: 0px;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skew(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}.active\:translate-x-0:active{--tw-translate-x: 0px;transform:translate(var(--tw-translate-x),var(--tw-translate-y)) rotate(var(--tw-rotate)) skew(var(--tw-skew-x)) skewY(var(--tw-skew-y)) scaleX(var(--tw-scale-x)) scaleY(var(--tw-scale-y))}@media (min-width: 1024px){.lg\:h-2\/5{height:40%}.lg\:w-2\/5{width:40%}.lg\:text-2xl{font-size:1.5rem;line-height:2rem}} 2 | -------------------------------------------------------------------------------- /API/static/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | Rustcord 7 | 8 | 9 | 10 | 11 |
12 | 13 | 14 | 15 | -------------------------------------------------------------------------------- /API/static/vite.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | ## Websocket Chat App Example - React + Rust 2 | This repo is intended to show an example of a websocket chat app created using React and Rust. 3 | 4 | ## Live Deployment 5 | Check out the live deployment [here](https://websocket-chat-react-rust-example.shuttleapp.rs). 6 | 7 | ![](./Screenshot.png) 8 | 9 | ## How To Use 10 | Run the following commands below: 11 | 12 | ``` 13 | npm i 14 | npm run dev 15 | ``` 16 | This installs all dependencies and runs both of the React and Rust programs. Bear in mind that for a first-time execution, you'll have to wait for Cargo to build. 17 | 18 | Now go to http://localhost:5173 and try entering a name, then typing in some messages. -------------------------------------------------------------------------------- /Screenshot.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/joshua-mo-143/react-websocket-chat-rust/HEAD/Screenshot.png -------------------------------------------------------------------------------- /index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | Rustcord 7 | 8 | 9 |
10 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "react-websocket-chat-rust", 3 | "private": true, 4 | "version": "0.0.0", 5 | "type": "module", 6 | "scripts": { 7 | "dev": "concurrently \"vite\" \"cargo shuttle run --working-directory API --port 9999\"", 8 | "dev-fe": "vite", 9 | "build": "tsc && vite build --emptyOutDir", 10 | "preview": "vite preview", 11 | "deploy": "npm run build && cargo shuttle deploy --working-directory ./API" 12 | 13 | }, 14 | "dependencies": { 15 | "framer-motion": "^8.4.0", 16 | "react": "^18.2.0", 17 | "react-dom": "^18.2.0", 18 | "react-use-websocket": "^4.2.0" 19 | }, 20 | "devDependencies": { 21 | "@types/node": "^18.11.18", 22 | "@types/react": "^18.0.26", 23 | "@types/react-dom": "^18.0.9", 24 | "@vitejs/plugin-react": "^3.0.0", 25 | "autoprefixer": "^10.4.13", 26 | "concurrently": "^7.6.0", 27 | "postcss": "^8.4.21", 28 | "tailwindcss": "^3.2.4", 29 | "typescript": "^4.9.3", 30 | "vite": "^4.0.0" 31 | } 32 | } 33 | -------------------------------------------------------------------------------- /postcss.config.cjs: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | plugins: { 3 | tailwindcss: {}, 4 | autoprefixer: {}, 5 | } 6 | } -------------------------------------------------------------------------------- /public/vite.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /src/App.tsx: -------------------------------------------------------------------------------- 1 | import React, { SetStateAction } from 'react' 2 | import NamePrompt from './components/NamePrompt'; 3 | 4 | type Message = { 5 | name: string, 6 | uid: number, 7 | message: string 8 | } 9 | function App() { 10 | const [name, setName] = React.useState(""); 11 | const [vis, setVis] = React.useState(true); 12 | 13 | const [message, setMessage] = React.useState(""); 14 | 15 | 16 | return ( 17 | 18 | <> 19 | 20 |
21 |
22 |
23 |
24 |

Hi! Welcome to Rustcord. Enjoy your stay!

25 |
26 |
27 |
sendMessage(e, name, message, setMessage)}> 28 | ) => setMessage(e.target.value)} /> 31 | 34 |
35 |
36 |
37 | 38 | 39 | ) 40 | } 41 | 42 | export default App 43 | 44 | const sendMessage = (e: React.FormEvent, name: string, message: string, setMessage: React.Dispatch>) => { 45 | e.preventDefault() 46 | // if user hasn't entered anything in to send, do nothing 47 | if (message.trim() == "") { 48 | return 49 | } 50 | // Send a websocket message to the server 51 | websocket.send( 52 | JSON.stringify({ 53 | name: name, 54 | message: message 55 | }) 56 | ); 57 | // Reset message input box 58 | setMessage("") 59 | } 60 | 61 | // Set up the websocket URL. 62 | const wsUri = ((window.location.protocol == "https:" && "wss://") || "ws://") + 63 | window.location.host + 64 | "/ws"; 65 | 66 | const websocket = new WebSocket(wsUri); 67 | 68 | // On open, do nothing - console.log() can be added for debugging purposes 69 | websocket.onopen = () => { 70 | 71 | } 72 | 73 | // On close, do nothing - console.log() can be added for debugging purposes 74 | websocket.onclose = () => { 75 | 76 | } 77 | 78 | // On receiving a message from the server, parse the data and then create an entry in the chat 79 | websocket.onmessage = (ev) => { 80 | let message = JSON.parse(ev.data); 81 | create_message(message); 82 | } 83 | 84 | // store the message classes as an array 85 | const message_classes = "mx-8 break-all chat-message bg-slate-600 rounded-xl w-fit max-w-screen rounded-xl px-5 py-4".split(" "); 86 | const username_css_classes = "text-gray-200 text-sm".split(" "); 87 | 88 | const create_message = (data: Message) => { 89 | let messageContainer = document.createElement('div'); 90 | messageContainer.classList.add(...message_classes); 91 | let chatbox = document.querySelector('#chatbox'); 92 | let username = document.createElement('span'); 93 | username.classList.add(...username_css_classes); 94 | username.innerText = `${data.name}`; 95 | messageContainer.append(username); 96 | let message = document.createElement('p'); 97 | message.innerText = `${data.message}`; 98 | messageContainer.append(message); 99 | chatbox?.append(messageContainer); 100 | window.scrollTo(0, document.body.scrollHeight); 101 | } -------------------------------------------------------------------------------- /src/assets/react.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /src/components/NamePrompt.tsx: -------------------------------------------------------------------------------- 1 | import React, { SetStateAction } from 'react' 2 | import { motion, AnimatePresence } from 'framer-motion'; 3 | 4 | type Props = { 5 | vis: boolean, 6 | name: string, 7 | setName: React.Dispatch>, 8 | setVis: React.Dispatch> 9 | } 10 | 11 | const NamePrompt = ({vis, name, setName, setVis}: Props) => { 12 | 13 | const submitName = (e: React.FormEvent) => { 14 | e.preventDefault() 15 | if (name == "") { 16 | return 17 | } 18 | setVis(false) 19 | } 20 | 21 | return ( 22 | 23 | 38 | 39 | ) 40 | } 41 | 42 | export default NamePrompt -------------------------------------------------------------------------------- /src/index.css: -------------------------------------------------------------------------------- 1 | @import url('https://fonts.googleapis.com/css2?family=Text+Me+One&display=swap'); 2 | @tailwind base; 3 | @tailwind components; 4 | @tailwind utilities; 5 | 6 | @layer base { 7 | 8 | input, button { 9 | box-shadow: 5px 5px rgba(0,0,0,0.5); 10 | } 11 | 12 | input:active, button:active { 13 | box-shadow: 3px 3px rgba(0,0,0,0.5); 14 | } 15 | } 16 | 17 | body { 18 | font-family: 'Text Me One', 'Sans Serif'; 19 | padding: 0; 20 | margin: 0; 21 | background-color: rgb(214 211 209); 22 | box-sizing: box-border; 23 | overflow-x: hidden; 24 | } -------------------------------------------------------------------------------- /src/main.tsx: -------------------------------------------------------------------------------- 1 | import React from 'react' 2 | import ReactDOM from 'react-dom/client' 3 | import App from './App' 4 | import './index.css' 5 | 6 | ReactDOM.createRoot(document.getElementById('root') as HTMLElement).render( 7 | 8 | 9 | 10 | ) 11 | -------------------------------------------------------------------------------- /src/vite-env.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | -------------------------------------------------------------------------------- /tailwind.config.cjs: -------------------------------------------------------------------------------- 1 | /** @type {import('tailwindcss').Config} */ 2 | module.exports = { 3 | content: ["./src/**/*.{html,js,ts,tsx}"], 4 | theme: { 5 | extend: { 6 | }, 7 | }, 8 | plugins: [], 9 | } 10 | -------------------------------------------------------------------------------- /tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ESNext", 4 | "useDefineForClassFields": true, 5 | "lib": ["DOM", "DOM.Iterable", "ESNext"], 6 | "allowJs": false, 7 | "skipLibCheck": true, 8 | "esModuleInterop": false, 9 | "allowSyntheticDefaultImports": true, 10 | "strict": true, 11 | "forceConsistentCasingInFileNames": true, 12 | "module": "ESNext", 13 | "moduleResolution": "Node", 14 | "resolveJsonModule": true, 15 | "isolatedModules": true, 16 | "noEmit": true, 17 | "jsx": "react-jsx" 18 | }, 19 | "include": ["src"], 20 | "references": [{ "path": "./tsconfig.node.json" }] 21 | } 22 | -------------------------------------------------------------------------------- /tsconfig.node.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "composite": true, 4 | "module": "ESNext", 5 | "moduleResolution": "Node", 6 | "allowSyntheticDefaultImports": true 7 | }, 8 | "include": ["vite.config.ts"] 9 | } 10 | -------------------------------------------------------------------------------- /vite.config.ts: -------------------------------------------------------------------------------- 1 | import { defineConfig } from 'vite' 2 | import react from '@vitejs/plugin-react' 3 | 4 | // https://vitejs.dev/config/ 5 | export default defineConfig({ 6 | base: '', 7 | plugins: [react()], 8 | build: { 9 | outDir: 'API/static', 10 | emptyOutDir: true 11 | } 12 | }) 13 | --------------------------------------------------------------------------------