├── .cargo └── config.toml ├── .gitattributes ├── .gitignore ├── Cargo.lock ├── Cargo.toml ├── README.md ├── postgres-ical-parser ├── Cargo.toml └── src │ ├── lib.rs │ ├── parser.rs │ └── types.rs ├── postgres_ical.control └── src ├── bin └── pgrx_embed.rs └── lib.rs /.cargo/config.toml: -------------------------------------------------------------------------------- 1 | [build] 2 | rustflags = ["-C", "link-args=-Wl,-undefined,dynamic_lookup"] 3 | -------------------------------------------------------------------------------- /.gitattributes: -------------------------------------------------------------------------------- 1 | /.cargo/config linguist-generated=true 2 | /.cargo/pgx-linker-script.sh linguist-generated=true 3 | /src/bin/sql-generator.rs linguist-generated=true 4 | /Cargo.lock linguist-generated=true 5 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | .DS_Store 2 | .idea/ 3 | /target 4 | *.iml 5 | **/*.rs.bk 6 | -------------------------------------------------------------------------------- /Cargo.lock: -------------------------------------------------------------------------------- 1 | # This file is automatically @generated by Cargo. 2 | # It is not intended for manual editing. 3 | version = 4 4 | 5 | [[package]] 6 | name = "addr2line" 7 | version = "0.24.2" 8 | source = "registry+https://github.com/rust-lang/crates.io-index" 9 | checksum = "dfbe277e56a376000877090da837660b4427aad530e3028d44e0bffe4f89a1c1" 10 | dependencies = [ 11 | "gimli", 12 | ] 13 | 14 | [[package]] 15 | name = "adler2" 16 | version = "2.0.0" 17 | source = "registry+https://github.com/rust-lang/crates.io-index" 18 | checksum = "512761e0bb2578dd7380c6baaa0f4ce03e84f95e960231d1dec8bf4d7d6e2627" 19 | 20 | [[package]] 21 | name = "aho-corasick" 22 | version = "1.1.3" 23 | source = "registry+https://github.com/rust-lang/crates.io-index" 24 | checksum = "8e60d3430d3a69478ad0993f19238d2df97c507009a52b3c10addcd7f6bcb916" 25 | dependencies = [ 26 | "memchr", 27 | ] 28 | 29 | [[package]] 30 | name = "android-tzdata" 31 | version = "0.1.1" 32 | source = "registry+https://github.com/rust-lang/crates.io-index" 33 | checksum = "e999941b234f3131b00bc13c22d06e8c5ff726d1b6318ac7eb276997bbb4fef0" 34 | 35 | [[package]] 36 | name = "android_system_properties" 37 | version = "0.1.5" 38 | source = "registry+https://github.com/rust-lang/crates.io-index" 39 | checksum = "819e7219dbd41043ac279b19830f2efc897156490d7fd6ea916720117ee66311" 40 | dependencies = [ 41 | "libc", 42 | ] 43 | 44 | [[package]] 45 | name = "annotate-snippets" 46 | version = "0.11.5" 47 | source = "registry+https://github.com/rust-lang/crates.io-index" 48 | checksum = "710e8eae58854cdc1790fcb56cca04d712a17be849eeb81da2a724bf4bae2bc4" 49 | dependencies = [ 50 | "anstyle", 51 | "unicode-width", 52 | ] 53 | 54 | [[package]] 55 | name = "anstyle" 56 | version = "1.0.10" 57 | source = "registry+https://github.com/rust-lang/crates.io-index" 58 | checksum = "55cc3b69f167a1ef2e161439aa98aed94e6028e5f9a59be9a6ffb47aef1651f9" 59 | 60 | [[package]] 61 | name = "anyhow" 62 | version = "1.0.97" 63 | source = "registry+https://github.com/rust-lang/crates.io-index" 64 | checksum = "dcfed56ad506cb2c684a14971b8861fdc3baaaae314b9e5f9bb532cbe3ba7a4f" 65 | 66 | [[package]] 67 | name = "async-trait" 68 | version = "0.1.88" 69 | source = "registry+https://github.com/rust-lang/crates.io-index" 70 | checksum = "e539d3fca749fcee5236ab05e93a52867dd549cc157c8cb7f99595f3cedffdb5" 71 | dependencies = [ 72 | "proc-macro2", 73 | "quote", 74 | "syn 2.0.100", 75 | ] 76 | 77 | [[package]] 78 | name = "atomic-traits" 79 | version = "0.4.0" 80 | source = "registry+https://github.com/rust-lang/crates.io-index" 81 | checksum = "707f750b93bd1b739cf9ddf85f8fe7c97a4a62c60ccf8b6f232514bd9103bedc" 82 | dependencies = [ 83 | "cfg-if", 84 | "rustc_version", 85 | ] 86 | 87 | [[package]] 88 | name = "autocfg" 89 | version = "1.4.0" 90 | source = "registry+https://github.com/rust-lang/crates.io-index" 91 | checksum = "ace50bade8e6234aa140d9a2f552bbee1db4d353f69b8217bc503490fc1a9f26" 92 | 93 | [[package]] 94 | name = "backtrace" 95 | version = "0.3.74" 96 | source = "registry+https://github.com/rust-lang/crates.io-index" 97 | checksum = "8d82cb332cdfaed17ae235a638438ac4d4839913cc2af585c3c6746e8f8bee1a" 98 | dependencies = [ 99 | "addr2line", 100 | "cfg-if", 101 | "libc", 102 | "miniz_oxide", 103 | "object", 104 | "rustc-demangle", 105 | "windows-targets", 106 | ] 107 | 108 | [[package]] 109 | name = "base64" 110 | version = "0.22.1" 111 | source = "registry+https://github.com/rust-lang/crates.io-index" 112 | checksum = "72b3254f16251a8381aa12e40e3c4d2f0199f8c6508fbecb9d91f575e0fbb8c6" 113 | 114 | [[package]] 115 | name = "bindgen" 116 | version = "0.71.1" 117 | source = "registry+https://github.com/rust-lang/crates.io-index" 118 | checksum = "5f58bf3d7db68cfbac37cfc485a8d711e87e064c3d0fe0435b92f7a407f9d6b3" 119 | dependencies = [ 120 | "annotate-snippets", 121 | "bitflags", 122 | "cexpr", 123 | "clang-sys", 124 | "itertools", 125 | "proc-macro2", 126 | "quote", 127 | "regex", 128 | "rustc-hash", 129 | "shlex", 130 | "syn 2.0.100", 131 | ] 132 | 133 | [[package]] 134 | name = "bit-set" 135 | version = "0.8.0" 136 | source = "registry+https://github.com/rust-lang/crates.io-index" 137 | checksum = "08807e080ed7f9d5433fa9b275196cfc35414f66a0c79d864dc51a0d825231a3" 138 | dependencies = [ 139 | "bit-vec", 140 | ] 141 | 142 | [[package]] 143 | name = "bit-vec" 144 | version = "0.8.0" 145 | source = "registry+https://github.com/rust-lang/crates.io-index" 146 | checksum = "5e764a1d40d510daf35e07be9eb06e75770908c27d411ee6c92109c9840eaaf7" 147 | 148 | [[package]] 149 | name = "bitflags" 150 | version = "2.9.0" 151 | source = "registry+https://github.com/rust-lang/crates.io-index" 152 | checksum = "5c8214115b7bf84099f1309324e63141d4c5d7cc26862f97a0a857dbefe165bd" 153 | 154 | [[package]] 155 | name = "bitvec" 156 | version = "1.0.1" 157 | source = "registry+https://github.com/rust-lang/crates.io-index" 158 | checksum = "1bc2832c24239b0141d5674bb9174f9d68a8b5b3f2753311927c172ca46f7e9c" 159 | dependencies = [ 160 | "funty", 161 | "radium", 162 | "tap", 163 | "wyz", 164 | ] 165 | 166 | [[package]] 167 | name = "block-buffer" 168 | version = "0.10.4" 169 | source = "registry+https://github.com/rust-lang/crates.io-index" 170 | checksum = "3078c7629b62d3f0439517fa394996acacc5cbc91c5a20d8c658e77abd503a71" 171 | dependencies = [ 172 | "generic-array", 173 | ] 174 | 175 | [[package]] 176 | name = "bumpalo" 177 | version = "3.17.0" 178 | source = "registry+https://github.com/rust-lang/crates.io-index" 179 | checksum = "1628fb46dfa0b37568d12e5edd512553eccf6a22a78e8bde00bb4aed84d5bdbf" 180 | 181 | [[package]] 182 | name = "byteorder" 183 | version = "1.5.0" 184 | source = "registry+https://github.com/rust-lang/crates.io-index" 185 | checksum = "1fd0f2584146f6f2ef48085050886acf353beff7305ebd1ae69500e27c67f64b" 186 | 187 | [[package]] 188 | name = "bytes" 189 | version = "1.10.1" 190 | source = "registry+https://github.com/rust-lang/crates.io-index" 191 | checksum = "d71b6127be86fdcfddb610f7182ac57211d4b18a3e9c82eb2d17662f2227ad6a" 192 | 193 | [[package]] 194 | name = "camino" 195 | version = "1.1.9" 196 | source = "registry+https://github.com/rust-lang/crates.io-index" 197 | checksum = "8b96ec4966b5813e2c0507c1f86115c8c5abaadc3980879c3424042a02fd1ad3" 198 | dependencies = [ 199 | "serde", 200 | ] 201 | 202 | [[package]] 203 | name = "cargo-platform" 204 | version = "0.1.9" 205 | source = "registry+https://github.com/rust-lang/crates.io-index" 206 | checksum = "e35af189006b9c0f00a064685c727031e3ed2d8020f7ba284d78cc2671bd36ea" 207 | dependencies = [ 208 | "serde", 209 | ] 210 | 211 | [[package]] 212 | name = "cargo_metadata" 213 | version = "0.18.1" 214 | source = "registry+https://github.com/rust-lang/crates.io-index" 215 | checksum = "2d886547e41f740c616ae73108f6eb70afe6d940c7bc697cb30f13daec073037" 216 | dependencies = [ 217 | "camino", 218 | "cargo-platform", 219 | "semver", 220 | "serde", 221 | "serde_json", 222 | "thiserror 1.0.69", 223 | ] 224 | 225 | [[package]] 226 | name = "cargo_toml" 227 | version = "0.21.0" 228 | source = "registry+https://github.com/rust-lang/crates.io-index" 229 | checksum = "5fbd1fe9db3ebf71b89060adaf7b0504c2d6a425cf061313099547e382c2e472" 230 | dependencies = [ 231 | "serde", 232 | "toml", 233 | ] 234 | 235 | [[package]] 236 | name = "cc" 237 | version = "1.2.17" 238 | source = "registry+https://github.com/rust-lang/crates.io-index" 239 | checksum = "1fcb57c740ae1daf453ae85f16e37396f672b039e00d9d866e07ddb24e328e3a" 240 | dependencies = [ 241 | "shlex", 242 | ] 243 | 244 | [[package]] 245 | name = "cee-scape" 246 | version = "0.2.0" 247 | source = "registry+https://github.com/rust-lang/crates.io-index" 248 | checksum = "4d67dfb052149f779f77e9ce089cea126e00657e8f0d11dafc7901fde4291101" 249 | dependencies = [ 250 | "cc", 251 | "libc", 252 | ] 253 | 254 | [[package]] 255 | name = "cexpr" 256 | version = "0.6.0" 257 | source = "registry+https://github.com/rust-lang/crates.io-index" 258 | checksum = "6fac387a98bb7c37292057cffc56d62ecb629900026402633ae9160df93a8766" 259 | dependencies = [ 260 | "nom", 261 | ] 262 | 263 | [[package]] 264 | name = "cfg-if" 265 | version = "1.0.0" 266 | source = "registry+https://github.com/rust-lang/crates.io-index" 267 | checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" 268 | 269 | [[package]] 270 | name = "chrono" 271 | version = "0.4.40" 272 | source = "registry+https://github.com/rust-lang/crates.io-index" 273 | checksum = "1a7964611d71df112cb1730f2ee67324fcf4d0fc6606acbbe9bfe06df124637c" 274 | dependencies = [ 275 | "android-tzdata", 276 | "iana-time-zone", 277 | "js-sys", 278 | "num-traits", 279 | "wasm-bindgen", 280 | "windows-link", 281 | ] 282 | 283 | [[package]] 284 | name = "chrono-tz" 285 | version = "0.10.3" 286 | source = "registry+https://github.com/rust-lang/crates.io-index" 287 | checksum = "efdce149c370f133a071ca8ef6ea340b7b88748ab0810097a9e2976eaa34b4f3" 288 | dependencies = [ 289 | "chrono", 290 | "chrono-tz-build", 291 | "phf", 292 | ] 293 | 294 | [[package]] 295 | name = "chrono-tz-build" 296 | version = "0.4.1" 297 | source = "registry+https://github.com/rust-lang/crates.io-index" 298 | checksum = "8f10f8c9340e31fc120ff885fcdb54a0b48e474bbd77cab557f0c30a3e569402" 299 | dependencies = [ 300 | "parse-zoneinfo", 301 | "phf_codegen", 302 | ] 303 | 304 | [[package]] 305 | name = "clang-sys" 306 | version = "1.8.1" 307 | source = "registry+https://github.com/rust-lang/crates.io-index" 308 | checksum = "0b023947811758c97c59bf9d1c188fd619ad4718dcaa767947df1cadb14f39f4" 309 | dependencies = [ 310 | "glob", 311 | "libc", 312 | "libloading", 313 | ] 314 | 315 | [[package]] 316 | name = "clap" 317 | version = "4.5.34" 318 | source = "registry+https://github.com/rust-lang/crates.io-index" 319 | checksum = "e958897981290da2a852763fe9cdb89cd36977a5d729023127095fa94d95e2ff" 320 | dependencies = [ 321 | "clap_builder", 322 | "clap_derive", 323 | ] 324 | 325 | [[package]] 326 | name = "clap-cargo" 327 | version = "0.14.1" 328 | source = "registry+https://github.com/rust-lang/crates.io-index" 329 | checksum = "23b2ea69cefa96b848b73ad516ad1d59a195cdf9263087d977f648a818c8b43e" 330 | dependencies = [ 331 | "anstyle", 332 | "cargo_metadata", 333 | "clap", 334 | ] 335 | 336 | [[package]] 337 | name = "clap_builder" 338 | version = "4.5.34" 339 | source = "registry+https://github.com/rust-lang/crates.io-index" 340 | checksum = "83b0f35019843db2160b5bb19ae09b4e6411ac33fc6a712003c33e03090e2489" 341 | dependencies = [ 342 | "anstyle", 343 | "clap_lex", 344 | ] 345 | 346 | [[package]] 347 | name = "clap_derive" 348 | version = "4.5.32" 349 | source = "registry+https://github.com/rust-lang/crates.io-index" 350 | checksum = "09176aae279615badda0765c0c0b3f6ed53f4709118af73cf4655d85d1530cd7" 351 | dependencies = [ 352 | "heck", 353 | "proc-macro2", 354 | "quote", 355 | "syn 2.0.100", 356 | ] 357 | 358 | [[package]] 359 | name = "clap_lex" 360 | version = "0.7.4" 361 | source = "registry+https://github.com/rust-lang/crates.io-index" 362 | checksum = "f46ad14479a25103f283c0f10005961cf086d8dc42205bb44c46ac563475dca6" 363 | 364 | [[package]] 365 | name = "convert_case" 366 | version = "0.7.1" 367 | source = "registry+https://github.com/rust-lang/crates.io-index" 368 | checksum = "bb402b8d4c85569410425650ce3eddc7d698ed96d39a73f941b08fb63082f1e7" 369 | dependencies = [ 370 | "unicode-segmentation", 371 | ] 372 | 373 | [[package]] 374 | name = "core-foundation-sys" 375 | version = "0.8.7" 376 | source = "registry+https://github.com/rust-lang/crates.io-index" 377 | checksum = "773648b94d0e5d620f64f280777445740e61fe701025087ec8b57f45c791888b" 378 | 379 | [[package]] 380 | name = "cpufeatures" 381 | version = "0.2.17" 382 | source = "registry+https://github.com/rust-lang/crates.io-index" 383 | checksum = "59ed5838eebb26a2bb2e58f6d5b5316989ae9d08bab10e0e6d103e656d1b0280" 384 | dependencies = [ 385 | "libc", 386 | ] 387 | 388 | [[package]] 389 | name = "crossbeam-channel" 390 | version = "0.5.14" 391 | source = "registry+https://github.com/rust-lang/crates.io-index" 392 | checksum = "06ba6d68e24814cb8de6bb986db8222d3a027d15872cabc0d18817bc3c0e4471" 393 | dependencies = [ 394 | "crossbeam-utils", 395 | ] 396 | 397 | [[package]] 398 | name = "crossbeam-deque" 399 | version = "0.8.6" 400 | source = "registry+https://github.com/rust-lang/crates.io-index" 401 | checksum = "9dd111b7b7f7d55b72c0a6ae361660ee5853c9af73f70c3c2ef6858b950e2e51" 402 | dependencies = [ 403 | "crossbeam-epoch", 404 | "crossbeam-utils", 405 | ] 406 | 407 | [[package]] 408 | name = "crossbeam-epoch" 409 | version = "0.9.18" 410 | source = "registry+https://github.com/rust-lang/crates.io-index" 411 | checksum = "5b82ac4a3c2ca9c3460964f020e1402edd5753411d7737aa39c3714ad1b5420e" 412 | dependencies = [ 413 | "crossbeam-utils", 414 | ] 415 | 416 | [[package]] 417 | name = "crossbeam-utils" 418 | version = "0.8.21" 419 | source = "registry+https://github.com/rust-lang/crates.io-index" 420 | checksum = "d0a5c400df2834b80a4c3327b3aad3a4c4cd4de0629063962b03235697506a28" 421 | 422 | [[package]] 423 | name = "crypto-common" 424 | version = "0.1.6" 425 | source = "registry+https://github.com/rust-lang/crates.io-index" 426 | checksum = "1bfb12502f3fc46cca1bb51ac28df9d618d813cdc3d2f25b9fe775a34af26bb3" 427 | dependencies = [ 428 | "generic-array", 429 | "typenum", 430 | ] 431 | 432 | [[package]] 433 | name = "curl" 434 | version = "0.4.47" 435 | source = "registry+https://github.com/rust-lang/crates.io-index" 436 | checksum = "d9fb4d13a1be2b58f14d60adba57c9834b78c62fd86c3e76a148f732686e9265" 437 | dependencies = [ 438 | "curl-sys", 439 | "libc", 440 | "openssl-probe", 441 | "openssl-sys", 442 | "schannel", 443 | "socket2", 444 | "windows-sys 0.52.0", 445 | ] 446 | 447 | [[package]] 448 | name = "curl-sys" 449 | version = "0.4.80+curl-8.12.1" 450 | source = "registry+https://github.com/rust-lang/crates.io-index" 451 | checksum = "55f7df2eac63200c3ab25bde3b2268ef2ee56af3d238e76d61f01c3c49bff734" 452 | dependencies = [ 453 | "cc", 454 | "libc", 455 | "libz-sys", 456 | "openssl-sys", 457 | "pkg-config", 458 | "vcpkg", 459 | "windows-sys 0.52.0", 460 | ] 461 | 462 | [[package]] 463 | name = "deranged" 464 | version = "0.4.1" 465 | source = "registry+https://github.com/rust-lang/crates.io-index" 466 | checksum = "28cfac68e08048ae1883171632c2aef3ebc555621ae56fbccce1cbf22dd7f058" 467 | dependencies = [ 468 | "powerfmt", 469 | ] 470 | 471 | [[package]] 472 | name = "digest" 473 | version = "0.10.7" 474 | source = "registry+https://github.com/rust-lang/crates.io-index" 475 | checksum = "9ed9a281f7bc9b7576e61468ba615a66a5c8cfdff42420a70aa82701a3b1e292" 476 | dependencies = [ 477 | "block-buffer", 478 | "crypto-common", 479 | "subtle", 480 | ] 481 | 482 | [[package]] 483 | name = "displaydoc" 484 | version = "0.2.5" 485 | source = "registry+https://github.com/rust-lang/crates.io-index" 486 | checksum = "97369cbbc041bc366949bc74d34658d6cda5621039731c6310521892a3a20ae0" 487 | dependencies = [ 488 | "proc-macro2", 489 | "quote", 490 | "syn 2.0.100", 491 | ] 492 | 493 | [[package]] 494 | name = "either" 495 | version = "1.15.0" 496 | source = "registry+https://github.com/rust-lang/crates.io-index" 497 | checksum = "48c757948c5ede0e46177b7add2e67155f70e33c07fea8284df6576da70b3719" 498 | 499 | [[package]] 500 | name = "enum-map" 501 | version = "2.7.3" 502 | source = "registry+https://github.com/rust-lang/crates.io-index" 503 | checksum = "6866f3bfdf8207509a033af1a75a7b08abda06bbaaeae6669323fd5a097df2e9" 504 | dependencies = [ 505 | "enum-map-derive", 506 | ] 507 | 508 | [[package]] 509 | name = "enum-map-derive" 510 | version = "0.17.0" 511 | source = "registry+https://github.com/rust-lang/crates.io-index" 512 | checksum = "f282cfdfe92516eb26c2af8589c274c7c17681f5ecc03c18255fe741c6aa64eb" 513 | dependencies = [ 514 | "proc-macro2", 515 | "quote", 516 | "syn 2.0.100", 517 | ] 518 | 519 | [[package]] 520 | name = "equivalent" 521 | version = "1.0.2" 522 | source = "registry+https://github.com/rust-lang/crates.io-index" 523 | checksum = "877a4ace8713b0bcf2a4e7eec82529c029f1d0619886d18145fea96c3ffe5c0f" 524 | 525 | [[package]] 526 | name = "errno" 527 | version = "0.3.10" 528 | source = "registry+https://github.com/rust-lang/crates.io-index" 529 | checksum = "33d852cb9b869c2a9b3df2f71a3074817f01e1844f839a144f5fcef059a4eb5d" 530 | dependencies = [ 531 | "libc", 532 | "windows-sys 0.59.0", 533 | ] 534 | 535 | [[package]] 536 | name = "eyre" 537 | version = "0.6.12" 538 | source = "registry+https://github.com/rust-lang/crates.io-index" 539 | checksum = "7cd915d99f24784cdc19fd37ef22b97e3ff0ae756c7e492e9fbfe897d61e2aec" 540 | dependencies = [ 541 | "indenter", 542 | "once_cell", 543 | ] 544 | 545 | [[package]] 546 | name = "fallible-iterator" 547 | version = "0.2.0" 548 | source = "registry+https://github.com/rust-lang/crates.io-index" 549 | checksum = "4443176a9f2c162692bd3d352d745ef9413eec5782a80d8fd6f8a1ac692a07f7" 550 | 551 | [[package]] 552 | name = "fastrand" 553 | version = "2.3.0" 554 | source = "registry+https://github.com/rust-lang/crates.io-index" 555 | checksum = "37909eebbb50d72f9059c3b6d82c0463f2ff062c9e95845c43a6c9c0355411be" 556 | 557 | [[package]] 558 | name = "fixedbitset" 559 | version = "0.5.7" 560 | source = "registry+https://github.com/rust-lang/crates.io-index" 561 | checksum = "1d674e81391d1e1ab681a28d99df07927c6d4aa5b027d7da16ba32d1d21ecd99" 562 | 563 | [[package]] 564 | name = "fnv" 565 | version = "1.0.7" 566 | source = "registry+https://github.com/rust-lang/crates.io-index" 567 | checksum = "3f9eec918d3f24069decb9af1554cad7c880e2da24a9afd88aca000531ab82c1" 568 | 569 | [[package]] 570 | name = "form_urlencoded" 571 | version = "1.2.1" 572 | source = "registry+https://github.com/rust-lang/crates.io-index" 573 | checksum = "e13624c2627564efccf4934284bdd98cbaa14e79b0b5a141218e507b3a823456" 574 | dependencies = [ 575 | "percent-encoding", 576 | ] 577 | 578 | [[package]] 579 | name = "funty" 580 | version = "2.0.0" 581 | source = "registry+https://github.com/rust-lang/crates.io-index" 582 | checksum = "e6d5a32815ae3f33302d95fdcb2ce17862f8c65363dcfd29360480ba1001fc9c" 583 | 584 | [[package]] 585 | name = "futures-channel" 586 | version = "0.3.31" 587 | source = "registry+https://github.com/rust-lang/crates.io-index" 588 | checksum = "2dff15bf788c671c1934e366d07e30c1814a8ef514e1af724a602e8a2fbe1b10" 589 | dependencies = [ 590 | "futures-core", 591 | "futures-sink", 592 | ] 593 | 594 | [[package]] 595 | name = "futures-core" 596 | version = "0.3.31" 597 | source = "registry+https://github.com/rust-lang/crates.io-index" 598 | checksum = "05f29059c0c2090612e8d742178b0580d2dc940c837851ad723096f87af6663e" 599 | 600 | [[package]] 601 | name = "futures-macro" 602 | version = "0.3.31" 603 | source = "registry+https://github.com/rust-lang/crates.io-index" 604 | checksum = "162ee34ebcb7c64a8abebc059ce0fee27c2262618d7b60ed8faf72fef13c3650" 605 | dependencies = [ 606 | "proc-macro2", 607 | "quote", 608 | "syn 2.0.100", 609 | ] 610 | 611 | [[package]] 612 | name = "futures-sink" 613 | version = "0.3.31" 614 | source = "registry+https://github.com/rust-lang/crates.io-index" 615 | checksum = "e575fab7d1e0dcb8d0c7bcf9a63ee213816ab51902e6d244a95819acacf1d4f7" 616 | 617 | [[package]] 618 | name = "futures-task" 619 | version = "0.3.31" 620 | source = "registry+https://github.com/rust-lang/crates.io-index" 621 | checksum = "f90f7dce0722e95104fcb095585910c0977252f286e354b5e3bd38902cd99988" 622 | 623 | [[package]] 624 | name = "futures-util" 625 | version = "0.3.31" 626 | source = "registry+https://github.com/rust-lang/crates.io-index" 627 | checksum = "9fa08315bb612088cc391249efdc3bc77536f16c91f6cf495e6fbe85b20a4a81" 628 | dependencies = [ 629 | "futures-core", 630 | "futures-macro", 631 | "futures-sink", 632 | "futures-task", 633 | "pin-project-lite", 634 | "pin-utils", 635 | "slab", 636 | ] 637 | 638 | [[package]] 639 | name = "generic-array" 640 | version = "0.14.7" 641 | source = "registry+https://github.com/rust-lang/crates.io-index" 642 | checksum = "85649ca51fd72272d7821adaf274ad91c288277713d9c18820d8499a7ff69e9a" 643 | dependencies = [ 644 | "typenum", 645 | "version_check", 646 | ] 647 | 648 | [[package]] 649 | name = "getrandom" 650 | version = "0.2.15" 651 | source = "registry+https://github.com/rust-lang/crates.io-index" 652 | checksum = "c4567c8db10ae91089c99af84c68c38da3ec2f087c3f82960bcdbf3656b6f4d7" 653 | dependencies = [ 654 | "cfg-if", 655 | "libc", 656 | "wasi 0.11.0+wasi-snapshot-preview1", 657 | ] 658 | 659 | [[package]] 660 | name = "getrandom" 661 | version = "0.3.2" 662 | source = "registry+https://github.com/rust-lang/crates.io-index" 663 | checksum = "73fea8450eea4bac3940448fb7ae50d91f034f941199fcd9d909a5a07aa455f0" 664 | dependencies = [ 665 | "cfg-if", 666 | "libc", 667 | "r-efi", 668 | "wasi 0.14.2+wasi-0.2.4", 669 | ] 670 | 671 | [[package]] 672 | name = "gimli" 673 | version = "0.31.1" 674 | source = "registry+https://github.com/rust-lang/crates.io-index" 675 | checksum = "07e28edb80900c19c28f1072f2e8aeca7fa06b23cd4169cefe1af5aa3260783f" 676 | 677 | [[package]] 678 | name = "glob" 679 | version = "0.3.2" 680 | source = "registry+https://github.com/rust-lang/crates.io-index" 681 | checksum = "a8d1add55171497b4705a648c6b583acafb01d58050a51727785f0b2c8e0a2b2" 682 | 683 | [[package]] 684 | name = "half" 685 | version = "1.8.3" 686 | source = "registry+https://github.com/rust-lang/crates.io-index" 687 | checksum = "1b43ede17f21864e81be2fa654110bf1e793774238d86ef8555c37e6519c0403" 688 | 689 | [[package]] 690 | name = "hash32" 691 | version = "0.3.1" 692 | source = "registry+https://github.com/rust-lang/crates.io-index" 693 | checksum = "47d60b12902ba28e2730cd37e95b8c9223af2808df9e902d4df49588d1470606" 694 | dependencies = [ 695 | "byteorder", 696 | ] 697 | 698 | [[package]] 699 | name = "hashbrown" 700 | version = "0.15.2" 701 | source = "registry+https://github.com/rust-lang/crates.io-index" 702 | checksum = "bf151400ff0baff5465007dd2f3e717f3fe502074ca563069ce3a6629d07b289" 703 | 704 | [[package]] 705 | name = "heapless" 706 | version = "0.8.0" 707 | source = "registry+https://github.com/rust-lang/crates.io-index" 708 | checksum = "0bfb9eb618601c89945a70e254898da93b13be0388091d42117462b265bb3fad" 709 | dependencies = [ 710 | "hash32", 711 | "stable_deref_trait", 712 | ] 713 | 714 | [[package]] 715 | name = "heck" 716 | version = "0.5.0" 717 | source = "registry+https://github.com/rust-lang/crates.io-index" 718 | checksum = "2304e00983f87ffb38b55b444b5e3b60a884b5d30c0fca7d82fe33449bbe55ea" 719 | 720 | [[package]] 721 | name = "hermit-abi" 722 | version = "0.5.0" 723 | source = "registry+https://github.com/rust-lang/crates.io-index" 724 | checksum = "fbd780fe5cc30f81464441920d82ac8740e2e46b29a6fad543ddd075229ce37e" 725 | 726 | [[package]] 727 | name = "hmac" 728 | version = "0.12.1" 729 | source = "registry+https://github.com/rust-lang/crates.io-index" 730 | checksum = "6c49c37c09c17a53d937dfbb742eb3a961d65a994e6bcdcf37e7399d0cc8ab5e" 731 | dependencies = [ 732 | "digest", 733 | ] 734 | 735 | [[package]] 736 | name = "home" 737 | version = "0.5.11" 738 | source = "registry+https://github.com/rust-lang/crates.io-index" 739 | checksum = "589533453244b0995c858700322199b2becb13b627df2851f64a2775d024abcf" 740 | dependencies = [ 741 | "windows-sys 0.59.0", 742 | ] 743 | 744 | [[package]] 745 | name = "iana-time-zone" 746 | version = "0.1.63" 747 | source = "registry+https://github.com/rust-lang/crates.io-index" 748 | checksum = "b0c919e5debc312ad217002b8048a17b7d83f80703865bbfcfebb0458b0b27d8" 749 | dependencies = [ 750 | "android_system_properties", 751 | "core-foundation-sys", 752 | "iana-time-zone-haiku", 753 | "js-sys", 754 | "log", 755 | "wasm-bindgen", 756 | "windows-core 0.61.0", 757 | ] 758 | 759 | [[package]] 760 | name = "iana-time-zone-haiku" 761 | version = "0.1.2" 762 | source = "registry+https://github.com/rust-lang/crates.io-index" 763 | checksum = "f31827a206f56af32e590ba56d5d2d085f558508192593743f16b2306495269f" 764 | dependencies = [ 765 | "cc", 766 | ] 767 | 768 | [[package]] 769 | name = "ical" 770 | version = "0.11.0" 771 | source = "registry+https://github.com/rust-lang/crates.io-index" 772 | checksum = "9b7cab7543a8b7729a19e2c04309f902861293dcdae6558dfbeb634454d279f6" 773 | dependencies = [ 774 | "thiserror 1.0.69", 775 | ] 776 | 777 | [[package]] 778 | name = "icu_collections" 779 | version = "1.5.0" 780 | source = "registry+https://github.com/rust-lang/crates.io-index" 781 | checksum = "db2fa452206ebee18c4b5c2274dbf1de17008e874b4dc4f0aea9d01ca79e4526" 782 | dependencies = [ 783 | "displaydoc", 784 | "yoke", 785 | "zerofrom", 786 | "zerovec", 787 | ] 788 | 789 | [[package]] 790 | name = "icu_locid" 791 | version = "1.5.0" 792 | source = "registry+https://github.com/rust-lang/crates.io-index" 793 | checksum = "13acbb8371917fc971be86fc8057c41a64b521c184808a698c02acc242dbf637" 794 | dependencies = [ 795 | "displaydoc", 796 | "litemap", 797 | "tinystr", 798 | "writeable", 799 | "zerovec", 800 | ] 801 | 802 | [[package]] 803 | name = "icu_locid_transform" 804 | version = "1.5.0" 805 | source = "registry+https://github.com/rust-lang/crates.io-index" 806 | checksum = "01d11ac35de8e40fdeda00d9e1e9d92525f3f9d887cdd7aa81d727596788b54e" 807 | dependencies = [ 808 | "displaydoc", 809 | "icu_locid", 810 | "icu_locid_transform_data", 811 | "icu_provider", 812 | "tinystr", 813 | "zerovec", 814 | ] 815 | 816 | [[package]] 817 | name = "icu_locid_transform_data" 818 | version = "1.5.1" 819 | source = "registry+https://github.com/rust-lang/crates.io-index" 820 | checksum = "7515e6d781098bf9f7205ab3fc7e9709d34554ae0b21ddbcb5febfa4bc7df11d" 821 | 822 | [[package]] 823 | name = "icu_normalizer" 824 | version = "1.5.0" 825 | source = "registry+https://github.com/rust-lang/crates.io-index" 826 | checksum = "19ce3e0da2ec68599d193c93d088142efd7f9c5d6fc9b803774855747dc6a84f" 827 | dependencies = [ 828 | "displaydoc", 829 | "icu_collections", 830 | "icu_normalizer_data", 831 | "icu_properties", 832 | "icu_provider", 833 | "smallvec", 834 | "utf16_iter", 835 | "utf8_iter", 836 | "write16", 837 | "zerovec", 838 | ] 839 | 840 | [[package]] 841 | name = "icu_normalizer_data" 842 | version = "1.5.1" 843 | source = "registry+https://github.com/rust-lang/crates.io-index" 844 | checksum = "c5e8338228bdc8ab83303f16b797e177953730f601a96c25d10cb3ab0daa0cb7" 845 | 846 | [[package]] 847 | name = "icu_properties" 848 | version = "1.5.1" 849 | source = "registry+https://github.com/rust-lang/crates.io-index" 850 | checksum = "93d6020766cfc6302c15dbbc9c8778c37e62c14427cb7f6e601d849e092aeef5" 851 | dependencies = [ 852 | "displaydoc", 853 | "icu_collections", 854 | "icu_locid_transform", 855 | "icu_properties_data", 856 | "icu_provider", 857 | "tinystr", 858 | "zerovec", 859 | ] 860 | 861 | [[package]] 862 | name = "icu_properties_data" 863 | version = "1.5.1" 864 | source = "registry+https://github.com/rust-lang/crates.io-index" 865 | checksum = "85fb8799753b75aee8d2a21d7c14d9f38921b54b3dbda10f5a3c7a7b82dba5e2" 866 | 867 | [[package]] 868 | name = "icu_provider" 869 | version = "1.5.0" 870 | source = "registry+https://github.com/rust-lang/crates.io-index" 871 | checksum = "6ed421c8a8ef78d3e2dbc98a973be2f3770cb42b606e3ab18d6237c4dfde68d9" 872 | dependencies = [ 873 | "displaydoc", 874 | "icu_locid", 875 | "icu_provider_macros", 876 | "stable_deref_trait", 877 | "tinystr", 878 | "writeable", 879 | "yoke", 880 | "zerofrom", 881 | "zerovec", 882 | ] 883 | 884 | [[package]] 885 | name = "icu_provider_macros" 886 | version = "1.5.0" 887 | source = "registry+https://github.com/rust-lang/crates.io-index" 888 | checksum = "1ec89e9337638ecdc08744df490b221a7399bf8d164eb52a665454e60e075ad6" 889 | dependencies = [ 890 | "proc-macro2", 891 | "quote", 892 | "syn 2.0.100", 893 | ] 894 | 895 | [[package]] 896 | name = "idna" 897 | version = "1.0.3" 898 | source = "registry+https://github.com/rust-lang/crates.io-index" 899 | checksum = "686f825264d630750a544639377bae737628043f20d38bbc029e8f29ea968a7e" 900 | dependencies = [ 901 | "idna_adapter", 902 | "smallvec", 903 | "utf8_iter", 904 | ] 905 | 906 | [[package]] 907 | name = "idna_adapter" 908 | version = "1.2.0" 909 | source = "registry+https://github.com/rust-lang/crates.io-index" 910 | checksum = "daca1df1c957320b2cf139ac61e7bd64fed304c5040df000a745aa1de3b4ef71" 911 | dependencies = [ 912 | "icu_normalizer", 913 | "icu_properties", 914 | ] 915 | 916 | [[package]] 917 | name = "indenter" 918 | version = "0.3.3" 919 | source = "registry+https://github.com/rust-lang/crates.io-index" 920 | checksum = "ce23b50ad8242c51a442f3ff322d56b02f08852c77e4c0b4d3fd684abc89c683" 921 | 922 | [[package]] 923 | name = "indexmap" 924 | version = "2.8.0" 925 | source = "registry+https://github.com/rust-lang/crates.io-index" 926 | checksum = "3954d50fe15b02142bf25d3b8bdadb634ec3948f103d04ffe3031bc8fe9d7058" 927 | dependencies = [ 928 | "equivalent", 929 | "hashbrown", 930 | ] 931 | 932 | [[package]] 933 | name = "is-terminal" 934 | version = "0.4.16" 935 | source = "registry+https://github.com/rust-lang/crates.io-index" 936 | checksum = "e04d7f318608d35d4b61ddd75cbdaee86b023ebe2bd5a66ee0915f0bf93095a9" 937 | dependencies = [ 938 | "hermit-abi", 939 | "libc", 940 | "windows-sys 0.59.0", 941 | ] 942 | 943 | [[package]] 944 | name = "is_ci" 945 | version = "1.2.0" 946 | source = "registry+https://github.com/rust-lang/crates.io-index" 947 | checksum = "7655c9839580ee829dfacba1d1278c2b7883e50a277ff7541299489d6bdfdc45" 948 | 949 | [[package]] 950 | name = "itertools" 951 | version = "0.13.0" 952 | source = "registry+https://github.com/rust-lang/crates.io-index" 953 | checksum = "413ee7dfc52ee1a4949ceeb7dbc8a33f2d6c088194d9f922fb8318faf1f01186" 954 | dependencies = [ 955 | "either", 956 | ] 957 | 958 | [[package]] 959 | name = "itoa" 960 | version = "1.0.15" 961 | source = "registry+https://github.com/rust-lang/crates.io-index" 962 | checksum = "4a5f13b858c8d314ee3e8f639011f7ccefe71f97f96e50151fb991f267928e2c" 963 | 964 | [[package]] 965 | name = "js-sys" 966 | version = "0.3.77" 967 | source = "registry+https://github.com/rust-lang/crates.io-index" 968 | checksum = "1cfaf33c695fc6e08064efbc1f72ec937429614f25eef83af942d0e227c3a28f" 969 | dependencies = [ 970 | "once_cell", 971 | "wasm-bindgen", 972 | ] 973 | 974 | [[package]] 975 | name = "lazy_static" 976 | version = "1.5.0" 977 | source = "registry+https://github.com/rust-lang/crates.io-index" 978 | checksum = "bbd2bcb4c963f2ddae06a2efc7e9f3591312473c50c6685e1f298068316e66fe" 979 | 980 | [[package]] 981 | name = "libc" 982 | version = "0.2.171" 983 | source = "registry+https://github.com/rust-lang/crates.io-index" 984 | checksum = "c19937216e9d3aa9956d9bb8dfc0b0c8beb6058fc4f7a4dc4d850edf86a237d6" 985 | 986 | [[package]] 987 | name = "libloading" 988 | version = "0.8.6" 989 | source = "registry+https://github.com/rust-lang/crates.io-index" 990 | checksum = "fc2f4eb4bc735547cfed7c0a4922cbd04a4655978c09b54f1f7b228750664c34" 991 | dependencies = [ 992 | "cfg-if", 993 | "windows-targets", 994 | ] 995 | 996 | [[package]] 997 | name = "libz-sys" 998 | version = "1.1.22" 999 | source = "registry+https://github.com/rust-lang/crates.io-index" 1000 | checksum = "8b70e7a7df205e92a1a4cd9aaae7898dac0aa555503cc0a649494d0d60e7651d" 1001 | dependencies = [ 1002 | "cc", 1003 | "libc", 1004 | "pkg-config", 1005 | "vcpkg", 1006 | ] 1007 | 1008 | [[package]] 1009 | name = "linux-raw-sys" 1010 | version = "0.9.3" 1011 | source = "registry+https://github.com/rust-lang/crates.io-index" 1012 | checksum = "fe7db12097d22ec582439daf8618b8fdd1a7bef6270e9af3b1ebcd30893cf413" 1013 | 1014 | [[package]] 1015 | name = "litemap" 1016 | version = "0.7.5" 1017 | source = "registry+https://github.com/rust-lang/crates.io-index" 1018 | checksum = "23fb14cb19457329c82206317a5663005a4d404783dc74f4252769b0d5f42856" 1019 | 1020 | [[package]] 1021 | name = "lock_api" 1022 | version = "0.4.12" 1023 | source = "registry+https://github.com/rust-lang/crates.io-index" 1024 | checksum = "07af8b9cdd281b7915f413fa73f29ebd5d55d0d3f0155584dade1ff18cea1b17" 1025 | dependencies = [ 1026 | "autocfg", 1027 | "scopeguard", 1028 | ] 1029 | 1030 | [[package]] 1031 | name = "log" 1032 | version = "0.4.27" 1033 | source = "registry+https://github.com/rust-lang/crates.io-index" 1034 | checksum = "13dc2df351e3202783a1fe0d44375f7295ffb4049267b0f3018346dc122a1d94" 1035 | 1036 | [[package]] 1037 | name = "md-5" 1038 | version = "0.10.6" 1039 | source = "registry+https://github.com/rust-lang/crates.io-index" 1040 | checksum = "d89e7ee0cfbedfc4da3340218492196241d89eefb6dab27de5df917a6d2e78cf" 1041 | dependencies = [ 1042 | "cfg-if", 1043 | "digest", 1044 | ] 1045 | 1046 | [[package]] 1047 | name = "memchr" 1048 | version = "2.7.4" 1049 | source = "registry+https://github.com/rust-lang/crates.io-index" 1050 | checksum = "78ca9ab1a0babb1e7d5695e3530886289c18cf2f87ec19a575a0abdce112e3a3" 1051 | 1052 | [[package]] 1053 | name = "minimal-lexical" 1054 | version = "0.2.1" 1055 | source = "registry+https://github.com/rust-lang/crates.io-index" 1056 | checksum = "68354c5c6bd36d73ff3feceb05efa59b6acb7626617f4962be322a825e61f79a" 1057 | 1058 | [[package]] 1059 | name = "miniz_oxide" 1060 | version = "0.8.5" 1061 | source = "registry+https://github.com/rust-lang/crates.io-index" 1062 | checksum = "8e3e04debbb59698c15bacbb6d93584a8c0ca9cc3213cb423d31f760d8843ce5" 1063 | dependencies = [ 1064 | "adler2", 1065 | ] 1066 | 1067 | [[package]] 1068 | name = "mio" 1069 | version = "1.0.3" 1070 | source = "registry+https://github.com/rust-lang/crates.io-index" 1071 | checksum = "2886843bf800fba2e3377cff24abf6379b4c4d5c6681eaf9ea5b0d15090450bd" 1072 | dependencies = [ 1073 | "libc", 1074 | "wasi 0.11.0+wasi-snapshot-preview1", 1075 | "windows-sys 0.52.0", 1076 | ] 1077 | 1078 | [[package]] 1079 | name = "nom" 1080 | version = "7.1.3" 1081 | source = "registry+https://github.com/rust-lang/crates.io-index" 1082 | checksum = "d273983c5a657a70a3e8f2a01329822f3b8c8172b73826411a55751e404a0a4a" 1083 | dependencies = [ 1084 | "memchr", 1085 | "minimal-lexical", 1086 | ] 1087 | 1088 | [[package]] 1089 | name = "ntapi" 1090 | version = "0.4.1" 1091 | source = "registry+https://github.com/rust-lang/crates.io-index" 1092 | checksum = "e8a3895c6391c39d7fe7ebc444a87eb2991b2a0bc718fdabd071eec617fc68e4" 1093 | dependencies = [ 1094 | "winapi", 1095 | ] 1096 | 1097 | [[package]] 1098 | name = "num-conv" 1099 | version = "0.1.0" 1100 | source = "registry+https://github.com/rust-lang/crates.io-index" 1101 | checksum = "51d515d32fb182ee37cda2ccdcb92950d6a3c2893aa280e540671c2cd0f3b1d9" 1102 | 1103 | [[package]] 1104 | name = "num-traits" 1105 | version = "0.2.19" 1106 | source = "registry+https://github.com/rust-lang/crates.io-index" 1107 | checksum = "071dfc062690e90b734c0b2273ce72ad0ffa95f0c74596bc250dcfd960262841" 1108 | dependencies = [ 1109 | "autocfg", 1110 | ] 1111 | 1112 | [[package]] 1113 | name = "object" 1114 | version = "0.36.7" 1115 | source = "registry+https://github.com/rust-lang/crates.io-index" 1116 | checksum = "62948e14d923ea95ea2c7c86c71013138b66525b86bdc08d2dcc262bdb497b87" 1117 | dependencies = [ 1118 | "memchr", 1119 | ] 1120 | 1121 | [[package]] 1122 | name = "once_cell" 1123 | version = "1.21.3" 1124 | source = "registry+https://github.com/rust-lang/crates.io-index" 1125 | checksum = "42f5e15c9953c5e4ccceeb2e7382a716482c34515315f7b03532b8b4e8393d2d" 1126 | 1127 | [[package]] 1128 | name = "openssl-probe" 1129 | version = "0.1.6" 1130 | source = "registry+https://github.com/rust-lang/crates.io-index" 1131 | checksum = "d05e27ee213611ffe7d6348b942e8f942b37114c00cc03cec254295a4a17852e" 1132 | 1133 | [[package]] 1134 | name = "openssl-sys" 1135 | version = "0.9.106" 1136 | source = "registry+https://github.com/rust-lang/crates.io-index" 1137 | checksum = "8bb61ea9811cc39e3c2069f40b8b8e2e70d8569b361f879786cc7ed48b777cdd" 1138 | dependencies = [ 1139 | "cc", 1140 | "libc", 1141 | "pkg-config", 1142 | "vcpkg", 1143 | ] 1144 | 1145 | [[package]] 1146 | name = "owo-colors" 1147 | version = "4.2.0" 1148 | source = "registry+https://github.com/rust-lang/crates.io-index" 1149 | checksum = "1036865bb9422d3300cf723f657c2851d0e9ab12567854b1f4eba3d77decf564" 1150 | dependencies = [ 1151 | "supports-color 2.1.0", 1152 | "supports-color 3.0.2", 1153 | ] 1154 | 1155 | [[package]] 1156 | name = "parking_lot" 1157 | version = "0.12.3" 1158 | source = "registry+https://github.com/rust-lang/crates.io-index" 1159 | checksum = "f1bf18183cf54e8d6059647fc3063646a1801cf30896933ec2311622cc4b9a27" 1160 | dependencies = [ 1161 | "lock_api", 1162 | "parking_lot_core", 1163 | ] 1164 | 1165 | [[package]] 1166 | name = "parking_lot_core" 1167 | version = "0.9.10" 1168 | source = "registry+https://github.com/rust-lang/crates.io-index" 1169 | checksum = "1e401f977ab385c9e4e3ab30627d6f26d00e2c73eef317493c4ec6d468726cf8" 1170 | dependencies = [ 1171 | "cfg-if", 1172 | "libc", 1173 | "redox_syscall", 1174 | "smallvec", 1175 | "windows-targets", 1176 | ] 1177 | 1178 | [[package]] 1179 | name = "parse-zoneinfo" 1180 | version = "0.3.1" 1181 | source = "registry+https://github.com/rust-lang/crates.io-index" 1182 | checksum = "1f2a05b18d44e2957b88f96ba460715e295bc1d7510468a2f3d3b44535d26c24" 1183 | dependencies = [ 1184 | "regex", 1185 | ] 1186 | 1187 | [[package]] 1188 | name = "paste" 1189 | version = "1.0.15" 1190 | source = "registry+https://github.com/rust-lang/crates.io-index" 1191 | checksum = "57c0d7b74b563b49d38dae00a0c37d4d6de9b432382b2892f0574ddcae73fd0a" 1192 | 1193 | [[package]] 1194 | name = "pathsearch" 1195 | version = "0.2.0" 1196 | source = "registry+https://github.com/rust-lang/crates.io-index" 1197 | checksum = "da983bc5e582ab17179c190b4b66c7d76c5943a69c6d34df2a2b6bf8a2977b05" 1198 | dependencies = [ 1199 | "anyhow", 1200 | "libc", 1201 | ] 1202 | 1203 | [[package]] 1204 | name = "percent-encoding" 1205 | version = "2.3.1" 1206 | source = "registry+https://github.com/rust-lang/crates.io-index" 1207 | checksum = "e3148f5046208a5d56bcfc03053e3ca6334e51da8dfb19b6cdc8b306fae3283e" 1208 | 1209 | [[package]] 1210 | name = "petgraph" 1211 | version = "0.7.1" 1212 | source = "registry+https://github.com/rust-lang/crates.io-index" 1213 | checksum = "3672b37090dbd86368a4145bc067582552b29c27377cad4e0a306c97f9bd7772" 1214 | dependencies = [ 1215 | "fixedbitset", 1216 | "indexmap", 1217 | ] 1218 | 1219 | [[package]] 1220 | name = "pgrx" 1221 | version = "0.13.1" 1222 | source = "registry+https://github.com/rust-lang/crates.io-index" 1223 | checksum = "74fb2c1fbb9edc39097200f882ee58550e68f519db52309e94d894a2ad1ddf07" 1224 | dependencies = [ 1225 | "atomic-traits", 1226 | "bitflags", 1227 | "bitvec", 1228 | "enum-map", 1229 | "heapless", 1230 | "libc", 1231 | "once_cell", 1232 | "pgrx-macros", 1233 | "pgrx-pg-sys", 1234 | "pgrx-sql-entity-graph", 1235 | "seahash", 1236 | "serde", 1237 | "serde_cbor", 1238 | "serde_json", 1239 | "thiserror 2.0.12", 1240 | "uuid", 1241 | ] 1242 | 1243 | [[package]] 1244 | name = "pgrx-bindgen" 1245 | version = "0.13.1" 1246 | source = "registry+https://github.com/rust-lang/crates.io-index" 1247 | checksum = "7bba29f6257193d1795eee0f96e72d368b30e95ab50d93397b5a76cc7784ddef" 1248 | dependencies = [ 1249 | "bindgen", 1250 | "cc", 1251 | "clang-sys", 1252 | "eyre", 1253 | "pgrx-pg-config", 1254 | "proc-macro2", 1255 | "quote", 1256 | "shlex", 1257 | "syn 2.0.100", 1258 | "walkdir", 1259 | ] 1260 | 1261 | [[package]] 1262 | name = "pgrx-macros" 1263 | version = "0.13.1" 1264 | source = "registry+https://github.com/rust-lang/crates.io-index" 1265 | checksum = "f1f9d2a6a94d8ea1a722ea489048acd203c6ba9b62f70edac587dbe8e1fb4585" 1266 | dependencies = [ 1267 | "pgrx-sql-entity-graph", 1268 | "proc-macro2", 1269 | "quote", 1270 | "syn 2.0.100", 1271 | ] 1272 | 1273 | [[package]] 1274 | name = "pgrx-named-columns" 1275 | version = "0.2.0" 1276 | source = "registry+https://github.com/rust-lang/crates.io-index" 1277 | checksum = "c78df7201a9112de5faf7c5d03501908736273615643dbb232553025c05231bc" 1278 | dependencies = [ 1279 | "proc-macro-error", 1280 | "proc-macro2", 1281 | "quote", 1282 | "syn 2.0.100", 1283 | ] 1284 | 1285 | [[package]] 1286 | name = "pgrx-pg-config" 1287 | version = "0.13.1" 1288 | source = "registry+https://github.com/rust-lang/crates.io-index" 1289 | checksum = "05be49ab66e458f4c164b45daa885e53dbbadc4f37bb47e8b5d85d5b4d9a0be4" 1290 | dependencies = [ 1291 | "cargo_toml", 1292 | "eyre", 1293 | "home", 1294 | "owo-colors", 1295 | "pathsearch", 1296 | "serde", 1297 | "serde_json", 1298 | "thiserror 2.0.12", 1299 | "toml", 1300 | "url", 1301 | ] 1302 | 1303 | [[package]] 1304 | name = "pgrx-pg-sys" 1305 | version = "0.13.1" 1306 | source = "registry+https://github.com/rust-lang/crates.io-index" 1307 | checksum = "a360ad31a947674a46e72a39881f1be8afe958157ae44cf8ad6ed70b984c0f40" 1308 | dependencies = [ 1309 | "cee-scape", 1310 | "libc", 1311 | "pgrx-bindgen", 1312 | "pgrx-macros", 1313 | "pgrx-sql-entity-graph", 1314 | "serde", 1315 | "sptr", 1316 | ] 1317 | 1318 | [[package]] 1319 | name = "pgrx-sql-entity-graph" 1320 | version = "0.13.1" 1321 | source = "registry+https://github.com/rust-lang/crates.io-index" 1322 | checksum = "c8f625bb35d59b2d6f308ed5d1b6da3783c8514d47f353ec23a8f05da0fef6f4" 1323 | dependencies = [ 1324 | "convert_case", 1325 | "eyre", 1326 | "petgraph", 1327 | "proc-macro2", 1328 | "quote", 1329 | "syn 2.0.100", 1330 | "thiserror 2.0.12", 1331 | "unescape", 1332 | ] 1333 | 1334 | [[package]] 1335 | name = "pgrx-tests" 1336 | version = "0.13.1" 1337 | source = "registry+https://github.com/rust-lang/crates.io-index" 1338 | checksum = "da3d8ab6d06831ad303a73e3b940df32792b6b06a2aaae3bdf416f83763fb09d" 1339 | dependencies = [ 1340 | "clap-cargo", 1341 | "eyre", 1342 | "libc", 1343 | "owo-colors", 1344 | "paste", 1345 | "pgrx", 1346 | "pgrx-macros", 1347 | "pgrx-pg-config", 1348 | "postgres", 1349 | "proptest", 1350 | "rand 0.9.0", 1351 | "regex", 1352 | "serde", 1353 | "serde_json", 1354 | "shlex", 1355 | "sysinfo", 1356 | "thiserror 2.0.12", 1357 | ] 1358 | 1359 | [[package]] 1360 | name = "phf" 1361 | version = "0.11.3" 1362 | source = "registry+https://github.com/rust-lang/crates.io-index" 1363 | checksum = "1fd6780a80ae0c52cc120a26a1a42c1ae51b247a253e4e06113d23d2c2edd078" 1364 | dependencies = [ 1365 | "phf_shared", 1366 | ] 1367 | 1368 | [[package]] 1369 | name = "phf_codegen" 1370 | version = "0.11.3" 1371 | source = "registry+https://github.com/rust-lang/crates.io-index" 1372 | checksum = "aef8048c789fa5e851558d709946d6d79a8ff88c0440c587967f8e94bfb1216a" 1373 | dependencies = [ 1374 | "phf_generator", 1375 | "phf_shared", 1376 | ] 1377 | 1378 | [[package]] 1379 | name = "phf_generator" 1380 | version = "0.11.3" 1381 | source = "registry+https://github.com/rust-lang/crates.io-index" 1382 | checksum = "3c80231409c20246a13fddb31776fb942c38553c51e871f8cbd687a4cfb5843d" 1383 | dependencies = [ 1384 | "phf_shared", 1385 | "rand 0.8.5", 1386 | ] 1387 | 1388 | [[package]] 1389 | name = "phf_shared" 1390 | version = "0.11.3" 1391 | source = "registry+https://github.com/rust-lang/crates.io-index" 1392 | checksum = "67eabc2ef2a60eb7faa00097bd1ffdb5bd28e62bf39990626a582201b7a754e5" 1393 | dependencies = [ 1394 | "siphasher", 1395 | ] 1396 | 1397 | [[package]] 1398 | name = "pin-project-lite" 1399 | version = "0.2.16" 1400 | source = "registry+https://github.com/rust-lang/crates.io-index" 1401 | checksum = "3b3cff922bd51709b605d9ead9aa71031d81447142d828eb4a6eba76fe619f9b" 1402 | 1403 | [[package]] 1404 | name = "pin-utils" 1405 | version = "0.1.0" 1406 | source = "registry+https://github.com/rust-lang/crates.io-index" 1407 | checksum = "8b870d8c151b6f2fb93e84a13146138f05d02ed11c7e7c54f8826aaaf7c9f184" 1408 | 1409 | [[package]] 1410 | name = "pipe" 1411 | version = "0.4.0" 1412 | source = "registry+https://github.com/rust-lang/crates.io-index" 1413 | checksum = "1c7b8f27da217eb966df4c58d4159ea939431950ca03cf782c22bd7c5c1d8d75" 1414 | dependencies = [ 1415 | "crossbeam-channel", 1416 | ] 1417 | 1418 | [[package]] 1419 | name = "pkg-config" 1420 | version = "0.3.32" 1421 | source = "registry+https://github.com/rust-lang/crates.io-index" 1422 | checksum = "7edddbd0b52d732b21ad9a5fab5c704c14cd949e5e9a1ec5929a24fded1b904c" 1423 | 1424 | [[package]] 1425 | name = "postgres" 1426 | version = "0.19.10" 1427 | source = "registry+https://github.com/rust-lang/crates.io-index" 1428 | checksum = "363e6dfbdd780d3aa3597b6eb430db76bb315fa9bad7fae595bb8def808b8470" 1429 | dependencies = [ 1430 | "bytes", 1431 | "fallible-iterator", 1432 | "futures-util", 1433 | "log", 1434 | "tokio", 1435 | "tokio-postgres", 1436 | ] 1437 | 1438 | [[package]] 1439 | name = "postgres-ical" 1440 | version = "0.1.0" 1441 | dependencies = [ 1442 | "chrono", 1443 | "curl", 1444 | "pgrx", 1445 | "pgrx-named-columns", 1446 | "pgrx-tests", 1447 | "pipe", 1448 | "postgres-ical-parser", 1449 | "time", 1450 | ] 1451 | 1452 | [[package]] 1453 | name = "postgres-ical-parser" 1454 | version = "0.0.0" 1455 | dependencies = [ 1456 | "chrono", 1457 | "chrono-tz", 1458 | "ical", 1459 | "log", 1460 | "thiserror 2.0.12", 1461 | ] 1462 | 1463 | [[package]] 1464 | name = "postgres-protocol" 1465 | version = "0.6.8" 1466 | source = "registry+https://github.com/rust-lang/crates.io-index" 1467 | checksum = "76ff0abab4a9b844b93ef7b81f1efc0a366062aaef2cd702c76256b5dc075c54" 1468 | dependencies = [ 1469 | "base64", 1470 | "byteorder", 1471 | "bytes", 1472 | "fallible-iterator", 1473 | "hmac", 1474 | "md-5", 1475 | "memchr", 1476 | "rand 0.9.0", 1477 | "sha2", 1478 | "stringprep", 1479 | ] 1480 | 1481 | [[package]] 1482 | name = "postgres-types" 1483 | version = "0.2.9" 1484 | source = "registry+https://github.com/rust-lang/crates.io-index" 1485 | checksum = "613283563cd90e1dfc3518d548caee47e0e725455ed619881f5cf21f36de4b48" 1486 | dependencies = [ 1487 | "bytes", 1488 | "fallible-iterator", 1489 | "postgres-protocol", 1490 | ] 1491 | 1492 | [[package]] 1493 | name = "powerfmt" 1494 | version = "0.2.0" 1495 | source = "registry+https://github.com/rust-lang/crates.io-index" 1496 | checksum = "439ee305def115ba05938db6eb1644ff94165c5ab5e9420d1c1bcedbba909391" 1497 | 1498 | [[package]] 1499 | name = "ppv-lite86" 1500 | version = "0.2.21" 1501 | source = "registry+https://github.com/rust-lang/crates.io-index" 1502 | checksum = "85eae3c4ed2f50dcfe72643da4befc30deadb458a9b590d720cde2f2b1e97da9" 1503 | dependencies = [ 1504 | "zerocopy", 1505 | ] 1506 | 1507 | [[package]] 1508 | name = "proc-macro-error" 1509 | version = "1.0.4" 1510 | source = "registry+https://github.com/rust-lang/crates.io-index" 1511 | checksum = "da25490ff9892aab3fcf7c36f08cfb902dd3e71ca0f9f9517bea02a73a5ce38c" 1512 | dependencies = [ 1513 | "proc-macro-error-attr", 1514 | "proc-macro2", 1515 | "quote", 1516 | "syn 1.0.109", 1517 | "version_check", 1518 | ] 1519 | 1520 | [[package]] 1521 | name = "proc-macro-error-attr" 1522 | version = "1.0.4" 1523 | source = "registry+https://github.com/rust-lang/crates.io-index" 1524 | checksum = "a1be40180e52ecc98ad80b184934baf3d0d29f979574e439af5a55274b35f869" 1525 | dependencies = [ 1526 | "proc-macro2", 1527 | "quote", 1528 | "version_check", 1529 | ] 1530 | 1531 | [[package]] 1532 | name = "proc-macro2" 1533 | version = "1.0.94" 1534 | source = "registry+https://github.com/rust-lang/crates.io-index" 1535 | checksum = "a31971752e70b8b2686d7e46ec17fb38dad4051d94024c88df49b667caea9c84" 1536 | dependencies = [ 1537 | "unicode-ident", 1538 | ] 1539 | 1540 | [[package]] 1541 | name = "proptest" 1542 | version = "1.6.0" 1543 | source = "registry+https://github.com/rust-lang/crates.io-index" 1544 | checksum = "14cae93065090804185d3b75f0bf93b8eeda30c7a9b4a33d3bdb3988d6229e50" 1545 | dependencies = [ 1546 | "bit-set", 1547 | "bit-vec", 1548 | "bitflags", 1549 | "lazy_static", 1550 | "num-traits", 1551 | "rand 0.8.5", 1552 | "rand_chacha 0.3.1", 1553 | "rand_xorshift", 1554 | "regex-syntax", 1555 | "rusty-fork", 1556 | "tempfile", 1557 | "unarray", 1558 | ] 1559 | 1560 | [[package]] 1561 | name = "quick-error" 1562 | version = "1.2.3" 1563 | source = "registry+https://github.com/rust-lang/crates.io-index" 1564 | checksum = "a1d01941d82fa2ab50be1e79e6714289dd7cde78eba4c074bc5a4374f650dfe0" 1565 | 1566 | [[package]] 1567 | name = "quote" 1568 | version = "1.0.40" 1569 | source = "registry+https://github.com/rust-lang/crates.io-index" 1570 | checksum = "1885c039570dc00dcb4ff087a89e185fd56bae234ddc7f056a945bf36467248d" 1571 | dependencies = [ 1572 | "proc-macro2", 1573 | ] 1574 | 1575 | [[package]] 1576 | name = "r-efi" 1577 | version = "5.2.0" 1578 | source = "registry+https://github.com/rust-lang/crates.io-index" 1579 | checksum = "74765f6d916ee2faa39bc8e68e4f3ed8949b48cccdac59983d287a7cb71ce9c5" 1580 | 1581 | [[package]] 1582 | name = "radium" 1583 | version = "0.7.0" 1584 | source = "registry+https://github.com/rust-lang/crates.io-index" 1585 | checksum = "dc33ff2d4973d518d823d61aa239014831e521c75da58e3df4840d3f47749d09" 1586 | 1587 | [[package]] 1588 | name = "rand" 1589 | version = "0.8.5" 1590 | source = "registry+https://github.com/rust-lang/crates.io-index" 1591 | checksum = "34af8d1a0e25924bc5b7c43c079c942339d8f0a8b57c39049bef581b46327404" 1592 | dependencies = [ 1593 | "libc", 1594 | "rand_chacha 0.3.1", 1595 | "rand_core 0.6.4", 1596 | ] 1597 | 1598 | [[package]] 1599 | name = "rand" 1600 | version = "0.9.0" 1601 | source = "registry+https://github.com/rust-lang/crates.io-index" 1602 | checksum = "3779b94aeb87e8bd4e834cee3650289ee9e0d5677f976ecdb6d219e5f4f6cd94" 1603 | dependencies = [ 1604 | "rand_chacha 0.9.0", 1605 | "rand_core 0.9.3", 1606 | "zerocopy", 1607 | ] 1608 | 1609 | [[package]] 1610 | name = "rand_chacha" 1611 | version = "0.3.1" 1612 | source = "registry+https://github.com/rust-lang/crates.io-index" 1613 | checksum = "e6c10a63a0fa32252be49d21e7709d4d4baf8d231c2dbce1eaa8141b9b127d88" 1614 | dependencies = [ 1615 | "ppv-lite86", 1616 | "rand_core 0.6.4", 1617 | ] 1618 | 1619 | [[package]] 1620 | name = "rand_chacha" 1621 | version = "0.9.0" 1622 | source = "registry+https://github.com/rust-lang/crates.io-index" 1623 | checksum = "d3022b5f1df60f26e1ffddd6c66e8aa15de382ae63b3a0c1bfc0e4d3e3f325cb" 1624 | dependencies = [ 1625 | "ppv-lite86", 1626 | "rand_core 0.9.3", 1627 | ] 1628 | 1629 | [[package]] 1630 | name = "rand_core" 1631 | version = "0.6.4" 1632 | source = "registry+https://github.com/rust-lang/crates.io-index" 1633 | checksum = "ec0be4795e2f6a28069bec0b5ff3e2ac9bafc99e6a9a7dc3547996c5c816922c" 1634 | dependencies = [ 1635 | "getrandom 0.2.15", 1636 | ] 1637 | 1638 | [[package]] 1639 | name = "rand_core" 1640 | version = "0.9.3" 1641 | source = "registry+https://github.com/rust-lang/crates.io-index" 1642 | checksum = "99d9a13982dcf210057a8a78572b2217b667c3beacbf3a0d8b454f6f82837d38" 1643 | dependencies = [ 1644 | "getrandom 0.3.2", 1645 | ] 1646 | 1647 | [[package]] 1648 | name = "rand_xorshift" 1649 | version = "0.3.0" 1650 | source = "registry+https://github.com/rust-lang/crates.io-index" 1651 | checksum = "d25bf25ec5ae4a3f1b92f929810509a2f53d7dca2f50b794ff57e3face536c8f" 1652 | dependencies = [ 1653 | "rand_core 0.6.4", 1654 | ] 1655 | 1656 | [[package]] 1657 | name = "rayon" 1658 | version = "1.10.0" 1659 | source = "registry+https://github.com/rust-lang/crates.io-index" 1660 | checksum = "b418a60154510ca1a002a752ca9714984e21e4241e804d32555251faf8b78ffa" 1661 | dependencies = [ 1662 | "either", 1663 | "rayon-core", 1664 | ] 1665 | 1666 | [[package]] 1667 | name = "rayon-core" 1668 | version = "1.12.1" 1669 | source = "registry+https://github.com/rust-lang/crates.io-index" 1670 | checksum = "1465873a3dfdaa8ae7cb14b4383657caab0b3e8a0aa9ae8e04b044854c8dfce2" 1671 | dependencies = [ 1672 | "crossbeam-deque", 1673 | "crossbeam-utils", 1674 | ] 1675 | 1676 | [[package]] 1677 | name = "redox_syscall" 1678 | version = "0.5.10" 1679 | source = "registry+https://github.com/rust-lang/crates.io-index" 1680 | checksum = "0b8c0c260b63a8219631167be35e6a988e9554dbd323f8bd08439c8ed1302bd1" 1681 | dependencies = [ 1682 | "bitflags", 1683 | ] 1684 | 1685 | [[package]] 1686 | name = "regex" 1687 | version = "1.11.1" 1688 | source = "registry+https://github.com/rust-lang/crates.io-index" 1689 | checksum = "b544ef1b4eac5dc2db33ea63606ae9ffcfac26c1416a2806ae0bf5f56b201191" 1690 | dependencies = [ 1691 | "aho-corasick", 1692 | "memchr", 1693 | "regex-automata", 1694 | "regex-syntax", 1695 | ] 1696 | 1697 | [[package]] 1698 | name = "regex-automata" 1699 | version = "0.4.9" 1700 | source = "registry+https://github.com/rust-lang/crates.io-index" 1701 | checksum = "809e8dc61f6de73b46c85f4c96486310fe304c434cfa43669d7b40f711150908" 1702 | dependencies = [ 1703 | "aho-corasick", 1704 | "memchr", 1705 | "regex-syntax", 1706 | ] 1707 | 1708 | [[package]] 1709 | name = "regex-syntax" 1710 | version = "0.8.5" 1711 | source = "registry+https://github.com/rust-lang/crates.io-index" 1712 | checksum = "2b15c43186be67a4fd63bee50d0303afffcef381492ebe2c5d87f324e1b8815c" 1713 | 1714 | [[package]] 1715 | name = "rustc-demangle" 1716 | version = "0.1.24" 1717 | source = "registry+https://github.com/rust-lang/crates.io-index" 1718 | checksum = "719b953e2095829ee67db738b3bfa9fa368c94900df327b3f07fe6e794d2fe1f" 1719 | 1720 | [[package]] 1721 | name = "rustc-hash" 1722 | version = "2.1.1" 1723 | source = "registry+https://github.com/rust-lang/crates.io-index" 1724 | checksum = "357703d41365b4b27c590e3ed91eabb1b663f07c4c084095e60cbed4362dff0d" 1725 | 1726 | [[package]] 1727 | name = "rustc_version" 1728 | version = "0.4.1" 1729 | source = "registry+https://github.com/rust-lang/crates.io-index" 1730 | checksum = "cfcb3a22ef46e85b45de6ee7e79d063319ebb6594faafcf1c225ea92ab6e9b92" 1731 | dependencies = [ 1732 | "semver", 1733 | ] 1734 | 1735 | [[package]] 1736 | name = "rustix" 1737 | version = "1.0.3" 1738 | source = "registry+https://github.com/rust-lang/crates.io-index" 1739 | checksum = "e56a18552996ac8d29ecc3b190b4fdbb2d91ca4ec396de7bbffaf43f3d637e96" 1740 | dependencies = [ 1741 | "bitflags", 1742 | "errno", 1743 | "libc", 1744 | "linux-raw-sys", 1745 | "windows-sys 0.59.0", 1746 | ] 1747 | 1748 | [[package]] 1749 | name = "rustversion" 1750 | version = "1.0.20" 1751 | source = "registry+https://github.com/rust-lang/crates.io-index" 1752 | checksum = "eded382c5f5f786b989652c49544c4877d9f015cc22e145a5ea8ea66c2921cd2" 1753 | 1754 | [[package]] 1755 | name = "rusty-fork" 1756 | version = "0.3.0" 1757 | source = "registry+https://github.com/rust-lang/crates.io-index" 1758 | checksum = "cb3dcc6e454c328bb824492db107ab7c0ae8fcffe4ad210136ef014458c1bc4f" 1759 | dependencies = [ 1760 | "fnv", 1761 | "quick-error", 1762 | "tempfile", 1763 | "wait-timeout", 1764 | ] 1765 | 1766 | [[package]] 1767 | name = "ryu" 1768 | version = "1.0.20" 1769 | source = "registry+https://github.com/rust-lang/crates.io-index" 1770 | checksum = "28d3b2b1366ec20994f1fd18c3c594f05c5dd4bc44d8bb0c1c632c8d6829481f" 1771 | 1772 | [[package]] 1773 | name = "same-file" 1774 | version = "1.0.6" 1775 | source = "registry+https://github.com/rust-lang/crates.io-index" 1776 | checksum = "93fc1dc3aaa9bfed95e02e6eadabb4baf7e3078b0bd1b4d7b6b0b68378900502" 1777 | dependencies = [ 1778 | "winapi-util", 1779 | ] 1780 | 1781 | [[package]] 1782 | name = "schannel" 1783 | version = "0.1.27" 1784 | source = "registry+https://github.com/rust-lang/crates.io-index" 1785 | checksum = "1f29ebaa345f945cec9fbbc532eb307f0fdad8161f281b6369539c8d84876b3d" 1786 | dependencies = [ 1787 | "windows-sys 0.59.0", 1788 | ] 1789 | 1790 | [[package]] 1791 | name = "scopeguard" 1792 | version = "1.2.0" 1793 | source = "registry+https://github.com/rust-lang/crates.io-index" 1794 | checksum = "94143f37725109f92c262ed2cf5e59bce7498c01bcc1502d7b9afe439a4e9f49" 1795 | 1796 | [[package]] 1797 | name = "seahash" 1798 | version = "4.1.0" 1799 | source = "registry+https://github.com/rust-lang/crates.io-index" 1800 | checksum = "1c107b6f4780854c8b126e228ea8869f4d7b71260f962fefb57b996b8959ba6b" 1801 | 1802 | [[package]] 1803 | name = "semver" 1804 | version = "1.0.26" 1805 | source = "registry+https://github.com/rust-lang/crates.io-index" 1806 | checksum = "56e6fa9c48d24d85fb3de5ad847117517440f6beceb7798af16b4a87d616b8d0" 1807 | dependencies = [ 1808 | "serde", 1809 | ] 1810 | 1811 | [[package]] 1812 | name = "serde" 1813 | version = "1.0.219" 1814 | source = "registry+https://github.com/rust-lang/crates.io-index" 1815 | checksum = "5f0e2c6ed6606019b4e29e69dbaba95b11854410e5347d525002456dbbb786b6" 1816 | dependencies = [ 1817 | "serde_derive", 1818 | ] 1819 | 1820 | [[package]] 1821 | name = "serde_cbor" 1822 | version = "0.11.2" 1823 | source = "registry+https://github.com/rust-lang/crates.io-index" 1824 | checksum = "2bef2ebfde456fb76bbcf9f59315333decc4fda0b2b44b420243c11e0f5ec1f5" 1825 | dependencies = [ 1826 | "half", 1827 | "serde", 1828 | ] 1829 | 1830 | [[package]] 1831 | name = "serde_derive" 1832 | version = "1.0.219" 1833 | source = "registry+https://github.com/rust-lang/crates.io-index" 1834 | checksum = "5b0276cf7f2c73365f7157c8123c21cd9a50fbbd844757af28ca1f5925fc2a00" 1835 | dependencies = [ 1836 | "proc-macro2", 1837 | "quote", 1838 | "syn 2.0.100", 1839 | ] 1840 | 1841 | [[package]] 1842 | name = "serde_json" 1843 | version = "1.0.140" 1844 | source = "registry+https://github.com/rust-lang/crates.io-index" 1845 | checksum = "20068b6e96dc6c9bd23e01df8827e6c7e1f2fddd43c21810382803c136b99373" 1846 | dependencies = [ 1847 | "itoa", 1848 | "memchr", 1849 | "ryu", 1850 | "serde", 1851 | ] 1852 | 1853 | [[package]] 1854 | name = "serde_spanned" 1855 | version = "0.6.8" 1856 | source = "registry+https://github.com/rust-lang/crates.io-index" 1857 | checksum = "87607cb1398ed59d48732e575a4c28a7a8ebf2454b964fe3f224f2afc07909e1" 1858 | dependencies = [ 1859 | "serde", 1860 | ] 1861 | 1862 | [[package]] 1863 | name = "sha2" 1864 | version = "0.10.8" 1865 | source = "registry+https://github.com/rust-lang/crates.io-index" 1866 | checksum = "793db75ad2bcafc3ffa7c68b215fee268f537982cd901d132f89c6343f3a3dc8" 1867 | dependencies = [ 1868 | "cfg-if", 1869 | "cpufeatures", 1870 | "digest", 1871 | ] 1872 | 1873 | [[package]] 1874 | name = "shlex" 1875 | version = "1.3.0" 1876 | source = "registry+https://github.com/rust-lang/crates.io-index" 1877 | checksum = "0fda2ff0d084019ba4d7c6f371c95d8fd75ce3524c3cb8fb653a3023f6323e64" 1878 | 1879 | [[package]] 1880 | name = "siphasher" 1881 | version = "1.0.1" 1882 | source = "registry+https://github.com/rust-lang/crates.io-index" 1883 | checksum = "56199f7ddabf13fe5074ce809e7d3f42b42ae711800501b5b16ea82ad029c39d" 1884 | 1885 | [[package]] 1886 | name = "slab" 1887 | version = "0.4.9" 1888 | source = "registry+https://github.com/rust-lang/crates.io-index" 1889 | checksum = "8f92a496fb766b417c996b9c5e57daf2f7ad3b0bebe1ccfca4856390e3d3bb67" 1890 | dependencies = [ 1891 | "autocfg", 1892 | ] 1893 | 1894 | [[package]] 1895 | name = "smallvec" 1896 | version = "1.14.0" 1897 | source = "registry+https://github.com/rust-lang/crates.io-index" 1898 | checksum = "7fcf8323ef1faaee30a44a340193b1ac6814fd9b7b4e88e9d4519a3e4abe1cfd" 1899 | 1900 | [[package]] 1901 | name = "socket2" 1902 | version = "0.5.9" 1903 | source = "registry+https://github.com/rust-lang/crates.io-index" 1904 | checksum = "4f5fd57c80058a56cf5c777ab8a126398ece8e442983605d280a44ce79d0edef" 1905 | dependencies = [ 1906 | "libc", 1907 | "windows-sys 0.52.0", 1908 | ] 1909 | 1910 | [[package]] 1911 | name = "sptr" 1912 | version = "0.3.2" 1913 | source = "registry+https://github.com/rust-lang/crates.io-index" 1914 | checksum = "3b9b39299b249ad65f3b7e96443bad61c02ca5cd3589f46cb6d610a0fd6c0d6a" 1915 | 1916 | [[package]] 1917 | name = "stable_deref_trait" 1918 | version = "1.2.0" 1919 | source = "registry+https://github.com/rust-lang/crates.io-index" 1920 | checksum = "a8f112729512f8e442d81f95a8a7ddf2b7c6b8a1a6f509a95864142b30cab2d3" 1921 | 1922 | [[package]] 1923 | name = "stringprep" 1924 | version = "0.1.5" 1925 | source = "registry+https://github.com/rust-lang/crates.io-index" 1926 | checksum = "7b4df3d392d81bd458a8a621b8bffbd2302a12ffe288a9d931670948749463b1" 1927 | dependencies = [ 1928 | "unicode-bidi", 1929 | "unicode-normalization", 1930 | "unicode-properties", 1931 | ] 1932 | 1933 | [[package]] 1934 | name = "subtle" 1935 | version = "2.6.1" 1936 | source = "registry+https://github.com/rust-lang/crates.io-index" 1937 | checksum = "13c2bddecc57b384dee18652358fb23172facb8a2c51ccc10d74c157bdea3292" 1938 | 1939 | [[package]] 1940 | name = "supports-color" 1941 | version = "2.1.0" 1942 | source = "registry+https://github.com/rust-lang/crates.io-index" 1943 | checksum = "d6398cde53adc3c4557306a96ce67b302968513830a77a95b2b17305d9719a89" 1944 | dependencies = [ 1945 | "is-terminal", 1946 | "is_ci", 1947 | ] 1948 | 1949 | [[package]] 1950 | name = "supports-color" 1951 | version = "3.0.2" 1952 | source = "registry+https://github.com/rust-lang/crates.io-index" 1953 | checksum = "c64fc7232dd8d2e4ac5ce4ef302b1d81e0b80d055b9d77c7c4f51f6aa4c867d6" 1954 | dependencies = [ 1955 | "is_ci", 1956 | ] 1957 | 1958 | [[package]] 1959 | name = "syn" 1960 | version = "1.0.109" 1961 | source = "registry+https://github.com/rust-lang/crates.io-index" 1962 | checksum = "72b64191b275b66ffe2469e8af2c1cfe3bafa67b529ead792a6d0160888b4237" 1963 | dependencies = [ 1964 | "proc-macro2", 1965 | "unicode-ident", 1966 | ] 1967 | 1968 | [[package]] 1969 | name = "syn" 1970 | version = "2.0.100" 1971 | source = "registry+https://github.com/rust-lang/crates.io-index" 1972 | checksum = "b09a44accad81e1ba1cd74a32461ba89dee89095ba17b32f5d03683b1b1fc2a0" 1973 | dependencies = [ 1974 | "proc-macro2", 1975 | "quote", 1976 | "unicode-ident", 1977 | ] 1978 | 1979 | [[package]] 1980 | name = "synstructure" 1981 | version = "0.13.1" 1982 | source = "registry+https://github.com/rust-lang/crates.io-index" 1983 | checksum = "c8af7666ab7b6390ab78131fb5b0fce11d6b7a6951602017c35fa82800708971" 1984 | dependencies = [ 1985 | "proc-macro2", 1986 | "quote", 1987 | "syn 2.0.100", 1988 | ] 1989 | 1990 | [[package]] 1991 | name = "sysinfo" 1992 | version = "0.33.1" 1993 | source = "registry+https://github.com/rust-lang/crates.io-index" 1994 | checksum = "4fc858248ea01b66f19d8e8a6d55f41deaf91e9d495246fd01368d99935c6c01" 1995 | dependencies = [ 1996 | "core-foundation-sys", 1997 | "libc", 1998 | "memchr", 1999 | "ntapi", 2000 | "rayon", 2001 | "windows", 2002 | ] 2003 | 2004 | [[package]] 2005 | name = "tap" 2006 | version = "1.0.1" 2007 | source = "registry+https://github.com/rust-lang/crates.io-index" 2008 | checksum = "55937e1799185b12863d447f42597ed69d9928686b8d88a1df17376a097d8369" 2009 | 2010 | [[package]] 2011 | name = "tempfile" 2012 | version = "3.19.1" 2013 | source = "registry+https://github.com/rust-lang/crates.io-index" 2014 | checksum = "7437ac7763b9b123ccf33c338a5cc1bac6f69b45a136c19bdd8a65e3916435bf" 2015 | dependencies = [ 2016 | "fastrand", 2017 | "getrandom 0.3.2", 2018 | "once_cell", 2019 | "rustix", 2020 | "windows-sys 0.59.0", 2021 | ] 2022 | 2023 | [[package]] 2024 | name = "thiserror" 2025 | version = "1.0.69" 2026 | source = "registry+https://github.com/rust-lang/crates.io-index" 2027 | checksum = "b6aaf5339b578ea85b50e080feb250a3e8ae8cfcdff9a461c9ec2904bc923f52" 2028 | dependencies = [ 2029 | "thiserror-impl 1.0.69", 2030 | ] 2031 | 2032 | [[package]] 2033 | name = "thiserror" 2034 | version = "2.0.12" 2035 | source = "registry+https://github.com/rust-lang/crates.io-index" 2036 | checksum = "567b8a2dae586314f7be2a752ec7474332959c6460e02bde30d702a66d488708" 2037 | dependencies = [ 2038 | "thiserror-impl 2.0.12", 2039 | ] 2040 | 2041 | [[package]] 2042 | name = "thiserror-impl" 2043 | version = "1.0.69" 2044 | source = "registry+https://github.com/rust-lang/crates.io-index" 2045 | checksum = "4fee6c4efc90059e10f81e6d42c60a18f76588c3d74cb83a0b242a2b6c7504c1" 2046 | dependencies = [ 2047 | "proc-macro2", 2048 | "quote", 2049 | "syn 2.0.100", 2050 | ] 2051 | 2052 | [[package]] 2053 | name = "thiserror-impl" 2054 | version = "2.0.12" 2055 | source = "registry+https://github.com/rust-lang/crates.io-index" 2056 | checksum = "7f7cf42b4507d8ea322120659672cf1b9dbb93f8f2d4ecfd6e51350ff5b17a1d" 2057 | dependencies = [ 2058 | "proc-macro2", 2059 | "quote", 2060 | "syn 2.0.100", 2061 | ] 2062 | 2063 | [[package]] 2064 | name = "time" 2065 | version = "0.3.41" 2066 | source = "registry+https://github.com/rust-lang/crates.io-index" 2067 | checksum = "8a7619e19bc266e0f9c5e6686659d394bc57973859340060a69221e57dbc0c40" 2068 | dependencies = [ 2069 | "deranged", 2070 | "num-conv", 2071 | "powerfmt", 2072 | "serde", 2073 | "time-core", 2074 | ] 2075 | 2076 | [[package]] 2077 | name = "time-core" 2078 | version = "0.1.4" 2079 | source = "registry+https://github.com/rust-lang/crates.io-index" 2080 | checksum = "c9e9a38711f559d9e3ce1cdb06dd7c5b8ea546bc90052da6d06bb76da74bb07c" 2081 | 2082 | [[package]] 2083 | name = "tinystr" 2084 | version = "0.7.6" 2085 | source = "registry+https://github.com/rust-lang/crates.io-index" 2086 | checksum = "9117f5d4db391c1cf6927e7bea3db74b9a1c1add8f7eda9ffd5364f40f57b82f" 2087 | dependencies = [ 2088 | "displaydoc", 2089 | "zerovec", 2090 | ] 2091 | 2092 | [[package]] 2093 | name = "tinyvec" 2094 | version = "1.9.0" 2095 | source = "registry+https://github.com/rust-lang/crates.io-index" 2096 | checksum = "09b3661f17e86524eccd4371ab0429194e0d7c008abb45f7a7495b1719463c71" 2097 | dependencies = [ 2098 | "tinyvec_macros", 2099 | ] 2100 | 2101 | [[package]] 2102 | name = "tinyvec_macros" 2103 | version = "0.1.1" 2104 | source = "registry+https://github.com/rust-lang/crates.io-index" 2105 | checksum = "1f3ccbac311fea05f86f61904b462b55fb3df8837a366dfc601a0161d0532f20" 2106 | 2107 | [[package]] 2108 | name = "tokio" 2109 | version = "1.44.1" 2110 | source = "registry+https://github.com/rust-lang/crates.io-index" 2111 | checksum = "f382da615b842244d4b8738c82ed1275e6c5dd90c459a30941cd07080b06c91a" 2112 | dependencies = [ 2113 | "backtrace", 2114 | "bytes", 2115 | "libc", 2116 | "mio", 2117 | "pin-project-lite", 2118 | "socket2", 2119 | "windows-sys 0.52.0", 2120 | ] 2121 | 2122 | [[package]] 2123 | name = "tokio-postgres" 2124 | version = "0.7.13" 2125 | source = "registry+https://github.com/rust-lang/crates.io-index" 2126 | checksum = "6c95d533c83082bb6490e0189acaa0bbeef9084e60471b696ca6988cd0541fb0" 2127 | dependencies = [ 2128 | "async-trait", 2129 | "byteorder", 2130 | "bytes", 2131 | "fallible-iterator", 2132 | "futures-channel", 2133 | "futures-util", 2134 | "log", 2135 | "parking_lot", 2136 | "percent-encoding", 2137 | "phf", 2138 | "pin-project-lite", 2139 | "postgres-protocol", 2140 | "postgres-types", 2141 | "rand 0.9.0", 2142 | "socket2", 2143 | "tokio", 2144 | "tokio-util", 2145 | "whoami", 2146 | ] 2147 | 2148 | [[package]] 2149 | name = "tokio-util" 2150 | version = "0.7.14" 2151 | source = "registry+https://github.com/rust-lang/crates.io-index" 2152 | checksum = "6b9590b93e6fcc1739458317cccd391ad3955e2bde8913edf6f95f9e65a8f034" 2153 | dependencies = [ 2154 | "bytes", 2155 | "futures-core", 2156 | "futures-sink", 2157 | "pin-project-lite", 2158 | "tokio", 2159 | ] 2160 | 2161 | [[package]] 2162 | name = "toml" 2163 | version = "0.8.20" 2164 | source = "registry+https://github.com/rust-lang/crates.io-index" 2165 | checksum = "cd87a5cdd6ffab733b2f74bc4fd7ee5fff6634124999ac278c35fc78c6120148" 2166 | dependencies = [ 2167 | "serde", 2168 | "serde_spanned", 2169 | "toml_datetime", 2170 | "toml_edit", 2171 | ] 2172 | 2173 | [[package]] 2174 | name = "toml_datetime" 2175 | version = "0.6.8" 2176 | source = "registry+https://github.com/rust-lang/crates.io-index" 2177 | checksum = "0dd7358ecb8fc2f8d014bf86f6f638ce72ba252a2c3a2572f2a795f1d23efb41" 2178 | dependencies = [ 2179 | "serde", 2180 | ] 2181 | 2182 | [[package]] 2183 | name = "toml_edit" 2184 | version = "0.22.24" 2185 | source = "registry+https://github.com/rust-lang/crates.io-index" 2186 | checksum = "17b4795ff5edd201c7cd6dca065ae59972ce77d1b80fa0a84d94950ece7d1474" 2187 | dependencies = [ 2188 | "indexmap", 2189 | "serde", 2190 | "serde_spanned", 2191 | "toml_datetime", 2192 | "winnow", 2193 | ] 2194 | 2195 | [[package]] 2196 | name = "typenum" 2197 | version = "1.18.0" 2198 | source = "registry+https://github.com/rust-lang/crates.io-index" 2199 | checksum = "1dccffe3ce07af9386bfd29e80c0ab1a8205a2fc34e4bcd40364df902cfa8f3f" 2200 | 2201 | [[package]] 2202 | name = "unarray" 2203 | version = "0.1.4" 2204 | source = "registry+https://github.com/rust-lang/crates.io-index" 2205 | checksum = "eaea85b334db583fe3274d12b4cd1880032beab409c0d774be044d4480ab9a94" 2206 | 2207 | [[package]] 2208 | name = "unescape" 2209 | version = "0.1.0" 2210 | source = "registry+https://github.com/rust-lang/crates.io-index" 2211 | checksum = "ccb97dac3243214f8d8507998906ca3e2e0b900bf9bf4870477f125b82e68f6e" 2212 | 2213 | [[package]] 2214 | name = "unicode-bidi" 2215 | version = "0.3.18" 2216 | source = "registry+https://github.com/rust-lang/crates.io-index" 2217 | checksum = "5c1cb5db39152898a79168971543b1cb5020dff7fe43c8dc468b0885f5e29df5" 2218 | 2219 | [[package]] 2220 | name = "unicode-ident" 2221 | version = "1.0.18" 2222 | source = "registry+https://github.com/rust-lang/crates.io-index" 2223 | checksum = "5a5f39404a5da50712a4c1eecf25e90dd62b613502b7e925fd4e4d19b5c96512" 2224 | 2225 | [[package]] 2226 | name = "unicode-normalization" 2227 | version = "0.1.24" 2228 | source = "registry+https://github.com/rust-lang/crates.io-index" 2229 | checksum = "5033c97c4262335cded6d6fc3e5c18ab755e1a3dc96376350f3d8e9f009ad956" 2230 | dependencies = [ 2231 | "tinyvec", 2232 | ] 2233 | 2234 | [[package]] 2235 | name = "unicode-properties" 2236 | version = "0.1.3" 2237 | source = "registry+https://github.com/rust-lang/crates.io-index" 2238 | checksum = "e70f2a8b45122e719eb623c01822704c4e0907e7e426a05927e1a1cfff5b75d0" 2239 | 2240 | [[package]] 2241 | name = "unicode-segmentation" 2242 | version = "1.12.0" 2243 | source = "registry+https://github.com/rust-lang/crates.io-index" 2244 | checksum = "f6ccf251212114b54433ec949fd6a7841275f9ada20dddd2f29e9ceea4501493" 2245 | 2246 | [[package]] 2247 | name = "unicode-width" 2248 | version = "0.2.0" 2249 | source = "registry+https://github.com/rust-lang/crates.io-index" 2250 | checksum = "1fc81956842c57dac11422a97c3b8195a1ff727f06e85c84ed2e8aa277c9a0fd" 2251 | 2252 | [[package]] 2253 | name = "url" 2254 | version = "2.5.4" 2255 | source = "registry+https://github.com/rust-lang/crates.io-index" 2256 | checksum = "32f8b686cadd1473f4bd0117a5d28d36b1ade384ea9b5069a1c40aefed7fda60" 2257 | dependencies = [ 2258 | "form_urlencoded", 2259 | "idna", 2260 | "percent-encoding", 2261 | ] 2262 | 2263 | [[package]] 2264 | name = "utf16_iter" 2265 | version = "1.0.5" 2266 | source = "registry+https://github.com/rust-lang/crates.io-index" 2267 | checksum = "c8232dd3cdaed5356e0f716d285e4b40b932ac434100fe9b7e0e8e935b9e6246" 2268 | 2269 | [[package]] 2270 | name = "utf8_iter" 2271 | version = "1.0.4" 2272 | source = "registry+https://github.com/rust-lang/crates.io-index" 2273 | checksum = "b6c140620e7ffbb22c2dee59cafe6084a59b5ffc27a8859a5f0d494b5d52b6be" 2274 | 2275 | [[package]] 2276 | name = "uuid" 2277 | version = "1.16.0" 2278 | source = "registry+https://github.com/rust-lang/crates.io-index" 2279 | checksum = "458f7a779bf54acc9f347480ac654f68407d3aab21269a6e3c9f922acd9e2da9" 2280 | dependencies = [ 2281 | "getrandom 0.3.2", 2282 | ] 2283 | 2284 | [[package]] 2285 | name = "vcpkg" 2286 | version = "0.2.15" 2287 | source = "registry+https://github.com/rust-lang/crates.io-index" 2288 | checksum = "accd4ea62f7bb7a82fe23066fb0957d48ef677f6eeb8215f372f52e48bb32426" 2289 | 2290 | [[package]] 2291 | name = "version_check" 2292 | version = "0.9.5" 2293 | source = "registry+https://github.com/rust-lang/crates.io-index" 2294 | checksum = "0b928f33d975fc6ad9f86c8f283853ad26bdd5b10b7f1542aa2fa15e2289105a" 2295 | 2296 | [[package]] 2297 | name = "wait-timeout" 2298 | version = "0.2.1" 2299 | source = "registry+https://github.com/rust-lang/crates.io-index" 2300 | checksum = "09ac3b126d3914f9849036f826e054cbabdc8519970b8998ddaf3b5bd3c65f11" 2301 | dependencies = [ 2302 | "libc", 2303 | ] 2304 | 2305 | [[package]] 2306 | name = "walkdir" 2307 | version = "2.5.0" 2308 | source = "registry+https://github.com/rust-lang/crates.io-index" 2309 | checksum = "29790946404f91d9c5d06f9874efddea1dc06c5efe94541a7d6863108e3a5e4b" 2310 | dependencies = [ 2311 | "same-file", 2312 | "winapi-util", 2313 | ] 2314 | 2315 | [[package]] 2316 | name = "wasi" 2317 | version = "0.11.0+wasi-snapshot-preview1" 2318 | source = "registry+https://github.com/rust-lang/crates.io-index" 2319 | checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" 2320 | 2321 | [[package]] 2322 | name = "wasi" 2323 | version = "0.14.2+wasi-0.2.4" 2324 | source = "registry+https://github.com/rust-lang/crates.io-index" 2325 | checksum = "9683f9a5a998d873c0d21fcbe3c083009670149a8fab228644b8bd36b2c48cb3" 2326 | dependencies = [ 2327 | "wit-bindgen-rt", 2328 | ] 2329 | 2330 | [[package]] 2331 | name = "wasite" 2332 | version = "0.1.0" 2333 | source = "registry+https://github.com/rust-lang/crates.io-index" 2334 | checksum = "b8dad83b4f25e74f184f64c43b150b91efe7647395b42289f38e50566d82855b" 2335 | 2336 | [[package]] 2337 | name = "wasm-bindgen" 2338 | version = "0.2.100" 2339 | source = "registry+https://github.com/rust-lang/crates.io-index" 2340 | checksum = "1edc8929d7499fc4e8f0be2262a241556cfc54a0bea223790e71446f2aab1ef5" 2341 | dependencies = [ 2342 | "cfg-if", 2343 | "once_cell", 2344 | "rustversion", 2345 | "wasm-bindgen-macro", 2346 | ] 2347 | 2348 | [[package]] 2349 | name = "wasm-bindgen-backend" 2350 | version = "0.2.100" 2351 | source = "registry+https://github.com/rust-lang/crates.io-index" 2352 | checksum = "2f0a0651a5c2bc21487bde11ee802ccaf4c51935d0d3d42a6101f98161700bc6" 2353 | dependencies = [ 2354 | "bumpalo", 2355 | "log", 2356 | "proc-macro2", 2357 | "quote", 2358 | "syn 2.0.100", 2359 | "wasm-bindgen-shared", 2360 | ] 2361 | 2362 | [[package]] 2363 | name = "wasm-bindgen-macro" 2364 | version = "0.2.100" 2365 | source = "registry+https://github.com/rust-lang/crates.io-index" 2366 | checksum = "7fe63fc6d09ed3792bd0897b314f53de8e16568c2b3f7982f468c0bf9bd0b407" 2367 | dependencies = [ 2368 | "quote", 2369 | "wasm-bindgen-macro-support", 2370 | ] 2371 | 2372 | [[package]] 2373 | name = "wasm-bindgen-macro-support" 2374 | version = "0.2.100" 2375 | source = "registry+https://github.com/rust-lang/crates.io-index" 2376 | checksum = "8ae87ea40c9f689fc23f209965b6fb8a99ad69aeeb0231408be24920604395de" 2377 | dependencies = [ 2378 | "proc-macro2", 2379 | "quote", 2380 | "syn 2.0.100", 2381 | "wasm-bindgen-backend", 2382 | "wasm-bindgen-shared", 2383 | ] 2384 | 2385 | [[package]] 2386 | name = "wasm-bindgen-shared" 2387 | version = "0.2.100" 2388 | source = "registry+https://github.com/rust-lang/crates.io-index" 2389 | checksum = "1a05d73b933a847d6cccdda8f838a22ff101ad9bf93e33684f39c1f5f0eece3d" 2390 | dependencies = [ 2391 | "unicode-ident", 2392 | ] 2393 | 2394 | [[package]] 2395 | name = "web-sys" 2396 | version = "0.3.77" 2397 | source = "registry+https://github.com/rust-lang/crates.io-index" 2398 | checksum = "33b6dd2ef9186f1f2072e409e99cd22a975331a6b3591b12c764e0e55c60d5d2" 2399 | dependencies = [ 2400 | "js-sys", 2401 | "wasm-bindgen", 2402 | ] 2403 | 2404 | [[package]] 2405 | name = "whoami" 2406 | version = "1.6.0" 2407 | source = "registry+https://github.com/rust-lang/crates.io-index" 2408 | checksum = "6994d13118ab492c3c80c1f81928718159254c53c472bf9ce36f8dae4add02a7" 2409 | dependencies = [ 2410 | "redox_syscall", 2411 | "wasite", 2412 | "web-sys", 2413 | ] 2414 | 2415 | [[package]] 2416 | name = "winapi" 2417 | version = "0.3.9" 2418 | source = "registry+https://github.com/rust-lang/crates.io-index" 2419 | checksum = "5c839a674fcd7a98952e593242ea400abe93992746761e38641405d28b00f419" 2420 | dependencies = [ 2421 | "winapi-i686-pc-windows-gnu", 2422 | "winapi-x86_64-pc-windows-gnu", 2423 | ] 2424 | 2425 | [[package]] 2426 | name = "winapi-i686-pc-windows-gnu" 2427 | version = "0.4.0" 2428 | source = "registry+https://github.com/rust-lang/crates.io-index" 2429 | checksum = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6" 2430 | 2431 | [[package]] 2432 | name = "winapi-util" 2433 | version = "0.1.9" 2434 | source = "registry+https://github.com/rust-lang/crates.io-index" 2435 | checksum = "cf221c93e13a30d793f7645a0e7762c55d169dbb0a49671918a2319d289b10bb" 2436 | dependencies = [ 2437 | "windows-sys 0.59.0", 2438 | ] 2439 | 2440 | [[package]] 2441 | name = "winapi-x86_64-pc-windows-gnu" 2442 | version = "0.4.0" 2443 | source = "registry+https://github.com/rust-lang/crates.io-index" 2444 | checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" 2445 | 2446 | [[package]] 2447 | name = "windows" 2448 | version = "0.57.0" 2449 | source = "registry+https://github.com/rust-lang/crates.io-index" 2450 | checksum = "12342cb4d8e3b046f3d80effd474a7a02447231330ef77d71daa6fbc40681143" 2451 | dependencies = [ 2452 | "windows-core 0.57.0", 2453 | "windows-targets", 2454 | ] 2455 | 2456 | [[package]] 2457 | name = "windows-core" 2458 | version = "0.57.0" 2459 | source = "registry+https://github.com/rust-lang/crates.io-index" 2460 | checksum = "d2ed2439a290666cd67ecce2b0ffaad89c2a56b976b736e6ece670297897832d" 2461 | dependencies = [ 2462 | "windows-implement 0.57.0", 2463 | "windows-interface 0.57.0", 2464 | "windows-result 0.1.2", 2465 | "windows-targets", 2466 | ] 2467 | 2468 | [[package]] 2469 | name = "windows-core" 2470 | version = "0.61.0" 2471 | source = "registry+https://github.com/rust-lang/crates.io-index" 2472 | checksum = "4763c1de310c86d75a878046489e2e5ba02c649d185f21c67d4cf8a56d098980" 2473 | dependencies = [ 2474 | "windows-implement 0.60.0", 2475 | "windows-interface 0.59.1", 2476 | "windows-link", 2477 | "windows-result 0.3.2", 2478 | "windows-strings", 2479 | ] 2480 | 2481 | [[package]] 2482 | name = "windows-implement" 2483 | version = "0.57.0" 2484 | source = "registry+https://github.com/rust-lang/crates.io-index" 2485 | checksum = "9107ddc059d5b6fbfbffdfa7a7fe3e22a226def0b2608f72e9d552763d3e1ad7" 2486 | dependencies = [ 2487 | "proc-macro2", 2488 | "quote", 2489 | "syn 2.0.100", 2490 | ] 2491 | 2492 | [[package]] 2493 | name = "windows-implement" 2494 | version = "0.60.0" 2495 | source = "registry+https://github.com/rust-lang/crates.io-index" 2496 | checksum = "a47fddd13af08290e67f4acabf4b459f647552718f683a7b415d290ac744a836" 2497 | dependencies = [ 2498 | "proc-macro2", 2499 | "quote", 2500 | "syn 2.0.100", 2501 | ] 2502 | 2503 | [[package]] 2504 | name = "windows-interface" 2505 | version = "0.57.0" 2506 | source = "registry+https://github.com/rust-lang/crates.io-index" 2507 | checksum = "29bee4b38ea3cde66011baa44dba677c432a78593e202392d1e9070cf2a7fca7" 2508 | dependencies = [ 2509 | "proc-macro2", 2510 | "quote", 2511 | "syn 2.0.100", 2512 | ] 2513 | 2514 | [[package]] 2515 | name = "windows-interface" 2516 | version = "0.59.1" 2517 | source = "registry+https://github.com/rust-lang/crates.io-index" 2518 | checksum = "bd9211b69f8dcdfa817bfd14bf1c97c9188afa36f4750130fcdf3f400eca9fa8" 2519 | dependencies = [ 2520 | "proc-macro2", 2521 | "quote", 2522 | "syn 2.0.100", 2523 | ] 2524 | 2525 | [[package]] 2526 | name = "windows-link" 2527 | version = "0.1.1" 2528 | source = "registry+https://github.com/rust-lang/crates.io-index" 2529 | checksum = "76840935b766e1b0a05c0066835fb9ec80071d4c09a16f6bd5f7e655e3c14c38" 2530 | 2531 | [[package]] 2532 | name = "windows-result" 2533 | version = "0.1.2" 2534 | source = "registry+https://github.com/rust-lang/crates.io-index" 2535 | checksum = "5e383302e8ec8515204254685643de10811af0ed97ea37210dc26fb0032647f8" 2536 | dependencies = [ 2537 | "windows-targets", 2538 | ] 2539 | 2540 | [[package]] 2541 | name = "windows-result" 2542 | version = "0.3.2" 2543 | source = "registry+https://github.com/rust-lang/crates.io-index" 2544 | checksum = "c64fd11a4fd95df68efcfee5f44a294fe71b8bc6a91993e2791938abcc712252" 2545 | dependencies = [ 2546 | "windows-link", 2547 | ] 2548 | 2549 | [[package]] 2550 | name = "windows-strings" 2551 | version = "0.4.0" 2552 | source = "registry+https://github.com/rust-lang/crates.io-index" 2553 | checksum = "7a2ba9642430ee452d5a7aa78d72907ebe8cfda358e8cb7918a2050581322f97" 2554 | dependencies = [ 2555 | "windows-link", 2556 | ] 2557 | 2558 | [[package]] 2559 | name = "windows-sys" 2560 | version = "0.52.0" 2561 | source = "registry+https://github.com/rust-lang/crates.io-index" 2562 | checksum = "282be5f36a8ce781fad8c8ae18fa3f9beff57ec1b52cb3de0789201425d9a33d" 2563 | dependencies = [ 2564 | "windows-targets", 2565 | ] 2566 | 2567 | [[package]] 2568 | name = "windows-sys" 2569 | version = "0.59.0" 2570 | source = "registry+https://github.com/rust-lang/crates.io-index" 2571 | checksum = "1e38bc4d79ed67fd075bcc251a1c39b32a1776bbe92e5bef1f0bf1f8c531853b" 2572 | dependencies = [ 2573 | "windows-targets", 2574 | ] 2575 | 2576 | [[package]] 2577 | name = "windows-targets" 2578 | version = "0.52.6" 2579 | source = "registry+https://github.com/rust-lang/crates.io-index" 2580 | checksum = "9b724f72796e036ab90c1021d4780d4d3d648aca59e491e6b98e725b84e99973" 2581 | dependencies = [ 2582 | "windows_aarch64_gnullvm", 2583 | "windows_aarch64_msvc", 2584 | "windows_i686_gnu", 2585 | "windows_i686_gnullvm", 2586 | "windows_i686_msvc", 2587 | "windows_x86_64_gnu", 2588 | "windows_x86_64_gnullvm", 2589 | "windows_x86_64_msvc", 2590 | ] 2591 | 2592 | [[package]] 2593 | name = "windows_aarch64_gnullvm" 2594 | version = "0.52.6" 2595 | source = "registry+https://github.com/rust-lang/crates.io-index" 2596 | checksum = "32a4622180e7a0ec044bb555404c800bc9fd9ec262ec147edd5989ccd0c02cd3" 2597 | 2598 | [[package]] 2599 | name = "windows_aarch64_msvc" 2600 | version = "0.52.6" 2601 | source = "registry+https://github.com/rust-lang/crates.io-index" 2602 | checksum = "09ec2a7bb152e2252b53fa7803150007879548bc709c039df7627cabbd05d469" 2603 | 2604 | [[package]] 2605 | name = "windows_i686_gnu" 2606 | version = "0.52.6" 2607 | source = "registry+https://github.com/rust-lang/crates.io-index" 2608 | checksum = "8e9b5ad5ab802e97eb8e295ac6720e509ee4c243f69d781394014ebfe8bbfa0b" 2609 | 2610 | [[package]] 2611 | name = "windows_i686_gnullvm" 2612 | version = "0.52.6" 2613 | source = "registry+https://github.com/rust-lang/crates.io-index" 2614 | checksum = "0eee52d38c090b3caa76c563b86c3a4bd71ef1a819287c19d586d7334ae8ed66" 2615 | 2616 | [[package]] 2617 | name = "windows_i686_msvc" 2618 | version = "0.52.6" 2619 | source = "registry+https://github.com/rust-lang/crates.io-index" 2620 | checksum = "240948bc05c5e7c6dabba28bf89d89ffce3e303022809e73deaefe4f6ec56c66" 2621 | 2622 | [[package]] 2623 | name = "windows_x86_64_gnu" 2624 | version = "0.52.6" 2625 | source = "registry+https://github.com/rust-lang/crates.io-index" 2626 | checksum = "147a5c80aabfbf0c7d901cb5895d1de30ef2907eb21fbbab29ca94c5b08b1a78" 2627 | 2628 | [[package]] 2629 | name = "windows_x86_64_gnullvm" 2630 | version = "0.52.6" 2631 | source = "registry+https://github.com/rust-lang/crates.io-index" 2632 | checksum = "24d5b23dc417412679681396f2b49f3de8c1473deb516bd34410872eff51ed0d" 2633 | 2634 | [[package]] 2635 | name = "windows_x86_64_msvc" 2636 | version = "0.52.6" 2637 | source = "registry+https://github.com/rust-lang/crates.io-index" 2638 | checksum = "589f6da84c646204747d1270a2a5661ea66ed1cced2631d546fdfb155959f9ec" 2639 | 2640 | [[package]] 2641 | name = "winnow" 2642 | version = "0.7.4" 2643 | source = "registry+https://github.com/rust-lang/crates.io-index" 2644 | checksum = "0e97b544156e9bebe1a0ffbc03484fc1ffe3100cbce3ffb17eac35f7cdd7ab36" 2645 | dependencies = [ 2646 | "memchr", 2647 | ] 2648 | 2649 | [[package]] 2650 | name = "wit-bindgen-rt" 2651 | version = "0.39.0" 2652 | source = "registry+https://github.com/rust-lang/crates.io-index" 2653 | checksum = "6f42320e61fe2cfd34354ecb597f86f413484a798ba44a8ca1165c58d42da6c1" 2654 | dependencies = [ 2655 | "bitflags", 2656 | ] 2657 | 2658 | [[package]] 2659 | name = "write16" 2660 | version = "1.0.0" 2661 | source = "registry+https://github.com/rust-lang/crates.io-index" 2662 | checksum = "d1890f4022759daae28ed4fe62859b1236caebfc61ede2f63ed4e695f3f6d936" 2663 | 2664 | [[package]] 2665 | name = "writeable" 2666 | version = "0.5.5" 2667 | source = "registry+https://github.com/rust-lang/crates.io-index" 2668 | checksum = "1e9df38ee2d2c3c5948ea468a8406ff0db0b29ae1ffde1bcf20ef305bcc95c51" 2669 | 2670 | [[package]] 2671 | name = "wyz" 2672 | version = "0.5.1" 2673 | source = "registry+https://github.com/rust-lang/crates.io-index" 2674 | checksum = "05f360fc0b24296329c78fda852a1e9ae82de9cf7b27dae4b7f62f118f77b9ed" 2675 | dependencies = [ 2676 | "tap", 2677 | ] 2678 | 2679 | [[package]] 2680 | name = "yoke" 2681 | version = "0.7.5" 2682 | source = "registry+https://github.com/rust-lang/crates.io-index" 2683 | checksum = "120e6aef9aa629e3d4f52dc8cc43a015c7724194c97dfaf45180d2daf2b77f40" 2684 | dependencies = [ 2685 | "serde", 2686 | "stable_deref_trait", 2687 | "yoke-derive", 2688 | "zerofrom", 2689 | ] 2690 | 2691 | [[package]] 2692 | name = "yoke-derive" 2693 | version = "0.7.5" 2694 | source = "registry+https://github.com/rust-lang/crates.io-index" 2695 | checksum = "2380878cad4ac9aac1e2435f3eb4020e8374b5f13c296cb75b4620ff8e229154" 2696 | dependencies = [ 2697 | "proc-macro2", 2698 | "quote", 2699 | "syn 2.0.100", 2700 | "synstructure", 2701 | ] 2702 | 2703 | [[package]] 2704 | name = "zerocopy" 2705 | version = "0.8.24" 2706 | source = "registry+https://github.com/rust-lang/crates.io-index" 2707 | checksum = "2586fea28e186957ef732a5f8b3be2da217d65c5969d4b1e17f973ebbe876879" 2708 | dependencies = [ 2709 | "zerocopy-derive", 2710 | ] 2711 | 2712 | [[package]] 2713 | name = "zerocopy-derive" 2714 | version = "0.8.24" 2715 | source = "registry+https://github.com/rust-lang/crates.io-index" 2716 | checksum = "a996a8f63c5c4448cd959ac1bab0aaa3306ccfd060472f85943ee0750f0169be" 2717 | dependencies = [ 2718 | "proc-macro2", 2719 | "quote", 2720 | "syn 2.0.100", 2721 | ] 2722 | 2723 | [[package]] 2724 | name = "zerofrom" 2725 | version = "0.1.6" 2726 | source = "registry+https://github.com/rust-lang/crates.io-index" 2727 | checksum = "50cc42e0333e05660c3587f3bf9d0478688e15d870fab3346451ce7f8c9fbea5" 2728 | dependencies = [ 2729 | "zerofrom-derive", 2730 | ] 2731 | 2732 | [[package]] 2733 | name = "zerofrom-derive" 2734 | version = "0.1.6" 2735 | source = "registry+https://github.com/rust-lang/crates.io-index" 2736 | checksum = "d71e5d6e06ab090c67b5e44993ec16b72dcbaabc526db883a360057678b48502" 2737 | dependencies = [ 2738 | "proc-macro2", 2739 | "quote", 2740 | "syn 2.0.100", 2741 | "synstructure", 2742 | ] 2743 | 2744 | [[package]] 2745 | name = "zerovec" 2746 | version = "0.10.4" 2747 | source = "registry+https://github.com/rust-lang/crates.io-index" 2748 | checksum = "aa2b893d79df23bfb12d5461018d408ea19dfafe76c2c7ef6d4eba614f8ff079" 2749 | dependencies = [ 2750 | "yoke", 2751 | "zerofrom", 2752 | "zerovec-derive", 2753 | ] 2754 | 2755 | [[package]] 2756 | name = "zerovec-derive" 2757 | version = "0.10.3" 2758 | source = "registry+https://github.com/rust-lang/crates.io-index" 2759 | checksum = "6eafa6dfb17584ea3e2bd6e76e0cc15ad7af12b09abdd1ca55961bed9b1063c6" 2760 | dependencies = [ 2761 | "proc-macro2", 2762 | "quote", 2763 | "syn 2.0.100", 2764 | ] 2765 | -------------------------------------------------------------------------------- /Cargo.toml: -------------------------------------------------------------------------------- 1 | [package] 2 | name = "postgres-ical" 3 | version = "0.1.0" 4 | authors = ["Edgar Onghena "] 5 | license = "UNLICENSED" 6 | edition = "2024" 7 | 8 | [lib] 9 | crate-type = ["cdylib", "lib"] 10 | 11 | [[bin]] 12 | name = "pgrx_embed_postgres-ical" 13 | path = "./src/bin/pgrx_embed.rs" 14 | 15 | [features] 16 | default = ["pg13"] 17 | pg12 = ["pgrx/pg12", "pgrx-tests/pg12"] 18 | pg13 = ["pgrx/pg13", "pgrx-tests/pg13"] 19 | pg14 = ["pgrx/pg14", "pgrx-tests/pg14"] 20 | pg15 = ["pgrx/pg15", "pgrx-tests/pg15"] 21 | pg16 = ["pgrx/pg16", "pgrx-tests/pg16"] 22 | pg17 = ["pgrx/pg17", "pgrx-tests/pg17"] 23 | pg_test = [] 24 | 25 | [dependencies] 26 | chrono = "0.4.19" 27 | curl = "0.4.42" 28 | postgres-ical-parser = { path = "postgres-ical-parser" } 29 | pgrx = "0.13.1" 30 | pgrx-named-columns = "0.2.0" 31 | pipe = "0.4.0" 32 | time = "0.3.7" 33 | 34 | [dev-dependencies] 35 | pgrx-tests = "0.13.1" 36 | 37 | [profile.dev] 38 | panic = "unwind" 39 | lto = "thin" 40 | 41 | [profile.release] 42 | panic = "unwind" 43 | opt-level = 3 44 | lto = "fat" 45 | codegen-units = 1 46 | 47 | [workspace] 48 | members = ["postgres-ical-parser"] 49 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # `postgres-ical` 2 | 3 | `postgres-ical` is a PostgreSQL extension that adds features related to parsing [RFC-5545 « iCalendar »](https://datatracker.ietf.org/doc/html/rfc5545) data from within a PostgreSQL database. 4 | 5 | ## Why ? 6 | 7 | _iCalendar_ files are nothing more than a big table of « components » with a lot of properties. That's what relational databases handle every day. 8 | 9 | The format is specifically designed not as a way to store calendar data, but as a way to transfer calendar data from a piece of software to another. Quite a few online calendar software programs allow their users to export a live version of their calendars as an _iCalendar_ URL. There are many situations in which being able to run SQL queries on such a file maybe be useful. Also, importing an _iCalendar_ file in an SQL database can be used as an easy caching system. 10 | 11 | > Can't we simply have a client daemon do this syncing between the database and the remote source ? 12 | 13 | Yes, definitely. And sometimes, installing PostgreSQL extensions is simply not possible. However, here are a few advantages of having the querying and parsing done from within the database : 14 | 1. [Separation of concerns](https://en.wikipedia.org/wiki/Separation_of_concerns): Whatever it is you're actually doing with the calendar data, it's probably not the business of your application to keep the table of events in sync. This whole system is just a kind of one-way replication, which is usually done by the database and not by database clients. 15 | 2. Atomicity and correctness: more often than not, the queried calendar data would be stored in a `materialized view`. Even if you could store your data in a normal table and always try to use a transaction to update it, nothing prevents you fundamentally, from doing "illegal" operations on the table, such as updates or insertions of data that is not present in the actual _iCalendar_ source. 16 | 3. Unique source of truth: since the calendar data is actually a replication of data from elsewhere, by using a `materialized view` that directly queries the source on refresh, it is clear to anyone reading your database structure that the data is a copy from elsewhere. Additionally, the queried data would not appear in a database dump, which just makes sense since it's replicated. 17 | 4. Simplicity ?: Depending on your use-case, doing part of the work inside the database might just be simpler than having to set up multiple clients, multiple systemd services, etc. 18 | 19 | ## Building 20 | 21 | _To be documented..._ 22 | 23 | ## Usage 24 | 25 | After installing the extension, you can use the 2 following functions : 26 | 27 | ```sql 28 | select * from pg_ical('BEGIN:VCALENDAR...'); 29 | select * from pg_ical_curl('https://example.com/calendar.ical'); 30 | ``` 31 | 32 | The columns that are returned are documented on the Rustdoc, by the structure called `Component`. You can build the Rustdoc using `cargo doc --no-deps --open`. 33 | 34 | Regarding compatibility and versioning, I don't consider column additions to be breaking changes, but alterations and deletions obviously are. You should ideally use precise `select` statements in order not to have surprises. 35 | 36 | ## Tech stack 37 | 38 | The extension is made in Rust, with [the `pgx` library](https://github.com/zombodb/pgx) doing the rotten job of handling FFI. General _iCalendar_ parsing is done by the [`ical`](https://github.com/Peltoche/ical-rs) crate, while the actual meaning of properties is inferred by a local crate (`/postgres-ical-parser`), that will be published independently one day. 39 | 40 | ## License 41 | 42 | The project doesn't have I license yet, and is thus considered "all rights reserved". I probably won't sue you if use it, but you technically don't have permission for the moment. I'm looking for a license similar to the AGPL, that would require you to distribute the source code to any remote users who ask for it, but in a way that doesn't infect your SQL code that uses the library functions (similar to the LGPL). An "LAGPL", so to say. Suggestions are welcome. 43 | -------------------------------------------------------------------------------- /postgres-ical-parser/Cargo.toml: -------------------------------------------------------------------------------- 1 | [package] 2 | name = "postgres-ical-parser" 3 | version = "0.0.0" 4 | description = "One day, this will be its own crate" 5 | edition = "2018" 6 | publish = false 7 | 8 | [dependencies] 9 | chrono = "0.4.40" 10 | chrono-tz = "0.10.3" 11 | ical = "0.11.0" 12 | log = "0.4.27" 13 | thiserror = "2.0" 14 | -------------------------------------------------------------------------------- /postgres-ical-parser/src/lib.rs: -------------------------------------------------------------------------------- 1 | mod parser; 2 | pub mod types; 3 | 4 | pub use parser::*; 5 | -------------------------------------------------------------------------------- /postgres-ical-parser/src/parser.rs: -------------------------------------------------------------------------------- 1 | //! Type-safe ical event representation 2 | 3 | use super::types::{IcalDateTime, IcalInt, IcalText, IcalType}; 4 | use ical::parser::ParserError; 5 | use ical::property::{Property, PropertyError}; 6 | use ical::PropertyParser; 7 | use std::io::BufRead; 8 | 9 | pub struct Event { 10 | pub created: Option, 11 | 12 | pub description: Option, 13 | 14 | pub dt_stamp: Option, 15 | 16 | pub dt_start: IcalDateTime, 17 | 18 | pub dt_end: Option, 19 | 20 | pub last_modified: Option, 21 | 22 | pub location: Option, 23 | 24 | pub sequence: i32, 25 | 26 | pub summary: Option, 27 | 28 | pub uid: String, 29 | } 30 | 31 | #[derive(Debug, thiserror::Error)] 32 | pub enum CalendarParseError { 33 | #[error("missing property {0}")] 34 | MissingProperty(&'static str), 35 | 36 | #[error("invalid property value {property}:{found:?}, expected {expected}")] 37 | InvalidPropertyValue { 38 | property: &'static str, 39 | found: String, 40 | expected: &'static str, 41 | }, 42 | 43 | #[error("unknown property {0}")] 44 | UnknownProperty(String), 45 | 46 | #[error("internal ical parser error: {0}")] 47 | ParserError(#[from] ParserError), 48 | } 49 | 50 | fn ical_parse( 51 | property_name: &'static str, 52 | property: Property, 53 | ) -> Result { 54 | T::parse(property).map_err(|value| CalendarParseError::InvalidPropertyValue { 55 | property: property_name, 56 | found: value, 57 | expected: T::TYPE_NAME, 58 | }) 59 | } 60 | 61 | macro_rules! event_from_properties { 62 | { 63 | for $property:ident in $properties:expr; 64 | $($name:literal $(! $($dummy:literal)*)? => $var:ident: $ical_type:ty $(= $default:expr)?,)* 65 | } => { 66 | $(let mut $var = event_from_properties!(@i $name; $property; $ical_type $(= $default)?);)* 67 | 68 | for $property in $properties { 69 | let $property = $property.map_err(ParserError::PropertyError)?; 70 | 71 | match $property.name.to_ascii_uppercase().as_str() { 72 | $($name => $var = event_from_properties!(@s $name; $property; $ical_type $(= $default)?),)* 73 | _ => (), // Unknown property 74 | } 75 | } 76 | 77 | Ok(Self { 78 | $($var $(: $var.ok_or(CalendarParseError::MissingProperty(event_from_properties!(@t $name @ $($dummy)*)))?)?,)* 79 | }) 80 | }; 81 | (@i $name:literal; $property:ident; $ical_type:ty = $default:expr) => { $default }; 82 | (@s $name:literal; $property:ident; $ical_type:ty = $default:expr) => { ical_parse::<$ical_type>($name, $property)? }; 83 | (@i $name:literal; $property:ident; $ical_type:ty) => { None }; 84 | (@s $name:literal; $property:ident; $ical_type:ty) => { Some(ical_parse::<$ical_type>($name, $property)?) }; 85 | (@t $lit:literal @ $($tt:tt)*) => { $lit }; 86 | } 87 | 88 | impl Event { 89 | fn from_properties( 90 | properties: impl Iterator>, 91 | ) -> Result { 92 | event_from_properties! { 93 | for property in properties; 94 | "CREATED" => created: IcalDateTime, 95 | "DESCRIPTION" => description: IcalText, 96 | "DTSTART"! => dt_start: IcalDateTime, 97 | "DTSTAMP" => dt_stamp: IcalDateTime, 98 | "DTEND" => dt_end: IcalDateTime, 99 | "LAST-MODIFIED" => last_modified: IcalDateTime, 100 | "LOCATION" => location: IcalText, 101 | "SEQUENCE" => sequence: IcalInt = 0, 102 | "SUMMARY" => summary: IcalText, 103 | "UID"! => uid: IcalText, 104 | } 105 | } 106 | } 107 | 108 | pub struct EventsReader { 109 | raw_reader: PropertyParser, 110 | } 111 | 112 | impl EventsReader { 113 | pub fn new(buf_read: R) -> Self { 114 | let raw_reader = PropertyParser::new(ical::LineReader::new(buf_read)); 115 | 116 | Self { raw_reader } 117 | } 118 | } 119 | 120 | impl Iterator for EventsReader { 121 | type Item = Result; 122 | 123 | fn next(&mut self) -> Option { 124 | loop { 125 | break match self.raw_reader.next() { 126 | None => None, 127 | Some(Err(err)) => Some(Err(CalendarParseError::ParserError(err.into()))), 128 | Some(Ok(mut property)) => { 129 | property.name.make_ascii_uppercase(); 130 | match property.name.as_str() { 131 | "BEGIN" => match property.value.as_deref() { 132 | None => Some(Err(ParserError::InvalidComponent.into())), 133 | Some("VEVENT") => { 134 | Some(Event::from_properties( 135 | (&mut self.raw_reader).take_while( 136 | |property| !matches!(property, Ok(p) if p.name.as_str() == "END" && p.value.as_deref() == Some("VEVENT")) 137 | ) 138 | )) 139 | } 140 | Some("VCALENDAR") => continue, 141 | Some(_other) => { 142 | // TODO 143 | continue; 144 | } 145 | }, 146 | _ => { 147 | // TODO 148 | continue 149 | } 150 | } 151 | } 152 | }; 153 | } 154 | } 155 | } 156 | -------------------------------------------------------------------------------- /postgres-ical-parser/src/types.rs: -------------------------------------------------------------------------------- 1 | use chrono::{DateTime, NaiveDateTime, TimeZone, Utc}; 2 | use chrono_tz::Tz; 3 | use ical::property::Property; 4 | 5 | type Result = std::result::Result; 6 | 7 | pub trait IcalType { 8 | const TYPE_NAME: &'static str; 9 | // When stable: type Output = Self; 10 | type Output; 11 | 12 | fn parse(property: Property) -> Result; 13 | } 14 | 15 | #[derive(Clone, Debug, Eq, PartialEq)] 16 | pub enum IcalDateTime { 17 | Naive(NaiveDateTime), 18 | Utc(DateTime), 19 | Tz(DateTime), 20 | } 21 | 22 | impl IcalType for IcalDateTime { 23 | const TYPE_NAME: &'static str = "DATE-TIME"; 24 | type Output = Self; 25 | 26 | fn parse(property: Property) -> Result { 27 | let value_string = property.value.unwrap_or_default(); 28 | 29 | let value = value_string.as_str(); 30 | let (date_time, is_utc) = match value.strip_suffix('Z') { 31 | Some(date_time) => (date_time, true), 32 | None => (value, false), 33 | }; 34 | 35 | let Ok(date_time) = NaiveDateTime::parse_from_str(date_time, "%Y%m%dT%H%M%S") else { 36 | return Err(value_string); // TODO 37 | }; 38 | 39 | let params = property.params.as_deref().unwrap_or_default(); 40 | let tz_id = params 41 | .iter() 42 | .rfind(|(n, _)| n == "TZID") 43 | .and_then(|(_, v)| v.last()); 44 | 45 | match (is_utc, tz_id) { 46 | (true, Some(_)) => Err(value_string), // TODO 47 | (false, Some(tz_id)) => { 48 | let tz = tz_id.parse::().map_err(|_| value_string)?; // TODO 49 | Ok(Self::Tz(tz.from_local_datetime(&date_time).unwrap())) // TODO unwrap 50 | } 51 | (true, None) => Ok(Self::Utc(Utc.from_utc_datetime(&date_time))), 52 | (false, None) => Ok(Self::Naive(date_time)), 53 | } 54 | } 55 | } 56 | 57 | pub struct IcalInt; 58 | 59 | impl IcalType for IcalInt { 60 | const TYPE_NAME: &'static str = "INT"; 61 | type Output = i32; 62 | 63 | fn parse(property: Property) -> Result { 64 | property 65 | .value 66 | .as_deref() 67 | .unwrap_or_default() 68 | .parse::() 69 | .map_err(|_| property.value.unwrap_or_default()) 70 | } 71 | } 72 | 73 | pub struct IcalText; 74 | 75 | impl IcalType for IcalText { 76 | const TYPE_NAME: &'static str = "TEXT"; 77 | type Output = String; 78 | 79 | fn parse(property: Property) -> Result { 80 | let value = property.value.unwrap_or_default(); 81 | 82 | // We attempt to reuse the string buffer if there's no replacement to be done 83 | if let Some(idx) = value.find('\\') { 84 | // FIXME: This algorithm is stupid and won't work as expected for i.e. «\\\\;» 85 | // It should also probably fail if an invalid escape sequence is used 86 | 87 | let mut clone = value[..idx].to_string(); 88 | clone += &value[idx..] 89 | .replace("\\n", "\n") 90 | .replace("\\N", "\n") 91 | .replace("\\;", ";") 92 | .replace("\\,", ",") 93 | .replace("\\\\", "\\"); 94 | 95 | Ok(clone) 96 | } else { 97 | Ok(value) 98 | } 99 | } 100 | } 101 | 102 | #[cfg(test)] 103 | mod tests { 104 | use super::*; 105 | use chrono::{NaiveDate, Utc}; 106 | 107 | macro_rules! p { 108 | ($name:literal $(;$prop:literal = $prop_value:literal)* : $value:literal) => { 109 | Property { 110 | name: ToString::to_string($name), 111 | params: Some(vec![$( 112 | (ToString::to_string($prop), vec![ToString::to_string($prop_value)]), 113 | )*]), 114 | value: Some(ToString::to_string($value)), 115 | } 116 | }; 117 | } 118 | 119 | #[test] 120 | fn parse_ical_date_time() { 121 | assert_eq!( 122 | IcalDateTime::parse(p!("": "20020110T123045")).unwrap(), 123 | IcalDateTime::Naive(NaiveDate::from_ymd(2002, 1, 10).and_hms(12, 30, 45)), 124 | ); 125 | 126 | assert_eq!( 127 | IcalDateTime::parse(p!("": "20020110T123045Z")).unwrap(), 128 | IcalDateTime::Utc(Utc.ymd(2002, 1, 10).and_hms(12, 30, 45)), 129 | ); 130 | 131 | use chrono_tz::Europe::Paris; 132 | 133 | assert_eq!( 134 | IcalDateTime::parse(p!(""; "TZID"="Europe/Paris": "20020110T123045")).unwrap(), 135 | IcalDateTime::Tz(Paris.ymd(2002, 1, 10).and_hms(12, 30, 45)), 136 | ); 137 | } 138 | 139 | #[test] 140 | fn parse_ical_date_time_invalid() { 141 | assert!(matches!( 142 | IcalDateTime::parse(p!(""; "TZID"="Middle_Earth/Minas_Tirith": "20020110T123045")), 143 | Err(_), 144 | )); 145 | 146 | assert!(matches!( 147 | IcalDateTime::parse(p!(""; "TZID"="Europe/Paris": "20020110T123045Z")), 148 | Err(_), 149 | )); 150 | } 151 | } 152 | -------------------------------------------------------------------------------- /postgres_ical.control: -------------------------------------------------------------------------------- 1 | comment = 'postgres_ical: Created by pgx' 2 | default_version = '@CARGO_VERSION@' 3 | module_pathname = '$libdir/postgres_ical' 4 | relocatable = false 5 | superuser = false 6 | -------------------------------------------------------------------------------- /src/bin/pgrx_embed.rs: -------------------------------------------------------------------------------- 1 | ::pgrx::pgrx_embed!(); 2 | -------------------------------------------------------------------------------- /src/lib.rs: -------------------------------------------------------------------------------- 1 | use chrono::{Datelike, Timelike}; 2 | use curl::easy::Easy; 3 | use pgrx::*; 4 | use pgrx_named_columns::*; 5 | use pipe::PipeReader; 6 | use postgres_ical_parser::types::IcalDateTime; 7 | use postgres_ical_parser::{CalendarParseError, Event}; 8 | use std::io::{BufRead, BufReader, Cursor, Write}; 9 | use std::thread::JoinHandle; 10 | use pgrx::datum::{Timestamp, TimestampWithTimeZone}; 11 | use time::{PrimitiveDateTime, UtcOffset}; 12 | 13 | pg_module_magic!(); 14 | 15 | /// [`curl`] is used instead of a Rustier alternative to make [`postgres_ical`] as lightweight as 16 | /// possible 17 | fn curl_get(url: &str) -> (PipeReader, JoinHandle<()>) { 18 | let (reader, mut writer) = pipe::pipe_buffered(); 19 | 20 | let mut easy = Easy::new(); 21 | easy.url(url).unwrap(); 22 | 23 | let handle = std::thread::spawn(move || { 24 | let mut transfer = easy.transfer(); 25 | transfer 26 | .write_function(move |data| { 27 | writer.write_all(data).unwrap(); 28 | Ok(data.len()) 29 | }) 30 | .unwrap(); 31 | 32 | transfer.perform().unwrap(); 33 | std::mem::drop(transfer); 34 | }); 35 | 36 | (reader, handle) 37 | } 38 | 39 | fn to_time(d: impl Datelike + Timelike) -> PrimitiveDateTime { 40 | use time::Month::*; 41 | use time::*; 42 | 43 | let month = match d.month() { 44 | 1 => January, 45 | 2 => February, 46 | 3 => March, 47 | 4 => April, 48 | 5 => May, 49 | 6 => June, 50 | 7 => July, 51 | 8 => August, 52 | 9 => September, 53 | 10 => October, 54 | 11 => November, 55 | 12 => December, 56 | _ => unreachable!(), 57 | }; 58 | 59 | PrimitiveDateTime::new( 60 | Date::from_calendar_date(d.year(), month, d.day() as u8).unwrap(), 61 | Time::from_hms(d.hour() as u8, d.minute() as u8, d.second() as u8).unwrap(), 62 | ) 63 | } 64 | 65 | fn serialize_datetime(date: IcalDateTime) -> (Option, Option) { 66 | match date { 67 | IcalDateTime::Naive(naive) => { 68 | let dt = to_time(naive); 69 | (None, Some(Timestamp::new(dt.year(), dt.month() as u8, dt.day(), dt.hour(), dt.minute(), dt.second() as _).unwrap())) 70 | }, 71 | IcalDateTime::Utc(utc) => { 72 | let dt = to_time(utc); 73 | ( 74 | Some(TimestampWithTimeZone::with_timezone(dt.year(), dt.month() as u8, dt.day(), dt.hour(), dt.minute(), dt.second() as _, "UTC").unwrap()), 75 | None, 76 | ) 77 | }, 78 | IcalDateTime::Tz(tz) => { 79 | use chrono::Offset; 80 | let offset = tz.offset().fix().local_minus_utc(); 81 | let offset = UtcOffset::from_whole_seconds(offset).unwrap(); 82 | let dt = to_time(tz); 83 | (Some(TimestampWithTimeZone::with_timezone(dt.year(), dt.month() as u8, dt.day(), dt.hour(), dt.minute(), dt.second() as _, offset.to_string()).unwrap()), None) 84 | } 85 | } 86 | } 87 | 88 | /// TODO 89 | #[deprecated] 90 | type Interval = i16; 91 | 92 | #[derive(PostgresEnum)] 93 | pub enum ComponentType { 94 | VCALENDAR, 95 | VEVENT, 96 | VTODO, 97 | VJOURNAL, 98 | VFREEBUSY, 99 | VTIMEZONE, 100 | VALARM, 101 | } 102 | 103 | #[derive(PostgresEnum)] 104 | pub enum Class { 105 | PUBLIC, 106 | PRIVATE, 107 | CONFIDENTIAL, 108 | } 109 | 110 | #[derive(PostgresEnum)] 111 | pub enum Status { 112 | TENTATIVE, 113 | CONFIRMED, 114 | CANCELLED, 115 | NEEDSACTION, 116 | COMPLETED, 117 | INPROCESS, 118 | DRAFT, 119 | FINAL, 120 | } 121 | 122 | /// Represents a row returned by [pg_ical] or [pg_ical_curl] 123 | pub struct Component { 124 | pub component_type: ComponentType, 125 | pub attachment: Option, 126 | pub categories: Vec, 127 | pub class: Option, 128 | pub comment: Vec, 129 | pub completed: Option, 130 | pub completed_naive: Option, 131 | pub created: Option, 132 | pub created_naive: Option, 133 | pub description: Option, 134 | pub dt_stamp: Option, 135 | pub dt_stamp_naive: Option, 136 | pub dt_start: Option, 137 | pub dt_start_naive: Option, 138 | pub dt_end: Option, 139 | pub dt_end_naive: Option, 140 | pub due: Option, 141 | pub due_naive: Option, 142 | pub duration: Option, 143 | pub geo_lat: Option, 144 | pub geo_lng: Option, 145 | pub last_modified: Option, 146 | pub last_modified_naive: Option, 147 | pub location: Option, 148 | pub percent_complete: Option, 149 | pub priority: Option, 150 | pub resources: Vec, 151 | pub status: Option, 152 | pub sequence: i32, 153 | pub summary: Option, 154 | pub uid: String, 155 | } 156 | 157 | fn convert_component(res: Result) -> Component { 158 | let event = res.unwrap(); 159 | 160 | let (created, created_naive) = event.created.map(serialize_datetime).unwrap_or_default(); 161 | let (dt_stamp, dt_stamp_naive) = event.dt_stamp.map(serialize_datetime).unwrap_or_default(); 162 | let (dt_start, dt_start_naive) = serialize_datetime(event.dt_start); 163 | let (dt_end, dt_end_naive) = event.dt_end.map(serialize_datetime).unwrap_or_default(); 164 | let (last_modified, last_modified_naive) = event 165 | .last_modified 166 | .map(serialize_datetime) 167 | .unwrap_or_default(); 168 | 169 | Component { 170 | component_type: ComponentType::VEVENT, 171 | attachment: None, // TODO 172 | categories: Vec::new(), // TODO 173 | class: None, // TODO 174 | comment: Vec::new(), // TODO 175 | completed: None, // TODO 176 | completed_naive: None, // TODO 177 | created, 178 | created_naive, 179 | description: event.description, 180 | dt_stamp, 181 | dt_stamp_naive, 182 | dt_start, 183 | dt_start_naive, 184 | dt_end, 185 | dt_end_naive, 186 | due: None, // TODO 187 | due_naive: None, // TODO 188 | duration: None, // TODO 189 | geo_lat: None, // TODO 190 | geo_lng: None, // TODO 191 | last_modified, 192 | last_modified_naive, 193 | location: event.location, 194 | percent_complete: None, // TODO 195 | priority: None, // TODO 196 | resources: Vec::new(), // TODO 197 | status: None, // TODO 198 | sequence: event.sequence, 199 | summary: event.summary, 200 | uid: event.uid, 201 | } 202 | } 203 | 204 | fn pg_ical_internal(calendar: impl BufRead) -> impl Iterator { 205 | let parser = postgres_ical_parser::EventsReader::new(calendar); 206 | parser.map(convert_component) 207 | } 208 | 209 | /// Load an [`ical`][ical] file from an in-memory text representation 210 | /// 211 | /// The number of columns may increase at any moment without it being considered a breaking change. 212 | /// For forward-compatibility, when consuming this function's output, always do an explicit select. 213 | /// Column deletion or altering is — however, and obviously — considered breaking. 214 | /// 215 | /// [ical]: https://datatracker.ietf.org/doc/html/rfc5545 216 | #[pg_extern_columns("src/lib.rs")] 217 | pub fn pg_ical(calendar: String) -> ::pgrx::iter::TableIterator<'static, Component> { 218 | pg_ical_internal(BufReader::new(Cursor::new(calendar.into_bytes()))) 219 | } 220 | 221 | /// Load an [`ical`][ical] file from an URL, making a [curl] request in the process 222 | /// 223 | /// The number of columns may increase at any moment without it being considered a breaking change. 224 | /// For forward-compatibility, when consuming this function's output, always do an explicit select. 225 | /// Column deletion or altering is — however, and obviously — considered breaking. 226 | /// 227 | /// [ical]: https://datatracker.ietf.org/doc/html/rfc5545 228 | #[pg_extern_columns("src/lib.rs")] 229 | pub fn pg_ical_curl(url: &str) -> ::pgrx::iter::TableIterator<'static, Component> { 230 | let (reader, handle) = curl_get(url); 231 | let mut handle = Some(handle); 232 | 233 | pg_ical_internal(reader).chain(std::iter::from_fn(move || { 234 | handle.take().unwrap().join().unwrap(); 235 | None 236 | })) 237 | } 238 | --------------------------------------------------------------------------------