├── .gitignore ├── Cargo.lock ├── Cargo.toml ├── README.md ├── schemas └── api_schema.json └── src ├── ai_functions ├── aifunc_architect.rs ├── aifunc_backend.rs ├── aifunc_managing.rs └── mod.rs ├── apis ├── call_request.rs └── mod.rs ├── helpers ├── command_line.rs ├── general.rs └── mod.rs ├── main.rs └── models ├── agent_basic ├── basic_agent.rs ├── basic_traits.rs └── mod.rs ├── agents ├── agent_architect.rs ├── agent_backend.rs ├── agent_traits.rs └── mod.rs ├── agents_manager ├── managing_agent.rs └── mod.rs ├── general ├── llm.rs └── mod.rs └── mod.rs /.gitignore: -------------------------------------------------------------------------------- 1 | /target 2 | .env 3 | -------------------------------------------------------------------------------- /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 = "ai_functions" 7 | version = "0.1.1" 8 | source = "registry+https://github.com/rust-lang/crates.io-index" 9 | checksum = "911649227e07403a6c53676f9d15bf919e6541ffaad3a6d5ba5c3f6beed3d11b" 10 | dependencies = [ 11 | "proc-macro2", 12 | "quote", 13 | "syn 2.0.18", 14 | ] 15 | 16 | [[package]] 17 | name = "async-trait" 18 | version = "0.1.68" 19 | source = "registry+https://github.com/rust-lang/crates.io-index" 20 | checksum = "b9ccdd8f2a161be9bd5c023df56f1b2a0bd1d83872ae53b71a84a12c9bf6e842" 21 | dependencies = [ 22 | "proc-macro2", 23 | "quote", 24 | "syn 2.0.18", 25 | ] 26 | 27 | [[package]] 28 | name = "auto_gippity" 29 | version = "0.1.0" 30 | dependencies = [ 31 | "ai_functions", 32 | "async-trait", 33 | "crossterm", 34 | "dotenv", 35 | "reqwest", 36 | "serde", 37 | "serde_json", 38 | "strum", 39 | "strum_macros", 40 | "tokio", 41 | "webbrowser", 42 | ] 43 | 44 | [[package]] 45 | name = "autocfg" 46 | version = "1.1.0" 47 | source = "registry+https://github.com/rust-lang/crates.io-index" 48 | checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa" 49 | 50 | [[package]] 51 | name = "base64" 52 | version = "0.21.2" 53 | source = "registry+https://github.com/rust-lang/crates.io-index" 54 | checksum = "604178f6c5c21f02dc555784810edfb88d34ac2c73b2eae109655649ee73ce3d" 55 | 56 | [[package]] 57 | name = "bitflags" 58 | version = "1.3.2" 59 | source = "registry+https://github.com/rust-lang/crates.io-index" 60 | checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a" 61 | 62 | [[package]] 63 | name = "bumpalo" 64 | version = "3.13.0" 65 | source = "registry+https://github.com/rust-lang/crates.io-index" 66 | checksum = "a3e2c3daef883ecc1b5d58c15adae93470a91d425f3532ba1695849656af3fc1" 67 | 68 | [[package]] 69 | name = "bytes" 70 | version = "1.4.0" 71 | source = "registry+https://github.com/rust-lang/crates.io-index" 72 | checksum = "89b2fd2a0dcf38d7971e2194b6b6eebab45ae01067456a7fd93d5547a61b70be" 73 | 74 | [[package]] 75 | name = "cc" 76 | version = "1.0.79" 77 | source = "registry+https://github.com/rust-lang/crates.io-index" 78 | checksum = "50d30906286121d95be3d479533b458f87493b30a4b5f79a607db8f5d11aa91f" 79 | 80 | [[package]] 81 | name = "cesu8" 82 | version = "1.1.0" 83 | source = "registry+https://github.com/rust-lang/crates.io-index" 84 | checksum = "6d43a04d8753f35258c91f8ec639f792891f748a1edbd759cf1dcea3382ad83c" 85 | 86 | [[package]] 87 | name = "cfg-if" 88 | version = "1.0.0" 89 | source = "registry+https://github.com/rust-lang/crates.io-index" 90 | checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" 91 | 92 | [[package]] 93 | name = "combine" 94 | version = "4.6.6" 95 | source = "registry+https://github.com/rust-lang/crates.io-index" 96 | checksum = "35ed6e9d84f0b51a7f52daf1c7d71dd136fd7a3f41a8462b8cdb8c78d920fad4" 97 | dependencies = [ 98 | "bytes", 99 | "memchr", 100 | ] 101 | 102 | [[package]] 103 | name = "core-foundation" 104 | version = "0.9.3" 105 | source = "registry+https://github.com/rust-lang/crates.io-index" 106 | checksum = "194a7a9e6de53fa55116934067c844d9d749312f75c6f6d0980e8c252f8c2146" 107 | dependencies = [ 108 | "core-foundation-sys", 109 | "libc", 110 | ] 111 | 112 | [[package]] 113 | name = "core-foundation-sys" 114 | version = "0.8.4" 115 | source = "registry+https://github.com/rust-lang/crates.io-index" 116 | checksum = "e496a50fda8aacccc86d7529e2c1e0892dbd0f898a6b5645b5561b89c3210efa" 117 | 118 | [[package]] 119 | name = "crossterm" 120 | version = "0.26.1" 121 | source = "registry+https://github.com/rust-lang/crates.io-index" 122 | checksum = "a84cda67535339806297f1b331d6dd6320470d2a0fe65381e79ee9e156dd3d13" 123 | dependencies = [ 124 | "bitflags", 125 | "crossterm_winapi", 126 | "libc", 127 | "mio", 128 | "parking_lot", 129 | "signal-hook", 130 | "signal-hook-mio", 131 | "winapi", 132 | ] 133 | 134 | [[package]] 135 | name = "crossterm_winapi" 136 | version = "0.9.0" 137 | source = "registry+https://github.com/rust-lang/crates.io-index" 138 | checksum = "2ae1b35a484aa10e07fe0638d02301c5ad24de82d310ccbd2f3693da5f09bf1c" 139 | dependencies = [ 140 | "winapi", 141 | ] 142 | 143 | [[package]] 144 | name = "dotenv" 145 | version = "0.15.0" 146 | source = "registry+https://github.com/rust-lang/crates.io-index" 147 | checksum = "77c90badedccf4105eca100756a0b1289e191f6fcbdadd3cee1d2f614f97da8f" 148 | 149 | [[package]] 150 | name = "encoding_rs" 151 | version = "0.8.32" 152 | source = "registry+https://github.com/rust-lang/crates.io-index" 153 | checksum = "071a31f4ee85403370b58aca746f01041ede6f0da2730960ad001edc2b71b394" 154 | dependencies = [ 155 | "cfg-if", 156 | ] 157 | 158 | [[package]] 159 | name = "errno" 160 | version = "0.3.1" 161 | source = "registry+https://github.com/rust-lang/crates.io-index" 162 | checksum = "4bcfec3a70f97c962c307b2d2c56e358cf1d00b558d74262b5f929ee8cc7e73a" 163 | dependencies = [ 164 | "errno-dragonfly", 165 | "libc", 166 | "windows-sys 0.48.0", 167 | ] 168 | 169 | [[package]] 170 | name = "errno-dragonfly" 171 | version = "0.1.2" 172 | source = "registry+https://github.com/rust-lang/crates.io-index" 173 | checksum = "aa68f1b12764fab894d2755d2518754e71b4fd80ecfb822714a1206c2aab39bf" 174 | dependencies = [ 175 | "cc", 176 | "libc", 177 | ] 178 | 179 | [[package]] 180 | name = "fastrand" 181 | version = "1.9.0" 182 | source = "registry+https://github.com/rust-lang/crates.io-index" 183 | checksum = "e51093e27b0797c359783294ca4f0a911c270184cb10f85783b118614a1501be" 184 | dependencies = [ 185 | "instant", 186 | ] 187 | 188 | [[package]] 189 | name = "fnv" 190 | version = "1.0.7" 191 | source = "registry+https://github.com/rust-lang/crates.io-index" 192 | checksum = "3f9eec918d3f24069decb9af1554cad7c880e2da24a9afd88aca000531ab82c1" 193 | 194 | [[package]] 195 | name = "foreign-types" 196 | version = "0.3.2" 197 | source = "registry+https://github.com/rust-lang/crates.io-index" 198 | checksum = "f6f339eb8adc052cd2ca78910fda869aefa38d22d5cb648e6485e4d3fc06f3b1" 199 | dependencies = [ 200 | "foreign-types-shared", 201 | ] 202 | 203 | [[package]] 204 | name = "foreign-types-shared" 205 | version = "0.1.1" 206 | source = "registry+https://github.com/rust-lang/crates.io-index" 207 | checksum = "00b0228411908ca8685dba7fc2cdd70ec9990a6e753e89b6ac91a84c40fbaf4b" 208 | 209 | [[package]] 210 | name = "form_urlencoded" 211 | version = "1.2.0" 212 | source = "registry+https://github.com/rust-lang/crates.io-index" 213 | checksum = "a62bc1cf6f830c2ec14a513a9fb124d0a213a629668a4186f329db21fe045652" 214 | dependencies = [ 215 | "percent-encoding", 216 | ] 217 | 218 | [[package]] 219 | name = "futures-channel" 220 | version = "0.3.28" 221 | source = "registry+https://github.com/rust-lang/crates.io-index" 222 | checksum = "955518d47e09b25bbebc7a18df10b81f0c766eaf4c4f1cccef2fca5f2a4fb5f2" 223 | dependencies = [ 224 | "futures-core", 225 | ] 226 | 227 | [[package]] 228 | name = "futures-core" 229 | version = "0.3.28" 230 | source = "registry+https://github.com/rust-lang/crates.io-index" 231 | checksum = "4bca583b7e26f571124fe5b7561d49cb2868d79116cfa0eefce955557c6fee8c" 232 | 233 | [[package]] 234 | name = "futures-sink" 235 | version = "0.3.28" 236 | source = "registry+https://github.com/rust-lang/crates.io-index" 237 | checksum = "f43be4fe21a13b9781a69afa4985b0f6ee0e1afab2c6f454a8cf30e2b2237b6e" 238 | 239 | [[package]] 240 | name = "futures-task" 241 | version = "0.3.28" 242 | source = "registry+https://github.com/rust-lang/crates.io-index" 243 | checksum = "76d3d132be6c0e6aa1534069c705a74a5997a356c0dc2f86a47765e5617c5b65" 244 | 245 | [[package]] 246 | name = "futures-util" 247 | version = "0.3.28" 248 | source = "registry+https://github.com/rust-lang/crates.io-index" 249 | checksum = "26b01e40b772d54cf6c6d721c1d1abd0647a0106a12ecaa1c186273392a69533" 250 | dependencies = [ 251 | "futures-core", 252 | "futures-task", 253 | "pin-project-lite", 254 | "pin-utils", 255 | ] 256 | 257 | [[package]] 258 | name = "h2" 259 | version = "0.3.19" 260 | source = "registry+https://github.com/rust-lang/crates.io-index" 261 | checksum = "d357c7ae988e7d2182f7d7871d0b963962420b0678b0997ce7de72001aeab782" 262 | dependencies = [ 263 | "bytes", 264 | "fnv", 265 | "futures-core", 266 | "futures-sink", 267 | "futures-util", 268 | "http", 269 | "indexmap", 270 | "slab", 271 | "tokio", 272 | "tokio-util", 273 | "tracing", 274 | ] 275 | 276 | [[package]] 277 | name = "hashbrown" 278 | version = "0.12.3" 279 | source = "registry+https://github.com/rust-lang/crates.io-index" 280 | checksum = "8a9ee70c43aaf417c914396645a0fa852624801b24ebb7ae78fe8272889ac888" 281 | 282 | [[package]] 283 | name = "heck" 284 | version = "0.4.1" 285 | source = "registry+https://github.com/rust-lang/crates.io-index" 286 | checksum = "95505c38b4572b2d910cecb0281560f54b440a19336cbbcb27bf6ce6adc6f5a8" 287 | 288 | [[package]] 289 | name = "hermit-abi" 290 | version = "0.2.6" 291 | source = "registry+https://github.com/rust-lang/crates.io-index" 292 | checksum = "ee512640fe35acbfb4bb779db6f0d80704c2cacfa2e39b601ef3e3f47d1ae4c7" 293 | dependencies = [ 294 | "libc", 295 | ] 296 | 297 | [[package]] 298 | name = "hermit-abi" 299 | version = "0.3.1" 300 | source = "registry+https://github.com/rust-lang/crates.io-index" 301 | checksum = "fed44880c466736ef9a5c5b5facefb5ed0785676d0c02d612db14e54f0d84286" 302 | 303 | [[package]] 304 | name = "home" 305 | version = "0.5.5" 306 | source = "registry+https://github.com/rust-lang/crates.io-index" 307 | checksum = "5444c27eef6923071f7ebcc33e3444508466a76f7a2b93da00ed6e19f30c1ddb" 308 | dependencies = [ 309 | "windows-sys 0.48.0", 310 | ] 311 | 312 | [[package]] 313 | name = "http" 314 | version = "0.2.9" 315 | source = "registry+https://github.com/rust-lang/crates.io-index" 316 | checksum = "bd6effc99afb63425aff9b05836f029929e345a6148a14b7ecd5ab67af944482" 317 | dependencies = [ 318 | "bytes", 319 | "fnv", 320 | "itoa", 321 | ] 322 | 323 | [[package]] 324 | name = "http-body" 325 | version = "0.4.5" 326 | source = "registry+https://github.com/rust-lang/crates.io-index" 327 | checksum = "d5f38f16d184e36f2408a55281cd658ecbd3ca05cce6d6510a176eca393e26d1" 328 | dependencies = [ 329 | "bytes", 330 | "http", 331 | "pin-project-lite", 332 | ] 333 | 334 | [[package]] 335 | name = "httparse" 336 | version = "1.8.0" 337 | source = "registry+https://github.com/rust-lang/crates.io-index" 338 | checksum = "d897f394bad6a705d5f4104762e116a75639e470d80901eed05a860a95cb1904" 339 | 340 | [[package]] 341 | name = "httpdate" 342 | version = "1.0.2" 343 | source = "registry+https://github.com/rust-lang/crates.io-index" 344 | checksum = "c4a1e36c821dbe04574f602848a19f742f4fb3c98d40449f11bcad18d6b17421" 345 | 346 | [[package]] 347 | name = "hyper" 348 | version = "0.14.26" 349 | source = "registry+https://github.com/rust-lang/crates.io-index" 350 | checksum = "ab302d72a6f11a3b910431ff93aae7e773078c769f0a3ef15fb9ec692ed147d4" 351 | dependencies = [ 352 | "bytes", 353 | "futures-channel", 354 | "futures-core", 355 | "futures-util", 356 | "h2", 357 | "http", 358 | "http-body", 359 | "httparse", 360 | "httpdate", 361 | "itoa", 362 | "pin-project-lite", 363 | "socket2", 364 | "tokio", 365 | "tower-service", 366 | "tracing", 367 | "want", 368 | ] 369 | 370 | [[package]] 371 | name = "hyper-tls" 372 | version = "0.5.0" 373 | source = "registry+https://github.com/rust-lang/crates.io-index" 374 | checksum = "d6183ddfa99b85da61a140bea0efc93fdf56ceaa041b37d553518030827f9905" 375 | dependencies = [ 376 | "bytes", 377 | "hyper", 378 | "native-tls", 379 | "tokio", 380 | "tokio-native-tls", 381 | ] 382 | 383 | [[package]] 384 | name = "idna" 385 | version = "0.4.0" 386 | source = "registry+https://github.com/rust-lang/crates.io-index" 387 | checksum = "7d20d6b07bfbc108882d88ed8e37d39636dcc260e15e30c45e6ba089610b917c" 388 | dependencies = [ 389 | "unicode-bidi", 390 | "unicode-normalization", 391 | ] 392 | 393 | [[package]] 394 | name = "indexmap" 395 | version = "1.9.3" 396 | source = "registry+https://github.com/rust-lang/crates.io-index" 397 | checksum = "bd070e393353796e801d209ad339e89596eb4c8d430d18ede6a1cced8fafbd99" 398 | dependencies = [ 399 | "autocfg", 400 | "hashbrown", 401 | ] 402 | 403 | [[package]] 404 | name = "instant" 405 | version = "0.1.12" 406 | source = "registry+https://github.com/rust-lang/crates.io-index" 407 | checksum = "7a5bbe824c507c5da5956355e86a746d82e0e1464f65d862cc5e71da70e94b2c" 408 | dependencies = [ 409 | "cfg-if", 410 | ] 411 | 412 | [[package]] 413 | name = "io-lifetimes" 414 | version = "1.0.11" 415 | source = "registry+https://github.com/rust-lang/crates.io-index" 416 | checksum = "eae7b9aee968036d54dce06cebaefd919e4472e753296daccd6d344e3e2df0c2" 417 | dependencies = [ 418 | "hermit-abi 0.3.1", 419 | "libc", 420 | "windows-sys 0.48.0", 421 | ] 422 | 423 | [[package]] 424 | name = "ipnet" 425 | version = "2.7.2" 426 | source = "registry+https://github.com/rust-lang/crates.io-index" 427 | checksum = "12b6ee2129af8d4fb011108c73d99a1b83a85977f23b82460c0ae2e25bb4b57f" 428 | 429 | [[package]] 430 | name = "itoa" 431 | version = "1.0.6" 432 | source = "registry+https://github.com/rust-lang/crates.io-index" 433 | checksum = "453ad9f582a441959e5f0d088b02ce04cfe8d51a8eaf077f12ac6d3e94164ca6" 434 | 435 | [[package]] 436 | name = "jni" 437 | version = "0.21.1" 438 | source = "registry+https://github.com/rust-lang/crates.io-index" 439 | checksum = "1a87aa2bb7d2af34197c04845522473242e1aa17c12f4935d5856491a7fb8c97" 440 | dependencies = [ 441 | "cesu8", 442 | "cfg-if", 443 | "combine", 444 | "jni-sys", 445 | "log", 446 | "thiserror", 447 | "walkdir", 448 | "windows-sys 0.45.0", 449 | ] 450 | 451 | [[package]] 452 | name = "jni-sys" 453 | version = "0.3.0" 454 | source = "registry+https://github.com/rust-lang/crates.io-index" 455 | checksum = "8eaf4bc02d17cbdd7ff4c7438cafcdf7fb9a4613313ad11b4f8fefe7d3fa0130" 456 | 457 | [[package]] 458 | name = "js-sys" 459 | version = "0.3.63" 460 | source = "registry+https://github.com/rust-lang/crates.io-index" 461 | checksum = "2f37a4a5928311ac501dee68b3c7613a1037d0edb30c8e5427bd832d55d1b790" 462 | dependencies = [ 463 | "wasm-bindgen", 464 | ] 465 | 466 | [[package]] 467 | name = "lazy_static" 468 | version = "1.4.0" 469 | source = "registry+https://github.com/rust-lang/crates.io-index" 470 | checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646" 471 | 472 | [[package]] 473 | name = "libc" 474 | version = "0.2.146" 475 | source = "registry+https://github.com/rust-lang/crates.io-index" 476 | checksum = "f92be4933c13fd498862a9e02a3055f8a8d9c039ce33db97306fd5a6caa7f29b" 477 | 478 | [[package]] 479 | name = "linux-raw-sys" 480 | version = "0.3.8" 481 | source = "registry+https://github.com/rust-lang/crates.io-index" 482 | checksum = "ef53942eb7bf7ff43a617b3e2c1c4a5ecf5944a7c1bc12d7ee39bbb15e5c1519" 483 | 484 | [[package]] 485 | name = "lock_api" 486 | version = "0.4.10" 487 | source = "registry+https://github.com/rust-lang/crates.io-index" 488 | checksum = "c1cc9717a20b1bb222f333e6a92fd32f7d8a18ddc5a3191a11af45dcbf4dcd16" 489 | dependencies = [ 490 | "autocfg", 491 | "scopeguard", 492 | ] 493 | 494 | [[package]] 495 | name = "log" 496 | version = "0.4.18" 497 | source = "registry+https://github.com/rust-lang/crates.io-index" 498 | checksum = "518ef76f2f87365916b142844c16d8fefd85039bc5699050210a7778ee1cd1de" 499 | 500 | [[package]] 501 | name = "malloc_buf" 502 | version = "0.0.6" 503 | source = "registry+https://github.com/rust-lang/crates.io-index" 504 | checksum = "62bb907fe88d54d8d9ce32a3cceab4218ed2f6b7d35617cafe9adf84e43919cb" 505 | dependencies = [ 506 | "libc", 507 | ] 508 | 509 | [[package]] 510 | name = "memchr" 511 | version = "2.5.0" 512 | source = "registry+https://github.com/rust-lang/crates.io-index" 513 | checksum = "2dffe52ecf27772e601905b7522cb4ef790d2cc203488bbd0e2fe85fcb74566d" 514 | 515 | [[package]] 516 | name = "mime" 517 | version = "0.3.17" 518 | source = "registry+https://github.com/rust-lang/crates.io-index" 519 | checksum = "6877bb514081ee2a7ff5ef9de3281f14a4dd4bceac4c09388074a6b5df8a139a" 520 | 521 | [[package]] 522 | name = "mio" 523 | version = "0.8.8" 524 | source = "registry+https://github.com/rust-lang/crates.io-index" 525 | checksum = "927a765cd3fc26206e66b296465fa9d3e5ab003e651c1b3c060e7956d96b19d2" 526 | dependencies = [ 527 | "libc", 528 | "log", 529 | "wasi", 530 | "windows-sys 0.48.0", 531 | ] 532 | 533 | [[package]] 534 | name = "native-tls" 535 | version = "0.2.11" 536 | source = "registry+https://github.com/rust-lang/crates.io-index" 537 | checksum = "07226173c32f2926027b63cce4bcd8076c3552846cbe7925f3aaffeac0a3b92e" 538 | dependencies = [ 539 | "lazy_static", 540 | "libc", 541 | "log", 542 | "openssl", 543 | "openssl-probe", 544 | "openssl-sys", 545 | "schannel", 546 | "security-framework", 547 | "security-framework-sys", 548 | "tempfile", 549 | ] 550 | 551 | [[package]] 552 | name = "ndk-context" 553 | version = "0.1.1" 554 | source = "registry+https://github.com/rust-lang/crates.io-index" 555 | checksum = "27b02d87554356db9e9a873add8782d4ea6e3e58ea071a9adb9a2e8ddb884a8b" 556 | 557 | [[package]] 558 | name = "num_cpus" 559 | version = "1.15.0" 560 | source = "registry+https://github.com/rust-lang/crates.io-index" 561 | checksum = "0fac9e2da13b5eb447a6ce3d392f23a29d8694bff781bf03a16cd9ac8697593b" 562 | dependencies = [ 563 | "hermit-abi 0.2.6", 564 | "libc", 565 | ] 566 | 567 | [[package]] 568 | name = "objc" 569 | version = "0.2.7" 570 | source = "registry+https://github.com/rust-lang/crates.io-index" 571 | checksum = "915b1b472bc21c53464d6c8461c9d3af805ba1ef837e1cac254428f4a77177b1" 572 | dependencies = [ 573 | "malloc_buf", 574 | ] 575 | 576 | [[package]] 577 | name = "once_cell" 578 | version = "1.18.0" 579 | source = "registry+https://github.com/rust-lang/crates.io-index" 580 | checksum = "dd8b5dd2ae5ed71462c540258bedcb51965123ad7e7ccf4b9a8cafaa4a63576d" 581 | 582 | [[package]] 583 | name = "openssl" 584 | version = "0.10.54" 585 | source = "registry+https://github.com/rust-lang/crates.io-index" 586 | checksum = "69b3f656a17a6cbc115b5c7a40c616947d213ba182135b014d6051b73ab6f019" 587 | dependencies = [ 588 | "bitflags", 589 | "cfg-if", 590 | "foreign-types", 591 | "libc", 592 | "once_cell", 593 | "openssl-macros", 594 | "openssl-sys", 595 | ] 596 | 597 | [[package]] 598 | name = "openssl-macros" 599 | version = "0.1.1" 600 | source = "registry+https://github.com/rust-lang/crates.io-index" 601 | checksum = "a948666b637a0f465e8564c73e89d4dde00d72d4d473cc972f390fc3dcee7d9c" 602 | dependencies = [ 603 | "proc-macro2", 604 | "quote", 605 | "syn 2.0.18", 606 | ] 607 | 608 | [[package]] 609 | name = "openssl-probe" 610 | version = "0.1.5" 611 | source = "registry+https://github.com/rust-lang/crates.io-index" 612 | checksum = "ff011a302c396a5197692431fc1948019154afc178baf7d8e37367442a4601cf" 613 | 614 | [[package]] 615 | name = "openssl-sys" 616 | version = "0.9.88" 617 | source = "registry+https://github.com/rust-lang/crates.io-index" 618 | checksum = "c2ce0f250f34a308dcfdbb351f511359857d4ed2134ba715a4eadd46e1ffd617" 619 | dependencies = [ 620 | "cc", 621 | "libc", 622 | "pkg-config", 623 | "vcpkg", 624 | ] 625 | 626 | [[package]] 627 | name = "parking_lot" 628 | version = "0.12.1" 629 | source = "registry+https://github.com/rust-lang/crates.io-index" 630 | checksum = "3742b2c103b9f06bc9fff0a37ff4912935851bee6d36f3c02bcc755bcfec228f" 631 | dependencies = [ 632 | "lock_api", 633 | "parking_lot_core", 634 | ] 635 | 636 | [[package]] 637 | name = "parking_lot_core" 638 | version = "0.9.8" 639 | source = "registry+https://github.com/rust-lang/crates.io-index" 640 | checksum = "93f00c865fe7cabf650081affecd3871070f26767e7b2070a3ffae14c654b447" 641 | dependencies = [ 642 | "cfg-if", 643 | "libc", 644 | "redox_syscall", 645 | "smallvec", 646 | "windows-targets 0.48.0", 647 | ] 648 | 649 | [[package]] 650 | name = "percent-encoding" 651 | version = "2.3.0" 652 | source = "registry+https://github.com/rust-lang/crates.io-index" 653 | checksum = "9b2a4787296e9989611394c33f193f676704af1686e70b8f8033ab5ba9a35a94" 654 | 655 | [[package]] 656 | name = "pin-project-lite" 657 | version = "0.2.9" 658 | source = "registry+https://github.com/rust-lang/crates.io-index" 659 | checksum = "e0a7ae3ac2f1173085d398531c705756c94a4c56843785df85a60c1a0afac116" 660 | 661 | [[package]] 662 | name = "pin-utils" 663 | version = "0.1.0" 664 | source = "registry+https://github.com/rust-lang/crates.io-index" 665 | checksum = "8b870d8c151b6f2fb93e84a13146138f05d02ed11c7e7c54f8826aaaf7c9f184" 666 | 667 | [[package]] 668 | name = "pkg-config" 669 | version = "0.3.27" 670 | source = "registry+https://github.com/rust-lang/crates.io-index" 671 | checksum = "26072860ba924cbfa98ea39c8c19b4dd6a4a25423dbdf219c1eca91aa0cf6964" 672 | 673 | [[package]] 674 | name = "proc-macro2" 675 | version = "1.0.60" 676 | source = "registry+https://github.com/rust-lang/crates.io-index" 677 | checksum = "dec2b086b7a862cf4de201096214fa870344cf922b2b30c167badb3af3195406" 678 | dependencies = [ 679 | "unicode-ident", 680 | ] 681 | 682 | [[package]] 683 | name = "quote" 684 | version = "1.0.28" 685 | source = "registry+https://github.com/rust-lang/crates.io-index" 686 | checksum = "1b9ab9c7eadfd8df19006f1cf1a4aed13540ed5cbc047010ece5826e10825488" 687 | dependencies = [ 688 | "proc-macro2", 689 | ] 690 | 691 | [[package]] 692 | name = "raw-window-handle" 693 | version = "0.5.2" 694 | source = "registry+https://github.com/rust-lang/crates.io-index" 695 | checksum = "f2ff9a1f06a88b01621b7ae906ef0211290d1c8a168a15542486a8f61c0833b9" 696 | 697 | [[package]] 698 | name = "redox_syscall" 699 | version = "0.3.5" 700 | source = "registry+https://github.com/rust-lang/crates.io-index" 701 | checksum = "567664f262709473930a4bf9e51bf2ebf3348f2e748ccc50dea20646858f8f29" 702 | dependencies = [ 703 | "bitflags", 704 | ] 705 | 706 | [[package]] 707 | name = "reqwest" 708 | version = "0.11.18" 709 | source = "registry+https://github.com/rust-lang/crates.io-index" 710 | checksum = "cde824a14b7c14f85caff81225f411faacc04a2013f41670f41443742b1c1c55" 711 | dependencies = [ 712 | "base64", 713 | "bytes", 714 | "encoding_rs", 715 | "futures-core", 716 | "futures-util", 717 | "h2", 718 | "http", 719 | "http-body", 720 | "hyper", 721 | "hyper-tls", 722 | "ipnet", 723 | "js-sys", 724 | "log", 725 | "mime", 726 | "native-tls", 727 | "once_cell", 728 | "percent-encoding", 729 | "pin-project-lite", 730 | "serde", 731 | "serde_json", 732 | "serde_urlencoded", 733 | "tokio", 734 | "tokio-native-tls", 735 | "tower-service", 736 | "url", 737 | "wasm-bindgen", 738 | "wasm-bindgen-futures", 739 | "web-sys", 740 | "winreg", 741 | ] 742 | 743 | [[package]] 744 | name = "rustix" 745 | version = "0.37.19" 746 | source = "registry+https://github.com/rust-lang/crates.io-index" 747 | checksum = "acf8729d8542766f1b2cf77eb034d52f40d375bb8b615d0b147089946e16613d" 748 | dependencies = [ 749 | "bitflags", 750 | "errno", 751 | "io-lifetimes", 752 | "libc", 753 | "linux-raw-sys", 754 | "windows-sys 0.48.0", 755 | ] 756 | 757 | [[package]] 758 | name = "rustversion" 759 | version = "1.0.12" 760 | source = "registry+https://github.com/rust-lang/crates.io-index" 761 | checksum = "4f3208ce4d8448b3f3e7d168a73f5e0c43a61e32930de3bceeccedb388b6bf06" 762 | 763 | [[package]] 764 | name = "ryu" 765 | version = "1.0.13" 766 | source = "registry+https://github.com/rust-lang/crates.io-index" 767 | checksum = "f91339c0467de62360649f8d3e185ca8de4224ff281f66000de5eb2a77a79041" 768 | 769 | [[package]] 770 | name = "same-file" 771 | version = "1.0.6" 772 | source = "registry+https://github.com/rust-lang/crates.io-index" 773 | checksum = "93fc1dc3aaa9bfed95e02e6eadabb4baf7e3078b0bd1b4d7b6b0b68378900502" 774 | dependencies = [ 775 | "winapi-util", 776 | ] 777 | 778 | [[package]] 779 | name = "schannel" 780 | version = "0.1.21" 781 | source = "registry+https://github.com/rust-lang/crates.io-index" 782 | checksum = "713cfb06c7059f3588fb8044c0fad1d09e3c01d225e25b9220dbfdcf16dbb1b3" 783 | dependencies = [ 784 | "windows-sys 0.42.0", 785 | ] 786 | 787 | [[package]] 788 | name = "scopeguard" 789 | version = "1.1.0" 790 | source = "registry+https://github.com/rust-lang/crates.io-index" 791 | checksum = "d29ab0c6d3fc0ee92fe66e2d99f700eab17a8d57d1c1d3b748380fb20baa78cd" 792 | 793 | [[package]] 794 | name = "security-framework" 795 | version = "2.9.1" 796 | source = "registry+https://github.com/rust-lang/crates.io-index" 797 | checksum = "1fc758eb7bffce5b308734e9b0c1468893cae9ff70ebf13e7090be8dcbcc83a8" 798 | dependencies = [ 799 | "bitflags", 800 | "core-foundation", 801 | "core-foundation-sys", 802 | "libc", 803 | "security-framework-sys", 804 | ] 805 | 806 | [[package]] 807 | name = "security-framework-sys" 808 | version = "2.9.0" 809 | source = "registry+https://github.com/rust-lang/crates.io-index" 810 | checksum = "f51d0c0d83bec45f16480d0ce0058397a69e48fcdc52d1dc8855fb68acbd31a7" 811 | dependencies = [ 812 | "core-foundation-sys", 813 | "libc", 814 | ] 815 | 816 | [[package]] 817 | name = "serde" 818 | version = "1.0.164" 819 | source = "registry+https://github.com/rust-lang/crates.io-index" 820 | checksum = "9e8c8cf938e98f769bc164923b06dce91cea1751522f46f8466461af04c9027d" 821 | dependencies = [ 822 | "serde_derive", 823 | ] 824 | 825 | [[package]] 826 | name = "serde_derive" 827 | version = "1.0.164" 828 | source = "registry+https://github.com/rust-lang/crates.io-index" 829 | checksum = "d9735b638ccc51c28bf6914d90a2e9725b377144fc612c49a611fddd1b631d68" 830 | dependencies = [ 831 | "proc-macro2", 832 | "quote", 833 | "syn 2.0.18", 834 | ] 835 | 836 | [[package]] 837 | name = "serde_json" 838 | version = "1.0.96" 839 | source = "registry+https://github.com/rust-lang/crates.io-index" 840 | checksum = "057d394a50403bcac12672b2b18fb387ab6d289d957dab67dd201875391e52f1" 841 | dependencies = [ 842 | "itoa", 843 | "ryu", 844 | "serde", 845 | ] 846 | 847 | [[package]] 848 | name = "serde_urlencoded" 849 | version = "0.7.1" 850 | source = "registry+https://github.com/rust-lang/crates.io-index" 851 | checksum = "d3491c14715ca2294c4d6a88f15e84739788c1d030eed8c110436aafdaa2f3fd" 852 | dependencies = [ 853 | "form_urlencoded", 854 | "itoa", 855 | "ryu", 856 | "serde", 857 | ] 858 | 859 | [[package]] 860 | name = "signal-hook" 861 | version = "0.3.15" 862 | source = "registry+https://github.com/rust-lang/crates.io-index" 863 | checksum = "732768f1176d21d09e076c23a93123d40bba92d50c4058da34d45c8de8e682b9" 864 | dependencies = [ 865 | "libc", 866 | "signal-hook-registry", 867 | ] 868 | 869 | [[package]] 870 | name = "signal-hook-mio" 871 | version = "0.2.3" 872 | source = "registry+https://github.com/rust-lang/crates.io-index" 873 | checksum = "29ad2e15f37ec9a6cc544097b78a1ec90001e9f71b81338ca39f430adaca99af" 874 | dependencies = [ 875 | "libc", 876 | "mio", 877 | "signal-hook", 878 | ] 879 | 880 | [[package]] 881 | name = "signal-hook-registry" 882 | version = "1.4.1" 883 | source = "registry+https://github.com/rust-lang/crates.io-index" 884 | checksum = "d8229b473baa5980ac72ef434c4415e70c4b5e71b423043adb4ba059f89c99a1" 885 | dependencies = [ 886 | "libc", 887 | ] 888 | 889 | [[package]] 890 | name = "slab" 891 | version = "0.4.8" 892 | source = "registry+https://github.com/rust-lang/crates.io-index" 893 | checksum = "6528351c9bc8ab22353f9d776db39a20288e8d6c37ef8cfe3317cf875eecfc2d" 894 | dependencies = [ 895 | "autocfg", 896 | ] 897 | 898 | [[package]] 899 | name = "smallvec" 900 | version = "1.10.0" 901 | source = "registry+https://github.com/rust-lang/crates.io-index" 902 | checksum = "a507befe795404456341dfab10cef66ead4c041f62b8b11bbb92bffe5d0953e0" 903 | 904 | [[package]] 905 | name = "socket2" 906 | version = "0.4.9" 907 | source = "registry+https://github.com/rust-lang/crates.io-index" 908 | checksum = "64a4a911eed85daf18834cfaa86a79b7d266ff93ff5ba14005426219480ed662" 909 | dependencies = [ 910 | "libc", 911 | "winapi", 912 | ] 913 | 914 | [[package]] 915 | name = "strum" 916 | version = "0.24.1" 917 | source = "registry+https://github.com/rust-lang/crates.io-index" 918 | checksum = "063e6045c0e62079840579a7e47a355ae92f60eb74daaf156fb1e84ba164e63f" 919 | 920 | [[package]] 921 | name = "strum_macros" 922 | version = "0.24.3" 923 | source = "registry+https://github.com/rust-lang/crates.io-index" 924 | checksum = "1e385be0d24f186b4ce2f9982191e7101bb737312ad61c1f2f984f34bcf85d59" 925 | dependencies = [ 926 | "heck", 927 | "proc-macro2", 928 | "quote", 929 | "rustversion", 930 | "syn 1.0.109", 931 | ] 932 | 933 | [[package]] 934 | name = "syn" 935 | version = "1.0.109" 936 | source = "registry+https://github.com/rust-lang/crates.io-index" 937 | checksum = "72b64191b275b66ffe2469e8af2c1cfe3bafa67b529ead792a6d0160888b4237" 938 | dependencies = [ 939 | "proc-macro2", 940 | "quote", 941 | "unicode-ident", 942 | ] 943 | 944 | [[package]] 945 | name = "syn" 946 | version = "2.0.18" 947 | source = "registry+https://github.com/rust-lang/crates.io-index" 948 | checksum = "32d41677bcbe24c20c52e7c70b0d8db04134c5d1066bf98662e2871ad200ea3e" 949 | dependencies = [ 950 | "proc-macro2", 951 | "quote", 952 | "unicode-ident", 953 | ] 954 | 955 | [[package]] 956 | name = "tempfile" 957 | version = "3.6.0" 958 | source = "registry+https://github.com/rust-lang/crates.io-index" 959 | checksum = "31c0432476357e58790aaa47a8efb0c5138f137343f3b5f23bd36a27e3b0a6d6" 960 | dependencies = [ 961 | "autocfg", 962 | "cfg-if", 963 | "fastrand", 964 | "redox_syscall", 965 | "rustix", 966 | "windows-sys 0.48.0", 967 | ] 968 | 969 | [[package]] 970 | name = "thiserror" 971 | version = "1.0.40" 972 | source = "registry+https://github.com/rust-lang/crates.io-index" 973 | checksum = "978c9a314bd8dc99be594bc3c175faaa9794be04a5a5e153caba6915336cebac" 974 | dependencies = [ 975 | "thiserror-impl", 976 | ] 977 | 978 | [[package]] 979 | name = "thiserror-impl" 980 | version = "1.0.40" 981 | source = "registry+https://github.com/rust-lang/crates.io-index" 982 | checksum = "f9456a42c5b0d803c8cd86e73dd7cc9edd429499f37a3550d286d5e86720569f" 983 | dependencies = [ 984 | "proc-macro2", 985 | "quote", 986 | "syn 2.0.18", 987 | ] 988 | 989 | [[package]] 990 | name = "tinyvec" 991 | version = "1.6.0" 992 | source = "registry+https://github.com/rust-lang/crates.io-index" 993 | checksum = "87cc5ceb3875bb20c2890005a4e226a4651264a5c75edb2421b52861a0a0cb50" 994 | dependencies = [ 995 | "tinyvec_macros", 996 | ] 997 | 998 | [[package]] 999 | name = "tinyvec_macros" 1000 | version = "0.1.1" 1001 | source = "registry+https://github.com/rust-lang/crates.io-index" 1002 | checksum = "1f3ccbac311fea05f86f61904b462b55fb3df8837a366dfc601a0161d0532f20" 1003 | 1004 | [[package]] 1005 | name = "tokio" 1006 | version = "1.28.2" 1007 | source = "registry+https://github.com/rust-lang/crates.io-index" 1008 | checksum = "94d7b1cfd2aa4011f2de74c2c4c63665e27a71006b0a192dcd2710272e73dfa2" 1009 | dependencies = [ 1010 | "autocfg", 1011 | "bytes", 1012 | "libc", 1013 | "mio", 1014 | "num_cpus", 1015 | "parking_lot", 1016 | "pin-project-lite", 1017 | "signal-hook-registry", 1018 | "socket2", 1019 | "tokio-macros", 1020 | "windows-sys 0.48.0", 1021 | ] 1022 | 1023 | [[package]] 1024 | name = "tokio-macros" 1025 | version = "2.1.0" 1026 | source = "registry+https://github.com/rust-lang/crates.io-index" 1027 | checksum = "630bdcf245f78637c13ec01ffae6187cca34625e8c63150d424b59e55af2675e" 1028 | dependencies = [ 1029 | "proc-macro2", 1030 | "quote", 1031 | "syn 2.0.18", 1032 | ] 1033 | 1034 | [[package]] 1035 | name = "tokio-native-tls" 1036 | version = "0.3.1" 1037 | source = "registry+https://github.com/rust-lang/crates.io-index" 1038 | checksum = "bbae76ab933c85776efabc971569dd6119c580d8f5d448769dec1764bf796ef2" 1039 | dependencies = [ 1040 | "native-tls", 1041 | "tokio", 1042 | ] 1043 | 1044 | [[package]] 1045 | name = "tokio-util" 1046 | version = "0.7.8" 1047 | source = "registry+https://github.com/rust-lang/crates.io-index" 1048 | checksum = "806fe8c2c87eccc8b3267cbae29ed3ab2d0bd37fca70ab622e46aaa9375ddb7d" 1049 | dependencies = [ 1050 | "bytes", 1051 | "futures-core", 1052 | "futures-sink", 1053 | "pin-project-lite", 1054 | "tokio", 1055 | "tracing", 1056 | ] 1057 | 1058 | [[package]] 1059 | name = "tower-service" 1060 | version = "0.3.2" 1061 | source = "registry+https://github.com/rust-lang/crates.io-index" 1062 | checksum = "b6bc1c9ce2b5135ac7f93c72918fc37feb872bdc6a5533a8b85eb4b86bfdae52" 1063 | 1064 | [[package]] 1065 | name = "tracing" 1066 | version = "0.1.37" 1067 | source = "registry+https://github.com/rust-lang/crates.io-index" 1068 | checksum = "8ce8c33a8d48bd45d624a6e523445fd21ec13d3653cd51f681abf67418f54eb8" 1069 | dependencies = [ 1070 | "cfg-if", 1071 | "pin-project-lite", 1072 | "tracing-core", 1073 | ] 1074 | 1075 | [[package]] 1076 | name = "tracing-core" 1077 | version = "0.1.31" 1078 | source = "registry+https://github.com/rust-lang/crates.io-index" 1079 | checksum = "0955b8137a1df6f1a2e9a37d8a6656291ff0297c1a97c24e0d8425fe2312f79a" 1080 | dependencies = [ 1081 | "once_cell", 1082 | ] 1083 | 1084 | [[package]] 1085 | name = "try-lock" 1086 | version = "0.2.4" 1087 | source = "registry+https://github.com/rust-lang/crates.io-index" 1088 | checksum = "3528ecfd12c466c6f163363caf2d02a71161dd5e1cc6ae7b34207ea2d42d81ed" 1089 | 1090 | [[package]] 1091 | name = "unicode-bidi" 1092 | version = "0.3.13" 1093 | source = "registry+https://github.com/rust-lang/crates.io-index" 1094 | checksum = "92888ba5573ff080736b3648696b70cafad7d250551175acbaa4e0385b3e1460" 1095 | 1096 | [[package]] 1097 | name = "unicode-ident" 1098 | version = "1.0.9" 1099 | source = "registry+https://github.com/rust-lang/crates.io-index" 1100 | checksum = "b15811caf2415fb889178633e7724bad2509101cde276048e013b9def5e51fa0" 1101 | 1102 | [[package]] 1103 | name = "unicode-normalization" 1104 | version = "0.1.22" 1105 | source = "registry+https://github.com/rust-lang/crates.io-index" 1106 | checksum = "5c5713f0fc4b5db668a2ac63cdb7bb4469d8c9fed047b1d0292cc7b0ce2ba921" 1107 | dependencies = [ 1108 | "tinyvec", 1109 | ] 1110 | 1111 | [[package]] 1112 | name = "url" 1113 | version = "2.4.0" 1114 | source = "registry+https://github.com/rust-lang/crates.io-index" 1115 | checksum = "50bff7831e19200a85b17131d085c25d7811bc4e186efdaf54bbd132994a88cb" 1116 | dependencies = [ 1117 | "form_urlencoded", 1118 | "idna", 1119 | "percent-encoding", 1120 | ] 1121 | 1122 | [[package]] 1123 | name = "vcpkg" 1124 | version = "0.2.15" 1125 | source = "registry+https://github.com/rust-lang/crates.io-index" 1126 | checksum = "accd4ea62f7bb7a82fe23066fb0957d48ef677f6eeb8215f372f52e48bb32426" 1127 | 1128 | [[package]] 1129 | name = "walkdir" 1130 | version = "2.3.3" 1131 | source = "registry+https://github.com/rust-lang/crates.io-index" 1132 | checksum = "36df944cda56c7d8d8b7496af378e6b16de9284591917d307c9b4d313c44e698" 1133 | dependencies = [ 1134 | "same-file", 1135 | "winapi-util", 1136 | ] 1137 | 1138 | [[package]] 1139 | name = "want" 1140 | version = "0.3.0" 1141 | source = "registry+https://github.com/rust-lang/crates.io-index" 1142 | checksum = "1ce8a968cb1cd110d136ff8b819a556d6fb6d919363c61534f6860c7eb172ba0" 1143 | dependencies = [ 1144 | "log", 1145 | "try-lock", 1146 | ] 1147 | 1148 | [[package]] 1149 | name = "wasi" 1150 | version = "0.11.0+wasi-snapshot-preview1" 1151 | source = "registry+https://github.com/rust-lang/crates.io-index" 1152 | checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" 1153 | 1154 | [[package]] 1155 | name = "wasm-bindgen" 1156 | version = "0.2.86" 1157 | source = "registry+https://github.com/rust-lang/crates.io-index" 1158 | checksum = "5bba0e8cb82ba49ff4e229459ff22a191bbe9a1cb3a341610c9c33efc27ddf73" 1159 | dependencies = [ 1160 | "cfg-if", 1161 | "wasm-bindgen-macro", 1162 | ] 1163 | 1164 | [[package]] 1165 | name = "wasm-bindgen-backend" 1166 | version = "0.2.86" 1167 | source = "registry+https://github.com/rust-lang/crates.io-index" 1168 | checksum = "19b04bc93f9d6bdee709f6bd2118f57dd6679cf1176a1af464fca3ab0d66d8fb" 1169 | dependencies = [ 1170 | "bumpalo", 1171 | "log", 1172 | "once_cell", 1173 | "proc-macro2", 1174 | "quote", 1175 | "syn 2.0.18", 1176 | "wasm-bindgen-shared", 1177 | ] 1178 | 1179 | [[package]] 1180 | name = "wasm-bindgen-futures" 1181 | version = "0.4.36" 1182 | source = "registry+https://github.com/rust-lang/crates.io-index" 1183 | checksum = "2d1985d03709c53167ce907ff394f5316aa22cb4e12761295c5dc57dacb6297e" 1184 | dependencies = [ 1185 | "cfg-if", 1186 | "js-sys", 1187 | "wasm-bindgen", 1188 | "web-sys", 1189 | ] 1190 | 1191 | [[package]] 1192 | name = "wasm-bindgen-macro" 1193 | version = "0.2.86" 1194 | source = "registry+https://github.com/rust-lang/crates.io-index" 1195 | checksum = "14d6b024f1a526bb0234f52840389927257beb670610081360e5a03c5df9c258" 1196 | dependencies = [ 1197 | "quote", 1198 | "wasm-bindgen-macro-support", 1199 | ] 1200 | 1201 | [[package]] 1202 | name = "wasm-bindgen-macro-support" 1203 | version = "0.2.86" 1204 | source = "registry+https://github.com/rust-lang/crates.io-index" 1205 | checksum = "e128beba882dd1eb6200e1dc92ae6c5dbaa4311aa7bb211ca035779e5efc39f8" 1206 | dependencies = [ 1207 | "proc-macro2", 1208 | "quote", 1209 | "syn 2.0.18", 1210 | "wasm-bindgen-backend", 1211 | "wasm-bindgen-shared", 1212 | ] 1213 | 1214 | [[package]] 1215 | name = "wasm-bindgen-shared" 1216 | version = "0.2.86" 1217 | source = "registry+https://github.com/rust-lang/crates.io-index" 1218 | checksum = "ed9d5b4305409d1fc9482fee2d7f9bcbf24b3972bf59817ef757e23982242a93" 1219 | 1220 | [[package]] 1221 | name = "web-sys" 1222 | version = "0.3.63" 1223 | source = "registry+https://github.com/rust-lang/crates.io-index" 1224 | checksum = "3bdd9ef4e984da1187bf8110c5cf5b845fbc87a23602cdf912386a76fcd3a7c2" 1225 | dependencies = [ 1226 | "js-sys", 1227 | "wasm-bindgen", 1228 | ] 1229 | 1230 | [[package]] 1231 | name = "webbrowser" 1232 | version = "0.8.10" 1233 | source = "registry+https://github.com/rust-lang/crates.io-index" 1234 | checksum = "fd222aa310eb7532e3fd427a5d7db7e44bc0b0cf1c1e21139c345325511a85b6" 1235 | dependencies = [ 1236 | "core-foundation", 1237 | "home", 1238 | "jni", 1239 | "log", 1240 | "ndk-context", 1241 | "objc", 1242 | "raw-window-handle", 1243 | "url", 1244 | "web-sys", 1245 | ] 1246 | 1247 | [[package]] 1248 | name = "winapi" 1249 | version = "0.3.9" 1250 | source = "registry+https://github.com/rust-lang/crates.io-index" 1251 | checksum = "5c839a674fcd7a98952e593242ea400abe93992746761e38641405d28b00f419" 1252 | dependencies = [ 1253 | "winapi-i686-pc-windows-gnu", 1254 | "winapi-x86_64-pc-windows-gnu", 1255 | ] 1256 | 1257 | [[package]] 1258 | name = "winapi-i686-pc-windows-gnu" 1259 | version = "0.4.0" 1260 | source = "registry+https://github.com/rust-lang/crates.io-index" 1261 | checksum = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6" 1262 | 1263 | [[package]] 1264 | name = "winapi-util" 1265 | version = "0.1.5" 1266 | source = "registry+https://github.com/rust-lang/crates.io-index" 1267 | checksum = "70ec6ce85bb158151cae5e5c87f95a8e97d2c0c4b001223f33a334e3ce5de178" 1268 | dependencies = [ 1269 | "winapi", 1270 | ] 1271 | 1272 | [[package]] 1273 | name = "winapi-x86_64-pc-windows-gnu" 1274 | version = "0.4.0" 1275 | source = "registry+https://github.com/rust-lang/crates.io-index" 1276 | checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" 1277 | 1278 | [[package]] 1279 | name = "windows-sys" 1280 | version = "0.42.0" 1281 | source = "registry+https://github.com/rust-lang/crates.io-index" 1282 | checksum = "5a3e1820f08b8513f676f7ab6c1f99ff312fb97b553d30ff4dd86f9f15728aa7" 1283 | dependencies = [ 1284 | "windows_aarch64_gnullvm 0.42.2", 1285 | "windows_aarch64_msvc 0.42.2", 1286 | "windows_i686_gnu 0.42.2", 1287 | "windows_i686_msvc 0.42.2", 1288 | "windows_x86_64_gnu 0.42.2", 1289 | "windows_x86_64_gnullvm 0.42.2", 1290 | "windows_x86_64_msvc 0.42.2", 1291 | ] 1292 | 1293 | [[package]] 1294 | name = "windows-sys" 1295 | version = "0.45.0" 1296 | source = "registry+https://github.com/rust-lang/crates.io-index" 1297 | checksum = "75283be5efb2831d37ea142365f009c02ec203cd29a3ebecbc093d52315b66d0" 1298 | dependencies = [ 1299 | "windows-targets 0.42.2", 1300 | ] 1301 | 1302 | [[package]] 1303 | name = "windows-sys" 1304 | version = "0.48.0" 1305 | source = "registry+https://github.com/rust-lang/crates.io-index" 1306 | checksum = "677d2418bec65e3338edb076e806bc1ec15693c5d0104683f2efe857f61056a9" 1307 | dependencies = [ 1308 | "windows-targets 0.48.0", 1309 | ] 1310 | 1311 | [[package]] 1312 | name = "windows-targets" 1313 | version = "0.42.2" 1314 | source = "registry+https://github.com/rust-lang/crates.io-index" 1315 | checksum = "8e5180c00cd44c9b1c88adb3693291f1cd93605ded80c250a75d472756b4d071" 1316 | dependencies = [ 1317 | "windows_aarch64_gnullvm 0.42.2", 1318 | "windows_aarch64_msvc 0.42.2", 1319 | "windows_i686_gnu 0.42.2", 1320 | "windows_i686_msvc 0.42.2", 1321 | "windows_x86_64_gnu 0.42.2", 1322 | "windows_x86_64_gnullvm 0.42.2", 1323 | "windows_x86_64_msvc 0.42.2", 1324 | ] 1325 | 1326 | [[package]] 1327 | name = "windows-targets" 1328 | version = "0.48.0" 1329 | source = "registry+https://github.com/rust-lang/crates.io-index" 1330 | checksum = "7b1eb6f0cd7c80c79759c929114ef071b87354ce476d9d94271031c0497adfd5" 1331 | dependencies = [ 1332 | "windows_aarch64_gnullvm 0.48.0", 1333 | "windows_aarch64_msvc 0.48.0", 1334 | "windows_i686_gnu 0.48.0", 1335 | "windows_i686_msvc 0.48.0", 1336 | "windows_x86_64_gnu 0.48.0", 1337 | "windows_x86_64_gnullvm 0.48.0", 1338 | "windows_x86_64_msvc 0.48.0", 1339 | ] 1340 | 1341 | [[package]] 1342 | name = "windows_aarch64_gnullvm" 1343 | version = "0.42.2" 1344 | source = "registry+https://github.com/rust-lang/crates.io-index" 1345 | checksum = "597a5118570b68bc08d8d59125332c54f1ba9d9adeedeef5b99b02ba2b0698f8" 1346 | 1347 | [[package]] 1348 | name = "windows_aarch64_gnullvm" 1349 | version = "0.48.0" 1350 | source = "registry+https://github.com/rust-lang/crates.io-index" 1351 | checksum = "91ae572e1b79dba883e0d315474df7305d12f569b400fcf90581b06062f7e1bc" 1352 | 1353 | [[package]] 1354 | name = "windows_aarch64_msvc" 1355 | version = "0.42.2" 1356 | source = "registry+https://github.com/rust-lang/crates.io-index" 1357 | checksum = "e08e8864a60f06ef0d0ff4ba04124db8b0fb3be5776a5cd47641e942e58c4d43" 1358 | 1359 | [[package]] 1360 | name = "windows_aarch64_msvc" 1361 | version = "0.48.0" 1362 | source = "registry+https://github.com/rust-lang/crates.io-index" 1363 | checksum = "b2ef27e0d7bdfcfc7b868b317c1d32c641a6fe4629c171b8928c7b08d98d7cf3" 1364 | 1365 | [[package]] 1366 | name = "windows_i686_gnu" 1367 | version = "0.42.2" 1368 | source = "registry+https://github.com/rust-lang/crates.io-index" 1369 | checksum = "c61d927d8da41da96a81f029489353e68739737d3beca43145c8afec9a31a84f" 1370 | 1371 | [[package]] 1372 | name = "windows_i686_gnu" 1373 | version = "0.48.0" 1374 | source = "registry+https://github.com/rust-lang/crates.io-index" 1375 | checksum = "622a1962a7db830d6fd0a69683c80a18fda201879f0f447f065a3b7467daa241" 1376 | 1377 | [[package]] 1378 | name = "windows_i686_msvc" 1379 | version = "0.42.2" 1380 | source = "registry+https://github.com/rust-lang/crates.io-index" 1381 | checksum = "44d840b6ec649f480a41c8d80f9c65108b92d89345dd94027bfe06ac444d1060" 1382 | 1383 | [[package]] 1384 | name = "windows_i686_msvc" 1385 | version = "0.48.0" 1386 | source = "registry+https://github.com/rust-lang/crates.io-index" 1387 | checksum = "4542c6e364ce21bf45d69fdd2a8e455fa38d316158cfd43b3ac1c5b1b19f8e00" 1388 | 1389 | [[package]] 1390 | name = "windows_x86_64_gnu" 1391 | version = "0.42.2" 1392 | source = "registry+https://github.com/rust-lang/crates.io-index" 1393 | checksum = "8de912b8b8feb55c064867cf047dda097f92d51efad5b491dfb98f6bbb70cb36" 1394 | 1395 | [[package]] 1396 | name = "windows_x86_64_gnu" 1397 | version = "0.48.0" 1398 | source = "registry+https://github.com/rust-lang/crates.io-index" 1399 | checksum = "ca2b8a661f7628cbd23440e50b05d705db3686f894fc9580820623656af974b1" 1400 | 1401 | [[package]] 1402 | name = "windows_x86_64_gnullvm" 1403 | version = "0.42.2" 1404 | source = "registry+https://github.com/rust-lang/crates.io-index" 1405 | checksum = "26d41b46a36d453748aedef1486d5c7a85db22e56aff34643984ea85514e94a3" 1406 | 1407 | [[package]] 1408 | name = "windows_x86_64_gnullvm" 1409 | version = "0.48.0" 1410 | source = "registry+https://github.com/rust-lang/crates.io-index" 1411 | checksum = "7896dbc1f41e08872e9d5e8f8baa8fdd2677f29468c4e156210174edc7f7b953" 1412 | 1413 | [[package]] 1414 | name = "windows_x86_64_msvc" 1415 | version = "0.42.2" 1416 | source = "registry+https://github.com/rust-lang/crates.io-index" 1417 | checksum = "9aec5da331524158c6d1a4ac0ab1541149c0b9505fde06423b02f5ef0106b9f0" 1418 | 1419 | [[package]] 1420 | name = "windows_x86_64_msvc" 1421 | version = "0.48.0" 1422 | source = "registry+https://github.com/rust-lang/crates.io-index" 1423 | checksum = "1a515f5799fe4961cb532f983ce2b23082366b898e52ffbce459c86f67c8378a" 1424 | 1425 | [[package]] 1426 | name = "winreg" 1427 | version = "0.10.1" 1428 | source = "registry+https://github.com/rust-lang/crates.io-index" 1429 | checksum = "80d0f4e272c85def139476380b12f9ac60926689dd2e01d4923222f40580869d" 1430 | dependencies = [ 1431 | "winapi", 1432 | ] 1433 | -------------------------------------------------------------------------------- /Cargo.toml: -------------------------------------------------------------------------------- 1 | [package] 2 | name = "auto_gippity" 3 | version = "0.1.0" 4 | edition = "2021" 5 | 6 | # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html 7 | 8 | [dependencies] 9 | dotenv = "0.15.0" 10 | reqwest = { version = "0.11.17", features = ["json"] } 11 | serde = { version = "1.0.160", features = ["derive"] } 12 | serde_json = "1.0.96" 13 | tokio = { version = "1.28.0", features = ["full"] } 14 | crossterm = "0.26.1" 15 | async-trait = "0.1.68" 16 | webbrowser = "0.8.9" 17 | strum = "0.24.1" 18 | strum_macros = "0.24.3" 19 | ai_functions = "0.1.1" 20 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | ### Create .env 2 | 3 | ```shell 4 | touch .env 5 | ``` 6 | 7 | Within the .env file created, paste the following: 8 | 9 | ```plaintext 10 | OPEN_AI_ORG=YOUR_OPEN_AI_ORG_ID 11 | OPEN_AI_KEY=YOUR_OPEN_AI_KEY 12 | ``` 13 | 14 | ### Update Paths 15 | 16 | Update constants in the src/helpers/general path. 17 | 18 | These should match where you have your web_template project saved. Recommend to save your web_template in the same 19 | folder as this project. 20 | 21 | Web template project: https://github.com/coderaidershaun/rust-web-server-template.git 22 | 23 | These should link to a code template which you want your web server to use and the main.rs file where it will attempt to execute new code it writes. 24 | 25 | ### Build Project 26 | 27 | ```shell 28 | cargo build 29 | ``` 30 | 31 | ### Run Project 32 | 33 | ```shell 34 | cargo run 35 | ``` 36 | -------------------------------------------------------------------------------- /schemas/api_schema.json: -------------------------------------------------------------------------------- 1 | [ 2 | { 3 | "route": "/weather/{date}", 4 | "is_route_dynamic": "true", 5 | "method": "get", 6 | "request_body": "None", 7 | "response": { 8 | "date": "string", 9 | "temperature": "number", 10 | "description": "string" 11 | } 12 | }, 13 | { 14 | "route": "/weather", 15 | "is_route_dynamic": "false", 16 | "method": "get", 17 | "request_body": "None", 18 | "response": [ 19 | { 20 | "date": "string", 21 | "temperature": "number", 22 | "description": "string" 23 | } 24 | ] 25 | } 26 | ] 27 | -------------------------------------------------------------------------------- /src/ai_functions/aifunc_architect.rs: -------------------------------------------------------------------------------- 1 | use ai_functions::ai_function; 2 | 3 | #[ai_function] 4 | pub fn print_project_scope(_project_description: &str) { 5 | /// Input: Takes in a user request to build a website project description 6 | /// Function: Converts user request into JSON response of information items required for a website build. 7 | /// Important: At least one of the bool results must be true 8 | /// Output: Prints an object response in the following format: 9 | /// { 10 | /// "is_crud_required": bool, // true if site needs CRUD functionality 11 | /// "is_user_login_and_logout": bool // true if site needs users to be able to log in and log out 12 | /// "is_external_urls_required": bool // true if site needs to fetch data from third part providers 13 | /// } 14 | /// Example 1: 15 | /// user_request = "I need a full stack website that accepts users and gets stock price data" 16 | /// prints: 17 | /// { 18 | /// "is_crud_required": true 19 | /// "is_user_login_and_logout": true 20 | /// "is_external_urls_required": bool true 21 | /// } 22 | /// Example 2: 23 | /// user_request = "I need a simple TODO app" 24 | /// prints: 25 | /// { 26 | /// "is_crud_required": true 27 | /// "is_user_login_and_logout": false 28 | /// "is_external_urls_required": bool false 29 | /// } 30 | println!(OUTPUT) 31 | } 32 | 33 | #[ai_function] 34 | pub fn print_site_urls(_project_description: &str) { 35 | /// Input: Takes in a project description of a website build 36 | /// Function: Outputs a list of external public API endpoints that should be used in the building of the website 37 | /// Important: Only selects url endpoint(s) which do not require any API Keys at all 38 | /// Output: Prints a list response of external urls in the following format: 39 | /// ["url1", "url2", "url3", ...] 40 | /// Example: 41 | /// website_team_spec = "website_purpose: Some("\"Provides Crypto Price Data from Binance and Kraken\"",)" 42 | /// prints: 43 | /// ["https://api.binance.com/api/v3/exchangeInfo", "https://api.binance.com/api/v3/klines?symbol=BTCUSDT&interval=1d"] 44 | println!(OUTPUT) 45 | } 46 | -------------------------------------------------------------------------------- /src/ai_functions/aifunc_backend.rs: -------------------------------------------------------------------------------- 1 | use ai_functions::ai_function; 2 | 3 | #[ai_function] 4 | pub fn print_backend_webserver_code(_project_description_and_template: &str) { 5 | /// INPUT: Takes in a PROJECT_DESCRIPTION and CODE_TEMPLATE for a website backend build 6 | /// IMPORTANT: The backend code is ONLY an example. If the Project Description requires it, make as many changes as you like. 7 | /// IMPORTANT: You do not need to follow the backend code exactly. Write functions that make sense for the users request if required. 8 | /// FUNCTION: Takes an existing set of code marked as CODE_TEMPLATE and updates or re-writes it to work for the purpose in the PROJECT_DESCRIPTION 9 | /// IMPORTANT: The following libraries are already installed 10 | /// reqwest, serde, serde_json, tokio, actix-web, async-trait, actix_cors 11 | /// No other external libraries should be used. Write functions that fit with the description from the PROJECT_DESCRIPTION 12 | /// OUTPUT: Print ONLY the code, nothing else. This function ONLY prints code. 13 | println!(OUTPUT) 14 | } 15 | 16 | #[ai_function] 17 | pub fn print_improved_webserver_code(_project_description_and_template: &str) { 18 | /// INPUT: Takes in a PROJECT_DESCRIPTION and CODE_TEMPLATE for a website backend build 19 | /// FUNCTION: Performs the following tasks: 20 | /// 1. Removes any bugs in the code and adds minor additional functionality 21 | /// 2. Makes sure everything requested in the spec from a backend standpoint was followed. If not, add the feature. No code should be implemented later. Everything should be written now. 22 | /// 3. ONLY writes the code. No commentary. 23 | /// IMPORTANT: The following libraries are already installed. Does not use ANY libraries other than what was provided in the template 24 | /// reqwest, serde, serde_json, tokio, actix-web, async-trait 25 | println!(OUTPUT) 26 | } 27 | 28 | #[ai_function] 29 | pub fn print_fixed_code(_broken_code_with_bugs: &str) { 30 | /// INPUT: Takes in Rust BROKEN_CODE and the ERROR_BUGS found 31 | /// FUNCTION: Removes bugs from code 32 | /// IMPORTANT: Only prints out the new and improved code. No commentary or anything else 33 | println!(OUTPUT) 34 | } 35 | 36 | #[ai_function] 37 | pub fn print_rest_api_endpoints(_code_input: &str) { 38 | /// INPUT: Takes in Rust webserver CODE_INPUT based on actix-web 39 | /// FUNCTION: Prints out the JSON schema for url endpoints and their respective types 40 | /// LOGIC: Script analyses all code and can categorize into the following object keys: 41 | /// "route": This represents the url path of the endpoint 42 | /// "is_route_dynamic": if a route has curly braces in it such as {symbol} or {id} as an example, then this will be set to true 43 | /// "method": This represents the method being called 44 | /// "request_body": This represents the body of a post method request 45 | /// "response": This represents the output based upon the structs in the code and understanding the functions 46 | /// IMPORTANT: Only prints out the JSON schema. No commentary or anything else. 47 | /// MUST READ: All keys are strings. Even bool should be wrapped in double quotes as "bool" 48 | /// EXAMPLE: 49 | /// INPUT_CODE: 50 | /// ... 51 | /// pub struct Item { 52 | /// pub id: u64, 53 | /// pub name: String, 54 | /// pub completed: bool, 55 | /// } 56 | /// pub struct User { 57 | /// pub id: u64, 58 | /// pub username: String, 59 | /// pub password: String, 60 | /// } 61 | /// ... 62 | /// HttpServer::new(move || { 63 | /// App::new() 64 | /// .app_data(data.clone()) 65 | /// .route("/item", web::post().to(create_item)) 66 | /// .route("/item/{id}", web::get().to(read_item)) 67 | /// .route("/item/{id}", web::put().to(update_item)) 68 | /// .route("/item/{id}", web::delete().to(delete_item)) 69 | /// .route("/signup", web::post().to(signup)) 70 | /// .route("/crypto", web::get().to(crypto)) 71 | /// PRINTS JSON FORMATTED OUTPUT: 72 | /// [ 73 | /// { 74 | /// "route": "/item/{id}", 75 | /// "is_route_dynamic": "true", 76 | /// "method": "get" 77 | /// "request_body": "None", 78 | /// "response": { 79 | /// "id": "number", 80 | /// "name": "string", 81 | /// "completed": "bool", 82 | /// } 83 | /// }, 84 | /// { 85 | /// "route": "/item", 86 | /// "is_route_dynamic": "false", 87 | /// "method": "post", 88 | /// "request_body": { 89 | /// "id": "number", 90 | /// "name": "string", 91 | /// "completed": "bool", 92 | /// }, 93 | /// "response": "None" 94 | /// }, 95 | /// { 96 | /// "route": "/item/{id}", 97 | /// "is_route_dynamic": "true", 98 | /// "method": "delete", 99 | /// "request_body": "None", 100 | /// "response": "None" 101 | /// }, 102 | /// { 103 | /// "route": "/crypto", 104 | /// "is_route_dynamic": "false", 105 | /// "method": "get", 106 | /// "request_body": "None", 107 | /// "response": "not_provided" 108 | /// }, 109 | /// ... // etc 110 | /// ] 111 | println!(OUTPUT) 112 | } 113 | -------------------------------------------------------------------------------- /src/ai_functions/aifunc_managing.rs: -------------------------------------------------------------------------------- 1 | use ai_functions::ai_function; 2 | 3 | #[ai_function] 4 | pub fn convert_user_input_to_goal(_user_request: &str) { 5 | /// Input: Takes in a user request 6 | /// Function: Converts user request into a short summarized goal 7 | /// Output: Prints goal. All outputs start with "build a website that ..." 8 | /// Example 1: 9 | /// user_request = "I need a website that lets users login and logout. It needs to look fancy and accept payments." 10 | /// OUTPUT = "build a website that handles users logging in and logging out and accepts payments" 11 | /// Example 2: 12 | /// user_request = "Create something that stores crypto price data in a database using supabase and retrieves prices on the frontend." 13 | /// OUTPUT = "build a website that fetches and stores crypto price data within a supabase setup including a frontend UI to fetch the data." 14 | println!(OUTPUT) 15 | } 16 | -------------------------------------------------------------------------------- /src/ai_functions/mod.rs: -------------------------------------------------------------------------------- 1 | pub mod aifunc_architect; 2 | pub mod aifunc_backend; 3 | pub mod aifunc_managing; 4 | -------------------------------------------------------------------------------- /src/apis/call_request.rs: -------------------------------------------------------------------------------- 1 | use crate::models::general::llm::{APIResponse, ChatCompletion, Message}; 2 | use dotenv::dotenv; 3 | use reqwest::header::{HeaderMap, HeaderValue}; 4 | use reqwest::Client; 5 | use std::env; 6 | 7 | // Call Large Language Model (i.e. GPT-4) 8 | pub async fn call_gpt(messages: Vec) -> Result> { 9 | dotenv().ok(); 10 | 11 | // Extract API Key information 12 | let api_key: String = 13 | env::var("OPEN_AI_KEY").expect("OPEN_AI_KEY not found in enviornment variables"); 14 | let api_org: String = 15 | env::var("OPEN_AI_ORG").expect("OPEN_AI_ORG not found in enviornment variables"); 16 | 17 | // Confirm endpoint 18 | let url: &str = "https://api.openai.com/v1/chat/completions"; 19 | 20 | // Create headers 21 | let mut headers: HeaderMap = HeaderMap::new(); 22 | 23 | // Create api key header 24 | headers.insert( 25 | "authorization", 26 | HeaderValue::from_str(&format!("Bearer {}", api_key)) 27 | .map_err(|e| -> Box { Box::new(e) })?, 28 | ); 29 | 30 | // Create Open AI Org header 31 | headers.insert( 32 | "OpenAI-Organization", 33 | HeaderValue::from_str(api_org.as_str()) 34 | .map_err(|e| -> Box { Box::new(e) })?, 35 | ); 36 | 37 | // Create client 38 | let client: Client = Client::builder() 39 | .default_headers(headers) 40 | .build() 41 | .map_err(|e| -> Box { Box::new(e) })?; 42 | 43 | // Create chat completion 44 | let chat_completion: ChatCompletion = ChatCompletion { 45 | model: "gpt-4".to_string(), 46 | messages, 47 | temperature: 0.1, 48 | }; 49 | 50 | // // Troubleshooting 51 | // let res_raw = client 52 | // .post(url) 53 | // .json(&chat_completion) 54 | // .send() 55 | // .await 56 | // .unwrap(); 57 | // dbg!(res_raw.text().await.unwrap()); 58 | 59 | // Extract API Response 60 | let res: APIResponse = client 61 | .post(url) 62 | .json(&chat_completion) 63 | .send() 64 | .await 65 | .map_err(|e| -> Box { Box::new(e) })? 66 | .json() 67 | .await 68 | .map_err(|e| -> Box { Box::new(e) })?; 69 | 70 | // Send Response 71 | Ok(res.choices[0].message.content.clone()) 72 | } 73 | 74 | #[cfg(test)] 75 | mod tests { 76 | use super::*; 77 | 78 | #[tokio::test] 79 | async fn tests_call_to_openai() { 80 | let message: Message = Message { 81 | role: "user".to_string(), 82 | content: "Hi there, this is a test. Give me a short reponse.".to_string(), 83 | }; 84 | 85 | let messages: Vec = vec![message]; 86 | 87 | let res: Result> = call_gpt(messages).await; 88 | match res { 89 | Ok(res_str) => { 90 | dbg!(res_str); 91 | assert!(true); 92 | } 93 | Err(_) => { 94 | assert!(false); 95 | } 96 | } 97 | } 98 | } 99 | -------------------------------------------------------------------------------- /src/apis/mod.rs: -------------------------------------------------------------------------------- 1 | pub mod call_request; 2 | -------------------------------------------------------------------------------- /src/helpers/command_line.rs: -------------------------------------------------------------------------------- 1 | use crossterm::{ 2 | style::{Color, ResetColor, SetForegroundColor}, 3 | ExecutableCommand, 4 | }; 5 | use std::io::{stdin, stdout}; 6 | 7 | #[derive(PartialEq, Debug)] 8 | pub enum PrintCommand { 9 | AICall, 10 | UnitTest, 11 | Issue, 12 | } 13 | 14 | impl PrintCommand { 15 | pub fn print_agent_message(&self, agent_pos: &str, agent_statement: &str) { 16 | let mut stdout: std::io::Stdout = stdout(); 17 | 18 | // Decide on the print color 19 | let statement_color: Color = match self { 20 | Self::AICall => Color::Cyan, 21 | Self::UnitTest => Color::Magenta, 22 | Self::Issue => Color::Red, 23 | }; 24 | 25 | // Print the agent statement in a specific color 26 | stdout.execute(SetForegroundColor(Color::Green)).unwrap(); 27 | print!("Agent: {}: ", agent_pos); 28 | 29 | // Make selected color 30 | stdout.execute(SetForegroundColor(statement_color)).unwrap(); 31 | println!("{}", agent_statement); 32 | 33 | // Reset color 34 | stdout.execute(ResetColor).unwrap(); 35 | } 36 | } 37 | 38 | // Get user request 39 | pub fn get_user_response(question: &str) -> String { 40 | let mut stdout: std::io::Stdout = stdout(); 41 | 42 | // Print the question in a specific color 43 | stdout.execute(SetForegroundColor(Color::Blue)).unwrap(); 44 | println!(""); 45 | println!("{}", question); 46 | 47 | // Reset Color 48 | stdout.execute(ResetColor).unwrap(); 49 | 50 | // Read user input 51 | let mut user_response: String = String::new(); 52 | stdin() 53 | .read_line(&mut user_response) 54 | .expect("Failed to read response"); 55 | 56 | // Trim whitespace and return 57 | return user_response.trim().to_string(); 58 | } 59 | 60 | // Get user response that code is safe to execute 61 | pub fn confirm_safe_code() -> bool { 62 | let mut stdout: std::io::Stdout = stdout(); 63 | loop { 64 | // Print the question in specified color 65 | stdout.execute(SetForegroundColor(Color::Blue)).unwrap(); 66 | println!(""); 67 | print!("WARNING: You are about to run code written entirely by AI. "); 68 | println!("Review your code and confirm you wish to continue."); 69 | 70 | // Reset Color 71 | stdout.execute(ResetColor).unwrap(); 72 | 73 | // Present Options with different colors 74 | stdout.execute(SetForegroundColor(Color::Green)).unwrap(); 75 | println!("[1] All good"); 76 | stdout.execute(SetForegroundColor(Color::DarkRed)).unwrap(); 77 | println!("[2] Lets stop this project"); 78 | 79 | // Reset Color 80 | stdout.execute(ResetColor).unwrap(); 81 | 82 | // Read user input 83 | let mut human_response: String = String::new(); 84 | stdin() 85 | .read_line(&mut human_response) 86 | .expect("Failed to read response"); 87 | 88 | // Trim whitespace and convert to lowercase 89 | let human_response: String = human_response.trim().to_lowercase(); 90 | 91 | // Match response 92 | match human_response.as_str() { 93 | "1" | "ok" | "y" => return true, 94 | "2" | "no" | "n" => return false, 95 | _ => { 96 | println!("Invalid input. Please select '1' or '2'") 97 | } 98 | } 99 | } 100 | } 101 | 102 | #[cfg(test)] 103 | mod tests { 104 | use super::*; 105 | 106 | #[test] 107 | fn tests_prints_agent_msg() { 108 | PrintCommand::AICall 109 | .print_agent_message("Managing Agent", "Testing testing, processing something"); 110 | } 111 | } 112 | -------------------------------------------------------------------------------- /src/helpers/general.rs: -------------------------------------------------------------------------------- 1 | use crate::apis::call_request::call_gpt; 2 | use crate::helpers::command_line::PrintCommand; 3 | use crate::models::general::llm::Message; 4 | use reqwest::Client; 5 | use serde::de::DeserializeOwned; 6 | use std::fs; 7 | 8 | const CODE_TEMPLATE_PATH: &str = 9 | "/Users/shaun/Code/TUTORIALS/rust_autogpt/web_template/src/code_template.rs"; 10 | 11 | pub const WEB_SERVER_PROJECT_PATH: &str = "/Users/shaun/Code/TUTORIALS/rust_autogpt/web_template/"; 12 | 13 | pub const EXEC_MAIN_PATH: &str = 14 | "/Users/shaun/Code/TUTORIALS/rust_autogpt/web_template/src/main.rs"; 15 | 16 | const API_SCHEMA_PATH: &str = 17 | "/Users/shaun/Code/TUTORIALS/rust_autogpt/auto_gippity/schemas/api_schema.json"; 18 | 19 | // Extend ai function to encourage specific output 20 | pub fn extend_ai_function(ai_func: fn(&str) -> &'static str, func_input: &str) -> Message { 21 | let ai_function_str: &str = ai_func(func_input); 22 | 23 | // Extend the string to encourage only printing the output 24 | let msg: String = format!( 25 | "FUNCTION: {} 26 | INSTRUCTION: You are a function printer. You ONLY print the results of functions. 27 | Nothing else. No commentary. Here is the input to the function: {}. 28 | Print out what the function will return.", 29 | ai_function_str, func_input 30 | ); 31 | 32 | // Return message 33 | Message { 34 | role: "system".to_string(), 35 | content: msg, 36 | } 37 | } 38 | 39 | // Performs call to LLM GPT 40 | pub async fn ai_task_request( 41 | msg_context: String, 42 | agent_position: &str, 43 | agent_operation: &str, 44 | function_pass: for<'a> fn(&'a str) -> &'static str, 45 | ) -> String { 46 | // Extend AI function 47 | let extended_msg: Message = extend_ai_function(function_pass, &msg_context); 48 | 49 | // Print current status 50 | PrintCommand::AICall.print_agent_message(agent_position, agent_operation); 51 | 52 | // Get LLM response 53 | let llm_response_res: Result> = 54 | call_gpt(vec![extended_msg.clone()]).await; 55 | 56 | // Return Success or try again 57 | match llm_response_res { 58 | Ok(llm_resp) => llm_resp, 59 | Err(_) => call_gpt(vec![extended_msg.clone()]) 60 | .await 61 | .expect("Failed twice to call OpenAI"), 62 | } 63 | } 64 | 65 | // Performs call to LLM GPT - Decoded 66 | pub async fn ai_task_request_decoded( 67 | msg_context: String, 68 | agent_position: &str, 69 | agent_operation: &str, 70 | function_pass: for<'a> fn(&'a str) -> &'static str, 71 | ) -> T { 72 | let llm_response: String = 73 | ai_task_request(msg_context, agent_position, agent_operation, function_pass).await; 74 | let decoded_response: T = serde_json::from_str(llm_response.as_str()) 75 | .expect("Failed to decode ai response from serde_json"); 76 | return decoded_response; 77 | } 78 | 79 | // Check whether request url is valid 80 | pub async fn check_status_code(client: &Client, url: &str) -> Result { 81 | let response: reqwest::Response = client.get(url).send().await?; 82 | Ok(response.status().as_u16()) 83 | } 84 | 85 | // Get Code Template 86 | pub fn read_code_template_contents() -> String { 87 | let path: String = String::from(CODE_TEMPLATE_PATH); 88 | fs::read_to_string(path).expect("Failed to read code template") 89 | } 90 | 91 | // Get Exec Main 92 | pub fn read_exec_main_contents() -> String { 93 | let path: String = String::from(EXEC_MAIN_PATH); 94 | fs::read_to_string(path).expect("Failed to read code template") 95 | } 96 | 97 | // Save New Backend Code 98 | pub fn save_backend_code(contents: &String) { 99 | let path: String = String::from(EXEC_MAIN_PATH); 100 | fs::write(path, contents).expect("Failed to write main.rs file"); 101 | } 102 | 103 | // Save JSON API Endpoint Schema 104 | pub fn save_api_endpoints(api_endpoints: &String) { 105 | let path: String = String::from(API_SCHEMA_PATH); 106 | fs::write(path, api_endpoints).expect("Failed to write API Endpoints to file"); 107 | } 108 | 109 | #[cfg(test)] 110 | mod tests { 111 | use super::*; 112 | use crate::ai_functions::aifunc_managing::convert_user_input_to_goal; 113 | 114 | #[test] 115 | fn tests_extending_ai_function() { 116 | let extended_msg: Message = 117 | extend_ai_function(convert_user_input_to_goal, "dummy variable"); 118 | dbg!(&extended_msg); 119 | assert_eq!(extended_msg.role, "system".to_string()); 120 | } 121 | 122 | #[tokio::test] 123 | async fn tests_ai_task_request() { 124 | let ai_func_param: String = 125 | "Build me a webserver for making stock price api requests.".to_string(); 126 | 127 | let res: String = ai_task_request( 128 | ai_func_param, 129 | "Managing Agent", 130 | "Defining user requirements", 131 | convert_user_input_to_goal, 132 | ) 133 | .await; 134 | 135 | assert!(res.len() > 20); 136 | } 137 | } 138 | -------------------------------------------------------------------------------- /src/helpers/mod.rs: -------------------------------------------------------------------------------- 1 | pub mod command_line; 2 | pub mod general; 3 | -------------------------------------------------------------------------------- /src/main.rs: -------------------------------------------------------------------------------- 1 | #[macro_export] 2 | macro_rules! get_function_string { 3 | ($func: ident) => {{ 4 | stringify!($func) 5 | }}; 6 | } 7 | 8 | #[macro_use] 9 | mod ai_functions; 10 | mod apis; 11 | mod helpers; 12 | mod models; 13 | 14 | use helpers::command_line::get_user_response; 15 | use models::agents_manager::managing_agent::ManagingAgent; 16 | 17 | #[tokio::main] 18 | async fn main() { 19 | let usr_req: String = get_user_response("What website are we building today?"); 20 | 21 | let mut manage_agent: ManagingAgent = ManagingAgent::new(usr_req) 22 | .await 23 | .expect("Error creating agent"); 24 | 25 | manage_agent.execute_project().await; 26 | 27 | // dbg!(manage_agent); 28 | } 29 | -------------------------------------------------------------------------------- /src/models/agent_basic/basic_agent.rs: -------------------------------------------------------------------------------- 1 | use crate::models::agent_basic::basic_traits::BasicTraits; 2 | use crate::models::general::llm::Message; 3 | 4 | #[derive(Debug, PartialEq)] 5 | pub enum AgentState { 6 | Discovery, 7 | Working, 8 | UnitTesting, 9 | Finished, 10 | } 11 | 12 | #[derive(Debug)] 13 | pub struct BasicAgent { 14 | pub objective: String, 15 | pub position: String, 16 | pub state: AgentState, 17 | pub memory: Vec, 18 | } 19 | 20 | impl BasicTraits for BasicAgent { 21 | fn new(objective: String, position: String) -> Self { 22 | Self { 23 | objective, 24 | position, 25 | state: AgentState::Discovery, 26 | memory: Vec::from([]), 27 | } 28 | } 29 | 30 | fn update_state(&mut self, new_state: AgentState) { 31 | self.state = new_state; 32 | } 33 | 34 | fn get_objective(&self) -> &String { 35 | &self.objective 36 | } 37 | 38 | fn get_position(&self) -> &String { 39 | &self.position 40 | } 41 | 42 | fn get_state(&self) -> &AgentState { 43 | &self.state 44 | } 45 | 46 | fn get_memory(&self) -> &Vec { 47 | &self.memory 48 | } 49 | } 50 | -------------------------------------------------------------------------------- /src/models/agent_basic/basic_traits.rs: -------------------------------------------------------------------------------- 1 | use crate::models::agent_basic::basic_agent::AgentState; 2 | use crate::models::general::llm::Message; 3 | 4 | pub trait BasicTraits { 5 | fn new(objective: String, position: String) -> Self; 6 | fn update_state(&mut self, new_state: AgentState); 7 | fn get_objective(&self) -> &String; 8 | fn get_position(&self) -> &String; 9 | fn get_state(&self) -> &AgentState; 10 | fn get_memory(&self) -> &Vec; 11 | } 12 | -------------------------------------------------------------------------------- /src/models/agent_basic/mod.rs: -------------------------------------------------------------------------------- 1 | pub mod basic_agent; 2 | pub mod basic_traits; 3 | -------------------------------------------------------------------------------- /src/models/agents/agent_architect.rs: -------------------------------------------------------------------------------- 1 | use crate::ai_functions::aifunc_architect::{print_project_scope, print_site_urls}; 2 | use crate::helpers::command_line::PrintCommand; 3 | use crate::helpers::general::{ai_task_request_decoded, check_status_code}; 4 | use crate::models::agent_basic::basic_agent::{AgentState, BasicAgent}; 5 | use crate::models::agent_basic::basic_traits::BasicTraits; 6 | use crate::models::agents::agent_traits::{FactSheet, ProjectScope, SpecialFunctions}; 7 | 8 | use async_trait::async_trait; 9 | use reqwest::Client; 10 | use std::time::Duration; 11 | 12 | // Solutions Architect 13 | #[derive(Debug)] 14 | pub struct AgentSolutionArchitect { 15 | attributes: BasicAgent, 16 | } 17 | 18 | impl AgentSolutionArchitect { 19 | pub fn new() -> Self { 20 | let attributes: BasicAgent = BasicAgent { 21 | objective: "Gathers information and design solutions for website development" 22 | .to_string(), 23 | position: "Solutions Architect".to_string(), 24 | state: AgentState::Discovery, 25 | memory: vec![], 26 | }; 27 | 28 | Self { attributes } 29 | } 30 | 31 | // Retrieve Project Scope 32 | async fn call_project_scope(&mut self, factsheet: &mut FactSheet) -> ProjectScope { 33 | let msg_context: String = format!("{}", factsheet.project_description); 34 | 35 | let ai_response: ProjectScope = ai_task_request_decoded::( 36 | msg_context, 37 | &self.attributes.position, 38 | get_function_string!(print_project_scope), 39 | print_project_scope, 40 | ) 41 | .await; 42 | 43 | factsheet.project_scope = Some(ai_response.clone()); 44 | self.attributes.update_state(AgentState::Finished); 45 | return ai_response; 46 | } 47 | 48 | // Retrieve Project Scope 49 | async fn call_determine_external_urls( 50 | &mut self, 51 | factsheet: &mut FactSheet, 52 | msg_context: String, 53 | ) { 54 | let ai_response: Vec = ai_task_request_decoded::>( 55 | msg_context, 56 | &self.attributes.position, 57 | get_function_string!(print_site_urls), 58 | print_site_urls, 59 | ) 60 | .await; 61 | 62 | factsheet.external_urls = Some(ai_response); 63 | self.attributes.state = AgentState::UnitTesting; 64 | } 65 | } 66 | 67 | #[async_trait] 68 | impl SpecialFunctions for AgentSolutionArchitect { 69 | fn get_attributes_from_agent(&self) -> &BasicAgent { 70 | &self.attributes 71 | } 72 | 73 | async fn execute( 74 | &mut self, 75 | factsheet: &mut FactSheet, 76 | ) -> Result<(), Box> { 77 | // !!! WARNING - BE CAREFUL OF INFINITATE LOOPS !!! 78 | while self.attributes.state != AgentState::Finished { 79 | match self.attributes.state { 80 | AgentState::Discovery => { 81 | let project_scope: ProjectScope = self.call_project_scope(factsheet).await; 82 | 83 | // Confirm if external urls 84 | if project_scope.is_external_urls_required { 85 | self.call_determine_external_urls( 86 | factsheet, 87 | factsheet.project_description.clone(), 88 | ) 89 | .await; 90 | self.attributes.state = AgentState::UnitTesting; 91 | } 92 | } 93 | 94 | AgentState::UnitTesting => { 95 | let mut exclude_urls: Vec = vec![]; 96 | 97 | let client: Client = Client::builder() 98 | .timeout(Duration::from_secs(5)) 99 | .build() 100 | .unwrap(); 101 | 102 | // Defining urls to check 103 | let urls: &Vec = factsheet 104 | .external_urls 105 | .as_ref() 106 | .expect("No URL object on factsheet"); 107 | 108 | // Find faulty urls 109 | for url in urls { 110 | let endpoint_str: String = format!("Testing URL Endpoint: {}", url); 111 | PrintCommand::UnitTest.print_agent_message( 112 | self.attributes.position.as_str(), 113 | endpoint_str.as_str(), 114 | ); 115 | 116 | // Perform URL Test 117 | match check_status_code(&client, url).await { 118 | Ok(status_code) => { 119 | if status_code != 200 { 120 | exclude_urls.push(url.clone()) 121 | } 122 | } 123 | Err(e) => println!("Error checking {}: {}", url, e), 124 | } 125 | } 126 | 127 | // Exclude any faulty urls 128 | if exclude_urls.len() > 0 { 129 | let new_urls: Vec = factsheet 130 | .external_urls 131 | .as_ref() 132 | .unwrap() 133 | .iter() 134 | .filter(|url| !exclude_urls.contains(&url)) 135 | .cloned() 136 | .collect(); 137 | factsheet.external_urls = Some(new_urls); 138 | } 139 | 140 | // Confirm done 141 | self.attributes.state = AgentState::Finished; 142 | } 143 | 144 | // Default to Finished state 145 | _ => { 146 | self.attributes.state = AgentState::Finished; 147 | } 148 | } 149 | } 150 | 151 | Ok(()) 152 | } 153 | } 154 | 155 | #[cfg(test)] 156 | mod tests { 157 | use super::*; 158 | 159 | #[tokio::test] 160 | async fn tests_solution_architect() { 161 | let mut agent: AgentSolutionArchitect = AgentSolutionArchitect::new(); 162 | 163 | let mut factsheet: FactSheet = FactSheet { 164 | project_description: "Build a full stack website with user login and logout that shows latest Forex prices".to_string(), 165 | project_scope: None, 166 | external_urls: None, 167 | backend_code: None, 168 | api_endpoint_schema: None, 169 | }; 170 | 171 | agent 172 | .execute(&mut factsheet) 173 | .await 174 | .expect("Unable to execute Solutions Architect Agent"); 175 | assert!(factsheet.project_scope != None); 176 | assert!(factsheet.external_urls.is_some()); 177 | 178 | dbg!(factsheet); 179 | } 180 | } 181 | -------------------------------------------------------------------------------- /src/models/agents/agent_backend.rs: -------------------------------------------------------------------------------- 1 | use crate::ai_functions::aifunc_backend::{ 2 | print_backend_webserver_code, print_fixed_code, print_improved_webserver_code, 3 | print_rest_api_endpoints, 4 | }; 5 | use crate::helpers::general::{ 6 | check_status_code, read_code_template_contents, read_exec_main_contents, save_api_endpoints, 7 | save_backend_code, WEB_SERVER_PROJECT_PATH, 8 | }; 9 | 10 | use crate::helpers::command_line::{confirm_safe_code, PrintCommand}; 11 | use crate::helpers::general::ai_task_request; 12 | use crate::models::agent_basic::basic_agent::{AgentState, BasicAgent}; 13 | use crate::models::agents::agent_traits::{FactSheet, RouteObject, SpecialFunctions}; 14 | 15 | use async_trait::async_trait; 16 | use reqwest::Client; 17 | use std::process::{Command, Stdio}; 18 | use std::time::Duration; 19 | use tokio::time; 20 | 21 | #[derive(Debug)] 22 | pub struct AgentBackendDeveloper { 23 | attributes: BasicAgent, 24 | bug_errors: Option, 25 | bug_count: u8, 26 | } 27 | 28 | impl AgentBackendDeveloper { 29 | pub fn new() -> Self { 30 | let attributes: BasicAgent = BasicAgent { 31 | objective: "Develops backend code for webserver and json database".to_string(), 32 | position: "Backend Developer".to_string(), 33 | state: AgentState::Discovery, 34 | memory: vec![], 35 | }; 36 | 37 | Self { 38 | attributes, 39 | bug_errors: None, 40 | bug_count: 0, 41 | } 42 | } 43 | 44 | async fn call_initial_backend_code(&mut self, factsheet: &mut FactSheet) { 45 | let code_template_str: String = read_code_template_contents(); 46 | 47 | // Concatenate Instruction 48 | let msg_context: String = format!( 49 | "CODE TEMPLATE: {} \n PROJECT_DESCRIPTION: {} \n", 50 | code_template_str, factsheet.project_description 51 | ); 52 | 53 | let ai_response: String = ai_task_request( 54 | msg_context, 55 | &self.attributes.position, 56 | get_function_string!(print_backend_webserver_code), 57 | print_backend_webserver_code, 58 | ) 59 | .await; 60 | 61 | save_backend_code(&ai_response); 62 | factsheet.backend_code = Some(ai_response); 63 | } 64 | 65 | async fn call_improved_backend_code(&mut self, factsheet: &mut FactSheet) { 66 | let msg_context: String = format!( 67 | "CODE TEMPLATE: {:?} \n PROJECT_DESCRIPTION: {:?} \n", 68 | factsheet.backend_code, factsheet 69 | ); 70 | 71 | let ai_response: String = ai_task_request( 72 | msg_context, 73 | &self.attributes.position, 74 | get_function_string!(print_improved_webserver_code), 75 | print_improved_webserver_code, 76 | ) 77 | .await; 78 | 79 | save_backend_code(&ai_response); 80 | factsheet.backend_code = Some(ai_response); 81 | } 82 | 83 | async fn call_fix_code_bugs(&mut self, factsheet: &mut FactSheet) { 84 | let msg_context: String = format!( 85 | "BROKEN_CODE: {:?} \n ERROR_BUGS: {:?} \n 86 | THIS FUNCTION ONLY OUTPUTS CODE. JUST OUTPUT THE CODE.", 87 | factsheet.backend_code, self.bug_errors 88 | ); 89 | 90 | let ai_response: String = ai_task_request( 91 | msg_context, 92 | &self.attributes.position, 93 | get_function_string!(print_fixed_code), 94 | print_fixed_code, 95 | ) 96 | .await; 97 | 98 | save_backend_code(&ai_response); 99 | factsheet.backend_code = Some(ai_response); 100 | } 101 | 102 | async fn call_extract_rest_api_endpoints(&self) -> String { 103 | let backend_code: String = read_exec_main_contents(); 104 | 105 | // Structure message context 106 | let msg_context: String = format!("CODE_INPUT: {}", backend_code); 107 | 108 | let ai_response: String = ai_task_request( 109 | msg_context, 110 | &self.attributes.position, 111 | get_function_string!(print_rest_api_endpoints), 112 | print_rest_api_endpoints, 113 | ) 114 | .await; 115 | 116 | ai_response 117 | } 118 | } 119 | 120 | #[async_trait] 121 | impl SpecialFunctions for AgentBackendDeveloper { 122 | fn get_attributes_from_agent(&self) -> &BasicAgent { 123 | &self.attributes 124 | } 125 | 126 | async fn execute( 127 | &mut self, 128 | factsheet: &mut FactSheet, 129 | ) -> Result<(), Box> { 130 | while self.attributes.state != AgentState::Finished { 131 | match &self.attributes.state { 132 | AgentState::Discovery => { 133 | self.call_initial_backend_code(factsheet).await; 134 | self.attributes.state = AgentState::Working; 135 | continue; 136 | } 137 | 138 | AgentState::Working => { 139 | if self.bug_count == 0 { 140 | self.call_improved_backend_code(factsheet).await; 141 | } else { 142 | self.call_fix_code_bugs(factsheet).await; 143 | } 144 | self.attributes.state = AgentState::UnitTesting; 145 | continue; 146 | } 147 | 148 | AgentState::UnitTesting => { 149 | // Guard:: ENSURE AI SAFETY 150 | PrintCommand::UnitTest.print_agent_message( 151 | self.attributes.position.as_str(), 152 | "Backend Code Unit Testing: Requesting user input", 153 | ); 154 | 155 | let is_safe_code: bool = confirm_safe_code(); 156 | 157 | if !is_safe_code { 158 | panic!("Better go work on some AI alignment instead...") 159 | } 160 | 161 | // Build and Test Code 162 | PrintCommand::UnitTest.print_agent_message( 163 | self.attributes.position.as_str(), 164 | "Backend Code Unit Testing: building project...", 165 | ); 166 | 167 | // Build Code 168 | let build_backend_server: std::process::Output = Command::new("cargo") 169 | .arg("build") 170 | .current_dir(WEB_SERVER_PROJECT_PATH) 171 | .stdout(Stdio::piped()) 172 | .stderr(Stdio::piped()) 173 | .output() 174 | .expect("Failed to build backend application"); 175 | 176 | // Determine if build errors 177 | if build_backend_server.status.success() { 178 | self.bug_count = 0; 179 | PrintCommand::UnitTest.print_agent_message( 180 | self.attributes.position.as_str(), 181 | "Backend Code Unit Testing: Test server build successful...", 182 | ); 183 | } else { 184 | let error_arr: Vec = build_backend_server.stderr; 185 | let error_str: String = String::from_utf8(error_arr).unwrap(); 186 | 187 | // Update error stats 188 | self.bug_count += 1; 189 | self.bug_errors = Some(error_str); 190 | 191 | // Exit if too many bugs 192 | if self.bug_count > 2 { 193 | PrintCommand::Issue.print_agent_message( 194 | self.attributes.position.as_str(), 195 | "Backend Code Unit Testing: Too many bugs found in code", 196 | ); 197 | panic!("Error: Too many bugs") 198 | } 199 | 200 | // Pass back for rework 201 | self.attributes.state = AgentState::Working; 202 | continue; 203 | } 204 | 205 | /* 206 | Extract and Test 207 | Rest API Endpoints 208 | */ 209 | 210 | // Extract API Endpoints 211 | let api_endpoints_str: String = self.call_extract_rest_api_endpoints().await; 212 | 213 | // Convert API Endpoints into Values 214 | let api_endpoints: Vec = 215 | serde_json::from_str(api_endpoints_str.as_str()) 216 | .expect("Failed to decode API Endpoints"); 217 | 218 | // Define endpoints to check 219 | let check_endpoints: Vec = api_endpoints 220 | .iter() 221 | .filter(|&route_object| { 222 | route_object.method == "get" && route_object.is_route_dynamic == "false" 223 | }) 224 | .cloned() 225 | .collect(); 226 | 227 | // Store API Endpoints 228 | factsheet.api_endpoint_schema = Some(check_endpoints.clone()); 229 | 230 | // Run backend application 231 | PrintCommand::UnitTest.print_agent_message( 232 | self.attributes.position.as_str(), 233 | "Backend Code Unit Testing: Starting web server...", 234 | ); 235 | 236 | // Execute running server 237 | let mut run_backend_server: std::process::Child = Command::new("cargo") 238 | .arg("run") 239 | .current_dir(WEB_SERVER_PROJECT_PATH) 240 | .stdout(Stdio::piped()) 241 | .stderr(Stdio::piped()) 242 | .spawn() 243 | .expect("Failed to run backend application"); 244 | 245 | // Let user know testing on server will take place soon 246 | PrintCommand::UnitTest.print_agent_message( 247 | self.attributes.position.as_str(), 248 | "Backend Code Unit Testing: Launching tests on server in 5 seconds...", 249 | ); 250 | 251 | let seconds_sleep: Duration = Duration::from_secs(5); 252 | time::sleep(seconds_sleep).await; 253 | 254 | // Check status code 255 | for endpoint in check_endpoints { 256 | // Confirm url testing 257 | let testing_msg: String = 258 | format!("Testing endpoint '{}'...", endpoint.route); 259 | PrintCommand::UnitTest.print_agent_message( 260 | self.attributes.position.as_str(), 261 | testing_msg.as_str(), 262 | ); 263 | 264 | // Create client with timout 265 | let client: Client = Client::builder() 266 | .timeout(Duration::from_secs(5)) 267 | .build() 268 | .unwrap(); 269 | 270 | // Test url 271 | let url: String = format!("http://localhost:8080{}", endpoint.route); 272 | match check_status_code(&client, &url).await { 273 | Ok(status_code) => { 274 | if status_code != 200 { 275 | let err_msg: String = format!( 276 | "WARNING: Failed to call backend url endpoint {}", 277 | endpoint.route 278 | ); 279 | PrintCommand::Issue.print_agent_message( 280 | self.attributes.position.as_str(), 281 | err_msg.as_str(), 282 | ); 283 | } 284 | } 285 | Err(e) => { 286 | // kill $(lsof -t -i:8080) 287 | run_backend_server 288 | .kill() 289 | .expect("Failed to kill backend web server"); 290 | let err_msg: String = format!("Error checking backend {}", e); 291 | PrintCommand::Issue.print_agent_message( 292 | self.attributes.position.as_str(), 293 | err_msg.as_str(), 294 | ); 295 | } 296 | } 297 | } 298 | 299 | save_api_endpoints(&api_endpoints_str); 300 | 301 | PrintCommand::UnitTest.print_agent_message( 302 | self.attributes.position.as_str(), 303 | "Backend testing complete...", 304 | ); 305 | 306 | run_backend_server 307 | .kill() 308 | .expect("Failed to kill backend web server on completion"); 309 | 310 | self.attributes.state = AgentState::Finished; 311 | } 312 | 313 | _ => {} 314 | } 315 | } 316 | Ok(()) 317 | } 318 | } 319 | 320 | #[cfg(test)] 321 | mod tests { 322 | use super::*; 323 | 324 | #[tokio::test] 325 | async fn tests_backend_developer() { 326 | let mut agent: AgentBackendDeveloper = AgentBackendDeveloper::new(); 327 | 328 | let factsheet_str: &str = r#" 329 | { 330 | "project_description": "build a website that fetches and tracks fitness progress with timezone information", 331 | "project_scope": { 332 | "is_crud_required": true, 333 | "is_user_login_and_logout": true, 334 | "is_external_urls_required": true 335 | }, 336 | "external_urls": [ 337 | "http://worldtimeapi.org/api/timezone" 338 | ], 339 | "backend_code": null, 340 | "api_endpoint_schema": null 341 | }"#; 342 | 343 | let mut factsheet: FactSheet = serde_json::from_str(factsheet_str).unwrap(); 344 | 345 | agent.attributes.state = AgentState::Discovery; 346 | agent 347 | .execute(&mut factsheet) 348 | .await 349 | .expect("Failed to execute Backend Developer agent"); 350 | } 351 | } 352 | -------------------------------------------------------------------------------- /src/models/agents/agent_traits.rs: -------------------------------------------------------------------------------- 1 | use crate::models::agent_basic::basic_agent::BasicAgent; 2 | use async_trait::async_trait; 3 | use serde::{Deserialize, Serialize}; 4 | use std::fmt::Debug; 5 | 6 | #[derive(Debug, Serialize, Deserialize, Clone, PartialEq)] 7 | pub struct RouteObject { 8 | pub is_route_dynamic: String, 9 | pub method: String, 10 | pub request_body: serde_json::Value, 11 | pub response: serde_json::Value, 12 | pub route: String, 13 | } 14 | 15 | #[derive(Debug, Serialize, Deserialize, Clone, Copy, PartialEq)] 16 | pub struct ProjectScope { 17 | pub is_crud_required: bool, 18 | pub is_user_login_and_logout: bool, 19 | pub is_external_urls_required: bool, 20 | } 21 | 22 | #[derive(Debug, Serialize, Deserialize, Clone, PartialEq)] 23 | pub struct FactSheet { 24 | pub project_description: String, 25 | pub project_scope: Option, 26 | pub external_urls: Option>, 27 | pub backend_code: Option, 28 | pub api_endpoint_schema: Option>, 29 | } 30 | 31 | #[async_trait] 32 | pub trait SpecialFunctions: Debug { 33 | // Used to that manager can get attributes from Agents 34 | fn get_attributes_from_agent(&self) -> &BasicAgent; 35 | 36 | // This function will allow agents to execute their logic 37 | async fn execute( 38 | &mut self, 39 | factsheet: &mut FactSheet, 40 | ) -> Result<(), Box>; 41 | } 42 | -------------------------------------------------------------------------------- /src/models/agents/mod.rs: -------------------------------------------------------------------------------- 1 | pub mod agent_architect; 2 | pub mod agent_backend; 3 | pub mod agent_traits; 4 | -------------------------------------------------------------------------------- /src/models/agents_manager/managing_agent.rs: -------------------------------------------------------------------------------- 1 | use crate::models::agent_basic::basic_agent::{AgentState, BasicAgent}; 2 | use crate::models::agents::agent_traits::{FactSheet, SpecialFunctions}; 3 | 4 | use crate::ai_functions::aifunc_managing::convert_user_input_to_goal; 5 | use crate::helpers::general::ai_task_request; 6 | use crate::models::agents::agent_architect::AgentSolutionArchitect; 7 | use crate::models::agents::agent_backend::AgentBackendDeveloper; 8 | 9 | #[derive(Debug)] 10 | pub struct ManagingAgent { 11 | _attributes: BasicAgent, 12 | factsheet: FactSheet, 13 | agents: Vec>, 14 | } 15 | 16 | impl ManagingAgent { 17 | pub async fn new(usr_req: String) -> Result> { 18 | let position: String = "Project Manager".to_string(); 19 | 20 | let attributes: BasicAgent = BasicAgent { 21 | objective: "Manage agents who are building an excellent website for the user" 22 | .to_string(), 23 | position: position.clone(), 24 | state: AgentState::Discovery, 25 | memory: vec![], 26 | }; 27 | 28 | let project_description: String = ai_task_request( 29 | usr_req, 30 | &position, 31 | get_function_string!(convert_user_input_to_goal), 32 | convert_user_input_to_goal, 33 | ) 34 | .await; 35 | 36 | let agents: Vec> = vec![]; 37 | 38 | let factsheet: FactSheet = FactSheet { 39 | project_description, 40 | project_scope: None, 41 | external_urls: None, 42 | backend_code: None, 43 | api_endpoint_schema: None, 44 | }; 45 | 46 | Ok(Self { 47 | _attributes: attributes, 48 | factsheet, 49 | agents, 50 | }) 51 | } 52 | 53 | fn add_agent(&mut self, agent: Box) { 54 | self.agents.push(agent); 55 | } 56 | 57 | fn create_agents(&mut self) { 58 | self.add_agent(Box::new(AgentSolutionArchitect::new())); 59 | self.add_agent(Box::new(AgentBackendDeveloper::new())); 60 | } 61 | 62 | pub async fn execute_project(&mut self) { 63 | self.create_agents(); 64 | 65 | for agent in &mut self.agents { 66 | let _agent_res: Result<(), Box> = 67 | agent.execute(&mut self.factsheet).await; 68 | 69 | // let agent_info: &BasicAgent = agent.get_attributes_from_agent(); 70 | // dbg!(agent_info); 71 | } 72 | } 73 | } 74 | 75 | #[cfg(test)] 76 | mod tests { 77 | use super::*; 78 | 79 | #[tokio::test] 80 | async fn tests_managing_agent() { 81 | let usr_request: &str = "need a full stack app that fetches and tracks my fitness progress. Needs to include timezone info from the web."; 82 | 83 | let mut managing_agent: ManagingAgent = ManagingAgent::new(usr_request.to_string()) 84 | .await 85 | .expect("Error creating Managing Agent"); 86 | 87 | managing_agent.execute_project().await; 88 | 89 | dbg!(managing_agent.factsheet); 90 | } 91 | } 92 | -------------------------------------------------------------------------------- /src/models/agents_manager/mod.rs: -------------------------------------------------------------------------------- 1 | pub mod managing_agent; 2 | -------------------------------------------------------------------------------- /src/models/general/llm.rs: -------------------------------------------------------------------------------- 1 | use serde::{Deserialize, Serialize}; 2 | 3 | #[derive(Debug, Serialize, Clone)] 4 | pub struct Message { 5 | pub role: String, 6 | pub content: String, 7 | } 8 | 9 | #[derive(Debug, Serialize, Clone)] 10 | pub struct ChatCompletion { 11 | pub model: String, 12 | pub messages: Vec, 13 | pub temperature: f32, 14 | } 15 | 16 | #[derive(Debug, Deserialize)] 17 | pub struct APIMessage { 18 | pub content: String, 19 | } 20 | 21 | #[derive(Debug, Deserialize)] 22 | pub struct APIChoice { 23 | pub message: APIMessage, 24 | } 25 | 26 | #[derive(Debug, Deserialize)] 27 | pub struct APIResponse { 28 | pub choices: Vec, 29 | } 30 | -------------------------------------------------------------------------------- /src/models/general/mod.rs: -------------------------------------------------------------------------------- 1 | pub mod llm; 2 | -------------------------------------------------------------------------------- /src/models/mod.rs: -------------------------------------------------------------------------------- 1 | pub mod agent_basic; 2 | pub mod agents; 3 | pub mod agents_manager; 4 | pub mod general; 5 | --------------------------------------------------------------------------------