From 3e5f816cf755ea00b25e4f8c3e06c564922753ba Mon Sep 17 00:00:00 2001 From: Timothy DeHerrera Date: Wed, 30 Aug 2023 14:56:27 -0600 Subject: [PATCH 01/18] fix: run `cargo update` to build with latest rust --- Cargo.lock | 521 ++++++++++++++++++++++------------------------------- 1 file changed, 217 insertions(+), 304 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 9511585..6d48c3e 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -4,9 +4,9 @@ version = 3 [[package]] name = "addr2line" -version = "0.19.0" +version = "0.21.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a76fd60b23679b7d19bd066031410fb7e458ccc5e958eb5c325888ce4baedc97" +checksum = "8a30b2e23b9e17a9f90641c7ab1549cd9b44f296d3ccbf309d2863cfe398a0cb" dependencies = [ "gimli", ] @@ -19,13 +19,19 @@ checksum = "f26201604c87b1e01bd3d98f8d5d9a8fcbb815e8cedb41ffccbeb4bf593a35fe" [[package]] name = "aho-corasick" -version = "1.0.1" +version = "1.0.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "67fc08ce920c31afb70f013dcce1bfc3a3195de6a228474e45e1f145b36f8d04" +checksum = "0c378d78423fdad8089616f827526ee33c19f2fddbd5de1629152c9593ba4783" dependencies = [ "memchr", ] +[[package]] +name = "android-tzdata" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e999941b234f3131b00bc13c22d06e8c5ff726d1b6318ac7eb276997bbb4fef0" + [[package]] name = "android_system_properties" version = "0.1.5" @@ -37,13 +43,13 @@ dependencies = [ [[package]] name = "async-trait" -version = "0.1.68" +version = "0.1.73" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b9ccdd8f2a161be9bd5c023df56f1b2a0bd1d83872ae53b71a84a12c9bf6e842" +checksum = "bc00ceb34980c03614e35a3a4e218276a0a824e911d07651cd0d858a51e8c0f0" dependencies = [ "proc-macro2", "quote", - "syn 2.0.15", + "syn 2.0.29", ] [[package]] @@ -65,9 +71,9 @@ checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa" [[package]] name = "backtrace" -version = "0.3.67" +version = "0.3.69" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "233d376d6d185f2a3093e58f283f60f880315b6c60075b01f36b3b85154564ca" +checksum = "2089b7e3f35b9dd2d0ed921ead4f6d318c27680d4a5bd167b3ee120edb105837" dependencies = [ "addr2line", "cc", @@ -90,11 +96,17 @@ version = "1.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a" +[[package]] +name = "bitflags" +version = "2.4.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b4682ae6287fcf752ecaabbfcc7b6f9b72aa33933dc23a554d853aea8eea8635" + [[package]] name = "bumpalo" -version = "3.12.2" +version = "3.13.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3c6ed94e98ecff0c12dd1b04c15ec0d7d9458ca8fe806cea6f12954efe74c63b" +checksum = "a3e2c3daef883ecc1b5d58c15adae93470a91d425f3532ba1695849656af3fc1" [[package]] name = "bytes" @@ -110,9 +122,12 @@ checksum = "89b2fd2a0dcf38d7971e2194b6b6eebab45ae01067456a7fd93d5547a61b70be" [[package]] name = "cc" -version = "1.0.79" +version = "1.0.83" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "50d30906286121d95be3d479533b458f87493b30a4b5f79a607db8f5d11aa91f" +checksum = "f1174fb0b6ec23863f8b971027804a42614e347eafb0a95bf0b12cdae21fc4d0" +dependencies = [ + "libc", +] [[package]] name = "cfdyndns" @@ -140,17 +155,17 @@ checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" [[package]] name = "chrono" -version = "0.4.24" +version = "0.4.28" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4e3c5919066adf22df73762e50cffcde3a758f2a848b113b586d1f86728b673b" +checksum = "95ed24df0632f708f5f6d8082675bef2596f7084dee3dd55f632290bf35bfe0f" dependencies = [ + "android-tzdata", "iana-time-zone", "js-sys", - "num-integer", "num-traits", "time", "wasm-bindgen", - "winapi 0.3.9", + "windows-targets", ] [[package]] @@ -171,15 +186,15 @@ checksum = "e496a50fda8aacccc86d7529e2c1e0892dbd0f898a6b5645b5561b89c3210efa" [[package]] name = "data-encoding" -version = "2.3.3" +version = "2.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "23d8666cb01533c39dde32bcbab8e227b4ed6679b2c925eba05feabea39508fb" +checksum = "c2e66c9d817f1720209181c316d28635c050fa304f9c79e47a520882661b7308" [[package]] name = "encoding_rs" -version = "0.8.32" +version = "0.8.33" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "071a31f4ee85403370b58aca746f01041ede6f0da2730960ad001edc2b71b394" +checksum = "7268b386296a025e474d5140678f75d6de9493ae55a5d709eeb9dd08149945e1" dependencies = [ "cfg-if 1.0.0", ] @@ -217,13 +232,13 @@ dependencies = [ [[package]] name = "errno" -version = "0.3.1" +version = "0.3.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4bcfec3a70f97c962c307b2d2c56e358cf1d00b558d74262b5f929ee8cc7e73a" +checksum = "136526188508e25c6fef639d7927dfb3e0e3084488bf202267829cf7fc23dbdd" dependencies = [ "errno-dragonfly", "libc", - "windows-sys 0.48.0", + "windows-sys", ] [[package]] @@ -238,12 +253,9 @@ dependencies = [ [[package]] name = "fastrand" -version = "1.9.0" +version = "2.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e51093e27b0797c359783294ca4f0a911c270184cb10f85783b118614a1501be" -dependencies = [ - "instant", -] +checksum = "6999dc1837253364c2ebb0704ba97994bd874e8f195d665c50b7548f6ea92764" [[package]] name = "fnv" @@ -268,9 +280,9 @@ checksum = "00b0228411908ca8685dba7fc2cdd70ec9990a6e753e89b6ac91a84c40fbaf4b" [[package]] name = "form_urlencoded" -version = "1.1.0" +version = "1.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a9c384f161156f5260c24a097c56119f9be8c798586aecc13afbcbe7b7e26bf8" +checksum = "a62bc1cf6f830c2ec14a513a9fb124d0a213a629668a4186f329db21fe045652" dependencies = [ "percent-encoding", ] @@ -281,7 +293,7 @@ version = "0.3.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2e9763c69ebaae630ba35f74888db465e49e259ba1bc0eda7d06f4a067615d82" dependencies = [ - "bitflags", + "bitflags 1.3.2", "fuchsia-zircon-sys", ] @@ -351,7 +363,7 @@ dependencies = [ "futures-sink", "futures-task", "memchr", - "pin-project-lite 0.2.9", + "pin-project-lite 0.2.13", "pin-utils", "slab", ] @@ -369,9 +381,9 @@ dependencies = [ [[package]] name = "gimli" -version = "0.27.2" +version = "0.28.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ad0a93d233ebf96623465aad4046a8d3aa4da22d4f4beba5388838c8a434bbb4" +checksum = "6fb8d784f27acf97159b40fc4db5ecd8aa23b9ad5ef69cdd136d3bc80665f0c0" [[package]] name = "h2" @@ -416,18 +428,9 @@ dependencies = [ [[package]] name = "hermit-abi" -version = "0.2.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ee512640fe35acbfb4bb779db6f0d80704c2cacfa2e39b601ef3e3f47d1ae4c7" -dependencies = [ - "libc", -] - -[[package]] -name = "hermit-abi" -version = "0.3.1" +version = "0.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fed44880c466736ef9a5c5b5facefb5ed0785676d0c02d612db14e54f0d84286" +checksum = "443144c8cdadd93ebf52ddb4056d257f5b52c04d3c804e657d19eb73fc33668b" [[package]] name = "http" @@ -437,7 +440,7 @@ checksum = "bd6effc99afb63425aff9b05836f029929e345a6148a14b7ecd5ab67af944482" dependencies = [ "bytes 1.4.0", "fnv", - "itoa 1.0.6", + "itoa 1.0.9", ] [[package]] @@ -510,9 +513,9 @@ dependencies = [ [[package]] name = "iana-time-zone" -version = "0.1.56" +version = "0.1.57" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0722cd7114b7de04316e7ea5456a0bbb20e4adb46fd27a3697adb812cff0f37c" +checksum = "2fad5b825842d2b38bd206f3e81d6957625fd7f0a361e345c30e01a0ae2dd613" dependencies = [ "android_system_properties", "core-foundation-sys", @@ -544,9 +547,9 @@ dependencies = [ [[package]] name = "idna" -version = "0.3.0" +version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e14ddfc70884202db2244c223200c204c2bda1bc6e0998d11b5e024d657209e6" +checksum = "7d20d6b07bfbc108882d88ed8e37d39636dcc260e15e30c45e6ba089610b917c" dependencies = [ "unicode-bidi", "unicode-normalization", @@ -562,26 +565,6 @@ dependencies = [ "hashbrown", ] -[[package]] -name = "instant" -version = "0.1.12" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7a5bbe824c507c5da5956355e86a746d82e0e1464f65d862cc5e71da70e94b2c" -dependencies = [ - "cfg-if 1.0.0", -] - -[[package]] -name = "io-lifetimes" -version = "1.0.10" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9c66c74d2ae7e79a5a8f7ac924adbe38ee42a859c6539ad869eb51f0b52dc220" -dependencies = [ - "hermit-abi 0.3.1", - "libc", - "windows-sys 0.48.0", -] - [[package]] name = "iovec" version = "0.1.4" @@ -593,9 +576,9 @@ dependencies = [ [[package]] name = "ipnet" -version = "2.7.2" +version = "2.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "12b6ee2129af8d4fb011108c73d99a1b83a85977f23b82460c0ae2e25bb4b57f" +checksum = "28b29a3cd74f0f4598934efe3aeba42bae0eb4680554128851ebbecb02af14e6" [[package]] name = "itoa" @@ -605,15 +588,15 @@ checksum = "b71991ff56294aa922b450139ee08b3bfc70982c6b2c7562771375cf73542dd4" [[package]] name = "itoa" -version = "1.0.6" +version = "1.0.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "453ad9f582a441959e5f0d088b02ce04cfe8d51a8eaf077f12ac6d3e94164ca6" +checksum = "af150ab688ff2122fcef229be89cb50dd66af9e01a4ff320cc137eecc9bacc38" [[package]] name = "js-sys" -version = "0.3.62" +version = "0.3.64" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "68c16e1bfd491478ab155fd8b4896b86f9ede344949b641e61501e07c2b8b4d5" +checksum = "c5f195fe497f702db0f318b07fdd68edb16955aed830df8363d837542f8f935a" dependencies = [ "wasm-bindgen", ] @@ -636,24 +619,21 @@ checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646" [[package]] name = "libc" -version = "0.2.144" +version = "0.2.147" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2b00cc1c228a6782d0f076e7b232802e0c5689d41bb5df366f2a6b6621cfdfe1" +checksum = "b4668fb0ea861c1df094127ac5f1da3409a82116a4ba74fca2e58ef927159bb3" [[package]] name = "linux-raw-sys" -version = "0.3.7" +version = "0.4.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ece97ea872ece730aed82664c424eb4c8291e1ff2480247ccf7409044bc6479f" +checksum = "57bcfdad1b858c2db7c38303a6d2ad4dfaf5eb53dfeb0910128b2c26d6158503" [[package]] name = "log" -version = "0.4.17" +version = "0.4.20" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "abb12e687cfb44aa40f41fc3978ef76448f9b6038cad6aef4259d3c095a2382e" -dependencies = [ - "cfg-if 1.0.0", -] +checksum = "b5e6163cb8c49088c2c36f57875e58ccd8c87c7427f7fbd50ea6710b2f3f2e8f" [[package]] name = "matches" @@ -663,9 +643,9 @@ checksum = "2532096657941c2fea9c289d370a250971c689d4f143798ff67113ec042024a5" [[package]] name = "memchr" -version = "2.5.0" +version = "2.6.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2dffe52ecf27772e601905b7522cb4ef790d2cc203488bbd0e2fe85fcb74566d" +checksum = "5486aed0026218e61b8a01d5fbd5a0a134649abb71a0e53b7bc088529dced86e" [[package]] name = "mime" @@ -685,9 +665,9 @@ dependencies = [ [[package]] name = "miniz_oxide" -version = "0.6.2" +version = "0.7.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b275950c28b37e794e8c55d88aeb5e139d0ce23fdbbeda68f8d7174abdf9e8fa" +checksum = "e7810e0be55b428ada41041c41f32c9f1a42817901b4ccf45fa3d4b6561e74c7" dependencies = [ "adler", ] @@ -743,9 +723,9 @@ dependencies = [ [[package]] name = "net2" -version = "0.2.38" +version = "0.2.39" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "74d0df99cfcd2530b2e694f6e17e7f37b8e26bb23983ac530c0c97408837c631" +checksum = "b13b648036a2339d06de780866fbdfda0dde886de7b3af2ddeba8b14f4ee34ac" dependencies = [ "cfg-if 0.1.10", "libc", @@ -758,57 +738,47 @@ version = "0.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c8d77f3db4bce033f4d04db08079b2ef1c3d02b44e86f25d08886fafa7756ffa" -[[package]] -name = "num-integer" -version = "0.1.45" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "225d3389fb3509a24c93f5c29eb6bde2586b98d9f016636dff58d7c6f7569cd9" -dependencies = [ - "autocfg", - "num-traits", -] - [[package]] name = "num-traits" -version = "0.2.15" +version = "0.2.16" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "578ede34cf02f8924ab9447f50c28075b4d3e5b269972345e7e0372b38c6cdcd" +checksum = "f30b0abd723be7e2ffca1272140fac1a2f084c77ec3e123c192b66af1ee9e6c2" dependencies = [ "autocfg", ] [[package]] name = "num_cpus" -version = "1.15.0" +version = "1.16.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0fac9e2da13b5eb447a6ce3d392f23a29d8694bff781bf03a16cd9ac8697593b" +checksum = "4161fcb6d602d4d2081af7c3a45852d875a03dd337a6bfdd6e06407b61342a43" dependencies = [ - "hermit-abi 0.2.6", + "hermit-abi 0.3.2", "libc", ] [[package]] name = "object" -version = "0.30.3" +version = "0.32.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ea86265d3d3dcb6a27fc51bd29a4bf387fae9d2986b823079d4986af253eb439" +checksum = "77ac5bbd07aea88c60a577a1ce218075ffd59208b2d7ca97adf9bfc5aeb21ebe" dependencies = [ "memchr", ] [[package]] name = "once_cell" -version = "1.17.1" +version = "1.18.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b7e5500299e16ebb147ae15a00a942af264cf3688f47923b8fc2cd5858f23ad3" +checksum = "dd8b5dd2ae5ed71462c540258bedcb51965123ad7e7ccf4b9a8cafaa4a63576d" [[package]] name = "openssl" -version = "0.10.52" +version = "0.10.57" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "01b8574602df80f7b85fdfc5392fa884a4e3b3f4f35402c070ab34c3d3f78d56" +checksum = "bac25ee399abb46215765b1cb35bc0212377e58a061560d8b29b024fd0430e7c" dependencies = [ - "bitflags", + "bitflags 2.4.0", "cfg-if 1.0.0", "foreign-types", "libc", @@ -825,7 +795,7 @@ checksum = "a948666b637a0f465e8564c73e89d4dde00d72d4d473cc972f390fc3dcee7d9c" dependencies = [ "proc-macro2", "quote", - "syn 2.0.15", + "syn 2.0.29", ] [[package]] @@ -836,9 +806,9 @@ checksum = "ff011a302c396a5197692431fc1948019154afc178baf7d8e37367442a4601cf" [[package]] name = "openssl-sys" -version = "0.9.87" +version = "0.9.92" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8e17f59264b2809d77ae94f0e1ebabc434773f370d6ca667bd223ea10e06cc7e" +checksum = "db7e971c2c2bba161b2d2fdf37080177eff520b3bc044787c7f1f5f9e78d869b" dependencies = [ "cc", "libc", @@ -848,28 +818,28 @@ dependencies = [ [[package]] name = "percent-encoding" -version = "2.2.0" +version = "2.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "478c572c3d73181ff3c2539045f6eb99e5491218eae919370993b890cdbdd98e" +checksum = "9b2a4787296e9989611394c33f193f676704af1686e70b8f8033ab5ba9a35a94" [[package]] name = "pin-project" -version = "1.0.12" +version = "1.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ad29a609b6bcd67fee905812e544992d216af9d755757c05ed2d0e15a74c6ecc" +checksum = "fda4ed1c6c173e3fc7a83629421152e01d7b1f9b7f65fb301e490e8cfc656422" dependencies = [ "pin-project-internal", ] [[package]] name = "pin-project-internal" -version = "1.0.12" +version = "1.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "069bdb1e05adc7a8990dce9cc75370895fbe4e3d58b9b73bf1aee56359344a55" +checksum = "4359fd9c9171ec6e8c62926d6faaf553a8dc3f64e1507e76da7911b4f6a04405" dependencies = [ "proc-macro2", "quote", - "syn 1.0.109", + "syn 2.0.29", ] [[package]] @@ -880,9 +850,9 @@ checksum = "257b64915a082f7811703966789728173279bdebb956b143dbcd23f6f970a777" [[package]] name = "pin-project-lite" -version = "0.2.9" +version = "0.2.13" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e0a7ae3ac2f1173085d398531c705756c94a4c56843785df85a60c1a0afac116" +checksum = "8afb450f006bf6385ca15ef45d71d2288452bc3683ce2e2cacc0d18e4be60b58" [[package]] name = "pin-utils" @@ -914,9 +884,9 @@ dependencies = [ [[package]] name = "proc-macro2" -version = "1.0.56" +version = "1.0.66" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2b63bdb0cd06f1f4dedf69b254734f9b45af66e4a031e42a7480257d9898b435" +checksum = "18fb31db3f9bddb2ea821cde30a9f70117e3f119938b5ee630b7403aa6e2ead9" dependencies = [ "unicode-ident", ] @@ -929,9 +899,9 @@ checksum = "a1d01941d82fa2ab50be1e79e6714289dd7cde78eba4c074bc5a4374f650dfe0" [[package]] name = "quote" -version = "1.0.27" +version = "1.0.33" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8f4f29d145265ec1c483c7c654450edde0bfe043d3938d6972630663356d9500" +checksum = "5267fca4496028628a95160fc423a33e8b2e6af8a5302579e322e4b520293cae" dependencies = [ "proc-macro2", ] @@ -993,14 +963,26 @@ version = "0.3.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "567664f262709473930a4bf9e51bf2ebf3348f2e748ccc50dea20646858f8f29" dependencies = [ - "bitflags", + "bitflags 1.3.2", ] [[package]] name = "regex" -version = "1.8.1" +version = "1.9.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "af83e617f331cc6ae2da5443c602dfa5af81e517212d9d611a5b3ba1777b5370" +checksum = "12de2eff854e5fa4b1295edd650e227e9d8fb0c9e90b12e7f36d6a6811791a29" +dependencies = [ + "aho-corasick", + "memchr", + "regex-automata", + "regex-syntax", +] + +[[package]] +name = "regex-automata" +version = "0.3.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "49530408a136e16e5b486e883fbb6ba058e8e4e8ae6621a77b048b314336e629" dependencies = [ "aho-corasick", "memchr", @@ -1009,9 +991,9 @@ dependencies = [ [[package]] name = "regex-syntax" -version = "0.7.1" +version = "0.7.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a5996294f19bd3aae0453a862ad728f60e6600695733dd5df01da90c54363a3c" +checksum = "dbb5fb1acd8a1a18b3dd5be62d25485eb770e05afb408a9627d14d451bae12da" [[package]] name = "reqwest" @@ -1036,7 +1018,7 @@ dependencies = [ "mime_guess", "native-tls", "percent-encoding", - "pin-project-lite 0.2.9", + "pin-project-lite 0.2.13", "serde", "serde_json", "serde_urlencoded", @@ -1057,40 +1039,39 @@ checksum = "d626bb9dae77e28219937af045c257c28bfd3f69333c512553507f5f9798cb76" [[package]] name = "rustix" -version = "0.37.19" +version = "0.38.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "acf8729d8542766f1b2cf77eb034d52f40d375bb8b615d0b147089946e16613d" +checksum = "ed6248e1caa625eb708e266e06159f135e8c26f2bb7ceb72dc4b2766d0340964" dependencies = [ - "bitflags", + "bitflags 2.4.0", "errno", - "io-lifetimes", "libc", "linux-raw-sys", - "windows-sys 0.48.0", + "windows-sys", ] [[package]] name = "ryu" -version = "1.0.13" +version = "1.0.15" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f91339c0467de62360649f8d3e185ca8de4224ff281f66000de5eb2a77a79041" +checksum = "1ad4cc8da4ef723ed60bced201181d83791ad433213d8c24efffda1eec85d741" [[package]] name = "schannel" -version = "0.1.21" +version = "0.1.22" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "713cfb06c7059f3588fb8044c0fad1d09e3c01d225e25b9220dbfdcf16dbb1b3" +checksum = "0c3733bf4cf7ea0880754e19cb5a462007c4a8c1914bff372ccc95b464f1df88" dependencies = [ - "windows-sys 0.42.0", + "windows-sys", ] [[package]] name = "security-framework" -version = "2.8.2" +version = "2.9.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a332be01508d814fed64bf28f798a146d73792121129962fdf335bb3c49a4254" +checksum = "05b64fb303737d99b81884b2c63433e9ae28abebe5eb5045dcdd175dc2ecf4de" dependencies = [ - "bitflags", + "bitflags 1.3.2", "core-foundation", "core-foundation-sys", "libc", @@ -1099,9 +1080,9 @@ dependencies = [ [[package]] name = "security-framework-sys" -version = "2.8.0" +version = "2.9.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "31c9bb296072e961fcbd8853511dd39c2d8be2deb1e17c6860b1d30732b323b4" +checksum = "e932934257d3b408ed8f30db49d85ea163bfe74961f017f405b025af298f0c7a" dependencies = [ "core-foundation-sys", "libc", @@ -1109,17 +1090,31 @@ dependencies = [ [[package]] name = "serde" -version = "1.0.163" +version = "1.0.188" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2113ab51b87a539ae008b5c6c02dc020ffa39afd2d83cffcb3f4eb2722cebec2" +checksum = "cf9e0fcba69a370eed61bcf2b728575f726b50b55cba78064753d708ddc7549e" +dependencies = [ + "serde_derive", +] + +[[package]] +name = "serde_derive" +version = "1.0.188" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4eca7ac642d82aa35b60049a6eccb4be6be75e599bd2e9adb5f875a737654af2" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.29", +] [[package]] name = "serde_json" -version = "1.0.96" +version = "1.0.105" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "057d394a50403bcac12672b2b18fb387ab6d289d957dab67dd201875391e52f1" +checksum = "693151e1ac27563d6dbcec9dee9fbd5da8539b20fa14ad3752b2e6d363ace360" dependencies = [ - "itoa 1.0.6", + "itoa 1.0.9", "ryu", "serde", ] @@ -1131,25 +1126,25 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d3491c14715ca2294c4d6a88f15e84739788c1d030eed8c110436aafdaa2f3fd" dependencies = [ "form_urlencoded", - "itoa 1.0.6", + "itoa 1.0.9", "ryu", "serde", ] [[package]] name = "slab" -version = "0.4.8" +version = "0.4.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6528351c9bc8ab22353f9d776db39a20288e8d6c37ef8cfe3317cf875eecfc2d" +checksum = "8f92a496fb766b417c996b9c5e57daf2f7ad3b0bebe1ccfca4856390e3d3bb67" dependencies = [ "autocfg", ] [[package]] name = "smallvec" -version = "1.10.0" +version = "1.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a507befe795404456341dfab10cef66ead4c041f62b8b11bbb92bffe5d0953e0" +checksum = "62bb4feee49fdd9f707ef802e22365a35de4b7b299de4763d44bfea899442ff9" [[package]] name = "socket2" @@ -1175,9 +1170,9 @@ dependencies = [ [[package]] name = "syn" -version = "2.0.15" +version = "2.0.29" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a34fcf3e8b60f57e6a14301a2e916d323af98b0ea63c599441eec8558660c822" +checksum = "c324c494eba9d92503e6f1ef2e6df781e78f6a7705a0202d9801b198807d518a" dependencies = [ "proc-macro2", "quote", @@ -1186,15 +1181,15 @@ dependencies = [ [[package]] name = "tempfile" -version = "3.5.0" +version = "3.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b9fbec84f381d5795b08656e4912bec604d162bff9291d6189a78f4c8ab87998" +checksum = "cb94d2f3cc536af71caac6b6fcebf65860b347e7ce0cc9ebe8f70d3e521054ef" dependencies = [ "cfg-if 1.0.0", "fastrand", "redox_syscall", "rustix", - "windows-sys 0.45.0", + "windows-sys", ] [[package]] @@ -1208,22 +1203,22 @@ dependencies = [ [[package]] name = "thiserror" -version = "1.0.40" +version = "1.0.47" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "978c9a314bd8dc99be594bc3c175faaa9794be04a5a5e153caba6915336cebac" +checksum = "97a802ec30afc17eee47b2855fc72e0c4cd62be9b4efe6591edde0ec5bd68d8f" dependencies = [ "thiserror-impl", ] [[package]] name = "thiserror-impl" -version = "1.0.40" +version = "1.0.47" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f9456a42c5b0d803c8cd86e73dd7cc9edd429499f37a3550d286d5e86720569f" +checksum = "6bb623b56e39ab7dcd4b1b98bb6c8f8d907ed255b18de254088016b27a8ee19b" dependencies = [ "proc-macro2", "quote", - "syn 2.0.15", + "syn 2.0.29", ] [[package]] @@ -1308,7 +1303,7 @@ checksum = "8ce8c33a8d48bd45d624a6e523445fd21ec13d3653cd51f681abf67418f54eb8" dependencies = [ "cfg-if 1.0.0", "log", - "pin-project-lite 0.2.9", + "pin-project-lite 0.2.13", "tracing-core", ] @@ -1380,9 +1375,9 @@ checksum = "3528ecfd12c466c6f163363caf2d02a71161dd5e1cc6ae7b34207ea2d42d81ed" [[package]] name = "unicase" -version = "2.6.0" +version = "2.7.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "50f37be617794602aabbeee0be4f259dc1778fabe05e2d67ee8f79326d5cb4f6" +checksum = "f7d2d4dafb69621809a81864c9c1b864479e1235c0dd4e199924b9742439ed89" dependencies = [ "version_check", ] @@ -1395,9 +1390,9 @@ checksum = "92888ba5573ff080736b3648696b70cafad7d250551175acbaa4e0385b3e1460" [[package]] name = "unicode-ident" -version = "1.0.8" +version = "1.0.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e5464a87b239f13a63a501f2701565754bae92d243d4bb7eb12f6d57d2269bf4" +checksum = "301abaae475aa91687eb82514b328ab47a211a533026cb25fc3e519b86adfc3c" [[package]] name = "unicode-normalization" @@ -1410,12 +1405,12 @@ dependencies = [ [[package]] name = "url" -version = "2.3.1" +version = "2.4.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0d68c799ae75762b8c3fe375feb6600ef5602c883c5d21eb51c09f22b83c4643" +checksum = "143b538f18257fac9cad154828a57c6bf5157e1aa604d4816b5995bf6de87ae5" dependencies = [ "form_urlencoded", - "idna 0.3.0", + "idna 0.4.0", "percent-encoding", ] @@ -1433,11 +1428,10 @@ checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f" [[package]] name = "want" -version = "0.3.0" +version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1ce8a968cb1cd110d136ff8b819a556d6fb6d919363c61534f6860c7eb172ba0" +checksum = "bfa7760aed19e106de2c7c0b581b509f2f25d3dacaf737cb82ac61bc6d760b0e" dependencies = [ - "log", "try-lock", ] @@ -1455,9 +1449,9 @@ checksum = "1a143597ca7c7793eff794def352d41792a93c481eb1042423ff7ff72ba2c31f" [[package]] name = "wasm-bindgen" -version = "0.2.85" +version = "0.2.87" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5b6cb788c4e39112fbe1822277ef6fb3c55cd86b95cb3d3c4c1c9597e4ac74b4" +checksum = "7706a72ab36d8cb1f80ffbf0e071533974a60d0a308d01a5d0375bf60499a342" dependencies = [ "cfg-if 1.0.0", "serde", @@ -1467,24 +1461,24 @@ dependencies = [ [[package]] name = "wasm-bindgen-backend" -version = "0.2.85" +version = "0.2.87" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "35e522ed4105a9d626d885b35d62501b30d9666283a5c8be12c14a8bdafe7822" +checksum = "5ef2b6d3c510e9625e5fe6f509ab07d66a760f0885d858736483c32ed7809abd" dependencies = [ "bumpalo", "log", "once_cell", "proc-macro2", "quote", - "syn 2.0.15", + "syn 2.0.29", "wasm-bindgen-shared", ] [[package]] name = "wasm-bindgen-futures" -version = "0.4.35" +version = "0.4.37" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "083abe15c5d88556b77bdf7aef403625be9e327ad37c62c4e4129af740168163" +checksum = "c02dbc21516f9f1f04f187958890d7e6026df8d16540b7ad9492bc34a67cea03" dependencies = [ "cfg-if 1.0.0", "js-sys", @@ -1494,9 +1488,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-macro" -version = "0.2.85" +version = "0.2.87" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "358a79a0cb89d21db8120cbfb91392335913e4890665b1a7981d9e956903b434" +checksum = "dee495e55982a3bd48105a7b947fd2a9b4a8ae3010041b9e0faab3f9cd028f1d" dependencies = [ "quote", "wasm-bindgen-macro-support", @@ -1504,28 +1498,28 @@ dependencies = [ [[package]] name = "wasm-bindgen-macro-support" -version = "0.2.85" +version = "0.2.87" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4783ce29f09b9d93134d41297aded3a712b7b979e9c6f28c32cb88c973a94869" +checksum = "54681b18a46765f095758388f2d0cf16eb8d4169b639ab575a8f5693af210c7b" dependencies = [ "proc-macro2", "quote", - "syn 2.0.15", + "syn 2.0.29", "wasm-bindgen-backend", "wasm-bindgen-shared", ] [[package]] name = "wasm-bindgen-shared" -version = "0.2.85" +version = "0.2.87" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a901d592cafaa4d711bc324edfaff879ac700b19c3dfd60058d2b445be2691eb" +checksum = "ca6ad05a4870b2bf5fe995117d3728437bd27d7cd5f06f13c17443ef369775a1" [[package]] name = "web-sys" -version = "0.3.62" +version = "0.3.64" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "16b5f940c7edfdc6d12126d98c9ef4d1b3d470011c47c76a6581df47ad9ba721" +checksum = "9b85cbef8c220a6abc02aefd892dfc0fc23afb1c6a426316ec33253a3877249b" dependencies = [ "js-sys", "wasm-bindgen", @@ -1580,31 +1574,7 @@ version = "0.48.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e686886bc078bc1b0b600cac0147aadb815089b6e4da64016cbd754b6342700f" dependencies = [ - "windows-targets 0.48.0", -] - -[[package]] -name = "windows-sys" -version = "0.42.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5a3e1820f08b8513f676f7ab6c1f99ff312fb97b553d30ff4dd86f9f15728aa7" -dependencies = [ - "windows_aarch64_gnullvm 0.42.2", - "windows_aarch64_msvc 0.42.2", - "windows_i686_gnu 0.42.2", - "windows_i686_msvc 0.42.2", - "windows_x86_64_gnu 0.42.2", - "windows_x86_64_gnullvm 0.42.2", - "windows_x86_64_msvc 0.42.2", -] - -[[package]] -name = "windows-sys" -version = "0.45.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "75283be5efb2831d37ea142365f009c02ec203cd29a3ebecbc093d52315b66d0" -dependencies = [ - "windows-targets 0.42.2", + "windows-targets", ] [[package]] @@ -1613,122 +1583,65 @@ version = "0.48.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "677d2418bec65e3338edb076e806bc1ec15693c5d0104683f2efe857f61056a9" dependencies = [ - "windows-targets 0.48.0", + "windows-targets", ] [[package]] name = "windows-targets" -version = "0.42.2" +version = "0.48.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8e5180c00cd44c9b1c88adb3693291f1cd93605ded80c250a75d472756b4d071" +checksum = "9a2fa6e2155d7247be68c096456083145c183cbbbc2764150dda45a87197940c" dependencies = [ - "windows_aarch64_gnullvm 0.42.2", - "windows_aarch64_msvc 0.42.2", - "windows_i686_gnu 0.42.2", - "windows_i686_msvc 0.42.2", - "windows_x86_64_gnu 0.42.2", - "windows_x86_64_gnullvm 0.42.2", - "windows_x86_64_msvc 0.42.2", + "windows_aarch64_gnullvm", + "windows_aarch64_msvc", + "windows_i686_gnu", + "windows_i686_msvc", + "windows_x86_64_gnu", + "windows_x86_64_gnullvm", + "windows_x86_64_msvc", ] -[[package]] -name = "windows-targets" -version = "0.48.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7b1eb6f0cd7c80c79759c929114ef071b87354ce476d9d94271031c0497adfd5" -dependencies = [ - "windows_aarch64_gnullvm 0.48.0", - "windows_aarch64_msvc 0.48.0", - "windows_i686_gnu 0.48.0", - "windows_i686_msvc 0.48.0", - "windows_x86_64_gnu 0.48.0", - "windows_x86_64_gnullvm 0.48.0", - "windows_x86_64_msvc 0.48.0", -] - -[[package]] -name = "windows_aarch64_gnullvm" -version = "0.42.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "597a5118570b68bc08d8d59125332c54f1ba9d9adeedeef5b99b02ba2b0698f8" - [[package]] name = "windows_aarch64_gnullvm" -version = "0.48.0" +version = "0.48.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "91ae572e1b79dba883e0d315474df7305d12f569b400fcf90581b06062f7e1bc" +checksum = "2b38e32f0abccf9987a4e3079dfb67dcd799fb61361e53e2882c3cbaf0d905d8" [[package]] name = "windows_aarch64_msvc" -version = "0.42.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e08e8864a60f06ef0d0ff4ba04124db8b0fb3be5776a5cd47641e942e58c4d43" - -[[package]] -name = "windows_aarch64_msvc" -version = "0.48.0" +version = "0.48.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b2ef27e0d7bdfcfc7b868b317c1d32c641a6fe4629c171b8928c7b08d98d7cf3" +checksum = "dc35310971f3b2dbbf3f0690a219f40e2d9afcf64f9ab7cc1be722937c26b4bc" [[package]] name = "windows_i686_gnu" -version = "0.42.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c61d927d8da41da96a81f029489353e68739737d3beca43145c8afec9a31a84f" - -[[package]] -name = "windows_i686_gnu" -version = "0.48.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "622a1962a7db830d6fd0a69683c80a18fda201879f0f447f065a3b7467daa241" - -[[package]] -name = "windows_i686_msvc" -version = "0.42.2" +version = "0.48.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "44d840b6ec649f480a41c8d80f9c65108b92d89345dd94027bfe06ac444d1060" +checksum = "a75915e7def60c94dcef72200b9a8e58e5091744960da64ec734a6c6e9b3743e" [[package]] name = "windows_i686_msvc" -version = "0.48.0" +version = "0.48.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4542c6e364ce21bf45d69fdd2a8e455fa38d316158cfd43b3ac1c5b1b19f8e00" +checksum = "8f55c233f70c4b27f66c523580f78f1004e8b5a8b659e05a4eb49d4166cca406" [[package]] name = "windows_x86_64_gnu" -version = "0.42.2" +version = "0.48.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8de912b8b8feb55c064867cf047dda097f92d51efad5b491dfb98f6bbb70cb36" - -[[package]] -name = "windows_x86_64_gnu" -version = "0.48.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ca2b8a661f7628cbd23440e50b05d705db3686f894fc9580820623656af974b1" +checksum = "53d40abd2583d23e4718fddf1ebec84dbff8381c07cae67ff7768bbf19c6718e" [[package]] name = "windows_x86_64_gnullvm" -version = "0.42.2" +version = "0.48.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "26d41b46a36d453748aedef1486d5c7a85db22e56aff34643984ea85514e94a3" - -[[package]] -name = "windows_x86_64_gnullvm" -version = "0.48.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7896dbc1f41e08872e9d5e8f8baa8fdd2677f29468c4e156210174edc7f7b953" - -[[package]] -name = "windows_x86_64_msvc" -version = "0.42.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9aec5da331524158c6d1a4ac0ab1541149c0b9505fde06423b02f5ef0106b9f0" +checksum = "0b7b52767868a23d5bab768e390dc5f5c55825b6d30b86c844ff2dc7414044cc" [[package]] name = "windows_x86_64_msvc" -version = "0.48.0" +version = "0.48.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1a515f5799fe4961cb532f983ce2b23082366b898e52ffbce459c86f67c8378a" +checksum = "ed94fce61571a4006852b7389a063ab983c02eb1bb37b47f8272ce92d06d9538" [[package]] name = "winreg" From 9cc9c6f7432f5e287d57d3bbe3aab568e23107f4 Mon Sep 17 00:00:00 2001 From: Timothy DeHerrera Date: Wed, 30 Aug 2023 17:52:22 -0600 Subject: [PATCH 02/18] feat: add Standard Nix framework integration Provides a working devshell and package binary. --- .envrc | 6 + .gitignore | 21 +++ flake.lock | 426 +++++++++++++++++++++++++++++++++++++++++++ flake.nix | 45 +++++ nix/bin/packages.nix | 20 ++ nix/repo/rust.nix | 23 +++ nix/repo/shells.nix | 92 ++++++++++ rustfmt.toml | 77 ++++++++ 8 files changed, 710 insertions(+) create mode 100644 .envrc create mode 100644 flake.lock create mode 100644 flake.nix create mode 100644 nix/bin/packages.nix create mode 100644 nix/repo/rust.nix create mode 100644 nix/repo/shells.nix create mode 100644 rustfmt.toml diff --git a/.envrc b/.envrc new file mode 100644 index 0000000..bfa560a --- /dev/null +++ b/.envrc @@ -0,0 +1,6 @@ +#! /bin/sh + +# shellcheck disable=SC1090 +. "$(fetchurl https://raw.githubusercontent.com/paisano-nix/direnv/main/lib sha256-IgQhKK7UHL1AfCUntJO2KCaIDJQotRnK2qC4Daxk+wI=)" + +use env //repo/shells/default diff --git a/.gitignore b/.gitignore index 9582cca..a6b9c32 100644 --- a/.gitignore +++ b/.gitignore @@ -1,3 +1,24 @@ target target-install systemd/cloudflare-dyndns.config + +.std + +result + +# prj-spec dirs +# +.bin +.cache +.config +.data +.run + +# nixago: ignore-linked-files +lefthook.yml +.editorconfig +.conform.yaml +treefmt.toml + +# nixago-auto-created: mdbook-build-folder +docs/build diff --git a/flake.lock b/flake.lock new file mode 100644 index 0000000..6aec6da --- /dev/null +++ b/flake.lock @@ -0,0 +1,426 @@ +{ + "nodes": { + "blank": { + "locked": { + "lastModified": 1625557891, + "narHash": "sha256-O8/MWsPBGhhyPoPLHZAuoZiiHo9q6FLlEeIDEXuj6T4=", + "owner": "divnix", + "repo": "blank", + "rev": "5a5d2684073d9f563072ed07c871d577a6c614a8", + "type": "github" + }, + "original": { + "owner": "divnix", + "repo": "blank", + "type": "github" + } + }, + "call-flake": { + "locked": { + "lastModified": 1693099034, + "narHash": "sha256-bmhE1TmrJG4ba93l9WQTLuYM53kwGQAjYHRvHOeuxWU=", + "owner": "divnix", + "repo": "call-flake", + "rev": "24473e390c03457fa6c33e5447e9a74999ff4d4f", + "type": "github" + }, + "original": { + "owner": "divnix", + "repo": "call-flake", + "type": "github" + } + }, + "crane": { + "inputs": { + "flake-compat": [], + "flake-utils": "flake-utils", + "nixpkgs": [ + "nixpkgs" + ], + "rust-overlay": [] + }, + "locked": { + "lastModified": 1693163878, + "narHash": "sha256-HXuyMUVaRSoIA602jfFuYGXt6AMZ+WUxuvLq8iJmYTA=", + "owner": "ipetkov", + "repo": "crane", + "rev": "43db881168bc65b568d36ceb614a0fc8b276191b", + "type": "github" + }, + "original": { + "owner": "ipetkov", + "repo": "crane", + "type": "github" + } + }, + "devshell": { + "inputs": { + "nixpkgs": "nixpkgs_2", + "systems": "systems_2" + }, + "locked": { + "lastModified": 1692793255, + "narHash": "sha256-yVyj0AE280JkccDHuG1XO9oGxN6bW8ksr/xttXcXzK0=", + "owner": "numtide", + "repo": "devshell", + "rev": "2aa26972b951bc05c3632d4e5ae683cb6771a7c6", + "type": "github" + }, + "original": { + "owner": "numtide", + "repo": "devshell", + "type": "github" + } + }, + "dmerge": { + "inputs": { + "haumea": [ + "std", + "haumea" + ], + "nixlib": [ + "std", + "haumea", + "nixpkgs" + ], + "yants": [ + "std", + "yants" + ] + }, + "locked": { + "lastModified": 1686862774, + "narHash": "sha256-ojGtRQ9pIOUrxsQEuEPerUkqIJEuod9hIflfNkY+9CE=", + "owner": "divnix", + "repo": "dmerge", + "rev": "9f7f7a8349d33d7bd02e0f2b484b1f076e503a96", + "type": "github" + }, + "original": { + "owner": "divnix", + "ref": "0.2.1", + "repo": "dmerge", + "type": "github" + } + }, + "fenix": { + "inputs": { + "nixpkgs": "nixpkgs", + "rust-analyzer-src": "rust-analyzer-src" + }, + "locked": { + "lastModified": 1693376454, + "narHash": "sha256-DPwnYASe7xGW6mNANEhKHOSFL2ySwIcDNW+SsYYzwmg=", + "owner": "nix-community", + "repo": "fenix", + "rev": "a08c2909476e953bd23a73f2f3ef5bf07bf1ae44", + "type": "github" + }, + "original": { + "owner": "nix-community", + "repo": "fenix", + "type": "github" + } + }, + "flake-utils": { + "inputs": { + "systems": "systems" + }, + "locked": { + "lastModified": 1689068808, + "narHash": "sha256-6ixXo3wt24N/melDWjq70UuHQLxGV8jZvooRanIHXw0=", + "owner": "numtide", + "repo": "flake-utils", + "rev": "919d646de7be200f3bf08cb76ae1f09402b6f9b4", + "type": "github" + }, + "original": { + "owner": "numtide", + "repo": "flake-utils", + "type": "github" + } + }, + "haumea": { + "inputs": { + "nixpkgs": "nixpkgs_3" + }, + "locked": { + "lastModified": 1685133229, + "narHash": "sha256-FePm/Gi9PBSNwiDFq3N+DWdfxFq0UKsVVTJS3cQPn94=", + "owner": "nix-community", + "repo": "haumea", + "rev": "34dd58385092a23018748b50f9b23de6266dffc2", + "type": "github" + }, + "original": { + "owner": "nix-community", + "ref": "v0.2.2", + "repo": "haumea", + "type": "github" + } + }, + "incl": { + "inputs": { + "nixlib": [ + "std", + "haumea", + "nixpkgs" + ] + }, + "locked": { + "lastModified": 1669263024, + "narHash": "sha256-E/+23NKtxAqYG/0ydYgxlgarKnxmDbg6rCMWnOBqn9Q=", + "owner": "divnix", + "repo": "incl", + "rev": "ce7bebaee048e4cd7ebdb4cee7885e00c4e2abca", + "type": "github" + }, + "original": { + "owner": "divnix", + "repo": "incl", + "type": "github" + } + }, + "nixpkgs": { + "locked": { + "lastModified": 1693250523, + "narHash": "sha256-y3up5gXMTbnCsXrNEB5j+7TVantDLUYyQLu/ueiXuyg=", + "owner": "nixos", + "repo": "nixpkgs", + "rev": "3efb0f6f404ec8dae31bdb1a9b17705ce0d6986e", + "type": "github" + }, + "original": { + "owner": "nixos", + "ref": "nixos-unstable", + "repo": "nixpkgs", + "type": "github" + } + }, + "nixpkgs_2": { + "locked": { + "lastModified": 1693355128, + "narHash": "sha256-+ZoAny3ZxLcfMaUoLVgL9Ywb/57wP+EtsdNGuXUJrwg=", + "owner": "NixOS", + "repo": "nixpkgs", + "rev": "a63a64b593dcf2fe05f7c5d666eb395950f36bc9", + "type": "github" + }, + "original": { + "owner": "NixOS", + "ref": "nixpkgs-unstable", + "repo": "nixpkgs", + "type": "github" + } + }, + "nixpkgs_3": { + "locked": { + "lastModified": 1681001314, + "narHash": "sha256-5sDnCLdrKZqxLPK4KA8+f4A3YKO/u6ElpMILvX0g72c=", + "owner": "nix-community", + "repo": "nixpkgs.lib", + "rev": "367c0e1086a4eb4502b24d872cea2c7acdd557f4", + "type": "github" + }, + "original": { + "owner": "nix-community", + "repo": "nixpkgs.lib", + "type": "github" + } + }, + "nosys": { + "locked": { + "lastModified": 1668010795, + "narHash": "sha256-JBDVBnos8g0toU7EhIIqQ1If5m/nyBqtHhL3sicdPwI=", + "owner": "divnix", + "repo": "nosys", + "rev": "feade0141487801c71ff55623b421ed535dbdefa", + "type": "github" + }, + "original": { + "owner": "divnix", + "repo": "nosys", + "type": "github" + } + }, + "paisano": { + "inputs": { + "call-flake": "call-flake", + "nixpkgs": [ + "std", + "nixpkgs" + ], + "nosys": "nosys", + "yants": [ + "std", + "yants" + ] + }, + "locked": { + "lastModified": 1691492062, + "narHash": "sha256-9izEr9crBjoBk4ecuTyFVYwjbXo1VjClRN1eaGITeag=", + "owner": "paisano-nix", + "repo": "core", + "rev": "218a7f50451cbc5c981fc8dfe6f962044041f9aa", + "type": "github" + }, + "original": { + "owner": "paisano-nix", + "repo": "core", + "type": "github" + } + }, + "paisano-tui": { + "flake": false, + "locked": { + "lastModified": 1681847764, + "narHash": "sha256-mdd7PJW1BZvxy0cIKsPfAO+ohVl/V7heE5ZTAHzTdv8=", + "owner": "paisano-nix", + "repo": "tui", + "rev": "3096bad91cae73ab8ab3367d31f8a143d248a244", + "type": "github" + }, + "original": { + "owner": "paisano-nix", + "ref": "0.1.1", + "repo": "tui", + "type": "github" + } + }, + "root": { + "inputs": { + "crane": "crane", + "fenix": "fenix", + "nixpkgs": [ + "fenix", + "nixpkgs" + ], + "std": "std" + } + }, + "rust-analyzer-src": { + "flake": false, + "locked": { + "lastModified": 1693293380, + "narHash": "sha256-ZTkBsglLJ7wmD+MKR67G677jM2x7SA3LqmSdggEv9dg=", + "owner": "rust-lang", + "repo": "rust-analyzer", + "rev": "b06503b6ec98c9ed44698870cbf3302b8560b442", + "type": "github" + }, + "original": { + "owner": "rust-lang", + "ref": "nightly", + "repo": "rust-analyzer", + "type": "github" + } + }, + "std": { + "inputs": { + "arion": [ + "std", + "blank" + ], + "blank": "blank", + "devshell": "devshell", + "dmerge": "dmerge", + "haumea": "haumea", + "incl": "incl", + "makes": [ + "std", + "blank" + ], + "microvm": [ + "std", + "blank" + ], + "n2c": [ + "std", + "blank" + ], + "nixago": [ + "std", + "blank" + ], + "nixpkgs": [ + "nixpkgs" + ], + "paisano": "paisano", + "paisano-tui": "paisano-tui", + "terranix": [ + "std", + "blank" + ], + "yants": "yants" + }, + "locked": { + "lastModified": 1692106836, + "narHash": "sha256-VaNAHPYd/inL0+4O7j4Gx+JfyKHT5RGXWZ3JWU5DPdk=", + "owner": "divnix", + "repo": "std", + "rev": "b12b4df9fd35e803896ff08802a219ec0e8d55db", + "type": "github" + }, + "original": { + "owner": "divnix", + "ref": "v0.24.0-1", + "repo": "std", + "type": "github" + } + }, + "systems": { + "locked": { + "lastModified": 1681028828, + "narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=", + "owner": "nix-systems", + "repo": "default", + "rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e", + "type": "github" + }, + "original": { + "owner": "nix-systems", + "repo": "default", + "type": "github" + } + }, + "systems_2": { + "locked": { + "lastModified": 1681028828, + "narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=", + "owner": "nix-systems", + "repo": "default", + "rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e", + "type": "github" + }, + "original": { + "owner": "nix-systems", + "repo": "default", + "type": "github" + } + }, + "yants": { + "inputs": { + "nixpkgs": [ + "std", + "haumea", + "nixpkgs" + ] + }, + "locked": { + "lastModified": 1686863218, + "narHash": "sha256-kooxYm3/3ornWtVBNHM3Zh020gACUyFX2G0VQXnB+mk=", + "owner": "divnix", + "repo": "yants", + "rev": "8f0da0dba57149676aa4817ec0c880fbde7a648d", + "type": "github" + }, + "original": { + "owner": "divnix", + "repo": "yants", + "type": "github" + } + } + }, + "root": "root", + "version": 7 +} diff --git a/flake.nix b/flake.nix new file mode 100644 index 0000000..9664a30 --- /dev/null +++ b/flake.nix @@ -0,0 +1,45 @@ +{ + description = "A very basic flake for Rust development"; + + inputs.std.url = "github:divnix/std/v0.24.0-1"; + inputs.std.inputs.nixpkgs.follows = "nixpkgs"; + + inputs.fenix.url = "github:nix-community/fenix"; + inputs.crane.url = "github:ipetkov/crane"; + inputs.crane.inputs.nixpkgs.follows = "nixpkgs"; + inputs.crane.inputs.flake-compat.follows = ""; + inputs.crane.inputs.rust-overlay.follows = ""; + + inputs.std.inputs.devshell.url = "github:numtide/devshell"; + + inputs.nixpkgs.follows = "fenix/nixpkgs"; + + outputs = inputs @ { + self, + std, + ... + }: + std.growOn { + inherit inputs; + systems = ["x86_64-linux"]; + cellsFrom = ./nix; + cellBlocks = with std.blockTypes; [ + (installables "packages") + # Contribution Environment + (devshells "shells") + (pkgs "rust") + ]; + } { + devShells = std.harvest self ["repo" "shells"]; + packages = std.harvest self ["bin" "packages"]; + }; + + nixConfig = { + extra-substituters = [ + "https://nix-community.cachix.org" + ]; + extra-trusted-public-keys = [ + "nix-community.cachix.org-1:mB9FSh9qf2dCimDSUo8Zy7bkq5CX+/rkCWyvRCYg3Fs=" + ]; + }; +} diff --git a/nix/bin/packages.nix b/nix/bin/packages.nix new file mode 100644 index 0000000..3bcc6f5 --- /dev/null +++ b/nix/bin/packages.nix @@ -0,0 +1,20 @@ +{ + inputs, + cell, +}: let + inherit (inputs) std self cells; + inherit (inputs.nixpkgs) pkgs; + + crane = inputs.crane.lib.overrideToolchain cells.repo.rust.toolchain; +in { + # sane default for a binary package + default = crane.buildPackage { + src = std.incl self [ + "${self}/Cargo.lock" + "${self}/Cargo.toml" + "${self}/src" + ]; + + buildInputs = [pkgs.openssl pkgs.pkgconfig]; + }; +} diff --git a/nix/repo/rust.nix b/nix/repo/rust.nix new file mode 100644 index 0000000..91fa1e1 --- /dev/null +++ b/nix/repo/rust.nix @@ -0,0 +1,23 @@ +# export fenix toolchain as its own package set +{ + inputs, + cell, +}: let + inherit (inputs) fenix; + + # you may change "default" to any of "[minimal|default|complete|latest]" for variants + # see upstream fenix documentation for details + rustPkgs = builtins.removeAttrs fenix.packages.complete ["withComponents" "name" "type"]; +in + # add rust-analyzer from nightly, if not present + if rustPkgs ? rust-analyzer + then rustPkgs + else + rustPkgs + // { + inherit (fenix.packages) rust-analyzer; + toolchain = fenix.packages.combine [ + (builtins.attrValues rustPkgs) + fenix.packages.rust-analyzer + ]; + } diff --git a/nix/repo/shells.nix b/nix/repo/shells.nix new file mode 100644 index 0000000..8c11358 --- /dev/null +++ b/nix/repo/shells.nix @@ -0,0 +1,92 @@ +{ + inputs, + cell, +}: let + inherit (inputs.std) std lib; + inherit (inputs) nixpkgs; + inherit (inputs.cells) bin; + + l = nixpkgs.lib // builtins; + + dev = lib.dev.mkShell { + packages = [ + nixpkgs.pkg-config + ]; + language.rust = { + packageSet = cell.rust; + enableDefaultToolchain = true; + tools = ["toolchain"]; # fenix collates them all in a convenience derivation + }; + + devshell.startup.link-cargo-home = { + deps = []; + text = '' + # ensure CARGO_HOME is populated + mkdir -p $PRJ_DATA_DIR/cargo + ln -snf -t $PRJ_DATA_DIR/cargo $(ls -d ${cell.rust.toolchain}/*) + ''; + }; + + env = [ + { + # ensures subcommands are picked up from the right place + # but also needs to be writable; see link-cargo-home above + name = "CARGO_HOME"; + eval = "$PRJ_DATA_DIR/cargo"; + } + { + # ensure we know where rustup_home will be + name = "RUSTUP_HOME"; + eval = "$PRJ_DATA_DIR/rustup"; + } + { + name = "RUST_SRC_PATH"; + # accessing via toolchain doesn't fail if it's not there + # and rust-analyzer is graceful if it's not set correctly: + # https://github.com/rust-lang/rust-analyzer/blob/7f1234492e3164f9688027278df7e915bc1d919c/crates/project-model/src/sysroot.rs#L196-L211 + value = "${cell.rust.toolchain}/lib/rustlib/src/rust/library"; + } + { + name = "PKG_CONFIG_PATH"; + value = l.makeSearchPath "lib/pkgconfig" bin.packages.default.buildInputs; + } + ]; + imports = [ + "${inputs.std.inputs.devshell}/extra/language/rust.nix" + ]; + + commands = let + rustCmds = + l.map (name: { + inherit name; + package = cell.rust.toolchain; # has all bins + category = "rust dev"; + # fenix doesn't include package descriptions, so pull those out of their equivalents in nixpkgs + help = nixpkgs.${name}.meta.description; + }) [ + "rustc" + "cargo" + "rustfmt" + "rust-analyzer" + ]; + in + [ + { + package = nixpkgs.treefmt; + category = "repo tools"; + } + { + package = nixpkgs.alejandra; + category = "repo tools"; + } + { + package = std.cli.default; + category = "std"; + } + ] + ++ rustCmds; + }; +in { + inherit dev; + default = dev; +} diff --git a/rustfmt.toml b/rustfmt.toml new file mode 100644 index 0000000..82fc48b --- /dev/null +++ b/rustfmt.toml @@ -0,0 +1,77 @@ +max_width = 80 +hard_tabs = true +tab_spaces = 4 +newline_style = "Unix" +use_small_heuristics = "Default" +fn_call_width = 60 +attr_fn_like_width = 70 +struct_lit_width = 18 +struct_variant_width = 35 +array_width = 60 +chain_width = 60 +single_line_if_else_max_width = 50 +reorder_imports = true +reorder_modules = true +remove_nested_parens = true +short_array_element_width_threshold = 10 +match_arm_leading_pipes = "Never" +fn_args_layout = "Vertical" +match_block_trailing_comma = false +edition = "2021" +merge_derives = true +use_try_shorthand = true +use_field_init_shorthand = true +force_explicit_abi = true +disable_all_formatting = false +# --- unstable settings --- +# indent_style = "Block" +# wrap_comments = false +# format_code_in_doc_comments = false +# doc_comment_code_block_width = 100 +# normalize_comments = false +# normalize_doc_attributes = false +# format_strings = false +# format_macro_matchers = false +# format_macro_bodies = true +# hex_literal_case = "Preserve" +# empty_item_single_line = true +# struct_lit_single_line = true +# fn_single_line = false +# comment_width = 80 +# where_single_line = false +# imports_indent = "Block" +# imports_layout = "Mixed" +# imports_granularity = "Preserve" +# group_imports = "Preserve" +# reorder_impl_items = false +# type_punctuation_density = "Wide" +# space_before_colon = false +# space_after_colon = true +# spaces_around_ranges = false +# binop_separator = "Front" +# combine_control_expr = true +# overflow_delimited_expr = false +# struct_field_align_threshold = 0 +# enum_discrim_align_threshold = 0 +# match_arm_blocks = true +# force_multiline_blocks = false +# brace_style = "SameLineWhere" +# control_brace_style = "AlwaysSameLine" +# trailing_semicolon = true +# trailing_comma = "Vertical" +# version = "One" +# blank_lines_upper_bound = 1 +# blank_lines_lower_bound = 0 +# inline_attribute_width = 0 +# format_generated_files = true +# condense_wildcard_suffixes = false +# color = "Auto" +# required_version = "1.5.1" +# unstable_features = false +# skip_children = false +# hide_parse_errors = false +# error_on_line_overflow = false +# error_on_unformatted = false +# ignore = [] +# emit_mode = "Files" +# make_backup = false From cf7c83a534c2b8e89c75c35913e4f54c69b9923c Mon Sep 17 00:00:00 2001 From: Timothy DeHerrera Date: Wed, 30 Aug 2023 18:00:25 -0600 Subject: [PATCH 03/18] feat: use treefmt for project wide formatting --- .gitignore | 6 -- src/main.rs | 291 ++++++++++++++++++++++++++------------------------- treefmt.toml | 21 ++++ 3 files changed, 171 insertions(+), 147 deletions(-) create mode 100644 treefmt.toml diff --git a/.gitignore b/.gitignore index a6b9c32..650c753 100644 --- a/.gitignore +++ b/.gitignore @@ -14,11 +14,5 @@ result .data .run -# nixago: ignore-linked-files -lefthook.yml -.editorconfig -.conform.yaml -treefmt.toml - # nixago-auto-created: mdbook-build-folder docs/build diff --git a/src/main.rs b/src/main.rs index c38c6b4..35e42d5 100644 --- a/src/main.rs +++ b/src/main.rs @@ -23,156 +23,165 @@ use trust_dns_client::udp::UdpClientConnection; const NS1_GOOGLE_COM_IP_ADDR: &'static str = "216.239.32.10:53"; fn env_var(n: &str) -> String { - let err = "Environment Variables CLOUDFLARE_RECORDS and either CLOUDFLARE_APITOKEN or CLOUDFLARE_EMAIL and CLOUDFLARE_APIKEY must be set!"; - env::var(n).ok().expect(&err) + let err = "Environment Variables CLOUDFLARE_RECORDS and either CLOUDFLARE_APITOKEN or CLOUDFLARE_EMAIL and CLOUDFLARE_APIKEY must be set!"; + env::var(n).ok().expect(&err) } // overloaded function. no body is treated as a get, body is treated as a put fn cloudflare_api( - client: &reqwest::blocking::Client, - url: &str, - body: Option, + client: &reqwest::blocking::Client, + url: &str, + body: Option, ) -> Result { - - let request = match body { - Some(body) => client.put(url).body(body), - None => client.get(url), - }; - - let authorized_request = match env::var("CLOUDFLARE_APITOKEN") { - Ok(val) => { - let mut bearer = "Bearer ".to_owned(); - bearer.push_str(&val); - request.header("Authorization", bearer.to_owned()) - } - Err(_e) => { - let cloudflare_apikey = env_var("CLOUDFLARE_APIKEY"); - let cloudflare_email = env_var("CLOUDFLARE_EMAIL"); - request - .header("X-Auth-Key", cloudflare_apikey.to_owned()) - .header("X-Auth-Email", cloudflare_email.to_owned()) - } - }; - - let response_json: Value = authorized_request - .send() - .unwrap() - .json() - .unwrap(); - - let success = response_json - .as_object() - .unwrap() - .get("success") - .unwrap() - .as_bool() - .unwrap(); - if !success { - return Err(format!("Request not successful: {}", response_json)); - } - - Ok(response_json) + let request = match body { + Some(body) => client.put(url).body(body), + None => client.get(url), + }; + + let authorized_request = match env::var("CLOUDFLARE_APITOKEN") { + Ok(val) => { + let mut bearer = "Bearer ".to_owned(); + bearer.push_str(&val); + request.header("Authorization", bearer.to_owned()) + } + Err(_e) => { + let cloudflare_apikey = env_var("CLOUDFLARE_APIKEY"); + let cloudflare_email = env_var("CLOUDFLARE_EMAIL"); + request + .header("X-Auth-Key", cloudflare_apikey.to_owned()) + .header("X-Auth-Email", cloudflare_email.to_owned()) + } + }; + + let response_json: Value = + authorized_request.send().unwrap().json().unwrap(); + + let success = response_json + .as_object() + .unwrap() + .get("success") + .unwrap() + .as_bool() + .unwrap(); + if !success { + return Err(format!("Request not successful: {}", response_json)); + } + + Ok(response_json) } fn get_current_ip() -> Result { - let gdns_addr = (NS1_GOOGLE_COM_IP_ADDR) - .parse() - .expect("Couldn't get Google DNS Socket Addr"); - let conn = UdpClientConnection::new(gdns_addr).expect("Couldn't open DNS UDP Connection"); - let client = SyncClient::new(conn); - - let name = domain::Name::new(); - let name = name - .append_label("o-o") - .unwrap() - .append_label("myaddr") - .unwrap() - .append_label("l") - .unwrap() - .append_label("google") - .unwrap() - .append_label("com") - .unwrap(); - let response = client.query(&name, DNSClass::IN, RecordType::TXT).unwrap(); - - let record = &response.answers()[0]; - match record.rdata() { - &RData::TXT(ref txt) => { - let val = txt.txt_data(); - return Ok(String::from_utf8(val[0].to_vec()).unwrap()); - } - _ => return Err(()), - } + let gdns_addr = (NS1_GOOGLE_COM_IP_ADDR) + .parse() + .expect("Couldn't get Google DNS Socket Addr"); + let conn = UdpClientConnection::new(gdns_addr) + .expect("Couldn't open DNS UDP Connection"); + let client = SyncClient::new(conn); + + let name = domain::Name::new(); + let name = name + .append_label("o-o") + .unwrap() + .append_label("myaddr") + .unwrap() + .append_label("l") + .unwrap() + .append_label("google") + .unwrap() + .append_label("com") + .unwrap(); + let response = client.query(&name, DNSClass::IN, RecordType::TXT).unwrap(); + + let record = &response.answers()[0]; + match record.rdata() { + &RData::TXT(ref txt) => { + let val = txt.txt_data(); + return Ok(String::from_utf8(val[0].to_vec()).unwrap()); + } + _ => return Err(()), + } } fn main() { - pretty_env_logger::init(); - - let current_ip = get_current_ip() - .ok() - .expect("Was unable to determine current IP address."); - info!("{}", current_ip); - let client = reqwest::blocking::Client::new(); - - let cloudflare_records_env = env_var("CLOUDFLARE_RECORDS"); - let cloudflare_records: Vec<&str> = cloudflare_records_env.split(|c: char| c == ',').collect(); - - let zones_url = "https://api.cloudflare.com/client/v4/zones"; - let zones_json = cloudflare_api(&client, zones_url, None).unwrap(); - - let zone_ids = zones_json - .as_object() - .unwrap() - .get("result") - .unwrap() - .as_array() - .unwrap() - .iter() - .map(|ref zone_node| zone_node.get("id").unwrap().as_str().unwrap()); - - for zone_id in zone_ids { - let records_url = format!( - "https://api.cloudflare.com/client/v4/zones/{}/dns_records", - zone_id - ); - let records_json = cloudflare_api(&client, &*records_url, None).unwrap(); - - let records = records_json - .as_object() - .unwrap() - .get("result") - .unwrap() - .as_array() - .unwrap() - .iter(); - - for record in records { - let record_id = record.get("id").unwrap().as_str().unwrap(); - let record_type = record.get("type").unwrap().as_str().unwrap(); - let record_name = record.get("name").unwrap().as_str().unwrap(); - let record_content = record.get("content").unwrap().as_str().unwrap(); - - if !cloudflare_records.contains(&record_name) || record_type != "A" { - continue; - } - - if record_content == current_ip { - info!("{} skipped, up to date", record_name); - continue; - } - - print!("{} ({} -> {})... ", record_name, record_content, current_ip); - io::stdout().flush().ok(); - - let record_url = format!( - "https://api.cloudflare.com/client/v4/zones/{}/dns_records/{}", - zone_id, record_id - ); - let record_update_body = format!( - r#"{{"name": "{}", "content": "{}", "type": "{}", "proxied": true}}"#, - record_name, current_ip, record_type - ); - cloudflare_api(&client, &*record_url, Some(record_update_body.to_string())).unwrap(); - } - } + pretty_env_logger::init(); + + let current_ip = get_current_ip() + .ok() + .expect("Was unable to determine current IP address."); + info!("{}", current_ip); + let client = reqwest::blocking::Client::new(); + + let cloudflare_records_env = env_var("CLOUDFLARE_RECORDS"); + let cloudflare_records: Vec<&str> = + cloudflare_records_env.split(|c: char| c == ',').collect(); + + let zones_url = "https://api.cloudflare.com/client/v4/zones"; + let zones_json = cloudflare_api(&client, zones_url, None).unwrap(); + + let zone_ids = zones_json + .as_object() + .unwrap() + .get("result") + .unwrap() + .as_array() + .unwrap() + .iter() + .map(|ref zone_node| zone_node.get("id").unwrap().as_str().unwrap()); + + for zone_id in zone_ids { + let records_url = format!( + "https://api.cloudflare.com/client/v4/zones/{}/dns_records", + zone_id + ); + let records_json = + cloudflare_api(&client, &*records_url, None).unwrap(); + + let records = records_json + .as_object() + .unwrap() + .get("result") + .unwrap() + .as_array() + .unwrap() + .iter(); + + for record in records { + let record_id = record.get("id").unwrap().as_str().unwrap(); + let record_type = record.get("type").unwrap().as_str().unwrap(); + let record_name = record.get("name").unwrap().as_str().unwrap(); + let record_content = + record.get("content").unwrap().as_str().unwrap(); + + if !cloudflare_records.contains(&record_name) || record_type != "A" + { + continue; + } + + if record_content == current_ip { + info!("{} skipped, up to date", record_name); + continue; + } + + print!( + "{} ({} -> {})... ", + record_name, record_content, current_ip + ); + io::stdout().flush().ok(); + + let record_url = format!( + "https://api.cloudflare.com/client/v4/zones/{}/dns_records/{}", + zone_id, record_id + ); + let record_update_body = format!( + r#"{{"name": "{}", "content": "{}", "type": "{}", "proxied": true}}"#, + record_name, current_ip, record_type + ); + cloudflare_api( + &client, + &*record_url, + Some(record_update_body.to_string()), + ) + .unwrap(); + } + } } diff --git a/treefmt.toml b/treefmt.toml new file mode 100644 index 0000000..3bfe4e2 --- /dev/null +++ b/treefmt.toml @@ -0,0 +1,21 @@ +# One CLI to format the code tree - https://github.com/numtide/treefmt +[formatter.nix] +command = "alejandra" +includes = ["*.nix"] + +[formatter.shell] +command = "shfmt" +options = [ + "-i", + "2", # indent 2 + "-s", # simplify the code + "-w", # write back to the file + +] +includes = ["*.sh"] +excludes = [] + +[formatter.rust] +command = "rustfmt" +includes = ["*.rs"] +excludes = [] From f4ce952d15642c36b75dcea1f82ab735b79ae0cd Mon Sep 17 00:00:00 2001 From: Timothy DeHerrera Date: Wed, 30 Aug 2023 18:05:40 -0600 Subject: [PATCH 04/18] chore: address clippy lints & use Rust 2021 --- Cargo.toml | 2 +- src/main.rs | 22 ++++++++++------------ 2 files changed, 11 insertions(+), 13 deletions(-) diff --git a/Cargo.toml b/Cargo.toml index 282e331..e348654 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -2,7 +2,7 @@ name = "cfdyndns" version = "0.0.3" authors = ["Cole Mickens "] -edition = "2018" +edition = "2021" [dependencies] log = "0.4.8" diff --git a/src/main.rs b/src/main.rs index 35e42d5..d8db733 100644 --- a/src/main.rs +++ b/src/main.rs @@ -20,11 +20,11 @@ use trust_dns_client::rr::record_data::RData; use trust_dns_client::rr::record_type::RecordType; use trust_dns_client::udp::UdpClientConnection; -const NS1_GOOGLE_COM_IP_ADDR: &'static str = "216.239.32.10:53"; +const NS1_GOOGLE_COM_IP_ADDR: &str = "216.239.32.10:53"; fn env_var(n: &str) -> String { let err = "Environment Variables CLOUDFLARE_RECORDS and either CLOUDFLARE_APITOKEN or CLOUDFLARE_EMAIL and CLOUDFLARE_APIKEY must be set!"; - env::var(n).ok().expect(&err) + env::var(n).expect(err) } // overloaded function. no body is treated as a get, body is treated as a put @@ -94,20 +94,19 @@ fn get_current_ip() -> Result { let record = &response.answers()[0]; match record.rdata() { - &RData::TXT(ref txt) => { + RData::TXT(txt) => { let val = txt.txt_data(); - return Ok(String::from_utf8(val[0].to_vec()).unwrap()); + Ok(String::from_utf8(val[0].to_vec()).unwrap()) } - _ => return Err(()), + _ => Err(()), } } fn main() { pretty_env_logger::init(); - let current_ip = get_current_ip() - .ok() - .expect("Was unable to determine current IP address."); + let current_ip = + get_current_ip().expect("Was unable to determine current IP address."); info!("{}", current_ip); let client = reqwest::blocking::Client::new(); @@ -126,15 +125,14 @@ fn main() { .as_array() .unwrap() .iter() - .map(|ref zone_node| zone_node.get("id").unwrap().as_str().unwrap()); + .map(|zone_node| zone_node.get("id").unwrap().as_str().unwrap()); for zone_id in zone_ids { let records_url = format!( "https://api.cloudflare.com/client/v4/zones/{}/dns_records", zone_id ); - let records_json = - cloudflare_api(&client, &*records_url, None).unwrap(); + let records_json = cloudflare_api(&client, &records_url, None).unwrap(); let records = records_json .as_object() @@ -178,7 +176,7 @@ fn main() { ); cloudflare_api( &client, - &*record_url, + &record_url, Some(record_update_body.to_string()), ) .unwrap(); From 223b780439862f34b86a9573a12cf9b1935d0e81 Mon Sep 17 00:00:00 2001 From: Timothy DeHerrera Date: Wed, 30 Aug 2023 18:22:03 -0600 Subject: [PATCH 05/18] fix: don't change proxy status Thanks to colemickens/cfdyndns#7 which could not be directly applied due to conflict. --- src/main.rs | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/main.rs b/src/main.rs index d8db733..9811897 100644 --- a/src/main.rs +++ b/src/main.rs @@ -149,6 +149,8 @@ fn main() { let record_name = record.get("name").unwrap().as_str().unwrap(); let record_content = record.get("content").unwrap().as_str().unwrap(); + let record_proxied = + record.get("proxied").unwrap().as_bool().unwrap(); if !cloudflare_records.contains(&record_name) || record_type != "A" { @@ -171,8 +173,8 @@ fn main() { zone_id, record_id ); let record_update_body = format!( - r#"{{"name": "{}", "content": "{}", "type": "{}", "proxied": true}}"#, - record_name, current_ip, record_type + r#"{{"name": "{}", "content": "{}", "type": "{}", "proxied": {}}}"#, + record_name, current_ip, record_type, record_proxied ); cloudflare_api( &client, From 4a3afb3fbd1aea8268b1b8d0bcb9b482321420ab Mon Sep 17 00:00:00 2001 From: Timothy DeHerrera Date: Thu, 31 Aug 2023 16:59:34 -0600 Subject: [PATCH 06/18] fix: use public-ip crate to resolve current ip DNS resolution from google produced a different IP every time, which isn't what we want. --- Cargo.lock | 444 +++++++++++++++++++++++++++++++++++++--------------- Cargo.toml | 4 +- src/main.rs | 64 ++------ 3 files changed, 327 insertions(+), 185 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 6d48c3e..5a10bb4 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -26,21 +26,6 @@ dependencies = [ "memchr", ] -[[package]] -name = "android-tzdata" -version = "0.1.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e999941b234f3131b00bc13c22d06e8c5ff726d1b6318ac7eb276997bbb4fef0" - -[[package]] -name = "android_system_properties" -version = "0.1.5" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "819e7219dbd41043ac279b19830f2efc897156490d7fd6ea916720117ee66311" -dependencies = [ - "libc", -] - [[package]] name = "async-trait" version = "0.1.73" @@ -135,10 +120,10 @@ version = "0.0.3" dependencies = [ "log", "pretty_env_logger", + "public-ip", "reqwest", - "serde", "serde_json", - "trust-dns-client", + "tokio 1.32.0", ] [[package]] @@ -153,21 +138,6 @@ version = "1.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" -[[package]] -name = "chrono" -version = "0.4.28" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "95ed24df0632f708f5f6d8082675bef2596f7084dee3dd55f632290bf35bfe0f" -dependencies = [ - "android-tzdata", - "iana-time-zone", - "js-sys", - "num-traits", - "time", - "wasm-bindgen", - "windows-targets", -] - [[package]] name = "core-foundation" version = "0.9.3" @@ -184,12 +154,90 @@ version = "0.8.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e496a50fda8aacccc86d7529e2c1e0892dbd0f898a6b5645b5561b89c3210efa" +[[package]] +name = "darling" +version = "0.10.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0d706e75d87e35569db781a9b5e2416cff1236a47ed380831f959382ccd5f858" +dependencies = [ + "darling_core", + "darling_macro", +] + +[[package]] +name = "darling_core" +version = "0.10.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f0c960ae2da4de88a91b2d920c2a7233b400bc33cb28453a2987822d8392519b" +dependencies = [ + "fnv", + "ident_case", + "proc-macro2", + "quote", + "strsim", + "syn 1.0.109", +] + +[[package]] +name = "darling_macro" +version = "0.10.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d9b5a2f4ac4969822c62224815d069952656cadc7084fdca9751e6d959189b72" +dependencies = [ + "darling_core", + "quote", + "syn 1.0.109", +] + [[package]] name = "data-encoding" version = "2.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c2e66c9d817f1720209181c316d28635c050fa304f9c79e47a520882661b7308" +[[package]] +name = "deranged" +version = "0.3.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f2696e8a945f658fd14dc3b87242e6b80cd0f36ff04ea560fa39082368847946" + +[[package]] +name = "derive_builder" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a2658621297f2cf68762a6f7dc0bb7e1ff2cfd6583daef8ee0fed6f7ec468ec0" +dependencies = [ + "darling", + "derive_builder_core", + "proc-macro2", + "quote", + "syn 1.0.109", +] + +[[package]] +name = "derive_builder_core" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2791ea3e372c8495c0bc2033991d76b512cd799d07491fbd6890124db9458bef" +dependencies = [ + "darling", + "proc-macro2", + "quote", + "syn 1.0.109", +] + +[[package]] +name = "dns-lookup" +version = "1.0.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "53ecafc952c4528d9b51a458d1a8904b81783feff9fde08ab6ed2545ff396872" +dependencies = [ + "cfg-if 1.0.0", + "libc", + "socket2 0.4.9", + "winapi 0.3.9", +] + [[package]] name = "encoding_rs" version = "0.8.33" @@ -311,6 +359,7 @@ checksum = "23342abe12aba583913b2e62f22225ff9c950774065e4bfb61a19cd9770fec40" dependencies = [ "futures-channel", "futures-core", + "futures-executor", "futures-io", "futures-sink", "futures-task", @@ -333,12 +382,34 @@ version = "0.3.28" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4bca583b7e26f571124fe5b7561d49cb2868d79116cfa0eefce955557c6fee8c" +[[package]] +name = "futures-executor" +version = "0.3.28" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ccecee823288125bd88b4d7f565c9e58e41858e47ab72e8ea2d64e93624386e0" +dependencies = [ + "futures-core", + "futures-task", + "futures-util", +] + [[package]] name = "futures-io" version = "0.3.28" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4fff74096e71ed47f8e023204cfd0aa1289cd54ae5430a9523be060cdb849964" +[[package]] +name = "futures-macro" +version = "0.3.28" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "89ca545a94061b6365f2c7355b4b32bd20df3ff95f02da9329b34ccc3bd6ee72" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.29", +] + [[package]] name = "futures-sink" version = "0.3.28" @@ -360,6 +431,7 @@ dependencies = [ "futures-channel", "futures-core", "futures-io", + "futures-macro", "futures-sink", "futures-task", "memchr", @@ -370,13 +442,13 @@ dependencies = [ [[package]] name = "getrandom" -version = "0.1.16" +version = "0.2.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8fc3cb4d91f53b50155bdcfd23f6a4c39ae1969c2ae85982b135750cccaf5fce" +checksum = "be4136b2a15dd319360be1c07d9933517ccf0be8f16bf62a3bee4f0d618df427" dependencies = [ "cfg-if 1.0.0", "libc", - "wasi 0.9.0+wasi-snapshot-preview1", + "wasi", ] [[package]] @@ -399,7 +471,7 @@ dependencies = [ "http", "indexmap", "slab", - "tokio", + "tokio 0.2.25", "tokio-util", "tracing", "tracing-futures", @@ -453,6 +525,17 @@ dependencies = [ "http", ] +[[package]] +name = "http-body" +version = "0.4.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d5f38f16d184e36f2408a55281cd658ecbd3ca05cce6d6510a176eca393e26d1" +dependencies = [ + "bytes 1.4.0", + "http", + "pin-project-lite 0.2.13", +] + [[package]] name = "httparse" version = "1.8.0" @@ -465,6 +548,12 @@ version = "0.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "494b4d60369511e7dea41cf646832512a94e542f68bb9c49e54518e0f468eb47" +[[package]] +name = "httpdate" +version = "1.0.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "df3b46402a9d5adb4c86a0cf463f42e19994e3ee891101b1841f30a545cb49a9" + [[package]] name = "humantime" version = "1.3.0" @@ -486,54 +575,74 @@ dependencies = [ "futures-util", "h2", "http", - "http-body", + "http-body 0.3.1", "httparse", - "httpdate", + "httpdate 0.3.2", "itoa 0.4.8", "pin-project", - "socket2", - "tokio", + "socket2 0.3.19", + "tokio 0.2.25", "tower-service", "tracing", "want", ] [[package]] -name = "hyper-tls" -version = "0.4.3" +name = "hyper" +version = "0.14.27" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d979acc56dcb5b8dddba3917601745e877576475aa046df3226eabdecef78eed" +checksum = "ffb1cfd654a8219eaef89881fdb3bb3b1cdc5fa75ded05d6933b2b382e395468" dependencies = [ - "bytes 0.5.6", - "hyper", - "native-tls", - "tokio", - "tokio-tls", + "bytes 1.4.0", + "futures-channel", + "futures-core", + "futures-util", + "http", + "http-body 0.4.5", + "httparse", + "httpdate 1.0.3", + "itoa 1.0.9", + "pin-project-lite 0.2.13", + "socket2 0.4.9", + "tokio 1.32.0", + "tower-service", + "tracing", + "want", ] [[package]] -name = "iana-time-zone" -version = "0.1.57" +name = "hyper-system-resolver" +version = "0.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2fad5b825842d2b38bd206f3e81d6957625fd7f0a361e345c30e01a0ae2dd613" +checksum = "6eea26c5d0b6ab9d72219f65000af310f042a740926f7b2fa3553e774036e2e7" dependencies = [ - "android_system_properties", - "core-foundation-sys", - "iana-time-zone-haiku", - "js-sys", - "wasm-bindgen", - "windows", + "derive_builder", + "dns-lookup", + "hyper 0.14.27", + "tokio 1.32.0", + "tower-service", + "tracing", ] [[package]] -name = "iana-time-zone-haiku" -version = "0.1.2" +name = "hyper-tls" +version = "0.4.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f31827a206f56af32e590ba56d5d2d085f558508192593743f16b2306495269f" +checksum = "d979acc56dcb5b8dddba3917601745e877576475aa046df3226eabdecef78eed" dependencies = [ - "cc", + "bytes 0.5.6", + "hyper 0.13.10", + "native-tls", + "tokio 0.2.25", + "tokio-tls", ] +[[package]] +name = "ident_case" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b9e0384b61958566e926dc50660321d12159025e767c18e043daf26b70104c39" + [[package]] name = "idna" version = "0.2.3" @@ -691,6 +800,17 @@ dependencies = [ "winapi 0.2.8", ] +[[package]] +name = "mio" +version = "0.8.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "927a765cd3fc26206e66b296465fa9d3e5ab003e651c1b3c060e7956d96b19d2" +dependencies = [ + "libc", + "wasi", + "windows-sys", +] + [[package]] name = "miow" version = "0.2.2" @@ -734,17 +854,11 @@ dependencies = [ [[package]] name = "nibble_vec" -version = "0.0.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c8d77f3db4bce033f4d04db08079b2ef1c3d02b44e86f25d08886fafa7756ffa" - -[[package]] -name = "num-traits" -version = "0.2.16" +version = "0.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f30b0abd723be7e2ffca1272140fac1a2f084c77ec3e123c192b66af1ee9e6c2" +checksum = "77a5d83df9f36fe23f0c3648c6bbb8b0298bb5f1939c8f2704431371f4b84d43" dependencies = [ - "autocfg", + "smallvec", ] [[package]] @@ -891,6 +1005,27 @@ dependencies = [ "unicode-ident", ] +[[package]] +name = "public-ip" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7b4c40db5262d93298c363a299f8bc1b3a956a78eecddba3bc0e58b76e2f419a" +dependencies = [ + "dns-lookup", + "futures-core", + "futures-util", + "http", + "hyper 0.14.27", + "hyper-system-resolver", + "pin-project-lite 0.2.13", + "thiserror", + "tokio 1.32.0", + "tracing", + "tracing-futures", + "trust-dns-client", + "trust-dns-proto", +] + [[package]] name = "quick-error" version = "1.2.3" @@ -908,9 +1043,9 @@ dependencies = [ [[package]] name = "radix_trie" -version = "0.1.6" +version = "0.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3d3681b28cd95acfb0560ea9441f82d6a4504fa3b15b97bd7b6e952131820e95" +checksum = "c069c179fcdc6a2fe24d8d18305cf085fdbd4f922c041943e203685d6a1c58fd" dependencies = [ "endian-type", "nibble_vec", @@ -918,22 +1053,20 @@ dependencies = [ [[package]] name = "rand" -version = "0.7.3" +version = "0.8.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6a6b1679d49b24bbfe0c803429aa1874472f50d9b363131f0e89fc356b544d03" +checksum = "34af8d1a0e25924bc5b7c43c079c942339d8f0a8b57c39049bef581b46327404" dependencies = [ - "getrandom", "libc", "rand_chacha", "rand_core", - "rand_hc", ] [[package]] name = "rand_chacha" -version = "0.2.2" +version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f4c8ed856279c9737206bf725bf36935d8666ead7aa69b52be55af369d193402" +checksum = "e6c10a63a0fa32252be49d21e7709d4d4baf8d231c2dbce1eaa8141b9b127d88" dependencies = [ "ppv-lite86", "rand_core", @@ -941,22 +1074,13 @@ dependencies = [ [[package]] name = "rand_core" -version = "0.5.1" +version = "0.6.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "90bde5296fc891b0cef12a6d03ddccc162ce7b2aff54160af9338f8d40df6d19" +checksum = "ec0be4795e2f6a28069bec0b5ff3e2ac9bafc99e6a9a7dc3547996c5c816922c" dependencies = [ "getrandom", ] -[[package]] -name = "rand_hc" -version = "0.2.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ca3129af7b92a17112d59ad498c6f81eaf463253766b90396d39ea7a39d6613c" -dependencies = [ - "rand_core", -] - [[package]] name = "redox_syscall" version = "0.3.5" @@ -1007,8 +1131,8 @@ dependencies = [ "futures-core", "futures-util", "http", - "http-body", - "hyper", + "http-body 0.3.1", + "hyper 0.13.10", "hyper-tls", "ipnet", "js-sys", @@ -1022,7 +1146,7 @@ dependencies = [ "serde", "serde_json", "serde_urlencoded", - "tokio", + "tokio 0.2.25", "tokio-tls", "url", "wasm-bindgen", @@ -1039,9 +1163,9 @@ checksum = "d626bb9dae77e28219937af045c257c28bfd3f69333c512553507f5f9798cb76" [[package]] name = "rustix" -version = "0.38.10" +version = "0.38.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ed6248e1caa625eb708e266e06159f135e8c26f2bb7ceb72dc4b2766d0340964" +checksum = "c0c3dde1fc030af041adc40e79c0e7fbcf431dd24870053d187d7c66e4b87453" dependencies = [ "bitflags 2.4.0", "errno", @@ -1157,6 +1281,32 @@ dependencies = [ "winapi 0.3.9", ] +[[package]] +name = "socket2" +version = "0.4.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "64a4a911eed85daf18834cfaa86a79b7d266ff93ff5ba14005426219480ed662" +dependencies = [ + "libc", + "winapi 0.3.9", +] + +[[package]] +name = "socket2" +version = "0.5.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2538b18701741680e0322a2302176d3253a35388e2e62f172f64f4f16605f877" +dependencies = [ + "libc", + "windows-sys", +] + +[[package]] +name = "strsim" +version = "0.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6446ced80d6c486436db5c078dde11a9f73d42b57fb273121e160b84f63d894c" + [[package]] name = "syn" version = "1.0.109" @@ -1223,15 +1373,21 @@ dependencies = [ [[package]] name = "time" -version = "0.1.45" +version = "0.3.28" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1b797afad3f312d1c66a56d11d0316f916356d11bd158fbc6ca6389ff6bf805a" +checksum = "17f6bb557fd245c28e6411aa56b6403c689ad95061f50e4be16c274e70a17e48" dependencies = [ - "libc", - "wasi 0.10.0+wasi-snapshot-preview1", - "winapi 0.3.9", + "deranged", + "serde", + "time-core", ] +[[package]] +name = "time-core" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7300fbefb4dadc1af235a9cef3737cea692a9d97e1b9cbcd4ebdae6f8868e6fb" + [[package]] name = "tinyvec" version = "1.6.0" @@ -1259,12 +1415,39 @@ dependencies = [ "iovec", "lazy_static", "memchr", - "mio", + "mio 0.6.23", "num_cpus", "pin-project-lite 0.1.12", "slab", ] +[[package]] +name = "tokio" +version = "1.32.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "17ed6077ed6cd6c74735e21f37eb16dc3935f96878b1fe961074089cc80893f9" +dependencies = [ + "backtrace", + "libc", + "mio 0.8.8", + "num_cpus", + "pin-project-lite 0.2.13", + "socket2 0.5.3", + "tokio-macros", + "windows-sys", +] + +[[package]] +name = "tokio-macros" +version = "2.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "630bdcf245f78637c13ec01ffae6187cca34625e8c63150d424b59e55af2675e" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.29", +] + [[package]] name = "tokio-tls" version = "0.3.1" @@ -1272,7 +1455,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9a70f4fcd7b3b24fb194f837560168208f669ca8cb70d0c4b862944452396343" dependencies = [ "native-tls", - "tokio", + "tokio 0.2.25", ] [[package]] @@ -1286,7 +1469,7 @@ dependencies = [ "futures-sink", "log", "pin-project-lite 0.1.12", - "tokio", + "tokio 0.2.25", ] [[package]] @@ -1304,9 +1487,21 @@ dependencies = [ "cfg-if 1.0.0", "log", "pin-project-lite 0.2.13", + "tracing-attributes", "tracing-core", ] +[[package]] +name = "tracing-attributes" +version = "0.1.26" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5f4f31f56159e98206da9efd823404b79b6ef3143b4a7ab76e67b1751b25a4ab" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.29", +] + [[package]] name = "tracing-core" version = "0.1.31" @@ -1322,48 +1517,54 @@ version = "0.2.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "97d095ae15e245a057c8e8451bab9b3ee1e1f68e9ba2b4fbc18d0ac5237835f2" dependencies = [ + "futures", + "futures-task", "pin-project", "tracing", ] [[package]] name = "trust-dns-client" -version = "0.19.7" +version = "0.20.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e935ae5a26a2745fb5a6b95f0e206e1cfb7f00066892d2cf78a8fee87bc2e0c6" +checksum = "5b4ef9b9bde0559b78a4abb00339143750085f05e5a453efb7b8bef1061f09dc" dependencies = [ "cfg-if 1.0.0", - "chrono", "data-encoding", - "futures", + "futures-channel", + "futures-util", "lazy_static", "log", "radix_trie", "rand", "thiserror", - "tokio", + "time", + "tokio 1.32.0", "trust-dns-proto", ] [[package]] name = "trust-dns-proto" -version = "0.19.7" +version = "0.20.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1cad71a0c0d68ab9941d2fb6e82f8fb2e86d9945b94e1661dd0aaea2b88215a9" +checksum = "ca94d4e9feb6a181c690c4040d7a24ef34018d8313ac5044a61d21222ae24e31" dependencies = [ "async-trait", - "backtrace", "cfg-if 1.0.0", "data-encoding", "enum-as-inner", - "futures", + "futures-channel", + "futures-io", + "futures-util", "idna 0.2.3", + "ipnet", "lazy_static", "log", "rand", "smallvec", "thiserror", - "tokio", + "tinyvec", + "tokio 1.32.0", "url", ] @@ -1437,15 +1638,9 @@ dependencies = [ [[package]] name = "wasi" -version = "0.9.0+wasi-snapshot-preview1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cccddf32554fecc6acb585f82a32a72e28b48f8c4c1883ddfeeeaa96f7d8e519" - -[[package]] -name = "wasi" -version = "0.10.0+wasi-snapshot-preview1" +version = "0.11.0+wasi-snapshot-preview1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1a143597ca7c7793eff794def352d41792a93c481eb1042423ff7ff72ba2c31f" +checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" [[package]] name = "wasm-bindgen" @@ -1568,15 +1763,6 @@ version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" -[[package]] -name = "windows" -version = "0.48.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e686886bc078bc1b0b600cac0147aadb815089b6e4da64016cbd754b6342700f" -dependencies = [ - "windows-targets", -] - [[package]] name = "windows-sys" version = "0.48.0" diff --git a/Cargo.toml b/Cargo.toml index e348654..f3ec0af 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -8,6 +8,6 @@ edition = "2021" log = "0.4.8" pretty_env_logger = "0.4.0" reqwest = { version = "0.10.4", features = ["blocking", "json"] } -serde = "1.0.104" serde_json = "1.0.48" -trust-dns-client = "0.19.3" +public-ip = "^0.2" +tokio = { version = "^1", features = ["rt-multi-thread", "macros"] } diff --git a/src/main.rs b/src/main.rs index 9811897..f86600b 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,10 +1,3 @@ -extern crate log; -extern crate pretty_env_logger; -extern crate reqwest; -extern crate serde; -extern crate serde_json; -extern crate trust_dns_client; - use log::info; use serde_json::value::*; @@ -13,14 +6,7 @@ use std::env; use std::io; use std::io::prelude::*; -use trust_dns_client::client::{Client as _Client, SyncClient}; -use trust_dns_client::rr::dns_class::DNSClass; -use trust_dns_client::rr::domain; -use trust_dns_client::rr::record_data::RData; -use trust_dns_client::rr::record_type::RecordType; -use trust_dns_client::udp::UdpClientConnection; - -const NS1_GOOGLE_COM_IP_ADDR: &str = "216.239.32.10:53"; +use public_ip::{http, Version}; fn env_var(n: &str) -> String { let err = "Environment Variables CLOUDFLARE_RECORDS and either CLOUDFLARE_APITOKEN or CLOUDFLARE_EMAIL and CLOUDFLARE_APIKEY must be set!"; @@ -70,44 +56,14 @@ fn cloudflare_api( Ok(response_json) } -fn get_current_ip() -> Result { - let gdns_addr = (NS1_GOOGLE_COM_IP_ADDR) - .parse() - .expect("Couldn't get Google DNS Socket Addr"); - let conn = UdpClientConnection::new(gdns_addr) - .expect("Couldn't open DNS UDP Connection"); - let client = SyncClient::new(conn); - - let name = domain::Name::new(); - let name = name - .append_label("o-o") - .unwrap() - .append_label("myaddr") - .unwrap() - .append_label("l") - .unwrap() - .append_label("google") - .unwrap() - .append_label("com") - .unwrap(); - let response = client.query(&name, DNSClass::IN, RecordType::TXT).unwrap(); - - let record = &response.answers()[0]; - match record.rdata() { - RData::TXT(txt) => { - let val = txt.txt_data(); - Ok(String::from_utf8(val[0].to_vec()).unwrap()) - } - _ => Err(()), - } -} - -fn main() { +#[tokio::main] +async fn main() { pretty_env_logger::init(); - let current_ip = - get_current_ip().expect("Was unable to determine current IP address."); - info!("{}", current_ip); + let current_ipv4 = public_ip::addr_with(http::ALL, Version::V4) + .await + .expect("Was unable to determine current IP address."); + info!("{}", current_ipv4); let client = reqwest::blocking::Client::new(); let cloudflare_records_env = env_var("CLOUDFLARE_RECORDS"); @@ -157,14 +113,14 @@ fn main() { continue; } - if record_content == current_ip { + if record_content == current_ipv4.to_string() { info!("{} skipped, up to date", record_name); continue; } print!( "{} ({} -> {})... ", - record_name, record_content, current_ip + record_name, record_content, current_ipv4 ); io::stdout().flush().ok(); @@ -174,7 +130,7 @@ fn main() { ); let record_update_body = format!( r#"{{"name": "{}", "content": "{}", "type": "{}", "proxied": {}}}"#, - record_name, current_ip, record_type, record_proxied + record_name, current_ipv4, record_type, record_proxied ); cloudflare_api( &client, From 9c01b443f8e2ebe5fa6f2399cf4dfd3695cf2e82 Mon Sep 17 00:00:00 2001 From: Timothy DeHerrera Date: Fri, 1 Sep 2023 12:38:50 -0600 Subject: [PATCH 07/18] feat: refactor using cloudflare api crate Potentially finished but cannot test due to an upstream issue with one of the endpoints: cloudflare/cloudflare-rs#198 --- Cargo.lock | 620 +++++++++++++++++++++++++++------------------------- Cargo.toml | 3 +- src/main.rs | 247 +++++++++++---------- 3 files changed, 449 insertions(+), 421 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 5a10bb4..4ef19de 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -26,6 +26,27 @@ dependencies = [ "memchr", ] +[[package]] +name = "android-tzdata" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e999941b234f3131b00bc13c22d06e8c5ff726d1b6318ac7eb276997bbb4fef0" + +[[package]] +name = "android_system_properties" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "819e7219dbd41043ac279b19830f2efc897156490d7fd6ea916720117ee66311" +dependencies = [ + "libc", +] + +[[package]] +name = "anyhow" +version = "1.0.75" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a4668cab20f66d8d020e1fbc0ebe47217433c1b6c8f2040faf858554e394ace6" + [[package]] name = "async-trait" version = "0.1.73" @@ -45,7 +66,7 @@ checksum = "d9b39be18770d11421cdb1b9947a45dd3f37e93092cbf377614828a319d5fee8" dependencies = [ "hermit-abi 0.1.19", "libc", - "winapi 0.3.9", + "winapi", ] [[package]] @@ -62,7 +83,7 @@ checksum = "2089b7e3f35b9dd2d0ed921ead4f6d318c27680d4a5bd167b3ee120edb105837" dependencies = [ "addr2line", "cc", - "cfg-if 1.0.0", + "cfg-if", "libc", "miniz_oxide", "object", @@ -75,6 +96,12 @@ version = "0.13.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9e1b586273c5702936fe7b7d6896644d8be71e6314cfe09d3167c95f712589e8" +[[package]] +name = "base64" +version = "0.21.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "414dcefbc63d77c526a76b3afcf6fbb9b5e2791c19c3aa2297733208750c6e53" + [[package]] name = "bitflags" version = "1.3.2" @@ -93,12 +120,6 @@ version = "3.13.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a3e2c3daef883ecc1b5d58c15adae93470a91d425f3532ba1695849656af3fc1" -[[package]] -name = "bytes" -version = "0.5.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0e4cec68f03f32e44924783795810fa50a7035d8c8ebe78580ad7e6c703fba38" - [[package]] name = "bytes" version = "1.4.0" @@ -118,25 +139,58 @@ dependencies = [ name = "cfdyndns" version = "0.0.3" dependencies = [ + "anyhow", + "cloudflare", "log", "pretty_env_logger", "public-ip", - "reqwest", "serde_json", - "tokio 1.32.0", + "tokio", ] [[package]] name = "cfg-if" -version = "0.1.10" +version = "1.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4785bdd1c96b2a846b2bd7cc02e86b6b3dbf14e7e53446c4f54c92a361040822" +checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" [[package]] -name = "cfg-if" -version = "1.0.0" +name = "chrono" +version = "0.4.28" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" +checksum = "95ed24df0632f708f5f6d8082675bef2596f7084dee3dd55f632290bf35bfe0f" +dependencies = [ + "android-tzdata", + "iana-time-zone", + "js-sys", + "num-traits", + "serde", + "time 0.1.45", + "wasm-bindgen", + "windows-targets", +] + +[[package]] +name = "cloudflare" +version = "0.10.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0778f99ea7ad39b49b758eb418da7117b93232a5f6a09f9b79a094b77ac88cc2" +dependencies = [ + "anyhow", + "async-trait", + "base64 0.13.1", + "cfg-if", + "chrono", + "http", + "percent-encoding", + "reqwest", + "serde", + "serde_json", + "serde_qs", + "serde_with", + "url", + "uuid", +] [[package]] name = "core-foundation" @@ -160,8 +214,18 @@ version = "0.10.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0d706e75d87e35569db781a9b5e2416cff1236a47ed380831f959382ccd5f858" dependencies = [ - "darling_core", - "darling_macro", + "darling_core 0.10.2", + "darling_macro 0.10.2", +] + +[[package]] +name = "darling" +version = "0.20.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0209d94da627ab5605dcccf08bb18afa5009cfbef48d8a8b7d7bdbc79be25c5e" +dependencies = [ + "darling_core 0.20.3", + "darling_macro 0.20.3", ] [[package]] @@ -174,21 +238,46 @@ dependencies = [ "ident_case", "proc-macro2", "quote", - "strsim", + "strsim 0.9.3", "syn 1.0.109", ] +[[package]] +name = "darling_core" +version = "0.20.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "177e3443818124b357d8e76f53be906d60937f0d3a90773a664fa63fa253e621" +dependencies = [ + "fnv", + "ident_case", + "proc-macro2", + "quote", + "strsim 0.10.0", + "syn 2.0.29", +] + [[package]] name = "darling_macro" version = "0.10.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d9b5a2f4ac4969822c62224815d069952656cadc7084fdca9751e6d959189b72" dependencies = [ - "darling_core", + "darling_core 0.10.2", "quote", "syn 1.0.109", ] +[[package]] +name = "darling_macro" +version = "0.20.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "836a9bbc7ad63342d6d6e7b815ccab164bc77a2d95d84bc3117a8c0d5c98e2d5" +dependencies = [ + "darling_core 0.20.3", + "quote", + "syn 2.0.29", +] + [[package]] name = "data-encoding" version = "2.4.0" @@ -200,6 +289,9 @@ name = "deranged" version = "0.3.8" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f2696e8a945f658fd14dc3b87242e6b80cd0f36ff04ea560fa39082368847946" +dependencies = [ + "serde", +] [[package]] name = "derive_builder" @@ -207,7 +299,7 @@ version = "0.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a2658621297f2cf68762a6f7dc0bb7e1ff2cfd6583daef8ee0fed6f7ec468ec0" dependencies = [ - "darling", + "darling 0.10.2", "derive_builder_core", "proc-macro2", "quote", @@ -220,7 +312,7 @@ version = "0.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2791ea3e372c8495c0bc2033991d76b512cd799d07491fbd6890124db9458bef" dependencies = [ - "darling", + "darling 0.10.2", "proc-macro2", "quote", "syn 1.0.109", @@ -232,10 +324,10 @@ version = "1.0.8" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "53ecafc952c4528d9b51a458d1a8904b81783feff9fde08ab6ed2545ff396872" dependencies = [ - "cfg-if 1.0.0", + "cfg-if", "libc", "socket2 0.4.9", - "winapi 0.3.9", + "winapi", ] [[package]] @@ -244,7 +336,7 @@ version = "0.8.33" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7268b386296a025e474d5140678f75d6de9493ae55a5d709eeb9dd08149945e1" dependencies = [ - "cfg-if 1.0.0", + "cfg-if", ] [[package]] @@ -335,22 +427,6 @@ dependencies = [ "percent-encoding", ] -[[package]] -name = "fuchsia-zircon" -version = "0.3.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2e9763c69ebaae630ba35f74888db465e49e259ba1bc0eda7d06f4a067615d82" -dependencies = [ - "bitflags 1.3.2", - "fuchsia-zircon-sys", -] - -[[package]] -name = "fuchsia-zircon-sys" -version = "0.3.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3dcaa9ae7725d12cdb85b3ad99a434db70b468c09ded17e012d86b5c1010f7a7" - [[package]] name = "futures" version = "0.3.28" @@ -435,7 +511,7 @@ dependencies = [ "futures-sink", "futures-task", "memchr", - "pin-project-lite 0.2.13", + "pin-project-lite", "pin-utils", "slab", ] @@ -446,9 +522,9 @@ version = "0.2.10" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "be4136b2a15dd319360be1c07d9933517ccf0be8f16bf62a3bee4f0d618df427" dependencies = [ - "cfg-if 1.0.0", + "cfg-if", "libc", - "wasi", + "wasi 0.11.0+wasi-snapshot-preview1", ] [[package]] @@ -459,11 +535,11 @@ checksum = "6fb8d784f27acf97159b40fc4db5ecd8aa23b9ad5ef69cdd136d3bc80665f0c0" [[package]] name = "h2" -version = "0.2.7" +version = "0.3.21" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5e4728fd124914ad25e99e3d15a9361a879f6620f63cb56bbb08f95abb97a535" +checksum = "91fc23aa11be92976ef4729127f1a74adf36d8436f7816b185d18df956790833" dependencies = [ - "bytes 0.5.6", + "bytes", "fnv", "futures-core", "futures-sink", @@ -471,10 +547,9 @@ dependencies = [ "http", "indexmap", "slab", - "tokio 0.2.25", + "tokio", "tokio-util", "tracing", - "tracing-futures", ] [[package]] @@ -504,25 +579,21 @@ version = "0.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "443144c8cdadd93ebf52ddb4056d257f5b52c04d3c804e657d19eb73fc33668b" +[[package]] +name = "hex" +version = "0.4.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7f24254aa9a54b5c858eaee2f5bccdb46aaf0e486a595ed5fd8f86ba55232a70" + [[package]] name = "http" version = "0.2.9" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bd6effc99afb63425aff9b05836f029929e345a6148a14b7ecd5ab67af944482" dependencies = [ - "bytes 1.4.0", + "bytes", "fnv", - "itoa 1.0.9", -] - -[[package]] -name = "http-body" -version = "0.3.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "13d5ff830006f7646652e057693569bfe0d51760c0085a071769d142a205111b" -dependencies = [ - "bytes 0.5.6", - "http", + "itoa", ] [[package]] @@ -531,9 +602,9 @@ version = "0.4.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d5f38f16d184e36f2408a55281cd658ecbd3ca05cce6d6510a176eca393e26d1" dependencies = [ - "bytes 1.4.0", + "bytes", "http", - "pin-project-lite 0.2.13", + "pin-project-lite", ] [[package]] @@ -542,12 +613,6 @@ version = "1.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d897f394bad6a705d5f4104762e116a75639e470d80901eed05a860a95cb1904" -[[package]] -name = "httpdate" -version = "0.3.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "494b4d60369511e7dea41cf646832512a94e542f68bb9c49e54518e0f468eb47" - [[package]] name = "httpdate" version = "1.0.3" @@ -563,48 +628,25 @@ dependencies = [ "quick-error", ] -[[package]] -name = "hyper" -version = "0.13.10" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8a6f157065790a3ed2f88679250419b5cdd96e714a0d65f7797fd337186e96bb" -dependencies = [ - "bytes 0.5.6", - "futures-channel", - "futures-core", - "futures-util", - "h2", - "http", - "http-body 0.3.1", - "httparse", - "httpdate 0.3.2", - "itoa 0.4.8", - "pin-project", - "socket2 0.3.19", - "tokio 0.2.25", - "tower-service", - "tracing", - "want", -] - [[package]] name = "hyper" version = "0.14.27" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ffb1cfd654a8219eaef89881fdb3bb3b1cdc5fa75ded05d6933b2b382e395468" dependencies = [ - "bytes 1.4.0", + "bytes", "futures-channel", "futures-core", "futures-util", + "h2", "http", - "http-body 0.4.5", + "http-body", "httparse", - "httpdate 1.0.3", - "itoa 1.0.9", - "pin-project-lite 0.2.13", + "httpdate", + "itoa", + "pin-project-lite", "socket2 0.4.9", - "tokio 1.32.0", + "tokio", "tower-service", "tracing", "want", @@ -618,23 +660,46 @@ checksum = "6eea26c5d0b6ab9d72219f65000af310f042a740926f7b2fa3553e774036e2e7" dependencies = [ "derive_builder", "dns-lookup", - "hyper 0.14.27", - "tokio 1.32.0", + "hyper", + "tokio", "tower-service", "tracing", ] [[package]] name = "hyper-tls" -version = "0.4.3" +version = "0.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d979acc56dcb5b8dddba3917601745e877576475aa046df3226eabdecef78eed" +checksum = "d6183ddfa99b85da61a140bea0efc93fdf56ceaa041b37d553518030827f9905" dependencies = [ - "bytes 0.5.6", - "hyper 0.13.10", + "bytes", + "hyper", "native-tls", - "tokio 0.2.25", - "tokio-tls", + "tokio", + "tokio-native-tls", +] + +[[package]] +name = "iana-time-zone" +version = "0.1.57" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2fad5b825842d2b38bd206f3e81d6957625fd7f0a361e345c30e01a0ae2dd613" +dependencies = [ + "android_system_properties", + "core-foundation-sys", + "iana-time-zone-haiku", + "js-sys", + "wasm-bindgen", + "windows", +] + +[[package]] +name = "iana-time-zone-haiku" +version = "0.1.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f31827a206f56af32e590ba56d5d2d085f558508192593743f16b2306495269f" +dependencies = [ + "cc", ] [[package]] @@ -672,15 +737,7 @@ checksum = "bd070e393353796e801d209ad339e89596eb4c8d430d18ede6a1cced8fafbd99" dependencies = [ "autocfg", "hashbrown", -] - -[[package]] -name = "iovec" -version = "0.1.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b2b3ea6ff95e175473f8ffe6a7eb7c00d054240321b84c57051175fe3c1e075e" -dependencies = [ - "libc", + "serde", ] [[package]] @@ -689,12 +746,6 @@ version = "2.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "28b29a3cd74f0f4598934efe3aeba42bae0eb4680554128851ebbecb02af14e6" -[[package]] -name = "itoa" -version = "0.4.8" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b71991ff56294aa922b450139ee08b3bfc70982c6b2c7562771375cf73542dd4" - [[package]] name = "itoa" version = "1.0.9" @@ -710,16 +761,6 @@ dependencies = [ "wasm-bindgen", ] -[[package]] -name = "kernel32-sys" -version = "0.2.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7507624b29483431c0ba2d82aece8ca6cdba9382bff4ddd0f7490560c056098d" -dependencies = [ - "winapi 0.2.8", - "winapi-build", -] - [[package]] name = "lazy_static" version = "1.4.0" @@ -762,16 +803,6 @@ version = "0.3.17" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6877bb514081ee2a7ff5ef9de3281f14a4dd4bceac4c09388074a6b5df8a139a" -[[package]] -name = "mime_guess" -version = "2.0.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4192263c238a5f0d0c6bfd21f336a313a4ce1c450542449ca191bb657b4642ef" -dependencies = [ - "mime", - "unicase", -] - [[package]] name = "miniz_oxide" version = "0.7.1" @@ -781,25 +812,6 @@ dependencies = [ "adler", ] -[[package]] -name = "mio" -version = "0.6.23" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4afd66f5b91bf2a3bc13fad0e21caedac168ca4c707504e75585648ae80e4cc4" -dependencies = [ - "cfg-if 0.1.10", - "fuchsia-zircon", - "fuchsia-zircon-sys", - "iovec", - "kernel32-sys", - "libc", - "log", - "miow", - "net2", - "slab", - "winapi 0.2.8", -] - [[package]] name = "mio" version = "0.8.8" @@ -807,22 +819,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "927a765cd3fc26206e66b296465fa9d3e5ab003e651c1b3c060e7956d96b19d2" dependencies = [ "libc", - "wasi", + "wasi 0.11.0+wasi-snapshot-preview1", "windows-sys", ] -[[package]] -name = "miow" -version = "0.2.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ebd808424166322d4a38da87083bfddd3ac4c131334ed55856112eb06d46944d" -dependencies = [ - "kernel32-sys", - "net2", - "winapi 0.2.8", - "ws2_32-sys", -] - [[package]] name = "native-tls" version = "0.2.11" @@ -842,23 +842,21 @@ dependencies = [ ] [[package]] -name = "net2" -version = "0.2.39" +name = "nibble_vec" +version = "0.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b13b648036a2339d06de780866fbdfda0dde886de7b3af2ddeba8b14f4ee34ac" +checksum = "77a5d83df9f36fe23f0c3648c6bbb8b0298bb5f1939c8f2704431371f4b84d43" dependencies = [ - "cfg-if 0.1.10", - "libc", - "winapi 0.3.9", + "smallvec", ] [[package]] -name = "nibble_vec" -version = "0.1.0" +name = "num-traits" +version = "0.2.16" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "77a5d83df9f36fe23f0c3648c6bbb8b0298bb5f1939c8f2704431371f4b84d43" +checksum = "f30b0abd723be7e2ffca1272140fac1a2f084c77ec3e123c192b66af1ee9e6c2" dependencies = [ - "smallvec", + "autocfg", ] [[package]] @@ -893,7 +891,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bac25ee399abb46215765b1cb35bc0212377e58a061560d8b29b024fd0430e7c" dependencies = [ "bitflags 2.4.0", - "cfg-if 1.0.0", + "cfg-if", "foreign-types", "libc", "once_cell", @@ -956,12 +954,6 @@ dependencies = [ "syn 2.0.29", ] -[[package]] -name = "pin-project-lite" -version = "0.1.12" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "257b64915a082f7811703966789728173279bdebb956b143dbcd23f6f970a777" - [[package]] name = "pin-project-lite" version = "0.2.13" @@ -1015,11 +1007,11 @@ dependencies = [ "futures-core", "futures-util", "http", - "hyper 0.14.27", + "hyper", "hyper-system-resolver", - "pin-project-lite 0.2.13", + "pin-project-lite", "thiserror", - "tokio 1.32.0", + "tokio", "tracing", "tracing-futures", "trust-dns-client", @@ -1121,33 +1113,34 @@ checksum = "dbb5fb1acd8a1a18b3dd5be62d25485eb770e05afb408a9627d14d451bae12da" [[package]] name = "reqwest" -version = "0.10.10" +version = "0.11.20" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0718f81a8e14c4dbb3b34cf23dc6aaf9ab8a0dfec160c534b3dbca1aaa21f47c" +checksum = "3e9ad3fe7488d7e34558a2033d45a0c90b72d97b4f80705666fea71472e2e6a1" dependencies = [ - "base64", - "bytes 0.5.6", + "base64 0.21.3", + "bytes", "encoding_rs", "futures-core", "futures-util", + "h2", "http", - "http-body 0.3.1", - "hyper 0.13.10", + "http-body", + "hyper", "hyper-tls", "ipnet", "js-sys", - "lazy_static", "log", "mime", - "mime_guess", "native-tls", + "once_cell", "percent-encoding", - "pin-project-lite 0.2.13", + "pin-project-lite", "serde", "serde_json", "serde_urlencoded", - "tokio 0.2.25", - "tokio-tls", + "tokio", + "tokio-native-tls", + "tower-service", "url", "wasm-bindgen", "wasm-bindgen-futures", @@ -1238,11 +1231,22 @@ version = "1.0.105" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "693151e1ac27563d6dbcec9dee9fbd5da8539b20fa14ad3752b2e6d363ace360" dependencies = [ - "itoa 1.0.9", + "itoa", "ryu", "serde", ] +[[package]] +name = "serde_qs" +version = "0.10.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8cac3f1e2ca2fe333923a1ae72caca910b98ed0630bb35ef6f8c8517d6e81afa" +dependencies = [ + "percent-encoding", + "serde", + "thiserror", +] + [[package]] name = "serde_urlencoded" version = "0.7.1" @@ -1250,11 +1254,39 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d3491c14715ca2294c4d6a88f15e84739788c1d030eed8c110436aafdaa2f3fd" dependencies = [ "form_urlencoded", - "itoa 1.0.9", + "itoa", "ryu", "serde", ] +[[package]] +name = "serde_with" +version = "2.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "07ff71d2c147a7b57362cead5e22f772cd52f6ab31cfcd9edcd7f6aeb2a0afbe" +dependencies = [ + "base64 0.13.1", + "chrono", + "hex", + "indexmap", + "serde", + "serde_json", + "serde_with_macros", + "time 0.3.28", +] + +[[package]] +name = "serde_with_macros" +version = "2.3.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "881b6f881b17d13214e5d494c939ebab463d01264ce1811e9d4ac3a882e7695f" +dependencies = [ + "darling 0.20.3", + "proc-macro2", + "quote", + "syn 2.0.29", +] + [[package]] name = "slab" version = "0.4.9" @@ -1270,17 +1302,6 @@ version = "1.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "62bb4feee49fdd9f707ef802e22365a35de4b7b299de4763d44bfea899442ff9" -[[package]] -name = "socket2" -version = "0.3.19" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "122e570113d28d773067fab24266b66753f6ea915758651696b6e35e49f88d6e" -dependencies = [ - "cfg-if 1.0.0", - "libc", - "winapi 0.3.9", -] - [[package]] name = "socket2" version = "0.4.9" @@ -1288,7 +1309,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "64a4a911eed85daf18834cfaa86a79b7d266ff93ff5ba14005426219480ed662" dependencies = [ "libc", - "winapi 0.3.9", + "winapi", ] [[package]] @@ -1307,6 +1328,12 @@ version = "0.9.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6446ced80d6c486436db5c078dde11a9f73d42b57fb273121e160b84f63d894c" +[[package]] +name = "strsim" +version = "0.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "73473c0e59e6d5812c5dfe2a064a6444949f089e20eec9a2e5506596494e4623" + [[package]] name = "syn" version = "1.0.109" @@ -1335,7 +1362,7 @@ version = "3.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "cb94d2f3cc536af71caac6b6fcebf65860b347e7ce0cc9ebe8f70d3e521054ef" dependencies = [ - "cfg-if 1.0.0", + "cfg-if", "fastrand", "redox_syscall", "rustix", @@ -1371,6 +1398,17 @@ dependencies = [ "syn 2.0.29", ] +[[package]] +name = "time" +version = "0.1.45" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1b797afad3f312d1c66a56d11d0316f916356d11bd158fbc6ca6389ff6bf805a" +dependencies = [ + "libc", + "wasi 0.10.0+wasi-snapshot-preview1", + "winapi", +] + [[package]] name = "time" version = "0.3.28" @@ -1378,8 +1416,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "17f6bb557fd245c28e6411aa56b6403c689ad95061f50e4be16c274e70a17e48" dependencies = [ "deranged", + "itoa", "serde", "time-core", + "time-macros", ] [[package]] @@ -1388,6 +1428,15 @@ version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7300fbefb4dadc1af235a9cef3737cea692a9d97e1b9cbcd4ebdae6f8868e6fb" +[[package]] +name = "time-macros" +version = "0.2.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1a942f44339478ef67935ab2bbaec2fb0322496cf3cbe84b261e06ac3814c572" +dependencies = [ + "time-core", +] + [[package]] name = "tinyvec" version = "1.6.0" @@ -1403,24 +1452,6 @@ version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1f3ccbac311fea05f86f61904b462b55fb3df8837a366dfc601a0161d0532f20" -[[package]] -name = "tokio" -version = "0.2.25" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6703a273949a90131b290be1fe7b039d0fc884aa1935860dfcbe056f28cd8092" -dependencies = [ - "bytes 0.5.6", - "fnv", - "futures-core", - "iovec", - "lazy_static", - "memchr", - "mio 0.6.23", - "num_cpus", - "pin-project-lite 0.1.12", - "slab", -] - [[package]] name = "tokio" version = "1.32.0" @@ -1428,10 +1459,11 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "17ed6077ed6cd6c74735e21f37eb16dc3935f96878b1fe961074089cc80893f9" dependencies = [ "backtrace", + "bytes", "libc", - "mio 0.8.8", + "mio", "num_cpus", - "pin-project-lite 0.2.13", + "pin-project-lite", "socket2 0.5.3", "tokio-macros", "windows-sys", @@ -1449,27 +1481,27 @@ dependencies = [ ] [[package]] -name = "tokio-tls" +name = "tokio-native-tls" version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9a70f4fcd7b3b24fb194f837560168208f669ca8cb70d0c4b862944452396343" +checksum = "bbae76ab933c85776efabc971569dd6119c580d8f5d448769dec1764bf796ef2" dependencies = [ "native-tls", - "tokio 0.2.25", + "tokio", ] [[package]] name = "tokio-util" -version = "0.3.1" +version = "0.7.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "be8242891f2b6cbef26a2d7e8605133c2c554cd35b3e4948ea892d6d68436499" +checksum = "806fe8c2c87eccc8b3267cbae29ed3ab2d0bd37fca70ab622e46aaa9375ddb7d" dependencies = [ - "bytes 0.5.6", + "bytes", "futures-core", "futures-sink", - "log", - "pin-project-lite 0.1.12", - "tokio 0.2.25", + "pin-project-lite", + "tokio", + "tracing", ] [[package]] @@ -1484,9 +1516,8 @@ version = "0.1.37" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8ce8c33a8d48bd45d624a6e523445fd21ec13d3653cd51f681abf67418f54eb8" dependencies = [ - "cfg-if 1.0.0", - "log", - "pin-project-lite 0.2.13", + "cfg-if", + "pin-project-lite", "tracing-attributes", "tracing-core", ] @@ -1529,7 +1560,7 @@ version = "0.20.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5b4ef9b9bde0559b78a4abb00339143750085f05e5a453efb7b8bef1061f09dc" dependencies = [ - "cfg-if 1.0.0", + "cfg-if", "data-encoding", "futures-channel", "futures-util", @@ -1538,8 +1569,8 @@ dependencies = [ "radix_trie", "rand", "thiserror", - "time", - "tokio 1.32.0", + "time 0.3.28", + "tokio", "trust-dns-proto", ] @@ -1550,7 +1581,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ca94d4e9feb6a181c690c4040d7a24ef34018d8313ac5044a61d21222ae24e31" dependencies = [ "async-trait", - "cfg-if 1.0.0", + "cfg-if", "data-encoding", "enum-as-inner", "futures-channel", @@ -1564,7 +1595,7 @@ dependencies = [ "smallvec", "thiserror", "tinyvec", - "tokio 1.32.0", + "tokio", "url", ] @@ -1574,15 +1605,6 @@ version = "0.2.4" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3528ecfd12c466c6f163363caf2d02a71161dd5e1cc6ae7b34207ea2d42d81ed" -[[package]] -name = "unicase" -version = "2.7.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f7d2d4dafb69621809a81864c9c1b864479e1235c0dd4e199924b9742439ed89" -dependencies = [ - "version_check", -] - [[package]] name = "unicode-bidi" version = "0.3.13" @@ -1616,16 +1638,20 @@ dependencies = [ ] [[package]] -name = "vcpkg" -version = "0.2.15" +name = "uuid" +version = "1.4.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "accd4ea62f7bb7a82fe23066fb0957d48ef677f6eeb8215f372f52e48bb32426" +checksum = "79daa5ed5740825c40b389c5e50312b9c86df53fccd33f281df655642b43869d" +dependencies = [ + "getrandom", + "serde", +] [[package]] -name = "version_check" -version = "0.9.4" +name = "vcpkg" +version = "0.2.15" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f" +checksum = "accd4ea62f7bb7a82fe23066fb0957d48ef677f6eeb8215f372f52e48bb32426" [[package]] name = "want" @@ -1636,6 +1662,12 @@ dependencies = [ "try-lock", ] +[[package]] +name = "wasi" +version = "0.10.0+wasi-snapshot-preview1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1a143597ca7c7793eff794def352d41792a93c481eb1042423ff7ff72ba2c31f" + [[package]] name = "wasi" version = "0.11.0+wasi-snapshot-preview1" @@ -1648,9 +1680,7 @@ version = "0.2.87" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7706a72ab36d8cb1f80ffbf0e071533974a60d0a308d01a5d0375bf60499a342" dependencies = [ - "cfg-if 1.0.0", - "serde", - "serde_json", + "cfg-if", "wasm-bindgen-macro", ] @@ -1675,7 +1705,7 @@ version = "0.4.37" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c02dbc21516f9f1f04f187958890d7e6026df8d16540b7ad9492bc34a67cea03" dependencies = [ - "cfg-if 1.0.0", + "cfg-if", "js-sys", "wasm-bindgen", "web-sys", @@ -1720,12 +1750,6 @@ dependencies = [ "wasm-bindgen", ] -[[package]] -name = "winapi" -version = "0.2.8" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "167dc9d6949a9b857f3451275e911c3f44255842c1f7a76f33c55103a909087a" - [[package]] name = "winapi" version = "0.3.9" @@ -1736,12 +1760,6 @@ dependencies = [ "winapi-x86_64-pc-windows-gnu", ] -[[package]] -name = "winapi-build" -version = "0.1.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2d315eee3b34aca4797b2da6b13ed88266e6d612562a0c46390af8299fc699bc" - [[package]] name = "winapi-i686-pc-windows-gnu" version = "0.4.0" @@ -1754,7 +1772,7 @@ version = "0.1.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "70ec6ce85bb158151cae5e5c87f95a8e97d2c0c4b001223f33a334e3ce5de178" dependencies = [ - "winapi 0.3.9", + "winapi", ] [[package]] @@ -1763,6 +1781,15 @@ version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" +[[package]] +name = "windows" +version = "0.48.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e686886bc078bc1b0b600cac0147aadb815089b6e4da64016cbd754b6342700f" +dependencies = [ + "windows-targets", +] + [[package]] name = "windows-sys" version = "0.48.0" @@ -1831,19 +1858,10 @@ checksum = "ed94fce61571a4006852b7389a063ab983c02eb1bb37b47f8272ce92d06d9538" [[package]] name = "winreg" -version = "0.7.0" +version = "0.50.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0120db82e8a1e0b9fb3345a539c478767c0048d842860994d96113d5b667bd69" +checksum = "524e57b2c537c0f9b1e69f1965311ec12182b4122e45035b1508cd24d2adadb1" dependencies = [ - "winapi 0.3.9", -] - -[[package]] -name = "ws2_32-sys" -version = "0.2.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d59cefebd0c892fa2dd6de581e937301d8552cb44489cdff035c6187cb63fa5e" -dependencies = [ - "winapi 0.2.8", - "winapi-build", + "cfg-if", + "windows-sys", ] diff --git a/Cargo.toml b/Cargo.toml index f3ec0af..115d4e0 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -7,7 +7,8 @@ edition = "2021" [dependencies] log = "0.4.8" pretty_env_logger = "0.4.0" -reqwest = { version = "0.10.4", features = ["blocking", "json"] } serde_json = "1.0.48" public-ip = "^0.2" tokio = { version = "^1", features = ["rt-multi-thread", "macros"] } +cloudflare = "^0.10" +anyhow = "^1" diff --git a/src/main.rs b/src/main.rs index f86600b..278eb8e 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,143 +1,152 @@ use log::info; -use serde_json::value::*; - +use cloudflare::{ + endpoints::{ + dns::{ + DnsContent, DnsRecord, ListDnsRecords, ListDnsRecordsParams, + UpdateDnsRecord, UpdateDnsRecordParams, + }, + zone::{ListZones, ListZonesParams, Zone}, + }, + framework::{ + async_api::{ApiClient, Client}, + auth::Credentials, + Environment, HttpApiClientConfig, + }, +}; use std::env; use std::io; -use std::io::prelude::*; +use std::io::prelude::Write; -use public_ip::{http, Version}; +use std::net::IpAddr; -fn env_var(n: &str) -> String { - let err = "Environment Variables CLOUDFLARE_RECORDS and either CLOUDFLARE_APITOKEN or CLOUDFLARE_EMAIL and CLOUDFLARE_APIKEY must be set!"; - env::var(n).expect(err) -} - -// overloaded function. no body is treated as a get, body is treated as a put -fn cloudflare_api( - client: &reqwest::blocking::Client, - url: &str, - body: Option, -) -> Result { - let request = match body { - Some(body) => client.put(url).body(body), - None => client.get(url), - }; - - let authorized_request = match env::var("CLOUDFLARE_APITOKEN") { - Ok(val) => { - let mut bearer = "Bearer ".to_owned(); - bearer.push_str(&val); - request.header("Authorization", bearer.to_owned()) - } - Err(_e) => { - let cloudflare_apikey = env_var("CLOUDFLARE_APIKEY"); - let cloudflare_email = env_var("CLOUDFLARE_EMAIL"); - request - .header("X-Auth-Key", cloudflare_apikey.to_owned()) - .header("X-Auth-Email", cloudflare_email.to_owned()) - } - }; - - let response_json: Value = - authorized_request.send().unwrap().json().unwrap(); - - let success = response_json - .as_object() - .unwrap() - .get("success") - .unwrap() - .as_bool() - .unwrap(); - if !success { - return Err(format!("Request not successful: {}", response_json)); - } +use public_ip::{http, Version}; - Ok(response_json) -} +use anyhow::{Context, Result}; #[tokio::main] -async fn main() { +async fn main() -> Result<()> { pretty_env_logger::init(); - let current_ipv4 = public_ip::addr_with(http::ALL, Version::V4) - .await - .expect("Was unable to determine current IP address."); - info!("{}", current_ipv4); - let client = reqwest::blocking::Client::new(); + let public_ipv4 = public_ip::addr_with(http::ALL, Version::V4).await; + let public_ipv6 = public_ip::addr_with(public_ip::ALL, Version::V6).await; + + if (None, None) == (public_ipv6, public_ipv4) { + panic!("Could not determine your current public IP address.") + } - let cloudflare_records_env = env_var("CLOUDFLARE_RECORDS"); + if let Some(ipv4) = public_ipv4 { + info!("{}", ipv4); + } + if let Some(ipv6) = public_ipv6 { + info!("{}", ipv6); + } + + let cloudflare_records_env = env::var("CLOUDFLARE_RECORDS").context("")?; let cloudflare_records: Vec<&str> = cloudflare_records_env.split(|c: char| c == ',').collect(); - let zones_url = "https://api.cloudflare.com/client/v4/zones"; - let zones_json = cloudflare_api(&client, zones_url, None).unwrap(); - - let zone_ids = zones_json - .as_object() - .unwrap() - .get("result") - .unwrap() - .as_array() - .unwrap() - .iter() - .map(|zone_node| zone_node.get("id").unwrap().as_str().unwrap()); - - for zone_id in zone_ids { - let records_url = format!( - "https://api.cloudflare.com/client/v4/zones/{}/dns_records", - zone_id - ); - let records_json = cloudflare_api(&client, &records_url, None).unwrap(); - - let records = records_json - .as_object() - .unwrap() - .get("result") - .unwrap() - .as_array() - .unwrap() - .iter(); + let credentials: Credentials = + if let Ok(token) = env::var("CLOUDFLARE_APITOKEN") { + Credentials::UserAuthToken { token } + } else if let (Ok(key), Ok(email)) = + (env::var("CLOUDFLARE_APIKEY"), env::var("CLOUDFLARE_EMAIL")) + { + Credentials::UserAuthKey { email, key } + } else { + panic!("Either API token or API key + email pair must be provided") + }; + + let api_client = Client::new( + credentials, + HttpApiClientConfig::default(), + Environment::Production, + )?; + + let zones = api_client + .request(&ListZones { + params: ListZonesParams::default(), + }) + .await? + .result; + + for zone in zones { + let records = api_client + .request(&ListDnsRecords { + zone_identifier: &zone.id, + params: ListDnsRecordsParams::default(), + }) + .await? + .result; for record in records { - let record_id = record.get("id").unwrap().as_str().unwrap(); - let record_type = record.get("type").unwrap().as_str().unwrap(); - let record_name = record.get("name").unwrap().as_str().unwrap(); - let record_content = - record.get("content").unwrap().as_str().unwrap(); - let record_proxied = - record.get("proxied").unwrap().as_bool().unwrap(); - - if !cloudflare_records.contains(&record_name) || record_type != "A" - { + if !cloudflare_records.contains(&record.name.as_str()) { continue; } - if record_content == current_ipv4.to_string() { - info!("{} skipped, up to date", record_name); - continue; + match record.content { + DnsContent::A { content: ipv4 } => match public_ipv4 { + Some(public) => { + update_record( + &record, + &IpAddr::V4(ipv4), + &public, + &api_client, + &zone, + ) + .await? + } + None => continue, + }, + DnsContent::AAAA { content: ipv6 } => match public_ipv6 { + Some(public) => { + update_record( + &record, + &IpAddr::V6(ipv6), + &public, + &api_client, + &zone, + ) + .await? + } + None => continue, + }, + _ => continue, } - - print!( - "{} ({} -> {})... ", - record_name, record_content, current_ipv4 - ); - io::stdout().flush().ok(); - - let record_url = format!( - "https://api.cloudflare.com/client/v4/zones/{}/dns_records/{}", - zone_id, record_id - ); - let record_update_body = format!( - r#"{{"name": "{}", "content": "{}", "type": "{}", "proxied": {}}}"#, - record_name, current_ipv4, record_type, record_proxied - ); - cloudflare_api( - &client, - &record_url, - Some(record_update_body.to_string()), - ) - .unwrap(); } } + Ok(()) +} + +async fn update_record( + record: &DnsRecord, + record_ip: &IpAddr, + public_ip: &IpAddr, + client: &Client, + zone: &Zone, +) -> Result<()> { + if public_ip == record_ip { + info!("{} skipped, up to date", record.name); + return Ok(()); + } + + print!("{} ({} -> {})... ", record.name, record_ip, public_ip); + io::stdout().flush().ok(); + + client + .request(&UpdateDnsRecord { + zone_identifier: &zone.id, + identifier: &record.id, + params: UpdateDnsRecordParams { + name: &record.name, + ttl: record.ttl.into(), + proxied: record.proxied.into(), + content: match public_ip { + IpAddr::V4(ip) => DnsContent::A { content: *ip }, + IpAddr::V6(ip) => DnsContent::AAAA { content: *ip }, + }, + }, + }) + .await?; + Ok(()) } From 4f2e2f2c1c750363eaf527fbad2042de42f7ddfb Mon Sep 17 00:00:00 2001 From: Timothy DeHerrera Date: Tue, 5 Sep 2023 17:43:12 -0600 Subject: [PATCH 08/18] fix: patch crates to fix upstream issues Both the public ip crate, and the cloudflare api crate have small issues that prevent them from working properly, yet both have open PRs upstream to fix these issues, so simply patch the crates for now to get this working. --- Cargo.lock | 177 ++++++++++++++++++++++++++++++++++++++++------------- Cargo.toml | 4 ++ 2 files changed, 138 insertions(+), 43 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 4ef19de..7814d96 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -55,7 +55,7 @@ checksum = "bc00ceb34980c03614e35a3a4e218276a0a824e911d07651cd0d858a51e8c0f0" dependencies = [ "proc-macro2", "quote", - "syn 2.0.29", + "syn 2.0.31", ] [[package]] @@ -156,9 +156,9 @@ checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" [[package]] name = "chrono" -version = "0.4.28" +version = "0.4.29" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "95ed24df0632f708f5f6d8082675bef2596f7084dee3dd55f632290bf35bfe0f" +checksum = "d87d9d13be47a5b7c3907137f1290b0459a7f80efb26be8c52afb11963bccb02" dependencies = [ "android-tzdata", "iana-time-zone", @@ -173,8 +173,7 @@ dependencies = [ [[package]] name = "cloudflare" version = "0.10.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0778f99ea7ad39b49b758eb418da7117b93232a5f6a09f9b79a094b77ac88cc2" +source = "git+https://github.com/jcgruenhage/cloudflare-rs.git?branch=make-owner-fields-optional#02397fc4211886548a31a0731b240f2e17309de4" dependencies = [ "anyhow", "async-trait", @@ -253,7 +252,7 @@ dependencies = [ "proc-macro2", "quote", "strsim 0.10.0", - "syn 2.0.29", + "syn 2.0.31", ] [[package]] @@ -275,7 +274,7 @@ checksum = "836a9bbc7ad63342d6d6e7b815ccab164bc77a2d95d84bc3117a8c0d5c98e2d5" dependencies = [ "darling_core 0.20.3", "quote", - "syn 2.0.29", + "syn 2.0.31", ] [[package]] @@ -347,9 +346,9 @@ checksum = "c34f04666d835ff5d62e058c3995147c06f42fe86ff053337632bca83e42702d" [[package]] name = "enum-as-inner" -version = "0.3.4" +version = "0.5.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "570d109b813e904becc80d8d5da38376818a143348413f7149f1340fe04754d4" +checksum = "c9720bba047d567ffc8a3cba48bf19126600e249ab7f128e9233e6376976a116" dependencies = [ "heck", "proc-macro2", @@ -483,7 +482,7 @@ checksum = "89ca545a94061b6365f2c7355b4b32bd20df3ff95f02da9329b34ccc3bd6ee72" dependencies = [ "proc-macro2", "quote", - "syn 2.0.29", + "syn 2.0.31", ] [[package]] @@ -652,6 +651,24 @@ dependencies = [ "want", ] +[[package]] +name = "hyper-openssl" +version = "0.9.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d6ee5d7a8f718585d1c3c61dfde28ef5b0bb14734b4db13f5ada856cdc6c612b" +dependencies = [ + "http", + "hyper", + "linked_hash_set", + "once_cell", + "openssl", + "openssl-sys", + "parking_lot", + "tokio", + "tokio-openssl", + "tower-layer", +] + [[package]] name = "hyper-system-resolver" version = "0.5.0" @@ -773,12 +790,37 @@ version = "0.2.147" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b4668fb0ea861c1df094127ac5f1da3409a82116a4ba74fca2e58ef927159bb3" +[[package]] +name = "linked-hash-map" +version = "0.5.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0717cef1bc8b636c6e1c1bbdefc09e6322da8a9321966e8928ef80d20f7f770f" + +[[package]] +name = "linked_hash_set" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "47186c6da4d81ca383c7c47c1bfc80f4b95f4720514d860a5407aaf4233f9588" +dependencies = [ + "linked-hash-map", +] + [[package]] name = "linux-raw-sys" version = "0.4.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "57bcfdad1b858c2db7c38303a6d2ad4dfaf5eb53dfeb0910128b2c26d6158503" +[[package]] +name = "lock_api" +version = "0.4.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c1cc9717a20b1bb222f333e6a92fd32f7d8a18ddc5a3191a11af45dcbf4dcd16" +dependencies = [ + "autocfg", + "scopeguard", +] + [[package]] name = "log" version = "0.4.20" @@ -793,9 +835,9 @@ checksum = "2532096657941c2fea9c289d370a250971c689d4f143798ff67113ec042024a5" [[package]] name = "memchr" -version = "2.6.2" +version = "2.6.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5486aed0026218e61b8a01d5fbd5a0a134649abb71a0e53b7bc088529dced86e" +checksum = "8f232d6ef707e1956a43342693d2a31e72989554d58299d7a88738cc95b0d35c" [[package]] name = "mime" @@ -871,9 +913,9 @@ dependencies = [ [[package]] name = "object" -version = "0.32.0" +version = "0.32.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "77ac5bbd07aea88c60a577a1ce218075ffd59208b2d7ca97adf9bfc5aeb21ebe" +checksum = "9cf5f9dd3933bd50a9e1f149ec995f39ae2c496d31fd772c1fd45ebc27e902b0" dependencies = [ "memchr", ] @@ -907,7 +949,7 @@ checksum = "a948666b637a0f465e8564c73e89d4dde00d72d4d473cc972f390fc3dcee7d9c" dependencies = [ "proc-macro2", "quote", - "syn 2.0.29", + "syn 2.0.31", ] [[package]] @@ -918,9 +960,9 @@ checksum = "ff011a302c396a5197692431fc1948019154afc178baf7d8e37367442a4601cf" [[package]] name = "openssl-sys" -version = "0.9.92" +version = "0.9.93" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "db7e971c2c2bba161b2d2fdf37080177eff520b3bc044787c7f1f5f9e78d869b" +checksum = "db4d56a4c0478783083cfafcc42493dd4a981d41669da64b4572a2a089b51b1d" dependencies = [ "cc", "libc", @@ -928,6 +970,29 @@ dependencies = [ "vcpkg", ] +[[package]] +name = "parking_lot" +version = "0.12.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3742b2c103b9f06bc9fff0a37ff4912935851bee6d36f3c02bcc755bcfec228f" +dependencies = [ + "lock_api", + "parking_lot_core", +] + +[[package]] +name = "parking_lot_core" +version = "0.9.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "93f00c865fe7cabf650081affecd3871070f26767e7b2070a3ffae14c654b447" +dependencies = [ + "cfg-if", + "libc", + "redox_syscall", + "smallvec", + "windows-targets", +] + [[package]] name = "percent-encoding" version = "2.3.0" @@ -951,7 +1016,7 @@ checksum = "4359fd9c9171ec6e8c62926d6faaf553a8dc3f64e1507e76da7911b4f6a04405" dependencies = [ "proc-macro2", "quote", - "syn 2.0.29", + "syn 2.0.31", ] [[package]] @@ -1000,18 +1065,20 @@ dependencies = [ [[package]] name = "public-ip" version = "0.2.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7b4c40db5262d93298c363a299f8bc1b3a956a78eecddba3bc0e58b76e2f419a" +source = "git+https://github.com/jcgruenhage/rust-public-ip.git?branch=cloudflare-provider#f0f0e68aebf9d796deaa3af04c8c6d4df3c515fe" dependencies = [ "dns-lookup", "futures-core", "futures-util", "http", "hyper", + "hyper-openssl", "hyper-system-resolver", + "openssl", "pin-project-lite", "thiserror", "tokio", + "tower-layer", "tracing", "tracing-futures", "trust-dns-client", @@ -1084,9 +1151,9 @@ dependencies = [ [[package]] name = "regex" -version = "1.9.4" +version = "1.9.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "12de2eff854e5fa4b1295edd650e227e9d8fb0c9e90b12e7f36d6a6811791a29" +checksum = "697061221ea1b4a94a624f67d0ae2bfe4e22b8a17b6a192afb11046542cc8c47" dependencies = [ "aho-corasick", "memchr", @@ -1096,9 +1163,9 @@ dependencies = [ [[package]] name = "regex-automata" -version = "0.3.7" +version = "0.3.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "49530408a136e16e5b486e883fbb6ba058e8e4e8ae6621a77b048b314336e629" +checksum = "c2f401f4955220693b56f8ec66ee9c78abffd8d1c4f23dc41a23839eb88f0795" dependencies = [ "aho-corasick", "memchr", @@ -1182,6 +1249,12 @@ dependencies = [ "windows-sys", ] +[[package]] +name = "scopeguard" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "94143f37725109f92c262ed2cf5e59bce7498c01bcc1502d7b9afe439a4e9f49" + [[package]] name = "security-framework" version = "2.9.2" @@ -1222,7 +1295,7 @@ checksum = "4eca7ac642d82aa35b60049a6eccb4be6be75e599bd2e9adb5f875a737654af2" dependencies = [ "proc-macro2", "quote", - "syn 2.0.29", + "syn 2.0.31", ] [[package]] @@ -1284,7 +1357,7 @@ dependencies = [ "darling 0.20.3", "proc-macro2", "quote", - "syn 2.0.29", + "syn 2.0.31", ] [[package]] @@ -1347,9 +1420,9 @@ dependencies = [ [[package]] name = "syn" -version = "2.0.29" +version = "2.0.31" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c324c494eba9d92503e6f1ef2e6df781e78f6a7705a0202d9801b198807d518a" +checksum = "718fa2415bcb8d8bd775917a1bf12a7931b6dfa890753378538118181e0cb398" dependencies = [ "proc-macro2", "quote", @@ -1380,22 +1453,22 @@ dependencies = [ [[package]] name = "thiserror" -version = "1.0.47" +version = "1.0.48" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "97a802ec30afc17eee47b2855fc72e0c4cd62be9b4efe6591edde0ec5bd68d8f" +checksum = "9d6d7a740b8a666a7e828dd00da9c0dc290dff53154ea77ac109281de90589b7" dependencies = [ "thiserror-impl", ] [[package]] name = "thiserror-impl" -version = "1.0.47" +version = "1.0.48" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6bb623b56e39ab7dcd4b1b98bb6c8f8d907ed255b18de254088016b27a8ee19b" +checksum = "49922ecae66cc8a249b77e68d1d0623c1b2c514f0060c27cdc68bd62a1219d35" dependencies = [ "proc-macro2", "quote", - "syn 2.0.29", + "syn 2.0.31", ] [[package]] @@ -1477,7 +1550,7 @@ checksum = "630bdcf245f78637c13ec01ffae6187cca34625e8c63150d424b59e55af2675e" dependencies = [ "proc-macro2", "quote", - "syn 2.0.29", + "syn 2.0.31", ] [[package]] @@ -1490,6 +1563,18 @@ dependencies = [ "tokio", ] +[[package]] +name = "tokio-openssl" +version = "0.6.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c08f9ffb7809f1b20c1b398d92acf4cc719874b3b2b2d9ea2f09b4a80350878a" +dependencies = [ + "futures-util", + "openssl", + "openssl-sys", + "tokio", +] + [[package]] name = "tokio-util" version = "0.7.8" @@ -1504,6 +1589,12 @@ dependencies = [ "tracing", ] +[[package]] +name = "tower-layer" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c20c8dbed6283a09604c3e69b4b7eeb54e298b8a600d4d5ecb5ad39de609f1d0" + [[package]] name = "tower-service" version = "0.3.2" @@ -1530,7 +1621,7 @@ checksum = "5f4f31f56159e98206da9efd823404b79b6ef3143b4a7ab76e67b1751b25a4ab" dependencies = [ "proc-macro2", "quote", - "syn 2.0.29", + "syn 2.0.31", ] [[package]] @@ -1556,29 +1647,29 @@ dependencies = [ [[package]] name = "trust-dns-client" -version = "0.20.4" +version = "0.22.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5b4ef9b9bde0559b78a4abb00339143750085f05e5a453efb7b8bef1061f09dc" +checksum = "6c408c32e6a9dbb38037cece35740f2cf23c875d8ca134d33631cec83f74d3fe" dependencies = [ "cfg-if", "data-encoding", "futures-channel", "futures-util", "lazy_static", - "log", "radix_trie", "rand", "thiserror", "time 0.3.28", "tokio", + "tracing", "trust-dns-proto", ] [[package]] name = "trust-dns-proto" -version = "0.20.4" +version = "0.22.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ca94d4e9feb6a181c690c4040d7a24ef34018d8313ac5044a61d21222ae24e31" +checksum = "4f7f83d1e4a0e4358ac54c5c3681e5d7da5efc5a7a632c90bb6d6669ddd9bc26" dependencies = [ "async-trait", "cfg-if", @@ -1590,12 +1681,12 @@ dependencies = [ "idna 0.2.3", "ipnet", "lazy_static", - "log", "rand", "smallvec", "thiserror", "tinyvec", "tokio", + "tracing", "url", ] @@ -1695,7 +1786,7 @@ dependencies = [ "once_cell", "proc-macro2", "quote", - "syn 2.0.29", + "syn 2.0.31", "wasm-bindgen-shared", ] @@ -1729,7 +1820,7 @@ checksum = "54681b18a46765f095758388f2d0cf16eb8d4169b639ab575a8f5693af210c7b" dependencies = [ "proc-macro2", "quote", - "syn 2.0.29", + "syn 2.0.31", "wasm-bindgen-backend", "wasm-bindgen-shared", ] diff --git a/Cargo.toml b/Cargo.toml index 115d4e0..a54f1cc 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -12,3 +12,7 @@ public-ip = "^0.2" tokio = { version = "^1", features = ["rt-multi-thread", "macros"] } cloudflare = "^0.10" anyhow = "^1" + +[patch.crates-io] +cloudflare = { git = "https://github.com/jcgruenhage/cloudflare-rs.git", branch = "make-owner-fields-optional" } +public-ip = { git = "https://github.com/jcgruenhage/rust-public-ip.git", branch = "cloudflare-provider" } \ No newline at end of file From cbe6f39cdf63c98371f685641bb46bed63573c6d Mon Sep 17 00:00:00 2001 From: Timothy DeHerrera Date: Tue, 5 Sep 2023 19:53:43 -0600 Subject: [PATCH 09/18] fix: use tokio::join to capture ips at once --- src/main.rs | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/main.rs b/src/main.rs index 278eb8e..caaede5 100644 --- a/src/main.rs +++ b/src/main.rs @@ -28,8 +28,10 @@ use anyhow::{Context, Result}; async fn main() -> Result<()> { pretty_env_logger::init(); - let public_ipv4 = public_ip::addr_with(http::ALL, Version::V4).await; - let public_ipv6 = public_ip::addr_with(public_ip::ALL, Version::V6).await; + let (public_ipv4, public_ipv6) = tokio::join!( + public_ip::addr_with(http::ALL, Version::V4), + public_ip::addr_with(public_ip::ALL, Version::V6) + ); if (None, None) == (public_ipv6, public_ipv4) { panic!("Could not determine your current public IP address.") From 8b4a86fb9cec4f64d6e77ac6151cee7e29fed073 Mon Sep 17 00:00:00 2001 From: Timothy DeHerrera Date: Tue, 5 Sep 2023 19:54:24 -0600 Subject: [PATCH 10/18] fix: use anyhow::bail! instead of panic! --- src/main.rs | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/main.rs b/src/main.rs index caaede5..27bd6cf 100644 --- a/src/main.rs +++ b/src/main.rs @@ -34,7 +34,7 @@ async fn main() -> Result<()> { ); if (None, None) == (public_ipv6, public_ipv4) { - panic!("Could not determine your current public IP address.") + anyhow::bail!("Could not determine your current public IP address.") } if let Some(ipv4) = public_ipv4 { @@ -56,7 +56,9 @@ async fn main() -> Result<()> { { Credentials::UserAuthKey { email, key } } else { - panic!("Either API token or API key + email pair must be provided") + anyhow::bail!( + "Either API token or API key + email pair must be provided" + ) }; let api_client = Client::new( From 3830726a348eff76bd078607dc0b5461cda4eab0 Mon Sep 17 00:00:00 2001 From: Timothy DeHerrera Date: Wed, 6 Sep 2023 10:25:37 -0600 Subject: [PATCH 11/18] feat: use clap to set arguments Allows for specifying the API in an intuitive way, and also automatically gives us a user help message. --- Cargo.lock | 147 +++++++++++++++++++++++++++++++++++++++++++++++++++- Cargo.toml | 4 ++ src/api.rs | 46 ++++++++++++++++ src/main.rs | 42 +++++++-------- 4 files changed, 214 insertions(+), 25 deletions(-) create mode 100644 src/api.rs diff --git a/Cargo.lock b/Cargo.lock index 7814d96..9e7c273 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -41,6 +41,54 @@ dependencies = [ "libc", ] +[[package]] +name = "anstream" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b1f58811cfac344940f1a400b6e6231ce35171f614f26439e80f8c1465c5cc0c" +dependencies = [ + "anstyle", + "anstyle-parse", + "anstyle-query", + "anstyle-wincon", + "colorchoice", + "utf8parse", +] + +[[package]] +name = "anstyle" +version = "1.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "15c4c2c83f81532e5845a733998b6971faca23490340a418e9b72a3ec9de12ea" + +[[package]] +name = "anstyle-parse" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "938874ff5980b03a87c5524b3ae5b59cf99b1d6bc836848df7bc5ada9643c333" +dependencies = [ + "utf8parse", +] + +[[package]] +name = "anstyle-query" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5ca11d4be1bab0c8bc8734a9aa7bf4ee8316d462a08c6ac5052f888fef5b494b" +dependencies = [ + "windows-sys", +] + +[[package]] +name = "anstyle-wincon" +version = "2.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "58f54d10c6dfa51283a066ceab3ec1ab78d13fae00aa49243a45e4571fb79dfd" +dependencies = [ + "anstyle", + "windows-sys", +] + [[package]] name = "anyhow" version = "1.0.75" @@ -140,6 +188,7 @@ name = "cfdyndns" version = "0.0.3" dependencies = [ "anyhow", + "clap", "cloudflare", "log", "pretty_env_logger", @@ -170,6 +219,47 @@ dependencies = [ "windows-targets", ] +[[package]] +name = "clap" +version = "4.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6a13b88d2c62ff462f88e4a121f17a82c1af05693a2f192b5c38d14de73c19f6" +dependencies = [ + "clap_builder", + "clap_derive", +] + +[[package]] +name = "clap_builder" +version = "4.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2bb9faaa7c2ef94b2743a21f5a29e6f0010dff4caa69ac8e9d6cf8b6fa74da08" +dependencies = [ + "anstream", + "anstyle", + "clap_lex", + "strsim 0.10.0", + "terminal_size", +] + +[[package]] +name = "clap_derive" +version = "4.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0862016ff20d69b84ef8247369fabf5c008a7417002411897d40ee1f4532b873" +dependencies = [ + "heck", + "proc-macro2", + "quote", + "syn 2.0.31", +] + +[[package]] +name = "clap_lex" +version = "0.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "cd7cc57abe963c6d3b9d8be5b06ba7c8957a930305ca90304f24ef040aa6f961" + [[package]] name = "cloudflare" version = "0.10.1" @@ -191,6 +281,12 @@ dependencies = [ "uuid", ] +[[package]] +name = "colorchoice" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "acbf1af155f9b9ef647e42cdc158db4b64a1b61f743629225fde6f3e0be2a7c7" + [[package]] name = "core-foundation" version = "0.9.3" @@ -757,6 +853,17 @@ dependencies = [ "serde", ] +[[package]] +name = "io-lifetimes" +version = "1.0.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "eae7b9aee968036d54dce06cebaefd919e4472e753296daccd6d344e3e2df0c2" +dependencies = [ + "hermit-abi 0.3.2", + "libc", + "windows-sys", +] + [[package]] name = "ipnet" version = "2.8.0" @@ -805,6 +912,12 @@ dependencies = [ "linked-hash-map", ] +[[package]] +name = "linux-raw-sys" +version = "0.3.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ef53942eb7bf7ff43a617b3e2c1c4a5ecf5944a7c1bc12d7ee39bbb15e5c1519" + [[package]] name = "linux-raw-sys" version = "0.4.5" @@ -1221,6 +1334,20 @@ version = "0.1.23" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d626bb9dae77e28219937af045c257c28bfd3f69333c512553507f5f9798cb76" +[[package]] +name = "rustix" +version = "0.37.23" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4d69718bf81c6127a49dc64e44a742e8bb9213c0ff8869a22c308f84c1d4ab06" +dependencies = [ + "bitflags 1.3.2", + "errno", + "io-lifetimes", + "libc", + "linux-raw-sys 0.3.8", + "windows-sys", +] + [[package]] name = "rustix" version = "0.38.11" @@ -1230,7 +1357,7 @@ dependencies = [ "bitflags 2.4.0", "errno", "libc", - "linux-raw-sys", + "linux-raw-sys 0.4.5", "windows-sys", ] @@ -1438,7 +1565,7 @@ dependencies = [ "cfg-if", "fastrand", "redox_syscall", - "rustix", + "rustix 0.38.11", "windows-sys", ] @@ -1451,6 +1578,16 @@ dependencies = [ "winapi-util", ] +[[package]] +name = "terminal_size" +version = "0.2.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8e6bf6f19e9f8ed8d4048dc22981458ebcf406d67e94cd422e5ecd73d63b3237" +dependencies = [ + "rustix 0.37.23", + "windows-sys", +] + [[package]] name = "thiserror" version = "1.0.48" @@ -1728,6 +1865,12 @@ dependencies = [ "percent-encoding", ] +[[package]] +name = "utf8parse" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "711b9620af191e0cdc7468a8d14e709c3dcdb115b36f838e601583af800a370a" + [[package]] name = "uuid" version = "1.4.1" diff --git a/Cargo.toml b/Cargo.toml index a54f1cc..72fbb2c 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -13,6 +13,10 @@ tokio = { version = "^1", features = ["rt-multi-thread", "macros"] } cloudflare = "^0.10" anyhow = "^1" +[dependencies.clap] +version = "^4.2" +features = ["wrap_help", "derive", "env"] + [patch.crates-io] cloudflare = { git = "https://github.com/jcgruenhage/cloudflare-rs.git", branch = "make-owner-fields-optional" } public-ip = { git = "https://github.com/jcgruenhage/rust-public-ip.git", branch = "cloudflare-provider" } \ No newline at end of file diff --git a/src/api.rs b/src/api.rs new file mode 100644 index 0000000..9d2c459 --- /dev/null +++ b/src/api.rs @@ -0,0 +1,46 @@ +use clap::Parser; + +#[derive(Parser)] +#[clap(author, version, about)] +pub struct Cli { + #[clap( + long, + short, + env = "CLOUDFLARE_RECORDS", + value_name = "RECORDS", + value_delimiter(',') + )] + /// Comma separated DNS records to update with the host's public IP + pub records: Vec, + #[clap( + long, + short, + env = "CLOUDFLARE_APITOKEN", + hide_env_values = true, + value_name = "TOKEN", + required_unless_present_all(["key", "email"]) + )] + /// recommended: The CloudFlare API token to authenticate with + pub token: Option, + #[clap( + long, + short, + env = "CLOUDFLARE_APIKEY", + hide_env_values = true, + value_name = "KEY", + required_unless_present("token"), + requires("email") + )] + /// deprecated: The CloudFlare API key to authenticate with, also requires email + pub key: Option, + #[clap( + long, + short, + env = "CLOUDFLARE_EMAIL", + value_name = "EMAIL", + required_unless_present("token"), + requires("key") + )] + /// deprecated: The CloudFlare email to authenticate with, also requires API key + pub email: Option, +} diff --git a/src/main.rs b/src/main.rs index 27bd6cf..8f8a0b2 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,4 +1,4 @@ -use log::info; +mod api; use cloudflare::{ endpoints::{ @@ -14,7 +14,6 @@ use cloudflare::{ Environment, HttpApiClientConfig, }, }; -use std::env; use std::io; use std::io::prelude::Write; @@ -22,12 +21,18 @@ use std::net::IpAddr; use public_ip::{http, Version}; -use anyhow::{Context, Result}; +use anyhow::Result; + +use api::Cli; +use clap::Parser; #[tokio::main] async fn main() -> Result<()> { pretty_env_logger::init(); + let cli = Cli::parse(); + log::debug!("Rquested records to update: {:#?}", cli.records); + let (public_ipv4, public_ipv6) = tokio::join!( public_ip::addr_with(http::ALL, Version::V4), public_ip::addr_with(public_ip::ALL, Version::V6) @@ -38,28 +43,19 @@ async fn main() -> Result<()> { } if let Some(ipv4) = public_ipv4 { - info!("{}", ipv4); + log::info!("{}", ipv4); } if let Some(ipv6) = public_ipv6 { - info!("{}", ipv6); + log::info!("{}", ipv6); } - let cloudflare_records_env = env::var("CLOUDFLARE_RECORDS").context("")?; - let cloudflare_records: Vec<&str> = - cloudflare_records_env.split(|c: char| c == ',').collect(); - - let credentials: Credentials = - if let Ok(token) = env::var("CLOUDFLARE_APITOKEN") { - Credentials::UserAuthToken { token } - } else if let (Ok(key), Ok(email)) = - (env::var("CLOUDFLARE_APIKEY"), env::var("CLOUDFLARE_EMAIL")) - { - Credentials::UserAuthKey { email, key } - } else { - anyhow::bail!( - "Either API token or API key + email pair must be provided" - ) - }; + let credentials: Credentials = if let Some(token) = cli.token { + Credentials::UserAuthToken { token } + } else if let (Some(key), Some(email)) = (cli.key, cli.email) { + Credentials::UserAuthKey { email, key } + } else { + unreachable!() + }; let api_client = Client::new( credentials, @@ -84,7 +80,7 @@ async fn main() -> Result<()> { .result; for record in records { - if !cloudflare_records.contains(&record.name.as_str()) { + if !cli.records.contains(&record.name) { continue; } @@ -130,7 +126,7 @@ async fn update_record( zone: &Zone, ) -> Result<()> { if public_ip == record_ip { - info!("{} skipped, up to date", record.name); + log::info!("{} skipped, up to date", record.name); return Ok(()); } From aad8553707b6db746400876f55def62b96cd81ea Mon Sep 17 00:00:00 2001 From: Timothy DeHerrera Date: Wed, 6 Sep 2023 10:49:20 -0600 Subject: [PATCH 12/18] feat: add a verbosity flag for easier log control --- Cargo.lock | 11 +++++++++++ Cargo.toml | 1 + src/api.rs | 6 +++++- src/main.rs | 7 +++++-- 4 files changed, 22 insertions(+), 3 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 9e7c273..f92619b 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -189,6 +189,7 @@ version = "0.0.3" dependencies = [ "anyhow", "clap", + "clap-verbosity-flag", "cloudflare", "log", "pretty_env_logger", @@ -229,6 +230,16 @@ dependencies = [ "clap_derive", ] +[[package]] +name = "clap-verbosity-flag" +version = "2.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1eef05769009513df2eb1c3b4613e7fad873a14c600ff025b08f250f59fee7de" +dependencies = [ + "clap", + "log", +] + [[package]] name = "clap_builder" version = "4.4.2" diff --git a/Cargo.toml b/Cargo.toml index 72fbb2c..0af2e09 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -12,6 +12,7 @@ public-ip = "^0.2" tokio = { version = "^1", features = ["rt-multi-thread", "macros"] } cloudflare = "^0.10" anyhow = "^1" +clap-verbosity-flag = "^2.0" [dependencies.clap] version = "^4.2" diff --git a/src/api.rs b/src/api.rs index 9d2c459..50ec5d1 100644 --- a/src/api.rs +++ b/src/api.rs @@ -1,6 +1,7 @@ use clap::Parser; +use clap_verbosity_flag::{InfoLevel, Verbosity}; -#[derive(Parser)] +#[derive(Debug, Parser)] #[clap(author, version, about)] pub struct Cli { #[clap( @@ -43,4 +44,7 @@ pub struct Cli { )] /// deprecated: The CloudFlare email to authenticate with, also requires API key pub email: Option, + + #[clap(flatten)] + pub verbose: Verbosity, } diff --git a/src/main.rs b/src/main.rs index 8f8a0b2..a4d3afe 100644 --- a/src/main.rs +++ b/src/main.rs @@ -28,9 +28,12 @@ use clap::Parser; #[tokio::main] async fn main() -> Result<()> { - pretty_env_logger::init(); - let cli = Cli::parse(); + + pretty_env_logger::formatted_builder() + .filter_level(cli.verbose.log_level_filter()) + .init(); + log::debug!("Rquested records to update: {:#?}", cli.records); let (public_ipv4, public_ipv6) = tokio::join!( From 6e0dd10163e3f737add449d3ebc5a8b5c32b1cd4 Mon Sep 17 00:00:00 2001 From: Timothy DeHerrera Date: Wed, 6 Sep 2023 10:53:55 -0600 Subject: [PATCH 13/18] chore: 0.0.3 -> 0.1.0 Also add myself as a crate author --- Cargo.lock | 2 +- Cargo.toml | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index f92619b..069c669 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -185,7 +185,7 @@ dependencies = [ [[package]] name = "cfdyndns" -version = "0.0.3" +version = "0.0.4" dependencies = [ "anyhow", "clap", diff --git a/Cargo.toml b/Cargo.toml index 0af2e09..f469858 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,7 +1,7 @@ [package] name = "cfdyndns" -version = "0.0.3" -authors = ["Cole Mickens "] +version = "0.1.0" +authors = ["Cole Mickens ", "Tim DeHerrera "] edition = "2021" [dependencies] From 25065bc9cb31ef81e0997def699e12c94d406a3e Mon Sep 17 00:00:00 2001 From: Timothy DeHerrera Date: Mon, 11 Sep 2023 10:44:20 -0600 Subject: [PATCH 14/18] feat: refactor to make all requests async --- rustfmt.toml | 2 +- src/api.rs | 8 +-- src/main.rs | 188 ++++++++++++++++++++++++++++++--------------------- 3 files changed, 117 insertions(+), 81 deletions(-) diff --git a/rustfmt.toml b/rustfmt.toml index 82fc48b..16a16a6 100644 --- a/rustfmt.toml +++ b/rustfmt.toml @@ -15,7 +15,7 @@ reorder_modules = true remove_nested_parens = true short_array_element_width_threshold = 10 match_arm_leading_pipes = "Never" -fn_args_layout = "Vertical" +fn_params_layout = "Vertical" match_block_trailing_comma = false edition = "2021" merge_derives = true diff --git a/src/api.rs b/src/api.rs index 50ec5d1..99c5cce 100644 --- a/src/api.rs +++ b/src/api.rs @@ -4,6 +4,7 @@ use clap_verbosity_flag::{InfoLevel, Verbosity}; #[derive(Debug, Parser)] #[clap(author, version, about)] pub struct Cli { + /// Comma separated DNS records to update with the host's public IP #[clap( long, short, @@ -11,8 +12,8 @@ pub struct Cli { value_name = "RECORDS", value_delimiter(',') )] - /// Comma separated DNS records to update with the host's public IP pub records: Vec, + /// recommended: The CloudFlare API token to authenticate with #[clap( long, short, @@ -21,7 +22,7 @@ pub struct Cli { value_name = "TOKEN", required_unless_present_all(["key", "email"]) )] - /// recommended: The CloudFlare API token to authenticate with + /// deprecated: The CloudFlare API key to authenticate with, also requires email pub token: Option, #[clap( long, @@ -32,7 +33,7 @@ pub struct Cli { required_unless_present("token"), requires("email") )] - /// deprecated: The CloudFlare API key to authenticate with, also requires email + /// deprecated: The CloudFlare email to authenticate with, also requires API key pub key: Option, #[clap( long, @@ -42,7 +43,6 @@ pub struct Cli { required_unless_present("token"), requires("key") )] - /// deprecated: The CloudFlare email to authenticate with, also requires API key pub email: Option, #[clap(flatten)] diff --git a/src/main.rs b/src/main.rs index a4d3afe..7440edf 100644 --- a/src/main.rs +++ b/src/main.rs @@ -6,7 +6,7 @@ use cloudflare::{ DnsContent, DnsRecord, ListDnsRecords, ListDnsRecordsParams, UpdateDnsRecord, UpdateDnsRecordParams, }, - zone::{ListZones, ListZonesParams, Zone}, + zone::{ListZones, ListZonesParams}, }, framework::{ async_api::{ApiClient, Client}, @@ -26,130 +26,166 @@ use anyhow::Result; use api::Cli; use clap::Parser; -#[tokio::main] -async fn main() -> Result<()> { - let cli = Cli::parse(); - - pretty_env_logger::formatted_builder() - .filter_level(cli.verbose.log_level_filter()) - .init(); +use std::sync::Arc; - log::debug!("Rquested records to update: {:#?}", cli.records); - - let (public_ipv4, public_ipv6) = tokio::join!( +async fn get_ips() -> Result<(Option, Option)> { + let (ipv4, ipv6) = tokio::join!( public_ip::addr_with(http::ALL, Version::V4), public_ip::addr_with(public_ip::ALL, Version::V6) ); - if (None, None) == (public_ipv6, public_ipv4) { + if (None, None) == (ipv6, ipv4) { anyhow::bail!("Could not determine your current public IP address.") } - if let Some(ipv4) = public_ipv4 { - log::info!("{}", ipv4); - } - if let Some(ipv6) = public_ipv6 { - log::info!("{}", ipv6); + if let Some(ip) = ipv4 { + log::info!("{}", ip); } + if let Some(ip) = ipv6 { + log::info!("{}", ip); + }; + Ok((ipv4, ipv6)) +} - let credentials: Credentials = if let Some(token) = cli.token { +fn get_client(cli: &Cli) -> Result { + let credentials: Credentials = if let Some(token) = cli.token.clone() { Credentials::UserAuthToken { token } - } else if let (Some(key), Some(email)) = (cli.key, cli.email) { + } else if let (Some(key), Some(email)) = + (cli.key.clone(), cli.email.clone()) + { + log::warn!("API Key & Email combo is deprecated. Please switch to using an API token"); Credentials::UserAuthKey { email, key } } else { unreachable!() }; - let api_client = Client::new( + Client::new( credentials, HttpApiClientConfig::default(), Environment::Production, - )?; + ) +} - let zones = api_client +async fn get_records(client: Arc) -> Result> { + let zones = client + .clone() .request(&ListZones { params: ListZonesParams::default(), }) .await? .result; - + let mut handles = Vec::with_capacity(zones.len()); + let mut records = Vec::with_capacity(zones.len() * 10); for zone in zones { - let records = api_client - .request(&ListDnsRecords { - zone_identifier: &zone.id, - params: ListDnsRecordsParams::default(), - }) - .await? - .result; - - for record in records { - if !cli.records.contains(&record.name) { - continue; - } - - match record.content { - DnsContent::A { content: ipv4 } => match public_ipv4 { - Some(public) => { - update_record( - &record, - &IpAddr::V4(ipv4), - &public, - &api_client, - &zone, - ) - .await? - } - None => continue, - }, - DnsContent::AAAA { content: ipv6 } => match public_ipv6 { - Some(public) => { - update_record( - &record, - &IpAddr::V6(ipv6), - &public, - &api_client, - &zone, - ) - .await? - } - None => continue, - }, - _ => continue, - } - } + let client = client.clone(); + handles.push(tokio::spawn(async move { + client + .request(&ListDnsRecords { + zone_identifier: &zone.id, + params: ListDnsRecordsParams::default(), + }) + .await + })); } - Ok(()) + + for handle in handles { + records.extend(handle.await??.result) + } + Ok(records) } async fn update_record( - record: &DnsRecord, - record_ip: &IpAddr, - public_ip: &IpAddr, - client: &Client, - zone: &Zone, + record: DnsRecord, + record_ip: IpAddr, + public_ip: IpAddr, + client: Arc, + zone: String, ) -> Result<()> { if public_ip == record_ip { log::info!("{} skipped, up to date", record.name); return Ok(()); } - print!("{} ({} -> {})... ", record.name, record_ip, public_ip); + log::info!("{} ({} → {})\n", record.name, record_ip, public_ip); io::stdout().flush().ok(); client .request(&UpdateDnsRecord { - zone_identifier: &zone.id, + zone_identifier: &zone, identifier: &record.id, params: UpdateDnsRecordParams { name: &record.name, ttl: record.ttl.into(), proxied: record.proxied.into(), content: match public_ip { - IpAddr::V4(ip) => DnsContent::A { content: *ip }, - IpAddr::V6(ip) => DnsContent::AAAA { content: *ip }, + IpAddr::V4(ip) => DnsContent::A { content: ip }, + IpAddr::V6(ip) => DnsContent::AAAA { content: ip }, }, }, }) .await?; Ok(()) } + +#[tokio::main] +async fn main() -> Result<()> { + let cli = Cli::parse(); + + pretty_env_logger::formatted_builder() + .filter_level(cli.verbose.log_level_filter()) + .init(); + + log::debug!("Rquested records to update: {:#?}", cli.records); + + let (public_ipv4, public_ipv6) = get_ips().await?; + let api_client = Arc::new(get_client(&cli)?); + let records = get_records(api_client.clone()).await?; + let mut handles = Vec::with_capacity(records.len()); + + for record in records { + if !cli.records.contains(&record.name) { + continue; + } + + let id = record.zone_id.clone(); + let client = api_client.clone(); + match record.content { + DnsContent::A { content: ipv4 } => match public_ipv4 { + Some(public) => { + handles.push(tokio::spawn(async move { + update_record( + record, + IpAddr::V4(ipv4), + public, + client, + id, + ) + .await + })); + } + None => continue, + }, + DnsContent::AAAA { content: ipv6 } => match public_ipv6 { + Some(public) => { + handles.push(tokio::spawn(async move { + update_record( + record, + IpAddr::V6(ipv6), + public, + client, + id, + ) + .await + })); + } + None => continue, + }, + _ => continue, + } + } + + for handle in handles { + handle.await?? + } + Ok(()) +} From a4ba3506836f910781920145b269f525201fdf98 Mon Sep 17 00:00:00 2001 From: Timothy DeHerrera Date: Sat, 16 Sep 2023 18:15:46 -0600 Subject: [PATCH 15/18] chore: refactor code Also adds logic to remove stale DNS records. --- src/clone.rs | 25 +++++ src/fns.rs | 159 +++++++++++++++++++++++++++++ src/main.rs | 277 +++++++++++++++++++++++---------------------------- 3 files changed, 306 insertions(+), 155 deletions(-) create mode 100644 src/clone.rs create mode 100644 src/fns.rs diff --git a/src/clone.rs b/src/clone.rs new file mode 100644 index 0000000..bd8555b --- /dev/null +++ b/src/clone.rs @@ -0,0 +1,25 @@ +use cloudflare::endpoints::dns::{DnsRecord, Meta}; +pub trait Clone_ { + fn clone(&self) -> Self; +} + +impl Clone_ for DnsRecord { + fn clone(&self) -> Self { + Self { + name: self.name.to_owned(), + meta: Meta { + auto_added: self.meta.auto_added, + }, + locked: self.locked, + ttl: self.ttl, + zone_id: self.zone_id.to_owned(), + modified_on: self.modified_on, + created_on: self.created_on, + proxiable: self.proxiable, + proxied: self.proxied, + content: self.content.clone(), + id: self.id.to_owned(), + zone_name: self.zone_name.to_owned(), + } + } +} diff --git a/src/fns.rs b/src/fns.rs new file mode 100644 index 0000000..1f09404 --- /dev/null +++ b/src/fns.rs @@ -0,0 +1,159 @@ +use cloudflare::{ + endpoints::{ + dns::{ + DnsContent, DnsRecord, ListDnsRecords, ListDnsRecordsParams, + UpdateDnsRecord, UpdateDnsRecordParams, + }, + zone::{ListZones, ListZonesParams}, + }, + framework::{ + async_api::{ApiClient, Client}, + auth::Credentials, + Environment, HttpApiClientConfig, + }, +}; + +use public_ip::{http, Version}; + +use std::net::IpAddr; + +use anyhow::Result; + +use crate::api::Cli; +use std::sync::Arc; + +use crate::clone::Clone_; + +pub async fn get_ips() -> Result<(Option, Option)> { + let (ipv4, ipv6) = tokio::join!( + public_ip::addr_with(http::ALL, Version::V4), + public_ip::addr_with(public_ip::ALL, Version::V6) + ); + + if (None, None) == (ipv6, ipv4) { + anyhow::bail!("Could not determine your current public IP address.") + } + + if let Some(ip) = ipv4 { + log::info!("{}", ip); + } + if let Some(ip) = ipv6 { + log::info!("{}", ip); + }; + Ok((ipv4, ipv6)) +} + +pub fn get_client(cli: &Cli) -> Result { + let credentials: Credentials = if let Some(token) = cli.token.clone() { + Credentials::UserAuthToken { token } + } else if let (Some(key), Some(email)) = + (cli.key.clone(), cli.email.clone()) + { + log::warn!("API Key & Email combo is deprecated. Please switch to using an API token"); + Credentials::UserAuthKey { email, key } + } else { + unreachable!() + }; + + Client::new( + credentials, + HttpApiClientConfig::default(), + Environment::Production, + ) +} + +pub async fn get_records( + cli: &Cli, + client: Arc, +) -> Result, Option, Option)>> +{ + let params = ListZones { + params: ListZonesParams::default(), + }; + let zones = client.request(¶ms); + // HACK: make a second call since dns::Zone does not implement Clone upstream + let zones2 = client.request(¶ms).await?.result; + + let mut handles = Vec::with_capacity(zones2.len()); + let mut records = Vec::with_capacity(zones2.len() * 10); + + for zone in zones.await?.result { + let client = client.clone(); + handles.push(tokio::spawn(async move { + client + .request(&ListDnsRecords { + zone_identifier: &zone.id, + params: ListDnsRecordsParams::default(), + }) + .await + })); + } + + for handle in handles { + records.extend(handle.await??.result) + } + + let locals = cli + .records + .iter() + .map(|r| { + ( + r.to_owned(), + zones2 + .iter() + .find(|z| r.contains(&z.name)) + .map(|z| z.id.to_owned()), + records + .iter() + .find(|rec| { + if let DnsContent::A { content: _ } = rec.content { + return rec.name == *r; + } + false + }) + .map(|r| r.clone()), + records + .iter() + .find(|rec| { + if let DnsContent::AAAA { content: _ } = rec.content { + return rec.name == *r; + } + false + }) + .map(|r| r.clone()), + ) + }) + .collect(); + Ok(locals) +} + +pub async fn update_record( + record: DnsRecord, + record_ip: IpAddr, + public_ip: IpAddr, + client: Arc, +) -> Result<()> { + if public_ip == record_ip { + log::info!("{} skipped, up to date", record.name); + return Ok(()); + } + + log::info!("{} ({} → {})\n", record.name, record_ip, public_ip); + + client + .request(&UpdateDnsRecord { + zone_identifier: &record.zone_id, + identifier: &record.id, + params: UpdateDnsRecordParams { + name: &record.name, + ttl: record.ttl.into(), + proxied: record.proxied.into(), + content: match public_ip { + IpAddr::V4(ip) => DnsContent::A { content: ip }, + IpAddr::V6(ip) => DnsContent::AAAA { content: ip }, + }, + }, + }) + .await?; + Ok(()) +} diff --git a/src/main.rs b/src/main.rs index 7440edf..075da35 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,26 +1,14 @@ mod api; +mod clone; +mod fns; -use cloudflare::{ - endpoints::{ - dns::{ - DnsContent, DnsRecord, ListDnsRecords, ListDnsRecordsParams, - UpdateDnsRecord, UpdateDnsRecordParams, - }, - zone::{ListZones, ListZonesParams}, - }, - framework::{ - async_api::{ApiClient, Client}, - auth::Credentials, - Environment, HttpApiClientConfig, - }, +use cloudflare::endpoints::dns::{ + CreateDnsRecord, CreateDnsRecordParams, DeleteDnsRecord, DnsContent, }; -use std::io; -use std::io::prelude::Write; +use cloudflare::framework::async_api::ApiClient; use std::net::IpAddr; -use public_ip::{http, Version}; - use anyhow::Result; use api::Cli; @@ -28,105 +16,6 @@ use clap::Parser; use std::sync::Arc; -async fn get_ips() -> Result<(Option, Option)> { - let (ipv4, ipv6) = tokio::join!( - public_ip::addr_with(http::ALL, Version::V4), - public_ip::addr_with(public_ip::ALL, Version::V6) - ); - - if (None, None) == (ipv6, ipv4) { - anyhow::bail!("Could not determine your current public IP address.") - } - - if let Some(ip) = ipv4 { - log::info!("{}", ip); - } - if let Some(ip) = ipv6 { - log::info!("{}", ip); - }; - Ok((ipv4, ipv6)) -} - -fn get_client(cli: &Cli) -> Result { - let credentials: Credentials = if let Some(token) = cli.token.clone() { - Credentials::UserAuthToken { token } - } else if let (Some(key), Some(email)) = - (cli.key.clone(), cli.email.clone()) - { - log::warn!("API Key & Email combo is deprecated. Please switch to using an API token"); - Credentials::UserAuthKey { email, key } - } else { - unreachable!() - }; - - Client::new( - credentials, - HttpApiClientConfig::default(), - Environment::Production, - ) -} - -async fn get_records(client: Arc) -> Result> { - let zones = client - .clone() - .request(&ListZones { - params: ListZonesParams::default(), - }) - .await? - .result; - let mut handles = Vec::with_capacity(zones.len()); - let mut records = Vec::with_capacity(zones.len() * 10); - for zone in zones { - let client = client.clone(); - handles.push(tokio::spawn(async move { - client - .request(&ListDnsRecords { - zone_identifier: &zone.id, - params: ListDnsRecordsParams::default(), - }) - .await - })); - } - - for handle in handles { - records.extend(handle.await??.result) - } - Ok(records) -} - -async fn update_record( - record: DnsRecord, - record_ip: IpAddr, - public_ip: IpAddr, - client: Arc, - zone: String, -) -> Result<()> { - if public_ip == record_ip { - log::info!("{} skipped, up to date", record.name); - return Ok(()); - } - - log::info!("{} ({} → {})\n", record.name, record_ip, public_ip); - io::stdout().flush().ok(); - - client - .request(&UpdateDnsRecord { - zone_identifier: &zone, - identifier: &record.id, - params: UpdateDnsRecordParams { - name: &record.name, - ttl: record.ttl.into(), - proxied: record.proxied.into(), - content: match public_ip { - IpAddr::V4(ip) => DnsContent::A { content: ip }, - IpAddr::V6(ip) => DnsContent::AAAA { content: ip }, - }, - }, - }) - .await?; - Ok(()) -} - #[tokio::main] async fn main() -> Result<()> { let cli = Cli::parse(); @@ -137,55 +26,133 @@ async fn main() -> Result<()> { log::debug!("Rquested records to update: {:#?}", cli.records); - let (public_ipv4, public_ipv6) = get_ips().await?; - let api_client = Arc::new(get_client(&cli)?); - let records = get_records(api_client.clone()).await?; - let mut handles = Vec::with_capacity(records.len()); - - for record in records { - if !cli.records.contains(&record.name) { - continue; - } - - let id = record.zone_id.clone(); - let client = api_client.clone(); - match record.content { - DnsContent::A { content: ipv4 } => match public_ipv4 { - Some(public) => { + let (public_ipv4, public_ipv6) = fns::get_ips().await?; + let api_client = Arc::new(fns::get_client(&cli)?); + let records = fns::get_records(&cli, api_client.clone()).await?; + let mut handles = Vec::with_capacity(cli.records.len()); + + for (record, zone, dns_v4, dns_v6) in records { + if let Some(zone) = zone { + if let Some(ip) = public_ipv4 { + let client = api_client.clone(); + if let Some(dns) = dns_v4 { + match dns.content { + DnsContent::A { content: ipv4 } => { + handles.push(tokio::spawn(async move { + fns::update_record( + dns, + IpAddr::V4(ipv4), + ip, + client, + ) + .await + })); + } + _ => continue, + } + } else { + log::info!("{} → {}\n", record, ip); + let name = record.clone(); + let id = zone.clone(); handles.push(tokio::spawn(async move { - update_record( - record, - IpAddr::V4(ipv4), - public, - client, - id, - ) - .await + client + .request(&CreateDnsRecord { + zone_identifier: &id, + params: CreateDnsRecordParams { + ttl: Some(1), + priority: None, + proxied: Some(false), + name: &name, + content: DnsContent::A { + content: match ip { + IpAddr::V4(ip) => ip, + _ => unreachable!(), + }, + }, + }, + }) + .await?; + Ok(()) })); } - None => continue, - }, - DnsContent::AAAA { content: ipv6 } => match public_ipv6 { - Some(public) => { + } else if let Some(dns) = dns_v4 { + log::info!("deleting A record: {}\n", record); + let client = api_client.clone(); + let id = zone.clone(); + handles.push(tokio::spawn(async move { + client + .request(&DeleteDnsRecord { + zone_identifier: &id, + identifier: &dns.id, + }) + .await?; + Ok(()) + })) + } + if let Some(ip) = public_ipv6 { + let client = api_client.clone(); + if let Some(dns) = dns_v6 { + match dns.content { + DnsContent::AAAA { content: ipv6 } => { + handles.push(tokio::spawn(async move { + fns::update_record( + dns, + IpAddr::V6(ipv6), + ip, + client, + ) + .await + })); + } + _ => continue, + } + } else { + log::info!("{} → {}\n", record, ip); handles.push(tokio::spawn(async move { - update_record( - record, - IpAddr::V6(ipv6), - public, - client, - id, - ) - .await + client + .request(&CreateDnsRecord { + zone_identifier: &zone, + params: CreateDnsRecordParams { + ttl: Some(1), + priority: None, + proxied: Some(false), + name: &record, + content: DnsContent::AAAA { + content: match ip { + IpAddr::V6(ip) => ip, + _ => unreachable!(), + }, + }, + }, + }) + .await?; + Ok(()) })); } - None => continue, - }, - _ => continue, + } else if let Some(dns) = dns_v6 { + log::info!("deleting AAAA record: {}\n", record); + let client = api_client.clone(); + handles.push(tokio::spawn(async move { + client + .request(&DeleteDnsRecord { + zone_identifier: &zone, + identifier: &dns.id, + }) + .await?; + Ok(()) + })) + } } } + // await all results before handling errors + let mut results = vec![]; for handle in handles { - handle.await?? + results.push(handle.await) + } + for result in results { + result?? } + Ok(()) } From ca79a16fd57d5dd4ed804bb2e4d9752d90609085 Mon Sep 17 00:00:00 2001 From: Timothy DeHerrera Date: Sun, 17 Sep 2023 17:56:42 -0600 Subject: [PATCH 16/18] fix: remove duplicates and verify domain names for sanity & efficiencies sake --- Cargo.lock | 26 ++++++++++++++++++++++++++ Cargo.toml | 1 + src/fns.rs | 28 +++++++++++++++++++++++++--- src/main.rs | 2 -- 4 files changed, 52 insertions(+), 5 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 253a66a..827bc41 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -2,6 +2,16 @@ # It is not intended for manual editing. version = 3 +[[package]] +name = "addr" +version = "0.15.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a93b8a41dbe230ad5087cc721f8d41611de654542180586b315d9f4cf6b72bef" +dependencies = [ + "psl", + "psl-types", +] + [[package]] name = "addr2line" version = "0.21.0" @@ -187,6 +197,7 @@ dependencies = [ name = "cfdyndns" version = "0.1.0" dependencies = [ + "addr", "anyhow", "clap", "clap-verbosity-flag", @@ -1186,6 +1197,21 @@ dependencies = [ "unicode-ident", ] +[[package]] +name = "psl" +version = "2.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4a1be0afcd844b15cfce18bf8cccf2dfa887a00a6454a9ea135f122b948cee91" +dependencies = [ + "psl-types", +] + +[[package]] +name = "psl-types" +version = "2.0.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "33cb294fe86a74cbcf50d4445b37da762029549ebeea341421c7c70370f86cac" + [[package]] name = "public-ip" version = "0.2.2" diff --git a/Cargo.toml b/Cargo.toml index f469858..8c27e32 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -13,6 +13,7 @@ tokio = { version = "^1", features = ["rt-multi-thread", "macros"] } cloudflare = "^0.10" anyhow = "^1" clap-verbosity-flag = "^2.0" +addr = "^0.15" [dependencies.clap] version = "^4.2" diff --git a/src/fns.rs b/src/fns.rs index 1f09404..81ff477 100644 --- a/src/fns.rs +++ b/src/fns.rs @@ -24,6 +24,8 @@ use std::sync::Arc; use crate::clone::Clone_; +use std::collections::HashSet; + pub async fn get_ips() -> Result<(Option, Option)> { let (ipv4, ipv6) = tokio::join!( public_ip::addr_with(http::ALL, Version::V4), @@ -93,8 +95,24 @@ pub async fn get_records( records.extend(handle.await??.result) } - let locals = cli - .records + let mut start: HashSet = cli.records.clone().into_iter().collect(); + let mut invalid = vec![]; + start.retain(|name| { + let mut res = false; + if let Ok(n) = addr::parse_domain_name(name) { + res = n.has_known_suffix(); + } + if !res { + invalid.push(name.clone()); + } + res + }); + + for name in invalid { + log::warn!("{} is an invalid domain name; skipping...", name); + } + + let locals = start .iter() .map(|r| { ( @@ -134,7 +152,11 @@ pub async fn update_record( client: Arc, ) -> Result<()> { if public_ip == record_ip { - log::info!("{} skipped, up to date", record.name); + let kind = match record_ip { + IpAddr::V4(_) => "A", + IpAddr::V6(_) => "AAAA", + }; + log::info!("{} record {} skipped, up to date", kind, record.name); return Ok(()); } diff --git a/src/main.rs b/src/main.rs index 075da35..ee64e9a 100644 --- a/src/main.rs +++ b/src/main.rs @@ -24,8 +24,6 @@ async fn main() -> Result<()> { .filter_level(cli.verbose.log_level_filter()) .init(); - log::debug!("Rquested records to update: {:#?}", cli.records); - let (public_ipv4, public_ipv6) = fns::get_ips().await?; let api_client = Arc::new(fns::get_client(&cli)?); let records = fns::get_records(&cli, api_client.clone()).await?; From 80a365ee6714300049e5b70181f8d2cbb8487a20 Mon Sep 17 00:00:00 2001 From: Timothy DeHerrera Date: Sun, 17 Sep 2023 18:01:09 -0600 Subject: [PATCH 17/18] chore: 0.1.0 -> 0.1.1 --- Cargo.lock | 2 +- Cargo.toml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 827bc41..2afc83b 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -195,7 +195,7 @@ dependencies = [ [[package]] name = "cfdyndns" -version = "0.1.0" +version = "0.1.1" dependencies = [ "addr", "anyhow", diff --git a/Cargo.toml b/Cargo.toml index 8c27e32..c8faf90 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "cfdyndns" -version = "0.1.0" +version = "0.1.1" authors = ["Cole Mickens ", "Tim DeHerrera "] edition = "2021" From 56c8d3bcf4de6dddb9080fb0b0120504ca9176c2 Mon Sep 17 00:00:00 2001 From: Timothy DeHerrera Date: Sun, 17 Sep 2023 18:13:06 -0600 Subject: [PATCH 18/18] chore: update README.md --- README.md | 65 ++++++++++++++----------------------------------------- 1 file changed, 16 insertions(+), 49 deletions(-) diff --git a/README.md b/README.md index 2d4f097..44484f9 100644 --- a/README.md +++ b/README.md @@ -6,30 +6,30 @@ Reimplementation of [cloudflare-dyndns](https://github.com/colemickens/cloudflar ## status known issues -* this is barely in maintenance mode, it seems to have been broken at times without many folks noticing, myself included * paging is not implemented -* some basic CI should be added, since I haven't officially abandoned this (yet) -* I'm wary of Cloudflare these days, YMMV +* some basic CI should be added ## building -* use cargo +`cargo build` ## usage -* simple test CLI usage - ```shell -[cole@zeph:~/code/cfdyndns]$ env | grep CLOUDFLARE - -[cole@zeph:~/code/cfdyndns]$ export CLOUDFLARE_RECORDS=test-cfdyndns.mickens.us - -[cole@zeph:~/code/cfdyndns]$ export CLOUDFLARE_APITOKEN="m1D9WwLDE6lz2hYpU_5MtkpzBpFvEYS3ZuOGB2Va" - -[cole@zeph:~/code/cfdyndns]$ cargo run - Finished dev [unoptimized + debuginfo] target(s) in 0.06s - Running `target/debug/cfdyndns` -test-cfdyndns.mickens.us (1.2.3.4 -> 72.209.157.122)... +Usage: cfdyndns [OPTIONS] + +Options: + -r, --records Comma separated DNS records to update with the host's public IP [env: + CLOUDFLARE_RECORDS=panzy.nrd.sh,panzy.nrd.sh,nrd.xp] + -t, --token recommended: The CloudFlare API token to authenticate with deprecated: The CloudFlare + API key to authenticate with, also requires email [env: CLOUDFLARE_APITOKEN] + -k, --key deprecated: The CloudFlare email to authenticate with, also requires API key [env: + CLOUDFLARE_APIKEY] + -e, --email [env: CLOUDFLARE_EMAIL=] + -v, --verbose... More output per occurrence + -q, --quiet... Less output per occurrence + -h, --help Print help + -V, --version Print version ``` ### installing as systemd service @@ -43,36 +43,3 @@ test-cfdyndns.mickens.us (1.2.3.4 -> 72.209.157.122)... ### uninstalling systemd service 1. `make uninstall-systemd` - -### example systemd journalctl log - -``` -Sep 20 15:36:40 chimera systemd[1]: Started Cloudflare-dyndns. -Sep 20 15:36:43 chimera cloudflare-dyndns[22760]: *.mickens.tv (74.125.186.11 -> 66.235.2.123)... done -Sep 20 15:36:44 chimera cloudflare-dyndns[22760]: mickens.tv (74.125.186.11 -> 66.235.2.123)... done -Sep 20 15:36:44 chimera cloudflare-dyndns[22760]: *.mickens.xxx (74.125.186.11 -> 66.235.2.123)... done -Sep 20 15:36:46 chimera cloudflare-dyndns[22760]: mickens.xxx (74.125.186.11 -> 66.235.2.123)... done -Sep 20 15:36:46 chimera cloudflare-dyndns[22760]: cole.mickens.us (74.125.186.11 -> 66.235.2.123)... done -Sep 20 15:36:46 chimera cloudflare-dyndns[22760]: *.mickens.us (74.125.186.11 -> 66.235.2.123)... done -Sep 20 15:36:47 chimera cloudflare-dyndns[22760]: mickens.us (74.125.186.11 -> 66.235.2.123)... done -Sep 20 15:36:47 chimera cloudflare-dyndns[22760]: *.mickens.me (74.125.186.11 -> 66.235.2.123)... done -Sep 20 15:36:48 chimera cloudflare-dyndns[22760]: mickens.me (74.125.186.11 -> 66.235.2.123)... done -Sep 20 15:36:48 chimera cloudflare-dyndns[22760]: recessionomics.us (74.125.186.11 -> 66.235.2.123)... done -Sep 20 15:36:49 chimera cloudflare-dyndns[22760]: www.recessionomics.us (74.125.186.11 -> 66.235.2.123)... done -Sep 20 15:36:49 chimera cloudflare-dyndns[22760]: *.mickens.io (74.125.186.11 -> 66.235.2.123)... done -Sep 20 15:36:49 chimera cloudflare-dyndns[22760]: mickens.io (74.125.186.11 -> 66.235.2.123)... done -Sep 20 15:41:45 chimera systemd[1]: Started Cloudflare-dyndns. -Sep 20 15:41:45 chimera cloudflare-dyndns[23288]: recessionomics.us skipped, up to date -Sep 20 15:41:45 chimera cloudflare-dyndns[23288]: www.recessionomics.us skipped, up to date -Sep 20 15:41:45 chimera cloudflare-dyndns[23288]: *.mickens.tv skipped, up to date -Sep 20 15:41:45 chimera cloudflare-dyndns[23288]: mickens.tv skipped, up to date -Sep 20 15:41:45 chimera cloudflare-dyndns[23288]: *.mickens.io skipped, up to date -Sep 20 15:41:45 chimera cloudflare-dyndns[23288]: mickens.io skipped, up to date -Sep 20 15:41:46 chimera cloudflare-dyndns[23288]: cole.mickens.us skipped, up to date -Sep 20 15:41:46 chimera cloudflare-dyndns[23288]: *.mickens.us skipped, up to date -Sep 20 15:41:46 chimera cloudflare-dyndns[23288]: mickens.us skipped, up to date -Sep 20 15:41:46 chimera cloudflare-dyndns[23288]: *.mickens.xxx skipped, up to date -Sep 20 15:41:46 chimera cloudflare-dyndns[23288]: mickens.xxx skipped, up to date -Sep 20 15:41:46 chimera cloudflare-dyndns[23288]: *.mickens.me skipped, up to date -Sep 20 15:41:46 chimera cloudflare-dyndns[23288]: mickens.me skipped, up to date -```