diff --git a/CHANGES.md b/CHANGES.md index 7bea91b..cd9a17f 100644 --- a/CHANGES.md +++ b/CHANGES.md @@ -3,10 +3,22 @@ All notable changes to this program are documented in this file. +## 0.32.1 (2023-02-02, `b7f075124503`) + +### Fixed + +- When using the boolean capability `moz:debuggerAddress` with a value of `true` + the site-isolation feature in Firefox will no longer accidentally be turned off. + This behavior affected all users of WebDriver clients especially Selenium, which + set this capability by default, and caused Firefox on desktop systems to be + launched in an unsupported mode. + ## 0.32.0 (2022-10-13, `4563dd583110`) ### Added +- Native aarch64 builds of geckodriver for Linux and Windows are now available. + - Support `wheel` input source for [Actions], which is associated with a wheel-type input device. This endpoint is supported by geckodriver when using Firefox version ≥106. @@ -30,12 +42,16 @@ All notable changes to this program are documented in this file. a location that both Firefox and geckodriver have read/write access to e.g.: + ```bash % mkdir $HOME/tmp % geckodriver --profile-root=~/tmp + ``` or + ```bash % TMPDIR=$HOME/tmp geckodriver + ``` Alternatively, geckodriver may be used with a Firefox install that is not packaged inside a sandbox e.g. from [mozilla.org]. @@ -45,6 +61,13 @@ All notable changes to this program are documented in this file. Implemented by [Olivier Tilloy]. +- On MacOS the geckodriver binary is now technically both signed and notarized. + + Note: The actual validation can only be performed if the machine that starts + the geckodriver binary for the very first time is online. You can find more + details on how to work around this issue in the [macOS notarization] section + of the documentation. + - The backup of the original Firefox preferences are now correctly restored on Android when the WebDriver session ends. diff --git a/Cargo.lock b/Cargo.lock index c5f2777..747195c 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -10,9 +10,9 @@ checksum = "f26201604c87b1e01bd3d98f8d5d9a8fcbb815e8cedb41ffccbeb4bf593a35fe" [[package]] name = "aho-corasick" -version = "0.7.19" +version = "0.7.20" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b4f55bd91a0978cbfd91c457a164bab8b4001c833b7f323132c0a4e1922dd44e" +checksum = "cc936419f96fa211c1b9166887b38e5e40b19958e5b895be7c1f93adec7071ac" dependencies = [ "memchr", ] @@ -34,9 +34,9 @@ checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa" [[package]] name = "base64" -version = "0.13.0" +version = "0.13.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "904dfeac50f3cdaba28fc6f57fdcddb75f49ed61346676a78c4ffe55877802fd" +checksum = "9e1b586273c5702936fe7b7d6896644d8be71e6314cfe09d3167c95f712589e8" [[package]] name = "bitflags" @@ -55,9 +55,9 @@ dependencies = [ [[package]] name = "bumpalo" -version = "3.11.0" +version = "3.12.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c1ad822118d20d2c234f427000d5acc36eabe1e29a348c89b63dd60b13f28e5d" +checksum = "0d261e256854913907f67ed06efbc3338dfe6179796deefc1ff763fc1aee5535" [[package]] name = "byteorder" @@ -67,15 +67,15 @@ checksum = "14c189c53d098945499cdfa7ecc63567cf3886b3332b312a5b4585d8d3a6a610" [[package]] name = "bytes" -version = "1.2.1" +version = "1.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ec8a7b6a70fde80372154c65702f00a0f56f3e1c36abbc6c440484be248856db" +checksum = "89b2fd2a0dcf38d7971e2194b6b6eebab45ae01067456a7fd93d5547a61b70be" [[package]] name = "cc" -version = "1.0.73" +version = "1.0.79" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2fff2a6927b3bb87f9595d67196a70493f627687a71d87a0d692242c33f58c11" +checksum = "50d30906286121d95be3d479533b458f87493b30a4b5f79a607db8f5d11aa91f" [[package]] name = "cfg-if" @@ -85,15 +85,15 @@ checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" [[package]] name = "chrono" -version = "0.4.22" +version = "0.4.23" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bfd4d1b31faaa3a89d7934dbded3111da0d2ef28e3ebccdb4f0179f5929d1ef1" +checksum = "16b0a3d9ed01224b22057780a37bb8c5dbfe1be8ba48678e7bf57ec4b385411f" dependencies = [ "iana-time-zone", "js-sys", "num-integer", "num-traits", - "time 0.1.44", + "time 0.1.45", "wasm-bindgen", "winapi", ] @@ -109,7 +109,7 @@ dependencies = [ "indexmap", "lazy_static", "strsim", - "terminal_size 0.1.17", + "terminal_size", "textwrap", ] @@ -134,11 +134,11 @@ dependencies = [ [[package]] name = "cookie" -version = "0.16.1" +version = "0.16.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "344adc371239ef32293cb1c4fe519592fcf21206c79c02854320afcdf3ab4917" +checksum = "e859cd57d0710d9e06c381b550c06e76992472a8c6d527aecd2fc673dcc231fb" dependencies = [ - "time 0.3.15", + "time 0.3.17", "version_check", ] @@ -168,9 +168,9 @@ dependencies = [ [[package]] name = "crossbeam-utils" -version = "0.8.12" +version = "0.8.14" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "edbafec5fa1f196ca66527c1b12c2ec4745ca14b50f1ad8f9f6f720b55d11fac" +checksum = "4fb766fa798726286dbbb842f174001dab8abc7b627a1dd86e0b7222a95d929f" dependencies = [ "cfg-if", ] @@ -187,9 +187,9 @@ dependencies = [ [[package]] name = "cxx" -version = "1.0.78" +version = "1.0.89" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "19f39818dcfc97d45b03953c1292efc4e80954e1583c4aa770bac1383e2310a4" +checksum = "bc831ee6a32dd495436e317595e639a587aa9907bef96fe6e6abc290ab6204e9" dependencies = [ "cc", "cxxbridge-flags", @@ -199,9 +199,9 @@ dependencies = [ [[package]] name = "cxx-build" -version = "1.0.78" +version = "1.0.89" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3e580d70777c116df50c390d1211993f62d40302881e54d4b79727acb83d0199" +checksum = "94331d54f1b1a8895cd81049f7eaaaef9d05a7dcb4d1fd08bf3ff0806246789d" dependencies = [ "cc", "codespan-reporting", @@ -214,15 +214,15 @@ dependencies = [ [[package]] name = "cxxbridge-flags" -version = "1.0.78" +version = "1.0.89" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "56a46460b88d1cec95112c8c363f0e2c39afdb237f60583b0b36343bf627ea9c" +checksum = "48dcd35ba14ca9b40d6e4b4b39961f23d835dbb8eed74565ded361d93e1feb8a" [[package]] name = "cxxbridge-macro" -version = "1.0.78" +version = "1.0.89" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "747b608fecf06b0d72d440f27acc99288207324b793be2c17991839f3d4995ea" +checksum = "81bbeb29798b407ccd82a3324ade1a7286e0d29851475990b612670f6f5124d2" dependencies = [ "proc-macro2", "quote", @@ -231,9 +231,9 @@ dependencies = [ [[package]] name = "digest" -version = "0.10.5" +version = "0.10.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "adfbc57365a37acbd2ebf2b64d7e69bb766e2fea813521ed536f5d0520dcf86c" +checksum = "8168378f4e5023e7218c89c891c0fd8ecdb5e5e4f18cb78f38cf245dd021e76f" dependencies = [ "block-buffer", "crypto-common", @@ -259,27 +259,6 @@ dependencies = [ "winapi", ] -[[package]] -name = "errno" -version = "0.2.8" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f639046355ee4f37944e44f60642c6f3a7efa3cf6b78c78a0d989a8ce6c396a1" -dependencies = [ - "errno-dragonfly", - "libc", - "winapi", -] - -[[package]] -name = "errno-dragonfly" -version = "0.1.2" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "aa68f1b12764fab894d2755d2518754e71b4fd80ecfb822714a1206c2aab39bf" -dependencies = [ - "cc", - "libc", -] - [[package]] name = "fastrand" version = "1.8.0" @@ -291,9 +270,9 @@ dependencies = [ [[package]] name = "flate2" -version = "1.0.24" +version = "1.0.25" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f82b0f4c27ad9f8bfd1f3208d882da2b09c301bc1c828fd3a00d0216d2fbbff6" +checksum = "a8a2db397cb1c8772f31494cb8917e48cd1e64f0fa7efac59fbd741a0a8ce841" dependencies = [ "crc32fast", "miniz_oxide", @@ -316,9 +295,9 @@ dependencies = [ [[package]] name = "futures-channel" -version = "0.3.24" +version = "0.3.26" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "30bdd20c28fadd505d0fd6712cdfcb0d4b5648baf45faef7f852afb2399bb050" +checksum = "2e5317663a9089767a1ec00a487df42e0ca174b61b4483213ac24448e4664df5" dependencies = [ "futures-core", "futures-sink", @@ -326,27 +305,27 @@ dependencies = [ [[package]] name = "futures-core" -version = "0.3.24" +version = "0.3.26" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4e5aa3de05362c3fb88de6531e6296e85cde7739cccad4b9dfeeb7f6ebce56bf" +checksum = "ec90ff4d0fe1f57d600049061dc6bb68ed03c7d2fbd697274c41805dcb3f8608" [[package]] name = "futures-sink" -version = "0.3.24" +version = "0.3.26" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "21b20ba5a92e727ba30e72834706623d94ac93a725410b6a6b6fbc1b07f7ba56" +checksum = "f310820bb3e8cfd46c80db4d7fb8353e15dfff853a127158425f31e0be6c8364" [[package]] name = "futures-task" -version = "0.3.24" +version = "0.3.26" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a6508c467c73851293f390476d4491cf4d227dbabcd4170f3bb6044959b294f1" +checksum = "dcf79a1bf610b10f42aea489289c5a2c478a786509693b80cd39c44ccd936366" [[package]] name = "futures-util" -version = "0.3.24" +version = "0.3.26" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "44fb6cb1be61cc1d2e43b262516aafcf63b241cffdb1d3fa115f91d9c7b09c90" +checksum = "9c1d6de3acfef38d2be4b1f543f553131788603495be83da675e180c8d6b7bd1" dependencies = [ "futures-core", "futures-sink", @@ -357,7 +336,7 @@ dependencies = [ [[package]] name = "geckodriver" -version = "0.32.0" +version = "0.32.1" dependencies = [ "base64", "chrono", @@ -376,6 +355,7 @@ dependencies = [ "serde_json", "serde_yaml", "tempfile", + "unicode-segmentation", "url", "uuid", "webdriver", @@ -394,9 +374,9 @@ dependencies = [ [[package]] name = "getrandom" -version = "0.2.7" +version = "0.2.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4eb1a864a501629691edf6c15a593b7a51eebaa1e8468e9ddc623de7c9b58ec6" +checksum = "c05aeb6a22b8f62540c194aac980f2115af067bfe15a0734d7277a768d396b31" dependencies = [ "cfg-if", "libc", @@ -405,9 +385,9 @@ dependencies = [ [[package]] name = "h2" -version = "0.3.14" +version = "0.3.15" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5ca32592cf21ac7ccab1825cd87f6c9b3d9022c44d086172ed0966bec8af30be" +checksum = "5f9f29bc9dda355256b2916cf526ab02ce0aeaaaf2bad60d65ef3f12f11dd0f4" dependencies = [ "bytes", "fnv", @@ -489,9 +469,9 @@ checksum = "c4a1e36c821dbe04574f602848a19f742f4fb3c98d40449f11bcad18d6b17421" [[package]] name = "hyper" -version = "0.14.20" +version = "0.14.23" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "02c929dc5c39e335a03c405292728118860721b10190d98c2a0f0efd5baafbac" +checksum = "034711faac9d2166cb1baf1a2fb0b60b1f277f8492fd72176c17f3515e1abd3c" dependencies = [ "bytes", "futures-channel", @@ -513,9 +493,9 @@ dependencies = [ [[package]] name = "iana-time-zone" -version = "0.1.51" +version = "0.1.53" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f5a6ef98976b22b3b7f2f3a806f858cb862044cfa66805aa3ad84cb3d3b785ed" +checksum = "64c122667b287044802d6ce17ee2ddf13207ed924c712de9a66a5814d5b64765" dependencies = [ "android_system_properties", "core-foundation-sys", @@ -527,9 +507,9 @@ dependencies = [ [[package]] name = "iana-time-zone-haiku" -version = "0.1.0" +version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fde6edd6cef363e9359ed3c98ba64590ba9eecba2293eb5a723ab32aee8926aa" +checksum = "0703ae284fc167426161c2e3f1da3ea71d94b21bedbcc9494e92b28e334e3dca" dependencies = [ "cxx", "cxx-build", @@ -547,9 +527,9 @@ dependencies = [ [[package]] name = "indexmap" -version = "1.9.1" +version = "1.9.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "10a35a97730320ffe8e2d410b5d3b69279b98d2c14bdb8b70ea89ecf7888d41e" +checksum = "1885e79c1fc4b10f0e172c475f458b7f7b93061064d98c3293e98c5ba0c8b399" dependencies = [ "autocfg", "hashbrown", @@ -564,23 +544,17 @@ dependencies = [ "cfg-if", ] -[[package]] -name = "io-lifetimes" -version = "0.7.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1ea37f355c05dde75b84bba2d767906ad522e97cd9e2eef2be7a4ab7fb442c06" - [[package]] name = "itoa" -version = "1.0.4" +version = "1.0.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4217ad341ebadf8d8e724e264f13e593e0648f5b3e94b3896a5df283be015ecc" +checksum = "fad582f4b9e86b6caa621cabeb0963332d92eea04729ab12892c2533951e6440" [[package]] name = "js-sys" -version = "0.3.60" +version = "0.3.61" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "49409df3e3bf0856b916e2ceaca09ee28e6871cf7d9ce97a692cacfdb2a25a47" +checksum = "445dde2150c55e483f3d8416706b97ec8e8237c307e5b7b4b8dd15e6af2a0730" dependencies = [ "wasm-bindgen", ] @@ -593,9 +567,9 @@ checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646" [[package]] name = "libc" -version = "0.2.135" +version = "0.2.139" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "68783febc7782c6c5cb401fbda4de5a9898be1762314da0bb2c10ced61f18b0c" +checksum = "201de327520df007757c1f0adce6e827fe8562fbc28bfd9c15571c66ca1f5f79" [[package]] name = "line-wrap" @@ -608,9 +582,9 @@ dependencies = [ [[package]] name = "link-cplusplus" -version = "1.0.7" +version = "1.0.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9272ab7b96c9046fbc5bc56c06c117cb639fe2d509df0c421cad82d2915cf369" +checksum = "ecd207c9c713c34f95a097a5b029ac2ce6010530c7b49d7fea24d977dede04f5" dependencies = [ "cc", ] @@ -621,12 +595,6 @@ version = "0.5.6" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0717cef1bc8b636c6e1c1bbdefc09e6322da8a9321966e8928ef80d20f7f770f" -[[package]] -name = "linux-raw-sys" -version = "0.0.46" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d4d2456c373231a208ad294c33dc5bff30051eafd954cd4caae83a712b12854d" - [[package]] name = "log" version = "0.4.17" @@ -638,9 +606,9 @@ dependencies = [ [[package]] name = "marionette" -version = "0.2.0" +version = "0.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d9da77b04880acc694aafbb3c9efc20880bb4884403b1c92b85ffda8b1820ec3" +checksum = "4931207b28bedfb366ee0271840f2b259ef881ff817023be1ae0608759a18e33" dependencies = [ "serde", "serde_json", @@ -671,18 +639,18 @@ dependencies = [ [[package]] name = "miniz_oxide" -version = "0.5.4" +version = "0.6.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "96590ba8f175222643a85693f33d26e9c8a015f599c216509b1a6894af675d34" +checksum = "f2e212582ede878b109755efd0773a4f0f4ec851584cf0aefbeb4d9ecc114822" dependencies = [ "adler", ] [[package]] name = "mio" -version = "0.8.4" +version = "0.8.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "57ee1c23c7c63b0c9250c339ffdc69255f110b298b901b9f6c82547b7b87caaf" +checksum = "e5d732bc30207a6423068df043e3d02e0735b155ad7ce1a6f76fe2baa5b158de" dependencies = [ "libc", "log", @@ -692,9 +660,9 @@ dependencies = [ [[package]] name = "mozdevice" -version = "0.5.0" +version = "0.5.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "853947b2e889c7ce59735b00833e75f27beecca6b2b03116cf1decd57b335ca0" +checksum = "f01c1b180a91304d9498e47120ac70498909647fefcccf9adb64ed3d6f4bf06c" dependencies = [ "log", "once_cell", @@ -708,18 +676,18 @@ dependencies = [ [[package]] name = "mozprofile" -version = "0.9.0" +version = "0.9.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dd320dce3c165cf4757a56f9cff929b747e003e80fcb9210a474dbb6e44d21c1" +checksum = "e22254a1861d33cce16327afbb5b071c819cd227aef40f382666ec537a689529" dependencies = [ "tempfile", ] [[package]] name = "mozrunner" -version = "0.15.0" +version = "0.15.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "69c22f9d5ab44661b7b767de8fd77e47a5b8b1738a60528e36d13cccc7398e72" +checksum = "0e8925a6f5235f6c586a1bcc79612325f2cb97c2d0da19b23ce668a60e7f6e5f" dependencies = [ "dirs", "log", @@ -730,9 +698,9 @@ dependencies = [ [[package]] name = "mozversion" -version = "0.5.0" +version = "0.5.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3e221ac6a095e7a40c8898783c9a10ec6a22601d569a0007d380ac455cc4d1f1" +checksum = "5e1c996f34cc52fa3de2ba1b683c35c66c279ea9f43735a179d0b0fab6c574d6" dependencies = [ "regex", "rust-ini", @@ -758,26 +726,17 @@ dependencies = [ "autocfg", ] -[[package]] -name = "num_threads" -version = "0.1.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2819ce041d2ee131036f4fc9d6ae7ae125a3a40e97ba64d04fe799ad9dabbb44" -dependencies = [ - "libc", -] - [[package]] name = "once_cell" -version = "1.15.0" +version = "1.17.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e82dad04139b71a90c080c8463fe0dc7902db5192d939bd0950f074d014339e1" +checksum = "6f61fba1741ea2b3d6a1e3178721804bb716a68a6aeba1149b5d52e3d464ea66" [[package]] name = "os_str_bytes" -version = "6.3.0" +version = "6.4.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9ff7415e9ae3fff1225851df9e0d9e4e5479f947619774677a63572e55e80eff" +checksum = "9b7820b9daea5457c9f21c69448905d723fbd21136ccf521748f23fd49e723ee" [[package]] name = "percent-encoding" @@ -819,32 +778,41 @@ checksum = "8b870d8c151b6f2fb93e84a13146138f05d02ed11c7e7c54f8826aaaf7c9f184" [[package]] name = "plist" -version = "1.3.1" +version = "1.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bd39bc6cdc9355ad1dc5eeedefee696bb35c34caf21768741e81826c0bbd7225" +checksum = "5329b8f106a176ab0dce4aae5da86bfcb139bb74fb00882859e03745011f3635" dependencies = [ "base64", "indexmap", "line-wrap", + "quick-xml", "serde", - "time 0.3.15", - "xml-rs", + "time 0.3.17", ] [[package]] name = "proc-macro2" -version = "1.0.46" +version = "1.0.50" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "94e2ef8dbfc347b10c094890f778ee2e36ca9bb4262e86dc99cd217e35f3470b" +checksum = "6ef7d57beacfaf2d8aee5937dab7b7f28de3cb8b1828479bb5de2a7106f2bae2" dependencies = [ "unicode-ident", ] +[[package]] +name = "quick-xml" +version = "0.26.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7f50b1c63b38611e7d4d7f68b82d3ad0cc71a2ad2e7f61fc10f1328d917c93cd" +dependencies = [ + "memchr", +] + [[package]] name = "quote" -version = "1.0.21" +version = "1.0.23" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bbe448f377a7d6961e30f5955f9b8d106c3f5e449d493ee1b125c1d43c2b5179" +checksum = "8856d8364d252a14d474036ea1358d63c9e6965c8e5c1885c18f73d70bff9c7b" dependencies = [ "proc-macro2", ] @@ -871,9 +839,9 @@ dependencies = [ [[package]] name = "regex" -version = "1.6.0" +version = "1.7.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4c4eb3267174b8c6c2f654116623910a0fef09c4753f8dd83db29c48a0df988b" +checksum = "48aaa5748ba571fb95cd2c85c09f629215d3a6ece942baa100950af03a34f733" dependencies = [ "aho-corasick", "memchr", @@ -882,9 +850,9 @@ dependencies = [ [[package]] name = "regex-syntax" -version = "0.6.27" +version = "0.6.28" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a3f87b73ce11b1619a3c6332f45341e0047173771e8b8b73f87bfeefb7b56244" +checksum = "456c603be3e8d448b072f410900c09faf164fbce2d480456f50eea6e25f9c848" [[package]] name = "remove_dir_all" @@ -901,20 +869,6 @@ version = "0.10.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8a654c5bda722c699be6b0fe4c0d90de218928da5b724c3e467fc48865c37263" -[[package]] -name = "rustix" -version = "0.35.11" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fbb2fda4666def1433b1b05431ab402e42a1084285477222b72d6c564c417cef" -dependencies = [ - "bitflags", - "errno", - "io-lifetimes", - "libc", - "linux-raw-sys", - "windows-sys", -] - [[package]] name = "rustls-pemfile" version = "0.2.1" @@ -926,9 +880,9 @@ dependencies = [ [[package]] name = "ryu" -version = "1.0.11" +version = "1.0.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4501abdff3ae82a1c1b477a17252eb69cee9e66eb915c1abaa4f44d873df9f09" +checksum = "7b4b9743ed687d4b4bcedf9ff5eaa7398495ae14e61cba0a295704edbc7decde" [[package]] name = "safemem" @@ -947,36 +901,36 @@ dependencies = [ [[package]] name = "scoped-tls" -version = "1.0.0" +version = "1.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ea6a9290e3c9cf0f18145ef7ffa62d68ee0bf5fcd651017e586dc7fd5da448c2" +checksum = "e1cf6437eb19a8f4a6cc0f7dca544973b0b78843adbfeb3683d1a94a0024a294" [[package]] name = "scratch" -version = "1.0.2" +version = "1.0.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9c8132065adcfd6e02db789d9285a0deb2f3fcb04002865ab67d5fb103533898" +checksum = "ddccb15bcce173023b3fedd9436f882a0739b8dfb45e4f6b6002bee5929f61b2" [[package]] name = "semver" -version = "1.0.14" +version = "1.0.16" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e25dfac463d778e353db5be2449d1cce89bd6fd23c9f1ea21310ce6e5a1b29c4" +checksum = "58bc9567378fc7690d6b2addae4e60ac2eeea07becb2c64b9f218b53865cba2a" [[package]] name = "serde" -version = "1.0.145" +version = "1.0.152" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "728eb6351430bccb993660dfffc5a72f91ccc1295abaa8ce19b27ebe4f75568b" +checksum = "bb7d1f0d3021d347a83e556fc4683dea2ea09d87bccdf88ff5c12545d89d5efb" dependencies = [ "serde_derive", ] [[package]] name = "serde_derive" -version = "1.0.145" +version = "1.0.152" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "81fa1584d3d1bcacd84c277a0dfe21f5b0f6accf4a23d04d4c6d61f1af522b4c" +checksum = "af487d118eecd09402d70a5d72551860e788df87b464af30e5ea6a38c75c541e" dependencies = [ "proc-macro2", "quote", @@ -985,9 +939,9 @@ dependencies = [ [[package]] name = "serde_json" -version = "1.0.86" +version = "1.0.91" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "41feea4228a6f1cd09ec7a3593a682276702cd67b5273544757dae23c096f074" +checksum = "877c235533714907a8c2464236f5c4b2a17262ef1bd71f38f35ea592c8da6883" dependencies = [ "itoa", "ryu", @@ -996,9 +950,9 @@ dependencies = [ [[package]] name = "serde_repr" -version = "0.1.9" +version = "0.1.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1fe39d9fbb0ebf5eb2c7cb7e2a47e4f462fad1379f1166b8ae49ad9eae89a7ca" +checksum = "9a5ec9fa74a20ebbe5d9ac23dac1fc96ba0ecfe9f50f2843b52e537b10fbcb4e" dependencies = [ "proc-macro2", "quote", @@ -1067,9 +1021,9 @@ checksum = "73473c0e59e6d5812c5dfe2a064a6444949f089e20eec9a2e5506596494e4623" [[package]] name = "syn" -version = "1.0.102" +version = "1.0.107" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3fcd952facd492f9be3ef0d0b7032a6e442ee9b361d4acc2b1d0c4aaa5f613a1" +checksum = "1f4064b5b16e03ae50984a5a8ed5d4f8803e6bc1fd170a3cda91a1be4b18e3f5" dependencies = [ "proc-macro2", "quote", @@ -1092,9 +1046,9 @@ dependencies = [ [[package]] name = "termcolor" -version = "1.1.3" +version = "1.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bab24d30b911b2376f3a13cc2cd443142f0c81dda04c118693e35b3835757755" +checksum = "be55cf8942feac5c765c2c993422806843c9a9a45d4d5c407ad6dd2ea95eb9b6" dependencies = [ "winapi-util", ] @@ -1109,39 +1063,29 @@ dependencies = [ "winapi", ] -[[package]] -name = "terminal_size" -version = "0.2.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8440c860cf79def6164e4a0a983bcc2305d82419177a0e0c71930d049e3ac5a1" -dependencies = [ - "rustix", - "windows-sys", -] - [[package]] name = "textwrap" -version = "0.15.1" +version = "0.15.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "949517c0cf1bf4ee812e2e07e08ab448e3ae0d23472aee8a06c985f0c8815b16" +checksum = "b7b3e525a49ec206798b40326a44121291b530c963cfb01018f63e135bac543d" dependencies = [ - "terminal_size 0.2.1", + "terminal_size", ] [[package]] name = "thiserror" -version = "1.0.37" +version = "1.0.38" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "10deb33631e3c9018b9baf9dcbbc4f737320d2b576bac10f6aefa048fa407e3e" +checksum = "6a9cd18aa97d5c45c6603caea1da6628790b37f7a34b6ca89522331c5180fed0" dependencies = [ "thiserror-impl", ] [[package]] name = "thiserror-impl" -version = "1.0.37" +version = "1.0.38" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "982d17546b47146b28f7c22e3d08465f6b8903d0ea13c1660d9d84a6e7adcdbb" +checksum = "1fb327af4685e4d03fa8cbcf1716380da910eeb2bb8be417e7f9fd3fb164f36f" dependencies = [ "proc-macro2", "quote", @@ -1150,9 +1094,9 @@ dependencies = [ [[package]] name = "time" -version = "0.1.44" +version = "0.1.45" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6db9e6914ab8b1ae1c260a4ae7a49b6c5611b40328a735b21862567685e73255" +checksum = "1b797afad3f312d1c66a56d11d0316f916356d11bd158fbc6ca6389ff6bf805a" dependencies = [ "libc", "wasi 0.10.0+wasi-snapshot-preview1", @@ -1161,21 +1105,30 @@ dependencies = [ [[package]] name = "time" -version = "0.3.15" +version = "0.3.17" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d634a985c4d4238ec39cacaed2e7ae552fbd3c476b552c1deac3021b7d7eaf0c" +checksum = "a561bf4617eebd33bca6434b988f39ed798e527f51a1e797d0ee4f61c0a38376" dependencies = [ "itoa", - "libc", - "num_threads", + "serde", + "time-core", "time-macros", ] +[[package]] +name = "time-core" +version = "0.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2e153e1f1acaef8acc537e68b44906d2db6436e2b35ac2c6b42640fff91f00fd" + [[package]] name = "time-macros" -version = "0.2.4" +version = "0.2.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "42657b1a6f4d817cda8e7a0ace261fe0cc946cf3a80314390b22cc61ae080792" +checksum = "d967f99f534ca7e495c575c62638eebc2898a8c84c119b89e250477bc4ba16b2" +dependencies = [ + "time-core", +] [[package]] name = "tinyvec" @@ -1194,9 +1147,9 @@ checksum = "cda74da7e1a664f795bb1f8a87ec406fb89a02522cf6e50620d016add6dbbf5c" [[package]] name = "tokio" -version = "1.21.2" +version = "1.25.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a9e03c497dc955702ba729190dc4aac6f2a0ce97f913e5b1b5912fc5039d9099" +checksum = "c8e00990ebabbe4c14c08aca901caed183ecd5c09562a12c824bb53d3c3fd3af" dependencies = [ "autocfg", "bytes", @@ -1205,7 +1158,7 @@ dependencies = [ "mio", "pin-project-lite", "socket2", - "winapi", + "windows-sys", ] [[package]] @@ -1262,15 +1215,15 @@ dependencies = [ [[package]] name = "try-lock" -version = "0.2.3" +version = "0.2.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "59547bce71d9c38b83d9c0e92b6066c4253371f15005def0c30d9657f50c7642" +checksum = "3528ecfd12c466c6f163363caf2d02a71161dd5e1cc6ae7b34207ea2d42d81ed" [[package]] name = "typenum" -version = "1.15.0" +version = "1.16.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dcf81ac59edc17cc8697ff311e8f5ef2d99fcbd9817b34cec66f90b6c3dfd987" +checksum = "497961ef93d974e23eb6f433eb5fe1b7930b659f06d12dec6fc44a8f554c0bba" [[package]] name = "unicase" @@ -1283,15 +1236,15 @@ dependencies = [ [[package]] name = "unicode-bidi" -version = "0.3.8" +version = "0.3.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "099b7128301d285f79ddd55b9a83d5e6b9e97c92e0ea0daebee7263e932de992" +checksum = "d54675592c1dbefd78cbd98db9bacd89886e1ca50692a0692baefffdeb92dd58" [[package]] name = "unicode-ident" -version = "1.0.5" +version = "1.0.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6ceab39d59e4c9499d4e5a8ee0e2735b891bb7308ac83dfb4e80cad195c9f6f3" +checksum = "84a22b9f218b40614adcb3f4ff08b703773ad44fa9423e4e0d346d5db86e4ebc" [[package]] name = "unicode-normalization" @@ -1304,9 +1257,9 @@ dependencies = [ [[package]] name = "unicode-segmentation" -version = "1.10.0" +version = "1.10.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0fdbf052a0783de01e944a6ce7a8cb939e295b1e7be835a1112c3b9a7f047a5a" +checksum = "1dd624098567895118886609431a7c3b8f516e41d30e0643f03d94592a147e36" [[package]] name = "unicode-width" @@ -1342,9 +1295,9 @@ dependencies = [ [[package]] name = "uuid" -version = "0.8.2" +version = "1.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bc5cf98d8186244414c848017f0e2676b3fcb46807f6668a97dfe67359a3c4b7" +checksum = "1674845326ee10d37ca60470760d4288a6f80f304007d92e5c53bab78c9cfd79" dependencies = [ "getrandom", "serde", @@ -1420,9 +1373,9 @@ checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" [[package]] name = "wasm-bindgen" -version = "0.2.83" +version = "0.2.84" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "eaf9f5aceeec8be17c128b2e93e031fb8a4d469bb9c4ae2d7dc1888b26887268" +checksum = "31f8dcbc21f30d9b8f2ea926ecb58f6b91192c17e9d33594b3df58b2007ca53b" dependencies = [ "cfg-if", "wasm-bindgen-macro", @@ -1430,9 +1383,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-backend" -version = "0.2.83" +version = "0.2.84" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4c8ffb332579b0557b52d268b91feab8df3615f265d5270fec2a8c95b17c1142" +checksum = "95ce90fd5bcc06af55a641a86428ee4229e44e07033963a2290a8e241607ccb9" dependencies = [ "bumpalo", "log", @@ -1445,9 +1398,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-macro" -version = "0.2.83" +version = "0.2.84" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "052be0f94026e6cbc75cdefc9bae13fd6052cdcaf532fa6c45e7ae33a1e6c810" +checksum = "4c21f77c0bedc37fd5dc21f897894a5ca01e7bb159884559461862ae90c0b4c5" dependencies = [ "quote", "wasm-bindgen-macro-support", @@ -1455,9 +1408,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-macro-support" -version = "0.2.83" +version = "0.2.84" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "07bc0c051dc5f23e307b13285f9d75df86bfdf816c5721e573dec1f9b8aa193c" +checksum = "2aff81306fcac3c7515ad4e177f521b5c9a15f2b08f4e32d823066102f35a5f6" dependencies = [ "proc-macro2", "quote", @@ -1468,15 +1421,15 @@ dependencies = [ [[package]] name = "wasm-bindgen-shared" -version = "0.2.83" +version = "0.2.84" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1c38c045535d93ec4f0b4defec448e4291638ee608530863b1e2ba115d4fff7f" +checksum = "0046fef7e28c3804e5e38bfa31ea2a0f73905319b677e57ebe37e49358989b5d" [[package]] name = "webdriver" -version = "0.47.0" +version = "0.47.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "aac1bf6257c9610cbf46e68a515a7f15580e324e03983852e902edb143a8469e" +checksum = "2fc1b5ed60152b107b1859694ba709b546ab9fe5487f856f1255bc6cf8bed55e" dependencies = [ "base64", "bytes", @@ -1486,7 +1439,7 @@ dependencies = [ "serde", "serde_derive", "serde_json", - "time 0.3.15", + "time 0.3.17", "tokio", "tokio-stream", "unicode-segmentation", @@ -1527,62 +1480,70 @@ checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" [[package]] name = "windows-sys" -version = "0.36.1" +version = "0.42.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ea04155a16a59f9eab786fe12a4a450e75cdb175f9e0d80da1e17db09f55b8d2" +checksum = "5a3e1820f08b8513f676f7ab6c1f99ff312fb97b553d30ff4dd86f9f15728aa7" dependencies = [ + "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_aarch64_gnullvm" +version = "0.42.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8c9864e83243fdec7fc9c5444389dcbbfd258f745e7853198f365e3c4968a608" + [[package]] name = "windows_aarch64_msvc" -version = "0.36.1" +version = "0.42.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9bb8c3fd39ade2d67e9874ac4f3db21f0d710bee00fe7cab16949ec184eeaa47" +checksum = "4c8b1b673ffc16c47a9ff48570a9d85e25d265735c503681332589af6253c6c7" [[package]] name = "windows_i686_gnu" -version = "0.36.1" +version = "0.42.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "180e6ccf01daf4c426b846dfc66db1fc518f074baa793aa7d9b9aaeffad6a3b6" +checksum = "de3887528ad530ba7bdbb1faa8275ec7a1155a45ffa57c37993960277145d640" [[package]] name = "windows_i686_msvc" -version = "0.36.1" +version = "0.42.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e2e7917148b2812d1eeafaeb22a97e4813dfa60a3f8f78ebe204bcc88f12f024" +checksum = "bf4d1122317eddd6ff351aa852118a2418ad4214e6613a50e0191f7004372605" [[package]] name = "windows_x86_64_gnu" -version = "0.36.1" +version = "0.42.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c1040f221285e17ebccbc2591ffdc2d44ee1f9186324dd3e84e99ac68d699c45" + +[[package]] +name = "windows_x86_64_gnullvm" +version = "0.42.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4dcd171b8776c41b97521e5da127a2d86ad280114807d0b2ab1e462bc764d9e1" +checksum = "628bfdf232daa22b0d64fdb62b09fcc36bb01f05a3939e20ab73aaf9470d0463" [[package]] name = "windows_x86_64_msvc" -version = "0.36.1" +version = "0.42.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c811ca4a8c853ef420abd8592ba53ddbbac90410fab6903b3e79972a631f7680" +checksum = "447660ad36a13288b1db4d4248e857b510e8c3a225c822ba4fb748c0aafecffd" [[package]] name = "winreg" -version = "0.5.1" +version = "0.10.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a27a759395c1195c4cc5cda607ef6f8f6498f64e78f7900f5de0a127a424704a" +checksum = "80d0f4e272c85def139476380b12f9ac60926689dd2e01d4923222f40580869d" dependencies = [ "winapi", ] -[[package]] -name = "xml-rs" -version = "0.8.4" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d2d7d3948613f75c98fd9328cfdcc45acc4d360655289d0a7d4ec931392200a3" - [[package]] name = "yaml-rust" version = "0.4.5" @@ -1594,9 +1555,9 @@ dependencies = [ [[package]] name = "zip" -version = "0.6.3" +version = "0.6.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "537ce7411d25e54e8ae21a7ce0b15840e7bfcff15b51d697ec3266cc76bdf080" +checksum = "0445d0fbc924bb93539b4316c11afb121ea39296f99a3c4c9edad09e3658cdef" dependencies = [ "byteorder", "crc32fast", diff --git a/Cargo.toml b/Cargo.toml index e8297d3..1722aa7 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,13 +1,24 @@ [package] +edition = "2018" name = "geckodriver" -version = "0.32.0" +version = "0.32.1" +authors = ["Mozilla"] +include = [ + "/.cargo", + "/build.rs", + "/src" + ] description = "Proxy for using WebDriver clients to interact with Gecko-based browsers." -keywords = ["webdriver", "w3c", "httpd", "mozilla", "firefox"] -repository = "https://hg.mozilla.org/mozilla-central/file/tip/testing/geckodriver" readme = "README.md" +keywords = [ + "firefox", + "httpd", + "mozilla", + "w3c", + "webdriver", + ] license = "MPL-2.0" -authors = ["Mozilla"] -edition = "2018" +repository = "https://hg.mozilla.org/mozilla-central/file/tip/testing/geckodriver" [dependencies] base64 = "0.13" @@ -16,9 +27,9 @@ clap = { version = "~3.1", default-features = false, features = ["cargo", "std", hyper = "0.14" lazy_static = "1.0" log = { version = "0.4", features = ["std"] } -marionette = "0.2.0" -mozdevice = "0.5.0" -mozprofile = "0.9.0" +marionette = "0.2.1" +mozdevice = "0.5.1" +mozprofile = "0.9.1" mozrunner = "0.15.0" mozversion = "0.5.0" regex = { version="1.0", default-features = false, features = ["perf", "std"] } @@ -27,9 +38,10 @@ serde_derive = "1.0" serde_json = "1.0" serde_yaml = "0.8" tempfile = "3" +unicode-segmentation = "1.9" url = "2.0" -uuid = { version = "0.8", features = ["v4"] } -webdriver = "0.47.0" +uuid = { version = "1.0", features = ["v4"] } +webdriver = "0.47.1" zip = { version = "0.6", default-features = false, features = ["deflate"] } [dev-dependencies] diff --git a/build.rs b/build.rs index 2fca20d..eb59047 100644 --- a/build.rs +++ b/build.rs @@ -79,11 +79,11 @@ impl Hg { impl BuildInfo for Hg { fn hash(&self) -> Option { - self.exec(&["log", "-r.", "-T{node|short}"]) + self.exec(["log", "-r.", "-T{node|short}"]) } fn date(&self) -> Option { - self.exec(&["log", "-r.", "-T{date|isodate}"]) + self.exec(["log", "-r.", "-T{date|isodate}"]) } } @@ -105,13 +105,13 @@ impl Git { } fn to_hg_sha(&self, git_sha: String) -> Option { - self.exec(&["cinnabar", "git2hg", &git_sha]) + self.exec(["cinnabar", "git2hg", &git_sha]) } } impl BuildInfo for Git { fn hash(&self) -> Option { - self.exec(&["rev-parse", "HEAD"]) + self.exec(["rev-parse", "HEAD"]) .and_then(|sha| self.to_hg_sha(sha)) .map(|mut s| { s.truncate(12); @@ -120,7 +120,7 @@ impl BuildInfo for Git { } fn date(&self) -> Option { - self.exec(&["log", "-1", "--date=short", "--pretty=format:%cd"]) + self.exec(["log", "-1", "--date=short", "--pretty=format:%cd"]) } } diff --git a/doc/ARM.md b/doc/ARM.md index 99ab6dd..8ae9afa 100644 --- a/doc/ARM.md +++ b/doc/ARM.md @@ -1,5 +1,4 @@ -Self-serving an ARM build -========================= +# Self-serving an ARM build Mozilla announced the intent to deprecate ARMv7 HF builds of geckodriver in September 2018. This does not mean you can no longer @@ -11,28 +10,41 @@ cross-compile ARMv7 from a Linux host system is as follows: 1. If you don’t have Rust installed: - # curl https://sh.rustup.rs -sSf | sh + ```shell + % curl https://sh.rustup.rs -sSf | sh + ``` 2. Install cross-compiler toolchain: - # apt install gcc-arm-linux-gnueabihf libc6-armhf-cross libc6-dev-armhf-cross + ```shell + % apt install gcc-arm-linux-gnueabihf libc6-armhf-cross libc6-dev-armhf-cross + ``` 3. Create a new shell, or to reuse the existing shell: - source $HOME/.cargo/env + ```shell + % source $HOME/.cargo/env + ``` 4. Install rustc target toolchain: - % rustup target install armv7-unknown-linux-gnueabihf + ```shell + % rustup target install armv7-unknown-linux-gnueabihf + ``` - 5. Put this in testing/geckodriver/.cargo/config: + 5. Put this in [testing/geckodriver/.cargo/config]: - [target.armv7-unknown-linux-gnueabihf] - linker = "arm-linux-gnueabihf-gcc" + ```rust + [target.armv7-unknown-linux-gnueabihf] + linker = "arm-linux-gnueabihf-gcc" + ``` 6. Build geckodriver from testing/geckodriver: - % cd testing/geckodriver - % cargo build --release --target armv7-unknown-linux-gnueabihf + ```shell + % cd testing/geckodriver + % cargo build --release --target armv7-unknown-linux-gnueabihf + ``` [central]: https://hg.mozilla.org/mozilla-central/ +[testing/geckodriver/.cargo/config]: https://searchfox.org/mozilla-central/source/testing/geckodriver/.cargo/config diff --git a/doc/Bugs.md b/doc/Bugs.md index c4117ea..6823e5d 100644 --- a/doc/Bugs.md +++ b/doc/Bugs.md @@ -1,5 +1,4 @@ -Reporting bugs -============== +# Reporting bugs When opening a new issue or commenting on existing issues, please make sure discussions are related to concrete technical issues diff --git a/doc/Building.md b/doc/Building.md index 18fab16..49a5a51 100644 --- a/doc/Building.md +++ b/doc/Building.md @@ -1,5 +1,4 @@ -Building geckodriver -==================== +# Building geckodriver geckodriver is written in [Rust], a systems programming language from Mozilla. Crucially, it relies on the [webdriver crate] to @@ -10,24 +9,30 @@ as a proxy between [WebDriver] and [Marionette]. To build geckodriver: - % ./mach build testing/geckodriver +```shell +% ./mach build testing/geckodriver +``` If you use artifact builds you may build geckodriver using cargo, since mach in this case does not have a compile environment: - % cd testing/geckodriver - % cargo build - … - Compiling geckodriver v0.21.0 (file:///code/gecko/testing/geckodriver) - … - Finished dev [optimized + debuginfo] target(s) in 7.83s +```shell +% cd testing/geckodriver +% cargo build +… +Compiling geckodriver v0.21.0 (file:///code/gecko/testing/geckodriver) +… +Finished dev [optimized + debuginfo] target(s) in 7.83s +``` Because all Rust code in central shares the same cargo workspace, the binary will be put in the `$(topsrcdir)/target` directory. You can run your freshly built geckodriver this way: - % ./mach geckodriver -- --other --flags +```shell +% ./mach geckodriver -- --other --flags +``` See [Testing](Testing.md) for how to run tests. diff --git a/doc/Capabilities.md b/doc/Capabilities.md index abeda22..c9eb7a5 100644 --- a/doc/Capabilities.md +++ b/doc/Capabilities.md @@ -1,5 +1,4 @@ -Firefox capabilities -==================== +# Firefox capabilities geckodriver has a few capabilities that are specific to Firefox. Most of these [are documented on MDN](https://developer.mozilla.org/en-US/docs/Web/WebDriver/Capabilities/firefoxOptions). @@ -7,9 +6,7 @@ Most of these [are documented on MDN](https://developer.mozilla.org/en-US/docs/W We additionally have some capabilities that largely are implementation concerns that normal users should not care about: - -`moz:debuggerAddress` --------------------- +## `moz:debuggerAddress` A boolean value to indicate if Firefox has to be started with the [Remote Protocol] enabled, which is a low-level debugging interface that @@ -23,29 +20,33 @@ HTTP endpoints: The browser version metadata: - { - "Browser": "Firefox/84.0a1", - "Protocol-Version": "1.0", - "User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10.15; rv:84.0) Gecko/20100101 Firefox/84.0", - "V8-Version": "1.0", - "WebKit-Version": "1.0", - "webSocketDebuggerUrl": "ws://localhost:9222/devtools/browser/fe507083-2960-a442-bbd7-7dfe1f111c05" - } +```json +{ + "Browser": "Firefox/84.0a1", + "Protocol-Version": "1.0", + "User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10.15; rv:84.0) Gecko/20100101 Firefox/84.0", + "V8-Version": "1.0", + "WebKit-Version": "1.0", + "webSocketDebuggerUrl": "ws://localhost:9222/devtools/browser/fe507083-2960-a442-bbd7-7dfe1f111c05" +} +``` ### GET /json/list A list of all available websocket targets: - [ { - "description": "", - "devtoolsFrontendUrl": null, - "faviconUrl": "", - "id": "ecbf9028-676a-1b40-8596-a5edc0e2875b", - "type": "page", - "url": "https://www.mozilla.org/en-US/", - "browsingContextId": 29, - "webSocketDebuggerUrl": "ws://localhost:9222/devtools/page/ecbf9028-676a-1b40-8596-a5edc0e2875b" - } ] +```json +[ { + "description": "", + "devtoolsFrontendUrl": null, + "faviconUrl": "", + "id": "ecbf9028-676a-1b40-8596-a5edc0e2875b", + "type": "page", + "url": "https://www.mozilla.org/en-US/", + "browsingContextId": 29, + "webSocketDebuggerUrl": "ws://localhost:9222/devtools/page/ecbf9028-676a-1b40-8596-a5edc0e2875b" +} ] +``` The contained `webSocketDebuggerUrl` entries can be used to connect to the websocket and interact with the browser by using the CDP protocol. @@ -53,9 +54,7 @@ websocket and interact with the browser by using the CDP protocol. [Remote Protocol]: /remote/index.rst [Chrome DevTools Protocol]: https://chromedevtools.github.io/devtools-protocol/ - -`moz:useNonSpecCompliantPointerOrigin` --------------------------------------- +## `moz:useNonSpecCompliantPointerOrigin` A boolean value to indicate how the pointer origin for an action command will be calculated. @@ -72,9 +71,7 @@ Please note that this capability exists only temporarily, and that it will be removed once all Selenium bindings can handle the new behavior. - -`moz:webdriverClick` --------------------- +## `moz:webdriverClick` A boolean value to indicate which kind of interactability checks to run when performing a click or sending keys to an elements. For diff --git a/doc/CrashReports.md b/doc/CrashReports.md index 98820ca..576bdda 100644 --- a/doc/CrashReports.md +++ b/doc/CrashReports.md @@ -1,13 +1,11 @@ -Analyzing crash data of Firefox -=============================== +# Analyzing crash data of Firefox It's not uncommon that under some special platform configurations and while running automated tests via Selenium and geckodriver Firefox could crash. In those cases it is very helpful to retrieve the generated crash data aka minidump files, and report these to us. -Retrieve the crash data ------------------------ +## Retrieve the crash data Because geckodriver creates a temporary user profile for Firefox, it also automatically removes all its folders once the tests have been finished. That @@ -15,26 +13,30 @@ also means that if Firefox crashed the created minidump files are lost. To prevent that a custom profile has to be used instead. The following code shows an example by using the Python Selenium bindings on Mac OS: - import tempfile +```python +import tempfile - from selenium import webdriver - from selenium.webdriver.firefox.options import Options +from selenium import webdriver +from selenium.webdriver.firefox.options import Options - # Custom profile folder to keep the minidump files - profile = tempfile.mkdtemp(".selenium") - print("*** Using profile: {}".format(profile)) +# Custom profile folder to keep the minidump files +profile = tempfile.mkdtemp(".selenium") +print("*** Using profile: {}".format(profile)) - # Use the above folder as custom profile - opts = Options() - opts.add_argument("-profile") - opts.add_argument(profile) - opts.binary = "/Applications/Firefox.app/Contents/MacOS/firefox" +# Use the above folder as custom profile +opts = Options() +opts.add_argument("-profile") +opts.add_argument(profile) +opts.binary = "/Applications/Firefox.app/Contents/MacOS/firefox" - driver = webdriver.Firefox(options=opts, - # hard-code the Marionette port so geckodriver can connect - service_args=["--marionette-port", "2828"]) +driver = webdriver.Firefox( + options=opts, + # hard-code the Marionette port so geckodriver can connect + service_args=["--marionette-port", "2828"] +) - # Your test code which crashes Firefox +# Your test code which crashes Firefox +``` Executing the test with Selenium now, which triggers the crash of Firefox will leave all the files from the user profile around in the above path. @@ -49,9 +51,7 @@ on Github. [geckodriver issue]: https://github.com/mozilla/geckodriver/issues/new - -Getting details of the crash ----------------------------- +## Getting details of the crash More advanced users can upload the generated minidump files themselves and receive details information about the crash. Therefore find the [crash reporter] @@ -64,8 +64,4 @@ If you submitted a crash please do not forget to also add the link of the crash report to the geckodriver issue. [crash reporter]: https://support.mozilla.org/kb/mozillacrashreporter#w_viewing-reports-outside-of-firefox -[view crash reports]: https://support.mozilla.orgkb/mozillacrashreporter#w_viewing-crash-reports - - - - +[view the crash reports]: https://support.mozilla.orgkb/mozillacrashreporter#w_viewing-crash-reports diff --git a/doc/Flags.md b/doc/Flags.md index 9bc156d..9c11ce5 100644 --- a/doc/Flags.md +++ b/doc/Flags.md @@ -1,3 +1,4 @@ + # Flags ## --allow-hosts ALLOW_HOSTS... @@ -75,7 +76,6 @@ By default `auto` is used. is rooted or not. - ## -b BINARY / --binary BINARY Path to the Firefox binary to use. By default geckodriver tries to @@ -88,8 +88,10 @@ On Linux systems it will use the first _firefox_ binary found by searching the `PATH` environmental variable, which is roughly equivalent to calling [whereis(1)] and extracting the second column: - % whereis firefox - firefox: /usr/bin/firefox /usr/local/firefox +```shell +% whereis firefox +firefox: /usr/bin/firefox /usr/local/firefox +``` On macOS, the binary is found by looking for the first _firefox-bin_ binary in the same fashion as on Linux systems. This means it is @@ -102,7 +104,6 @@ scanning the Windows registry. [creating a new session]: https://w3c.github.io/webdriver/#new-session [whereis(1)]: http://www.manpagez.com/man/1/whereis/ - ## --connect-existing Connect geckodriver to an existing Firefox instance. This means @@ -116,8 +117,7 @@ has been user-set, Marionette will listen on port 2828. So when using `--connect-existing` it is likely you will also have to use `--marionette-port` to set the correct port. -[`--marionette-port`]: #marionette-port - +`--marionette-port`: #marionette-port ## --host HOST @@ -161,13 +161,15 @@ argument is passed to geckodriver. Set the Gecko and geckodriver log level. Possible values are `fatal`, `error`, `warn`, `info`, `config`, `debug`, and `trace`. +## --log-no-truncate + +Disables truncation of long log lines. ## --marionette-host HOST Selects the host for geckodriver’s connection to the [Marionette] remote protocol. Defaults to 127.0.0.1. - ## --marionette-port PORT Selects the port for geckodriver’s connection to the [Marionette] @@ -180,8 +182,7 @@ process, it will pick a free port assigned by the system and set the When `--connect-existing` is used and the Firefox process is not under geckodriver’s control, it will simply connect to PORT. -[`--connect-existing`]: #connect-existing - +`--connect-existing`: #connect-existing ## -p PORT / --port PORT @@ -190,7 +191,6 @@ Port to use for the WebDriver server. Defaults to 4444. A helpful trick is that it is possible to bind to 0 to get the system to atomically assign a free port. - ## --profile-root PROFILE_ROOT Path to the directory to use when creating temporary profiles. By @@ -202,19 +202,17 @@ filesystem such that it doesn't share the same system temporary directory as geckodriver (e.g. when running Firefox inside a container or packaged as a snap). - ## -v[v] Increases the logging verbosity by to debug level when passing a single `-v`, or to trace level if `-vv` is passed. This is analogous to passing `--log debug` and `--log trace`, respectively. -[Marionette]: /testing/marionette/index.rst - - ## --websocket-portPORT Port to use to connect to WebDriver BiDi. Defaults to 9222. A helpful trick is that it is possible to bind to 0 to get the system to atomically assign a free port. + +[Marionette]: /testing/marionette/index.rst diff --git a/doc/Notarization.md b/doc/Notarization.md index c2b171b..ba1ba08 100644 --- a/doc/Notarization.md +++ b/doc/Notarization.md @@ -1,4 +1,4 @@ -# macOS notarization +# MacOS notarization With the introduction of macOS 10.15 “Catalina” Apple introduced [new notarization requirements] that all software must be signed diff --git a/doc/Patches.md b/doc/Patches.md index 5559280..e559da0 100644 --- a/doc/Patches.md +++ b/doc/Patches.md @@ -1,5 +1,4 @@ -Submitting patches -================== +# Submitting patches You can submit patches by using [Phabricator]. Walk through its documentation in how to set it up, and uploading patches for review. Don't worry about which @@ -13,13 +12,17 @@ level 1, you will have permission to use the [Firefox CI] to trigger your own “try runs” to test your changes. You can use the following [try preset] to run the most relevant tests: - mach try --preset geckodriver +```shell +% ./mach try --preset geckodriver +``` This preset will schedule geckodriver-related tests on various platforms. You can reduce the number of tasks by filtering on platforms (e.g. linux) or build type (e.g. opt): - mach try --preset geckodriver -xq "'linux 'opt" +```shell +% ./mach try --preset geckodriver -xq "'linux 'opt" +``` [Phabricator]: https://moz-conduit.readthedocs.io/en/latest/phabricator-user.html [commit creation guidelines]: https://mozilla-version-control-tools.readthedocs.io/en/latest/devguide/contributing.html?highlight=phabricator#submitting-patches-for-review diff --git a/doc/Profiles.md b/doc/Profiles.md index d4665f4..abad9af 100644 --- a/doc/Profiles.md +++ b/doc/Profiles.md @@ -1,5 +1,4 @@ -Profiles -======== +# Profiles geckodriver uses [profiles] to instrument Firefox’ behaviour. The user will usually rely on geckodriver to generate a temporary, @@ -36,9 +35,7 @@ two distinct systems. [`profile` capability]: https://developer.mozilla.org/en-US/docs/Web/WebDriver/Capabilities/firefoxOptions#profile_string [known bug concerning `--profile`]: https://github.com/mozilla/geckodriver/issues/1058 - -Default locations for temporary profiles ----------------------------------------- +## Default locations for temporary profiles When a custom user profile is not provided with the `-profile` command-line argument geckodriver generates a temporary, throwaway @@ -61,11 +58,9 @@ It is not necessary to change the temporary directory system-wide. All you have to do is make sure it gets set for the environment of the geckodriver process: - % TMPDIR=/some/location ./geckodriver - + TMPDIR=/some/location ./geckodriver -Automation preferences ----------------------- +## Automation preferences As indicated in the introduction, geckodriver configures Firefox so it is well-behaved in automation environments. It uses a @@ -98,9 +93,7 @@ the Marionette server in Firefox which port to use. [user.js file]: http://kb.mozillazine.org/User.js_file [`prefs` capability]: https://developer.mozilla.org/en-US/docs/Web/WebDriver/Capabilities/firefoxOptions#prefs_preferences_object - -Temporary profiles not being removed ------------------------------------- +## Temporary profiles not being removed It is a known bug that geckodriver in some instances fails to remove the temporary profile, particularly when the session is not explicitly diff --git a/doc/Releasing.md b/doc/Releasing.md index 10405c5..2419079 100644 --- a/doc/Releasing.md +++ b/doc/Releasing.md @@ -17,16 +17,18 @@ In any case, the steps to release geckodriver are as follows: geckodriver depends on a number of Rust crates that also live in central by using relative paths. Here an excerpt from its `Cargo.toml`: - [dependencies] - … - marionette = { path = "./marionette" } - … - mozdevice = { path = "../mozbase/rust/mozdevice" } - mozprofile = { path = "../mozbase/rust/mozprofile" } - mozrunner = { path = "../mozbase/rust/mozrunner" } - mozversion = { path = "../mozbase/rust/mozversion" } - … - webdriver = { path = "../webdriver" } +```ini +[dependencies] +… +marionette = { path = "./marionette" } +… +mozdevice = { path = "../mozbase/rust/mozdevice" } +mozprofile = { path = "../mozbase/rust/mozprofile" } +mozrunner = { path = "../mozbase/rust/mozrunner" } +mozversion = { path = "../mozbase/rust/mozversion" } +… +webdriver = { path = "../webdriver" } +``` Because we need to export the geckodriver source code to the old GitHub repository when we release, we first need to publish these @@ -48,26 +50,22 @@ For each crate: currently modified crate. Note that running `cargo update` (see next step) will fail if you missed updating a crate's dependency. 2. Update the crate: `cargo update -p ` -3. Commit the changes for the modified `Cargo.toml`, and `Cargo.lock` - (can be found in the repositories root folder). Use a commit message - like `Bug XYZ - [rust-] Release version .` +3. We also publish audit information for the crates based on Mozilla's + [audit criteria], and that must be updated for each release. To do that run: -[semantic versioning rules]: https://semver.org/ -## Update libraries - -Make relevant changes to [Cargo.toml] to upgrade dependencies, then run - - % ./mach vendor rust - % ./mach build testing/geckodriver - -to pull down and vendor the upgraded libraries. + ```shell + % ./mach cargo vet certify --force + ``` -The updates to dependencies should always be made as a separate -commit to not confuse reviewers, because vendoring involves checking -in a lot of extra code already reviewed downstream. +4. Commit the changes for the modified [Cargo.toml] files, [Cargo.lock] and the + [supply-chain/] folder, which can be found in the repositories root folder. + Use a commit message like `Bug XYZ - [rust-] Release version `. +[semantic versioning rules]: https://semver.org/ +[audit criteria]: https://mozilla.github.io/cargo-vet/audit-criteria.html [Cargo.toml]: https://searchfox.org/mozilla-central/source/testing/geckodriver/Cargo.toml [Cargo.lock]: https://searchfox.org/mozilla-central/source/Cargo.lock +[supply-chain/]: https://searchfox.org/mozilla-central/source/supply-chain ## Update the change log @@ -84,6 +82,20 @@ It is good practice to also include relevant information from the since these are the most important dependencies of geckodriver and a lot of its functionality is implemented there. +To get a list of all the changes for one of the above crates one of the following +commands can be used: + +```shell +% hg log -M -r ::central --template "{node|short}\t{desc|firstline}\n" +% git log --reverse $(git cinnabar hg2git )..HEAD --pretty="%s" +``` + +where `` is the changeset of the last geckodriver release and `` +the location of the crate in the repository. + +Add the list of changes to the related release bug on Bugzilla, and also check the +dependency list of the bug for other fixes that are worth mentioning. + We follow the writing style of the existing change log, with one section per version (with a release date), with subsections ‘Added’, ‘Changed’, 'Fixed' and ‘Removed’. If the targeted @@ -106,7 +118,9 @@ familiarise yourself with that before deciding on the version number. After you’ve changed the version number, run - % ./mach build testing/geckodriver +```shell +% ./mach build testing/geckodriver +``` again to update [Cargo.lock]. @@ -142,30 +156,22 @@ released first. Therefore change into each of the directories for crates with an update and run the following command to publish the crate: - % cargo publish +```shell +% cargo publish +``` Note that if a crate has an in-tree dependency make sure to first change the dependency information. -We also publish audit information for the crates, and that must be -updated for each release. To do that run: - - % ./mach cargo vet certify --force +Do not release the geckodriver crate yet! -where `` is the name of the crate and `` is the version of the -crate that was published. - -Once the above steps are done for all published crates, create a single revision -for the supply-chain changes. - -[audit criteria]: https://mozilla.github.io/cargo-vet/audit-criteria.html +Once all crates have been published observe the `/target/package/` folder under +the root of the mozilla-central repository and remove all the folders related +to the above published packages (it will save ~1GB disk space). ## Export to GitHub -The canonical GitHub repository is - - https://github.com/mozilla/geckodriver.git - +The canonical GitHub repository is so make sure you have a local clone of that. It has three branches: _master_ which only contains the [README.md]; _old_ which was the state of the project when it was exported to mozilla-central; and @@ -175,26 +181,34 @@ Before we copy the code over to the GitHub repository we need to check out the [release commit that bumped the version number](#add-the-changeset-id) on mozilla-central: - % hg update $RELEASE_REVISION +```shell +% hg update $RELEASE_REVISION +``` Or: - % git checkout $(git cinnabar hg2git $RELEASE_REVISION) +```shell +% git checkout $(git cinnabar hg2git $RELEASE_REVISION) +``` We will now export the contents of [testing/geckodriver] to a new branch that is based on the _release_ branch, which will be used to create a pull request: - % cd $SRC/geckodriver - % git checkout release - % git pull - % git checkout -b do_release_X.Y.Z - % git rm -rf . - % git clean -fxd - % cp -rt $SRC/gecko/testing/geckodriver . +```shell +% cd $SRC/geckodriver +% git checkout release +% git pull +% git checkout -b do_release_X.Y.Z +% git rm -rf . +% git clean -fxd +% cp -rt $SRC/gecko/testing/geckodriver . +``` Now verify that geckodriver builds correctly by running: - % cargo build +```shell +% cargo build +``` [README.md]: https://searchfox.org/mozilla-central/source/testing/geckodriver/README.md [testing/geckodriver]: https://searchfox.org/mozilla-central/source/testing/geckodriver @@ -205,17 +219,23 @@ Now commit all the changes you have made locally to the _release_ branch. It is recommended to setup a [GPG key] for signing the commit, so that the release commit is marked as `verified`. - % git add . -- ':!mach_commands.py :!moz.build :!target/*' - % git commit -S -am "Import of vX.Y.Z" (signed) +```shell +% git add . -- ':!mach_commands.py :!moz.build :!target/*' +% git commit -S -am "Import of vX.Y.Z" (signed) +``` or if you cannot use signing use: - % git add . -- ':!mach_commands.py :!moz.build :!target/*' - % git commit -am "Import of vX.Y.Z" (unsigned) +```shell +% git add . -- ':!mach_commands.py :!moz.build :!target/*' +% git commit -am "Import of vX.Y.Z" (unsigned) +``` Then push the changes, and create a pull request: - % git push origin do_release_X.Y.Z +```shell +% git push origin do_release_X.Y.Z +``` As indicated above, the changes you make to this branch will not be upstreamed back into mozilla-central. It is merely used as a @@ -240,7 +260,7 @@ geckodriver needs to be manually released on github.com. Therefore start to 4. Find the signed geckodriver archives in the [taskcluster index] by replacing %changeset% with the full release changeset id. Rename the individual files so the basename looks like 'geckodriver-v%version%-%platform%'. - Upload them all, including the checksum files for both the Linux platforms. + Upload them all, including the checksum files for the Linux platforms. 5. Before announcing the release on GitHub publish the geckodriver crate as well on crates.io by running `cargo publish` from the release branch. @@ -252,5 +272,3 @@ geckodriver needs to be manually released on github.com. Therefore start to [dev-webdriver]: https://groups.google.com/a/mozilla.org/g/dev-webdriver Congratulations! You’ve released geckodriver! - -[releases page]: https://github.com/mozilla/geckodriver/releases diff --git a/doc/Support.md b/doc/Support.md index 27bb666..023f0d2 100644 --- a/doc/Support.md +++ b/doc/Support.md @@ -22,6 +22,11 @@ and required versions of Selenium and Firefox: max + + 0.32.1 + ≥ 3.11 (3.14 Python) + 102 ESR + n/a 0.32.0 ≥ 3.11 (3.14 Python) @@ -158,7 +163,6 @@ have to be set when requesting a new session. See the Android section under [Selenium]: https://github.com/seleniumhq/selenium [WebDriver]: https://w3c.github.io/webdriver/ [implementation status]: https://bugzilla.mozilla.org/showdependencytree.cgi?id=721859&hide_resolved=1 -[Firefox Nightly]: https://whattrainisitnow.com/ [remote protocol]: https://github.com/mozilla/geckodriver/issues?q=is%3Aissue+is%3Aopen+label%3Amarionette [specification]: https://github.com/mozilla/geckodriver/issues?q=is%3Aissue+is%3Aopen+label%3Aspec [issue tracker]: https://github.com/mozilla/geckodriver/issues diff --git a/doc/Testing.md b/doc/Testing.md index d8c97ce..2f8f5c9 100644 --- a/doc/Testing.md +++ b/doc/Testing.md @@ -1,5 +1,4 @@ -Testing geckodriver -=================== +# Testing geckodriver We verify and test geckodriver in a couple of different ways. Since it is an implementation of the WebDriver web standard, we share @@ -12,24 +11,33 @@ In addition to the WPT tests, geckodriver and webdriver have unit tests. These are written in Rust, but you must explicitly tell mach to build these by adding the following line to your [mozconfig]: - ac_add_options --enable-rust-tests +```make +ac_add_options --enable-rust-tests +``` -Tests can then be run by using `cargo test` in the specific source folder: +Tests can then be run by using the `test` sub command for [cargo] in the +specific source folder: - % cd testing/geckodriver/src - % cargo test +```shell +% cd testing/geckodriver/src +% cargo test +``` To run the more extensive WPT tests you can use mach, but first make sure you have built Firefox: - % ./mach build - % ./mach wpt testing/web-platform/tests/webdriver +```shell +% ./mach build +% ./mach wpt testing/web-platform/tests/webdriver +``` As these are functional integration tests and pop up Firefox windows sporadically, a helpful tip is to suppress the window whilst you are running them by using Firefox’ [headless mode]: - % ./mach wpt --headless testing/web-platform/tests/webdriver +```shell +% ./mach wpt --headless testing/web-platform/tests/webdriver +``` The `--headless` flag is equivalent to setting the `MOZ_HEADLESS` output variable. In addition to `MOZ_HEADLESS` there is also @@ -49,7 +57,9 @@ and finally the output—or the HTTP response—back to the client. The [trace-level logs] can be surfaced by passing on the `-vv` flag to geckodriver through WPT: - % ./mach wpt --webdriver-arg=-vv testing/web-platform/tests/webdriver +```shell +% ./mach wpt --webdriver-arg=-vv testing/web-platform/tests/webdriver +``` [Web Platform Tests]: http://web-platform-tests.org/ [cargo]: http://doc.crates.io/guide.html diff --git a/doc/TraceLogs.md b/doc/TraceLogs.md index c16fdd7..1c0c18f 100644 --- a/doc/TraceLogs.md +++ b/doc/TraceLogs.md @@ -1,5 +1,4 @@ -Enabling trace logs -=================== +# Enabling trace logs geckodriver provides different bands of logs for different audiences. The most important log entries are shown to everyone by default, @@ -51,11 +50,15 @@ and us a favour and provide a trace-level log right away. To silence geckodriver altogether you may for example either redirect all output to append to some log files: - % geckodriver >>geckodriver.log 2>>geckodriver.err.log +```shell +% geckodriver >>geckodriver.log 2>>geckodriver.err.log +``` Or a black hole somewhere: - % geckodriver >/dev/null 2>&1 +```shell +% geckodriver >/dev/null 2>&1 +``` The log level set for geckodriver is propagated to the Marionette logger in Firefox. Marionette is the remote protocol that geckodriver @@ -68,7 +71,9 @@ from the list above, or by using the `-v` (for debug) or `-vv` (for trace) shorthands. For example, the following command will enable trace logs for both geckodriver and Marionette: - % geckodriver -vv +```shell +% geckodriver -vv +``` The second way of setting the log level is through capabilities. geckodriver accepts a Mozilla-specific configuration object @@ -86,7 +91,9 @@ It is often advisable to use these helpers instead of encoding the JSON Object yourself because it can be difficult to get the exact details right, but if you choose to, it should look like this: - {"moz:firefoxOptions": {"log": {"level": "trace"}}} +```json +{"moz:firefoxOptions": {"log": {"level": "trace"}}} +``` Note that most known WebDriver clients, such as those provided by the Selenium project, do not expose a way to actually _see_ the logs @@ -104,53 +111,54 @@ geckodriver. If you find your language missing, please consider [submitting a patch]: Patches.md - -C# --- +## C-Sharp The Selenium [C# client] comes with a [`FirefoxOptions`] helper for constructing the [`moz:firefoxOptions`] capabilities object: - FirefoxOptions options = new FirefoxOptions(); - options.LogLevel = FirefoxDriverLogLevel.Trace; - IWebDriver driver = new FirefoxDriver(options); +```csharp +FirefoxOptions options = new FirefoxOptions(); +options.LogLevel = FirefoxDriverLogLevel.Trace; +IWebDriver driver = new FirefoxDriver(options); +``` The log output is directed to stdout. [C# client]: https://seleniumhq.github.io/selenium/docs/api/dotnet/ [`FirefoxOptions`]: https://seleniumhq.github.io/selenium/docs/api/dotnet/html/T_OpenQA_Selenium_Firefox_FirefoxOptions.htm -Java ----- +## Java The Selenium [Java client] also comes with a [`org.openqa.selenium.firefox.FirefoxOptions`] helper for constructing the [`moz:firefoxOptions`] capabilities object: - FirefoxOptions options = new FirefoxOptions(); - options.setLogLevel(FirefoxDriverLogLevel.TRACE); - WebDriver driver = new FirefoxDriver(options); +```java +FirefoxOptions options = new FirefoxOptions(); +options.setLogLevel(FirefoxDriverLogLevel.TRACE); +WebDriver driver = new FirefoxDriver(options); +``` As with C#, the log output is helpfully propagated to stdout. [Java client]: https://seleniumhq.github.io/selenium/docs/api/java/ [`org.openqa.selenium.firefox.FirefoxOptions`]: https://seleniumhq.github.io/selenium/docs/api/java/org/openqa/selenium/firefox/FirefoxOptions.html - -Python ------- +## Python The Selenium [Python client] comes with a [`selenium.webdriver.firefox.options.Options`] helper that can be used programmatically to construct the [`moz:firefoxOptions`] capabilities object: - from selenium.webdriver import Firefox - from selenium.webdriver.firefox.options import Options +```python +from selenium.webdriver import Firefox +from selenium.webdriver.firefox.options import Options - opts = Options() - opts.log.level = "trace" - driver = Firefox(options=opts) +opts = Options() +opts.log.level = "trace" +driver = Firefox(options=opts) +``` The log output is stored in a file called _geckodriver.log_ in your script’s current working directory. @@ -158,16 +166,16 @@ script’s current working directory. [Python client]: https://selenium-python.readthedocs.io/ [`selenium.webdriver.firefox.options.Options`]: https://github.com/SeleniumHQ/selenium/blob/master/py/selenium/webdriver/firefox/options.py - -Ruby ----- +## Ruby The Selenium [Ruby client] comes with an [`Options`] helper to generate the correct [`moz:firefoxOptions`] capabilities object: - Selenium::WebDriver.logger.level = :debug - opts = Selenium::WebDriver::Firefox::Options.new(log_level: :trace) - driver = Selenium::WebDriver.for :firefox, options: opts +```ruby +Selenium::WebDriver.logger.level = :debug +opts = Selenium::WebDriver::Firefox::Options.new(log_level: :trace) +driver = Selenium::WebDriver.for :firefox, options: opts +``` [Ruby client]: https://seleniumhq.github.io/selenium/docs/api/rb/ [`Options`]: https://seleniumhq.github.io/selenium/docs/api/rb/Selenium/WebDriver/Firefox/Options.html diff --git a/doc/Usage.md b/doc/Usage.md index d3ce68a..1575da3 100644 --- a/doc/Usage.md +++ b/doc/Usage.md @@ -1,13 +1,10 @@ -Usage -===== +# Usage geckodriver is an implementation of WebDriver, and WebDriver can be used for widely different purposes. How you invoke geckodriver largely depends on your use case. - -Selenium --------- +## Selenium If you are using geckodriver through [Selenium], you must ensure that you have version 3.11 or greater. Because geckodriver implements the @@ -26,11 +23,15 @@ from your [system’s `PATH` environmental variable][PATH] unless you override it by setting the `webdriver.gecko.driver` [Java VM system property]: - System.setProperty("webdriver.gecko.driver", "/home/user/bin"); +```java +System.setProperty("webdriver.gecko.driver", "/home/user/bin"); +``` Or by passing it as a flag to the [java(1)] launcher: - % java -Dwebdriver.gecko.driver=/home/user/bin YourApplication +```shell +% java -Dwebdriver.gecko.driver=/home/user/bin YourApplication +``` Your mileage with this approach may vary based on which programming language bindings you are using. It is in any case generally the case @@ -38,9 +39,11 @@ that geckodriver will be picked up if it is available on the system path. In a bash compatible shell, you can make other programs aware of its location by exporting or setting the `PATH` variable: - % export PATH=$PATH:/home/user/bin - % whereis geckodriver - geckodriver: /home/user/bin/geckodriver +```shell +% export PATH=$PATH:/home/user/bin +% whereis geckodriver +geckodriver: /home/user/bin/geckodriver +``` On Window systems you can change the system path by right-clicking **My Computer** and choosing **Properties**. In the dialogue that appears, @@ -48,11 +51,11 @@ navigate **Advanced** → **Environmental Variables** → **Path**. Or in the Windows console window: - $ set PATH=%PATH%;C:\bin\geckodriver - +```shell +% set PATH=%PATH%;C:\bin\geckodriver +``` -Standalone ----------- +## Standalone Since geckodriver is a separate HTTP server that is a complete remote end implementation of [WebDriver], it is possible to avoid using the Selenium @@ -65,41 +68,45 @@ to any Selenium server. Using [curl(1)]: - % geckodriver & - [1] 16010 - % 1491834109194 geckodriver INFO Listening on 127.0.0.1:4444 - % curl -H 'Content-Type: application/json' -d '{"capabilities": {"alwaysMatch": {"acceptInsecureCerts": true}}}' http://localhost:4444/session - {"value":{"sessionId":"d4605710-5a4e-4d64-a52a-778bb0c31e00","capabilities":{"acceptInsecureCerts":true,[...]}}} - % curl -H 'Content-Type: application/json' -d '{"url": "https://mozilla.org"}' http://localhost:4444/session/d4605710-5a4e-4d64-a52a-778bb0c31e00/url - {} - % curl http://localhost:4444/session/d4605710-5a4e-4d64-a52a-778bb0c31e00/url - {"value":"https://www.mozilla.org/en-US/" - % curl -X DELETE http://localhost:4444/session/d4605710-5a4e-4d64-a52a-778bb0c31e00 - {} - % fg - geckodriver - ^C - % +```shell +% geckodriver & +[1] 16010 +% 1491834109194 geckodriver INFO Listening on 127.0.0.1:4444 +% curl -H 'Content-Type: application/json' -d '{"capabilities": {"alwaysMatch": {"acceptInsecureCerts": true}}}' http://localhost:4444/session +{"value":{"sessionId":"d4605710-5a4e-4d64-a52a-778bb0c31e00","capabilities":{"acceptInsecureCerts":true,[...]}}} +% curl -H 'Content-Type: application/json' -d '{"url": "https://mozilla.org"}' http://localhost:4444/session/d4605710-5a4e-4d64-a52a-778bb0c31e00/url +{} +% curl http://localhost:4444/session/d4605710-5a4e-4d64-a52a-778bb0c31e00/url +{"value":"https://www.mozilla.org/en-US/" +% curl -X DELETE http://localhost:4444/session/d4605710-5a4e-4d64-a52a-778bb0c31e00 +{} +% fg +geckodriver +^C +``` Using the Python [wdclient] library: - import webdriver +```python +import webdriver - with webdriver.Session("127.0.0.1", 4444) as session: - session.url = "https://mozilla.org" - print "The current URL is %s" % session.url +with webdriver.Session("127.0.0.1", 4444) as session: + session.url = "https://mozilla.org" + print "The current URL is %s" % session.url +``` And to run: - % geckodriver & - [1] 16054 - % python example.py - 1491835308354 geckodriver INFO Listening on 127.0.0.1:4444 - The current URL is https://www.mozilla.org/en-US/ - % fg - geckodriver - ^C - % +```shell +% geckodriver & +[1] 16054 +% python example.py +1491835308354 geckodriver INFO Listening on 127.0.0.1:4444 +The current URL is https://www.mozilla.org/en-US/ +% fg +geckodriver +^C +``` [Selenium]: http://seleniumhq.org/ [e10s]: https://developer.mozilla.org/en-US/Firefox/Multiprocess_Firefox diff --git a/marionette/Cargo.toml b/marionette/Cargo.toml index 98a1cc9..22d5d1c 100644 --- a/marionette/Cargo.toml +++ b/marionette/Cargo.toml @@ -1,12 +1,12 @@ [package] name = "marionette" -version = "0.2.0" +version = "0.2.1" +authors = ["Mozilla"] description = "Library implementing the client side of Gecko's Marionette remote automation protocol." +edition = "2018" keywords = ["mozilla", "firefox", "marionette", "webdriver"] -repository = "https://hg.mozilla.org/mozilla-central/file/tip/testing/geckodriver/marionette" license = "MPL-2.0" -authors = ["Mozilla"] -edition = "2018" +repository = "https://hg.mozilla.org/mozilla-central/file/tip/testing/geckodriver/marionette" [dependencies] serde = { version = "1.0", features = ["derive"] } diff --git a/marionette/src/message.rs b/marionette/src/message.rs index f9aac74..704d52f 100644 --- a/marionette/src/message.rs +++ b/marionette/src/message.rs @@ -32,7 +32,7 @@ impl Command { } fn first_entry(&self) -> (String, serde_json::Value) { - match serde_json::to_value(&self).unwrap() { + match serde_json::to_value(self).unwrap() { Value::String(cmd) => (cmd, Value::Object(Map::new())), Value::Object(items) => { let mut iter = items.iter(); diff --git a/marionette/src/webdriver.rs b/marionette/src/webdriver.rs index a795701..efac877 100644 --- a/marionette/src/webdriver.rs +++ b/marionette/src/webdriver.rs @@ -12,11 +12,6 @@ pub struct Url { pub url: String, } -#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)] -pub struct LegacyWebElement { - pub id: String, -} - #[derive(Clone, Debug, PartialEq, Serialize, Deserialize)] pub struct Locator { pub using: Selector, @@ -172,9 +167,9 @@ pub enum Command { #[serde(rename = "WebDriver:DismissAlert")] DismissAlert, #[serde(rename = "WebDriver:ElementClear")] - ElementClear(LegacyWebElement), + ElementClear { id: String }, #[serde(rename = "WebDriver:ElementClick")] - ElementClick(LegacyWebElement), + ElementClick { id: String }, #[serde(rename = "WebDriver:ElementSendKeys")] ElementSendKeys { id: String, @@ -224,11 +219,11 @@ pub enum Command { #[serde(rename = "WebDriver:GetElementProperty")] GetElementProperty { id: String, name: String }, #[serde(rename = "WebDriver:GetElementRect")] - GetElementRect(LegacyWebElement), + GetElementRect { id: String }, #[serde(rename = "WebDriver:GetElementTagName")] - GetElementTagName(LegacyWebElement), + GetElementTagName { id: String }, #[serde(rename = "WebDriver:GetElementText")] - GetElementText(LegacyWebElement), + GetElementText { id: String }, #[serde(rename = "WebDriver:GetPageSource")] GetPageSource, #[serde(rename = "WebDriver:GetShadowRoot")] @@ -248,11 +243,11 @@ pub enum Command { #[serde(rename = "WebDriver:Forward")] GoForward, #[serde(rename = "WebDriver:IsElementDisplayed")] - IsDisplayed(LegacyWebElement), + IsDisplayed { id: String }, #[serde(rename = "WebDriver:IsElementEnabled")] - IsEnabled(LegacyWebElement), + IsEnabled { id: String }, #[serde(rename = "WebDriver:IsElementSelected")] - IsSelected(LegacyWebElement), + IsSelected { id: String }, #[serde(rename = "WebDriver:MaximizeWindow")] MaximizeWindow, #[serde(rename = "WebDriver:MinimizeWindow")] diff --git a/src/android.rs b/src/android.rs index 3cc87b0..10293d5 100644 --- a/src/android.rs +++ b/src/android.rs @@ -291,7 +291,7 @@ impl AndroidHandler { { // To configure GeckoView, we use the automation techniques documented at // https://mozilla.github.io/geckoview/consumer/docs/automation. - #[derive(Serialize, Deserialize, PartialEq, Debug)] + #[derive(Serialize, Deserialize, PartialEq, Eq, Debug)] pub struct Config { pub env: Mapping, pub args: Vec, diff --git a/src/browser.rs b/src/browser.rs index 902f7f7..7d99d9b 100644 --- a/src/browser.rs +++ b/src/browser.rs @@ -17,6 +17,7 @@ use webdriver::error::{ErrorStatus, WebDriverError, WebDriverResult}; /// A running Gecko instance. #[derive(Debug)] +#[allow(clippy::large_enum_variant)] pub(crate) enum Browser { Local(LocalBrowser), Remote(RemoteBrowser), @@ -482,7 +483,7 @@ mod tests { let prefs_path = initial_prefs.path.clone(); let mut conflicting_backup_path = initial_prefs.path.clone(); - conflicting_backup_path.set_extension("geckodriver_backup".to_string()); + conflicting_backup_path.set_extension("geckodriver_backup"); println!("{:?}", conflicting_backup_path); let mut file = File::create(&conflicting_backup_path).unwrap(); file.write_all(b"test").unwrap(); @@ -501,7 +502,7 @@ mod tests { assert!(user_prefs.path.exists()); let mut backup_path = user_prefs.path.clone(); - backup_path.set_extension("geckodriver_backup_1".to_string()); + backup_path.set_extension("geckodriver_backup_1"); assert!(backup_path.exists()); diff --git a/src/capabilities.rs b/src/capabilities.rs index 3654cc5..e5f4566 100644 --- a/src/capabilities.rs +++ b/src/capabilities.rs @@ -433,7 +433,7 @@ impl FirefoxOptions { rv.log = FirefoxOptions::load_log(options)?; rv.prefs = FirefoxOptions::load_prefs(options)?; if let Some(profile) = FirefoxOptions::load_profile( - settings.profile_root.as_ref().map(|x| x.as_path()), + settings.profile_root.as_deref(), options, )? { rv.profile = ProfileType::Path(profile); @@ -544,16 +544,6 @@ impl FirefoxOptions { } } - // Force Fission disabled until the CDP implementation is compatible, - // and preference hasn't been already set - if has_debugger_address { - let has_fission_pref = rv.prefs.iter().find(|&x| x.0 == "fission.autostart"); - if has_fission_pref.is_none() { - rv.prefs - .push(("fission.autostart".to_owned(), Pref::new(false))); - } - } - Ok(rv) } @@ -1095,11 +1085,6 @@ mod tests { } else { panic!("CLI arguments for Firefox not found"); } - - assert!(opts - .prefs - .iter() - .any(|pref| pref == &("fission.autostart".to_owned(), Pref::new(false)))); } #[test] diff --git a/src/command.rs b/src/command.rs index c011238..798a4c0 100644 --- a/src/command.rs +++ b/src/command.rs @@ -16,7 +16,7 @@ use webdriver::httpapi::WebDriverExtensionRoute; use webdriver::Parameters; pub fn extension_routes() -> Vec<(Method, &'static str, GeckoExtensionRoute)> { - return vec![ + vec![ ( Method::GET, "/session/{sessionId}/moz/context", @@ -42,10 +42,10 @@ pub fn extension_routes() -> Vec<(Method, &'static str, GeckoExtensionRoute)> { "/session/{sessionId}/moz/screenshot/full", GeckoExtensionRoute::TakeFullScreenshot, ), - ]; + ] } -#[derive(Clone, PartialEq)] +#[derive(Clone, PartialEq, Eq)] pub enum GeckoExtensionRoute { GetContext, SetContext, @@ -104,7 +104,7 @@ impl WebDriverExtensionCommand for GeckoExtensionCommand { } } -#[derive(Clone, Debug, PartialEq, Serialize)] +#[derive(Clone, Debug, PartialEq, Eq, Serialize)] pub struct AddonInstallParameters { pub path: String, pub temporary: Option, @@ -168,30 +168,30 @@ impl<'de> Deserialize<'de> for AddonInstallParameters { } } -#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)] +#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)] pub struct AddonUninstallParameters { pub id: String, } -#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)] +#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)] #[serde(rename_all = "lowercase")] pub enum GeckoContext { Content, Chrome, } -#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)] +#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)] pub struct GeckoContextParameters { pub context: GeckoContext, } -#[derive(Clone, Debug, PartialEq, Serialize, Deserialize)] +#[derive(Clone, Debug, PartialEq, Eq, Serialize, Deserialize)] pub struct XblLocatorParameters { pub name: String, pub value: String, } -#[derive(Default, Debug, PartialEq)] +#[derive(Default, Debug, PartialEq, Eq)] pub struct LogOptions { pub level: Option, } diff --git a/src/logging.rs b/src/logging.rs index 73ce062..073da95 100644 --- a/src/logging.rs +++ b/src/logging.rs @@ -7,7 +7,7 @@ //! The [`log`] crate provides a single logging API that abstracts over the //! actual logging implementation. This module uses the logging API //! to provide a log implementation that shares many aesthetical traits with -//! [Log.jsm] from Gecko. +//! [Log.sys.mjs] from Gecko. //! //! Using the [`error!`], [`warn!`], [`info!`], [`debug!`], and //! [`trace!`] macros from `log` will output a timestamp field, followed by the @@ -22,7 +22,7 @@ //! and `Level::Config` becomes `log::Level::Debug`. //! //! [`log`]: https://docs.rs/log/newest/log/ -//! [Log.jsm]: https://developer.mozilla.org/en/docs/Mozilla/JavaScript_code_modules/Log.jsm +//! [Log.sys.mjs]: https://searchfox.org/mozilla-central/source/toolkit/modules/Log.sys.mjs //! [`error!`]: https://docs.rs/log/newest/log/macro.error.html //! [`warn!`]: https://docs.rs/log/newest/log/macro.warn.html //! [`info!`]: https://docs.rs/log/newest/log/macro.info.html @@ -35,11 +35,16 @@ use std::fmt; use std::io; use std::io::Write; use std::str; -use std::sync::atomic::{AtomicUsize, Ordering}; +use std::sync::atomic::{AtomicBool, AtomicUsize, Ordering}; +use unicode_segmentation::UnicodeSegmentation; use mozprofile::preferences::Pref; +static LOG_TRUNCATE: AtomicBool = AtomicBool::new(true); static MAX_LOG_LEVEL: AtomicUsize = AtomicUsize::new(0); + +const MAX_STRING_LENGTH: usize = 250; + const LOGGED_TARGETS: &[&str] = &[ "geckodriver", "mozdevice", @@ -49,9 +54,9 @@ const LOGGED_TARGETS: &[&str] = &[ "webdriver", ]; -/// Logger levels from [Log.jsm]. +/// Logger levels from [Log.sys.mjs]. /// -/// [Log.jsm]: https://developer.mozilla.org/en/docs/Mozilla/JavaScript_code_modules/Log.jsm +/// [Log.sys.mjs]: https://searchfox.org/mozilla-central/source/toolkit/modules/Log.sys.mjs #[repr(usize)] #[derive(Clone, Copy, Eq, Debug, Hash, PartialEq)] pub enum Level { @@ -165,14 +170,24 @@ impl log::Log for Logger { fn log(&self, record: &log::Record) { if self.enabled(record.metadata()) { - let ts = format_ts(chrono::Local::now()); - println!( - "{}\t{}\t{}\t{}", - ts, - record.target(), - record.level(), - record.args() - ); + if let Some((s1, s2)) = truncate_message(record.args()) { + println!( + "{}\t{}\t{}\t{} ... {}", + format_ts(chrono::Local::now()), + record.target(), + record.level(), + s1, + s2 + ); + } else { + println!( + "{}\t{}\t{}\t{}", + format_ts(chrono::Local::now()), + record.target(), + record.level(), + record.args() + ) + } } } @@ -182,14 +197,15 @@ impl log::Log for Logger { } /// Initialises the logging subsystem with the default log level. -pub fn init() -> Result<(), log::SetLoggerError> { - init_with_level(Level::Info) +pub fn init(truncate: bool) -> Result<(), log::SetLoggerError> { + init_with_level(Level::Info, truncate) } /// Initialises the logging subsystem. -pub fn init_with_level(level: Level) -> Result<(), log::SetLoggerError> { +pub fn init_with_level(level: Level, truncate: bool) -> Result<(), log::SetLoggerError> { let logger = Logger {}; set_max_level(level); + set_truncate(truncate); log::set_boxed_logger(Box::new(logger))?; Ok(()) } @@ -207,14 +223,44 @@ pub fn set_max_level(level: Level) { log::set_max_level(slevel.to_level_filter()) } +/// Sets the global maximum log level. +pub fn set_truncate(truncate: bool) { + LOG_TRUNCATE.store(truncate, Ordering::SeqCst); +} + +/// Returns the truncation flag. +pub fn truncate() -> bool { + LOG_TRUNCATE.load(Ordering::Relaxed) +} + /// Produces a 13-digit Unix Epoch timestamp similar to Gecko. fn format_ts(ts: chrono::DateTime) -> String { format!("{}{:03}", ts.timestamp(), ts.timestamp_subsec_millis()) } +/// Truncate a log message if it's too long +fn truncate_message(args: &fmt::Arguments) -> Option<(String, String)> { + // Don't truncate the message if requested. + if !truncate() { + return None; + } + + let message = format!("{}", args); + let chars = message.graphemes(true).collect::>(); + + if chars.len() > MAX_STRING_LENGTH { + let middle: usize = MAX_STRING_LENGTH / 2; + let s1 = chars[0..middle].concat(); + let s2 = chars[chars.len() - middle..].concat(); + Some((s1, s2)) + } else { + None + } +} + #[cfg(test)] mod tests { - use super::{format_ts, init_with_level, max_level, set_max_level, Level}; + use super::*; use std::str::FromStr; use std::sync::Mutex; @@ -322,9 +368,9 @@ mod tests { #[test] fn test_init_with_level() { let _guard = LEVEL_MUTEX.lock(); - init_with_level(Level::Debug).unwrap(); + init_with_level(Level::Debug, false).unwrap(); assert_eq!(max_level(), Level::Debug); - assert!(init_with_level(Level::Warn).is_err()); + assert!(init_with_level(Level::Warn, false).is_err()); } #[test] @@ -333,4 +379,25 @@ mod tests { let s = format_ts(ts); assert_eq!(s.len(), 13); } + + #[test] + fn test_truncate() { + let short_message = (0..MAX_STRING_LENGTH).map(|_| "x").collect::(); + // A message up to MAX_STRING_LENGTH is not truncated + assert_eq!(truncate_message(&format_args!("{}", short_message)), None); + + let long_message = (0..MAX_STRING_LENGTH + 1).map(|_| "x").collect::(); + let part = (0..MAX_STRING_LENGTH / 2).map(|_| "x").collect::(); + + // A message longer than MAX_STRING_LENGTH is not truncated if requested + set_truncate(false); + assert_eq!(truncate_message(&format_args!("{}", long_message)), None); + + // A message longer than MAX_STRING_LENGTH is truncated if requested + set_truncate(true); + assert_eq!( + truncate_message(&format_args!("{}", long_message)), + Some((part.to_owned(), part)) + ); + } } diff --git a/src/main.rs b/src/main.rs index 7742b36..64df65a 100644 --- a/src/main.rs +++ b/src/main.rs @@ -130,6 +130,7 @@ enum Operation { Version, Server { log_level: Option, + log_truncate: bool, address: SocketAddr, allow_hosts: Vec, allow_origins: Vec, @@ -161,8 +162,8 @@ fn server_address(webdriver_host: &str, webdriver_port: u16) -> ProgramResult ProgramResult { }; Ok(Operation::Server { log_level, + log_truncate: !args.is_present("log_no_truncate"), allow_hosts, allow_origins, address, @@ -347,6 +349,7 @@ fn inner_main(cmd: &mut Command) -> ProgramResult<()> { Operation::Server { log_level, + log_truncate, address, allow_hosts, allow_origins, @@ -354,9 +357,9 @@ fn inner_main(cmd: &mut Command) -> ProgramResult<()> { deprecated_storage_arg, } => { if let Some(ref level) = log_level { - logging::init_with_level(*level).unwrap(); + logging::init_with_level(*level, log_truncate).unwrap(); } else { - logging::init().unwrap(); + logging::init(log_truncate).unwrap(); } if deprecated_storage_arg { @@ -474,9 +477,14 @@ fn make_command<'a>() -> Command<'a> { .long("log") .takes_value(true) .value_name("LEVEL") - .possible_values(&["fatal", "error", "warn", "info", "config", "debug", "trace"]) + .possible_values(["fatal", "error", "warn", "info", "config", "debug", "trace"]) .help("Set Gecko log level"), ) + .arg( + Arg::new("log_no_truncate") + .long("log-no-truncate") + .help("Disable truncation of long log lines"), + ) .arg( Arg::new("help") .short('h') @@ -499,7 +507,7 @@ fn make_command<'a>() -> Command<'a> { .arg( Arg::new("android_storage") .long("android-storage") - .possible_values(&["auto", "app", "internal", "sdcard"]) + .possible_values(["auto", "app", "internal", "sdcard"]) .value_name("ANDROID_STORAGE") .help("Selects storage location to be used for test data (deprecated)."), ) diff --git a/src/marionette.rs b/src/marionette.rs index 0de05f8..b89980e 100644 --- a/src/marionette.rs +++ b/src/marionette.rs @@ -17,7 +17,7 @@ use marionette_rs::common::{ use marionette_rs::marionette::AppStatus; use marionette_rs::message::{Command, Message, MessageId, Request}; use marionette_rs::webdriver::{ - Command as MarionetteWebDriverCommand, Keys as MarionetteKeys, LegacyWebElement, + Command as MarionetteWebDriverCommand, Keys as MarionetteKeys, Locator as MarionetteLocator, NewWindow as MarionetteNewWindow, PrintMargins as MarionettePrintMargins, PrintOrientation as MarionettePrintOrientation, PrintPage as MarionettePrintPage, PrintParameters as MarionettePrintParameters, @@ -189,14 +189,14 @@ impl MarionetteHandler { options, marionette_port, websocket_port, - self.settings.profile_root.as_ref().map(|x| x.as_path()), + self.settings.profile_root.as_deref(), )?) } else if !self.settings.connect_existing { Browser::Local(LocalBrowser::new( options, marionette_port, self.settings.jsdebugger, - self.settings.profile_root.as_ref().map(|x| x.as_path()), + self.settings.profile_root.as_deref(), )?) } else { Browser::Existing(marionette_port) @@ -296,7 +296,7 @@ struct MarionetteSession { impl MarionetteSession { fn new(session_id: Option, capabilities: Map) -> MarionetteSession { - let initital_id = session_id.unwrap_or_else(|| "".to_string()); + let initital_id = session_id.unwrap_or_default(); MarionetteSession { session_id: initital_id, capabilities, @@ -773,10 +773,14 @@ fn try_convert_to_marionette_message( }, DismissAlert => Some(Command::WebDriver(MarionetteWebDriverCommand::DismissAlert)), ElementClear(ref e) => Some(Command::WebDriver( - MarionetteWebDriverCommand::ElementClear(e.to_marionette()?), + MarionetteWebDriverCommand::ElementClear { + id: e.clone().to_string(), + } )), ElementClick(ref e) => Some(Command::WebDriver( - MarionetteWebDriverCommand::ElementClick(e.to_marionette()?), + MarionetteWebDriverCommand::ElementClick { + id: e.clone().to_string(), + } )), ElementSendKeys(ref e, ref x) => { let keys = x.to_marionette()?; @@ -854,14 +858,20 @@ fn try_convert_to_marionette_message( name: x.clone(), }, )), - GetElementRect(ref x) => Some(Command::WebDriver( - MarionetteWebDriverCommand::GetElementRect(x.to_marionette()?), + GetElementRect(ref e) => Some(Command::WebDriver( + MarionetteWebDriverCommand::GetElementRect { + id: e.clone().to_string(), + } )), - GetElementTagName(ref x) => Some(Command::WebDriver( - MarionetteWebDriverCommand::GetElementTagName(x.to_marionette()?), + GetElementTagName(ref e) => Some(Command::WebDriver( + MarionetteWebDriverCommand::GetElementTagName { + id: e.clone().to_string(), + } )), - GetElementText(ref x) => Some(Command::WebDriver( - MarionetteWebDriverCommand::GetElementText(x.to_marionette()?), + GetElementText(ref e) => Some(Command::WebDriver( + MarionetteWebDriverCommand::GetElementText { + id: e.clone().to_string(), + } )), GetPageSource => Some(Command::WebDriver( MarionetteWebDriverCommand::GetPageSource, @@ -884,15 +894,21 @@ fn try_convert_to_marionette_message( GetTimeouts => Some(Command::WebDriver(MarionetteWebDriverCommand::GetTimeouts)), GoBack => Some(Command::WebDriver(MarionetteWebDriverCommand::GoBack)), GoForward => Some(Command::WebDriver(MarionetteWebDriverCommand::GoForward)), - IsDisplayed(ref x) => Some(Command::WebDriver(MarionetteWebDriverCommand::IsDisplayed( - x.to_marionette()?, - ))), - IsEnabled(ref x) => Some(Command::WebDriver(MarionetteWebDriverCommand::IsEnabled( - x.to_marionette()?, - ))), - IsSelected(ref x) => Some(Command::WebDriver(MarionetteWebDriverCommand::IsSelected( - x.to_marionette()?, - ))), + IsDisplayed(ref e) => Some(Command::WebDriver( + MarionetteWebDriverCommand::IsDisplayed { + id: e.clone().to_string(), + } + )), + IsEnabled(ref e) => Some(Command::WebDriver( + MarionetteWebDriverCommand::IsEnabled { + id: e.clone().to_string(), + } + )), + IsSelected(ref e) => Some(Command::WebDriver( + MarionetteWebDriverCommand::IsSelected { + id: e.clone().to_string(), + }, + )), MaximizeWindow => Some(Command::WebDriver( MarionetteWebDriverCommand::MaximizeWindow, )), @@ -1273,7 +1289,7 @@ impl MarionetteConnection { } fn send(&mut self, data: String) -> WebDriverResult { - if self.stream.write(&*data.as_bytes()).is_err() { + if self.stream.write(data.as_bytes()).is_err() { let mut err = WebDriverError::new( ErrorStatus::UnknownError, "Failed to write request to stream", @@ -1354,7 +1370,7 @@ impl ToMarionette> for AddonInstallParameters { if self.temporary.is_some() { data.insert( "temporary".to_string(), - serde_json::to_value(&self.temporary)?, + serde_json::to_value(self.temporary)?, ); } Ok(data) @@ -1559,14 +1575,6 @@ impl ToMarionette for TimeoutsParameters { } } -impl ToMarionette for WebElement { - fn to_marionette(&self) -> WebDriverResult { - Ok(LegacyWebElement { - id: self.to_string(), - }) - } -} - impl ToMarionette for WebElement { fn to_marionette(&self) -> WebDriverResult { Ok(MarionetteWebElement { diff --git a/src/prefs.rs b/src/prefs.rs index b9b1785..d3c874c 100644 --- a/src/prefs.rs +++ b/src/prefs.rs @@ -6,11 +6,8 @@ use mozprofile::preferences::Pref; // ALL CHANGES TO THIS FILE MUST HAVE REVIEW FROM A GECKODRIVER PEER! // -// All preferences in this file are not immediately effective, and -// require a restart of Firefox, or have to be set in the profile before -// Firefox gets started the first time. If a preference has to be added, -// which is immediately effective, it needs to be done in Marionette -// (marionette.js). +// Please refer to INSTRUCTIONS TO ADD A NEW PREFERENCE in +// remote/shared/RecommendedPreferences.sys.mjs // // Note: geckodriver is used out-of-tree with various builds of Firefox. // Removing a preference from this file will cause regressions,