From f5ad729f8109586f825f2062b81d736f6067109b Mon Sep 17 00:00:00 2001 From: Ronald Holshausen Date: Tue, 7 May 2024 17:36:26 +1000 Subject: [PATCH] chore: Moved mock server crates to pact-foundation/pact-core-mock-server --- rust/Cargo.lock | 273 +++---- rust/Cargo.toml | 2 + rust/README.md | 15 +- rust/pact_consumer/Cargo.toml | 2 +- rust/pact_ffi/Cargo.toml | 2 +- rust/pact_mock_server/CHANGELOG.md | 715 ------------------ rust/pact_mock_server/Cargo.toml | 55 -- rust/pact_mock_server/README.md | 47 +- rust/pact_mock_server/release.groovy | 113 --- rust/pact_mock_server/src/hyper_server.rs | 523 ------------- rust/pact_mock_server/src/lib.rs | 499 ------------ rust/pact_mock_server/src/matching.rs | 147 ---- rust/pact_mock_server/src/mock_server.rs | 408 ---------- rust/pact_mock_server/src/server_manager.rs | 449 ----------- rust/pact_mock_server/src/tests.rs | 295 -------- rust/pact_mock_server/src/tls.rs | 185 ----- rust/pact_mock_server/src/utils.rs | 11 - rust/pact_mock_server_cli/.dockerignore | 1 - rust/pact_mock_server_cli/CHANGELOG.md | 470 ------------ rust/pact_mock_server_cli/Cargo.toml | 55 -- rust/pact_mock_server_cli/Dockerfile | 22 - rust/pact_mock_server_cli/README.md | 490 +----------- rust/pact_mock_server_cli/release-docker.sh | 29 - rust/pact_mock_server_cli/release-linux.sh | 43 -- rust/pact_mock_server_cli/release-macos.sh | 48 -- rust/pact_mock_server_cli/release-win.sh | 40 - rust/pact_mock_server_cli/release.groovy | 113 --- rust/pact_mock_server_cli/src/create_mock.rs | 78 -- rust/pact_mock_server_cli/src/list.rs | 68 -- rust/pact_mock_server_cli/src/main.rs | 353 --------- .../pact_mock_server_cli/src/self-signed.cert | 29 - rust/pact_mock_server_cli/src/self-signed.key | 52 -- rust/pact_mock_server_cli/src/server.rs | 408 ---------- rust/pact_mock_server_cli/src/shutdown.rs | 65 -- rust/pact_mock_server_cli/src/verify.rs | 129 ---- rust/pact_mock_server_cli/tests/cli-tests.rs | 8 - .../tests/cmd/create.stderr | 0 .../tests/cmd/create.stdout | 16 - .../tests/cmd/create.toml | 2 - .../tests/cmd/list.stderr | 0 .../tests/cmd/list.stdout | 13 - rust/pact_mock_server_cli/tests/cmd/list.toml | 2 - .../tests/cmd/main.stderr | 0 .../tests/cmd/main.stdout | 22 - rust/pact_mock_server_cli/tests/cmd/main.toml | 3 - .../tests/cmd/shutdown.stderr | 0 .../tests/cmd/shutdown.stdout | 24 - .../tests/cmd/shutdown.toml | 2 - .../tests/cmd/start.stderr | 0 .../tests/cmd/start.stdout | 16 - .../pact_mock_server_cli/tests/cmd/start.toml | 2 - .../tests/cmd/verify.stderr | 0 .../tests/cmd/verify.stdout | 24 - .../tests/cmd/verify.toml | 2 - 54 files changed, 117 insertions(+), 6253 deletions(-) delete mode 100644 rust/pact_mock_server/CHANGELOG.md delete mode 100644 rust/pact_mock_server/Cargo.toml delete mode 100755 rust/pact_mock_server/release.groovy delete mode 100644 rust/pact_mock_server/src/hyper_server.rs delete mode 100644 rust/pact_mock_server/src/lib.rs delete mode 100644 rust/pact_mock_server/src/matching.rs delete mode 100644 rust/pact_mock_server/src/mock_server.rs delete mode 100644 rust/pact_mock_server/src/server_manager.rs delete mode 100644 rust/pact_mock_server/src/tests.rs delete mode 100644 rust/pact_mock_server/src/tls.rs delete mode 100644 rust/pact_mock_server/src/utils.rs delete mode 100644 rust/pact_mock_server_cli/.dockerignore delete mode 100644 rust/pact_mock_server_cli/CHANGELOG.md delete mode 100644 rust/pact_mock_server_cli/Cargo.toml delete mode 100644 rust/pact_mock_server_cli/Dockerfile delete mode 100755 rust/pact_mock_server_cli/release-docker.sh delete mode 100755 rust/pact_mock_server_cli/release-linux.sh delete mode 100755 rust/pact_mock_server_cli/release-macos.sh delete mode 100644 rust/pact_mock_server_cli/release-win.sh delete mode 100755 rust/pact_mock_server_cli/release.groovy delete mode 100644 rust/pact_mock_server_cli/src/create_mock.rs delete mode 100644 rust/pact_mock_server_cli/src/list.rs delete mode 100644 rust/pact_mock_server_cli/src/main.rs delete mode 100644 rust/pact_mock_server_cli/src/self-signed.cert delete mode 100644 rust/pact_mock_server_cli/src/self-signed.key delete mode 100644 rust/pact_mock_server_cli/src/server.rs delete mode 100644 rust/pact_mock_server_cli/src/shutdown.rs delete mode 100644 rust/pact_mock_server_cli/src/verify.rs delete mode 100644 rust/pact_mock_server_cli/tests/cli-tests.rs delete mode 100644 rust/pact_mock_server_cli/tests/cmd/create.stderr delete mode 100644 rust/pact_mock_server_cli/tests/cmd/create.stdout delete mode 100644 rust/pact_mock_server_cli/tests/cmd/create.toml delete mode 100644 rust/pact_mock_server_cli/tests/cmd/list.stderr delete mode 100644 rust/pact_mock_server_cli/tests/cmd/list.stdout delete mode 100644 rust/pact_mock_server_cli/tests/cmd/list.toml delete mode 100644 rust/pact_mock_server_cli/tests/cmd/main.stderr delete mode 100644 rust/pact_mock_server_cli/tests/cmd/main.stdout delete mode 100644 rust/pact_mock_server_cli/tests/cmd/main.toml delete mode 100644 rust/pact_mock_server_cli/tests/cmd/shutdown.stderr delete mode 100644 rust/pact_mock_server_cli/tests/cmd/shutdown.stdout delete mode 100644 rust/pact_mock_server_cli/tests/cmd/shutdown.toml delete mode 100644 rust/pact_mock_server_cli/tests/cmd/start.stderr delete mode 100644 rust/pact_mock_server_cli/tests/cmd/start.stdout delete mode 100644 rust/pact_mock_server_cli/tests/cmd/start.toml delete mode 100644 rust/pact_mock_server_cli/tests/cmd/verify.stderr delete mode 100644 rust/pact_mock_server_cli/tests/cmd/verify.stdout delete mode 100644 rust/pact_mock_server_cli/tests/cmd/verify.toml diff --git a/rust/Cargo.lock b/rust/Cargo.lock index ec40267b5..220f3c906 100644 --- a/rust/Cargo.lock +++ b/rust/Cargo.lock @@ -156,9 +156,9 @@ version = "0.3.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "16e62a023e7c117e27523144c5d2459f4397fcc3cab0085af8e2224f643a0193" dependencies = [ - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", - "syn 2.0.60", + "syn 2.0.61", ] [[package]] @@ -167,9 +167,9 @@ version = "0.1.80" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c6fa2087f2753a7da8cc1c0dbfcf89579dd57458e36769de5ac750b4671737ca" dependencies = [ - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", - "syn 2.0.60", + "syn 2.0.61", ] [[package]] @@ -532,15 +532,6 @@ dependencies = [ "cfg-if", ] -[[package]] -name = "crossbeam-channel" -version = "0.5.12" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ab3db02a9c5b5121e1e42fbdb1aeb65f5e02624cc58c43f2884c6ccac0b82f95" -dependencies = [ - "crossbeam-utils", -] - [[package]] name = "crossbeam-deque" version = "0.8.5" @@ -594,10 +585,10 @@ checksum = "9c2cf1c23a687a1feeb728783b993c4e1ad83d99f351801977dd809b48d0a70f" dependencies = [ "fnv", "ident_case", - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", "strsim 0.10.0", - "syn 2.0.60", + "syn 2.0.61", ] [[package]] @@ -608,7 +599,7 @@ checksum = "a668eda54683121533a393014d8692171709ff57a7d61f187b6e782719f8933f" dependencies = [ "darling_core", "quote 1.0.36", - "syn 2.0.60", + "syn 2.0.61", ] [[package]] @@ -627,7 +618,7 @@ version = "0.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7a2c35ab6e03642397cdda1dd58abbc05d418aef8e36297f336d5aba060fe8df" dependencies = [ - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", "syn 1.0.109", ] @@ -866,9 +857,9 @@ version = "0.3.30" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "87750cf4b7a4c0625b1529e4c543c2182106e4dedc60a2a6455e00d212c489ac" dependencies = [ - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", - "syn 2.0.60", + "syn 2.0.61", ] [[package]] @@ -1500,10 +1491,10 @@ checksum = "dc487311295e0002e452025d6b580b77bb17286de87b57138f3b5db711cded68" dependencies = [ "beef", "fnv", - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", "regex-syntax 0.6.29", - "syn 2.0.60", + "syn 2.0.61", ] [[package]] @@ -1669,7 +1660,7 @@ version = "0.9.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "197eff6c12b80ff5de6173e438fa3c1340a9e708118c1626e690f65aee1e5332" dependencies = [ - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", "syn 1.0.109", ] @@ -1681,7 +1672,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ef492b5cf80f90c050b287e747228a1fa6517e9d754f364b5a7e0e038e49a25f" dependencies = [ "proc-macro-crate", - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", "syn 1.0.109", ] @@ -1788,15 +1779,6 @@ dependencies = [ "libc", ] -[[package]] -name = "num_threads" -version = "0.1.7" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5c7398b9c8b70908f6371f47ed36737907c87c52af34c268fed0bf0ceb92ead9" -dependencies = [ - "libc", -] - [[package]] name = "number_prefix" version = "0.4.0" @@ -1927,7 +1909,7 @@ dependencies = [ "lazy_static", "maplit", "pact-plugin-driver", - "pact_matching", + "pact_matching 1.2.3", "pact_mock_server", "pact_models 1.2.0", "pretty_assertions", @@ -1971,7 +1953,7 @@ dependencies = [ "onig", "os_info", "pact-plugin-driver", - "pact_matching", + "pact_matching 1.2.3", "pact_mock_server", "pact_models 1.2.0", "pact_verifier", @@ -2002,7 +1984,9 @@ dependencies = [ [[package]] name = "pact_matching" -version = "1.2.3" +version = "1.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9183bf02dfc92afae178174c5c2bf64787e7fdb98081742ca6f2318f3e7af5a5" dependencies = [ "ansi_term", "anyhow", @@ -2010,10 +1994,7 @@ dependencies = [ "bytes", "chrono", "difference", - "env_logger 0.11.3", - "expectest", "futures", - "hamcrest2", "hex", "http 1.1.0", "itertools 0.12.1", @@ -2024,97 +2005,98 @@ dependencies = [ "mime", "multer", "nom", - "ntest", "onig", "pact-plugin-driver", "pact_models 1.2.0", - "pretty_assertions", - "quickcheck", "rand", "reqwest 0.12.4", - "rstest 0.19.0", "semver", "serde", "serde_json", "serde_urlencoded", "sxd-document", - "test-log", "tokio", "tracing", "tracing-core", - "tracing-subscriber", "tree_magic_mini", "uuid", ] [[package]] -name = "pact_mock_server" -version = "1.2.7" +name = "pact_matching" +version = "1.2.3" dependencies = [ + "ansi_term", "anyhow", + "base64 0.22.1", "bytes", + "chrono", + "difference", "env_logger 0.11.3", "expectest", "futures", - "hyper 0.14.28", - "hyper-rustls 0.24.2", + "hamcrest2", + "hex", + "http 1.1.0", "itertools 0.12.1", "lazy_static", + "lenient_semver", "maplit", + "md5", + "mime", + "multer", + "nom", + "ntest", + "onig", "pact-plugin-driver", - "pact_matching", "pact_models 1.2.0", + "pretty_assertions", "quickcheck", + "rand", "reqwest 0.12.4", - "rustls 0.21.12", - "rustls-pemfile 1.0.4", + "rstest 0.19.0", + "semver", "serde", "serde_json", - "test-env-log", + "serde_urlencoded", + "sxd-document", "test-log", - "thiserror", "tokio", - "tokio-rustls 0.24.1", "tracing", "tracing-core", "tracing-subscriber", - "url", + "tree_magic_mini", "uuid", ] [[package]] -name = "pact_mock_server_cli" -version = "1.0.6" +name = "pact_mock_server" +version = "1.2.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fb43567a0954ecba3b91d70543617923d9217a98ea3f5f0a5149648b46f0aa55" dependencies = [ "anyhow", - "clap 4.4.18", - "env_logger 0.11.3", - "expectest", + "bytes", "futures", - "http 0.2.12", "hyper 0.14.28", + "hyper-rustls 0.24.2", "itertools 0.12.1", "lazy_static", - "log", "maplit", - "pact_matching", - "pact_mock_server", + "pact-plugin-driver", + "pact_matching 1.2.2", "pact_models 1.2.0", - "quickcheck", - "rand", - "regex", - "reqwest 0.11.27", + "rustls 0.21.12", + "rustls-pemfile 1.0.4", + "serde", "serde_json", - "test-log", + "thiserror", "tokio", + "tokio-rustls 0.24.1", "tracing", - "tracing-appender", "tracing-core", - "tracing-subscriber", - "trycmd", "url", "uuid", - "webmachine-rust", ] [[package]] @@ -2225,7 +2207,7 @@ dependencies = [ "mime", "pact-plugin-driver", "pact_consumer", - "pact_matching", + "pact_matching 1.2.3", "pact_models 1.2.0", "pretty_assertions", "quickcheck", @@ -2406,9 +2388,9 @@ version = "1.1.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2f38a4412a78282e09a2cf38d195ea5420d15ba0602cb375210efbc877243965" dependencies = [ - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", - "syn 2.0.60", + "syn 2.0.61", ] [[package]] @@ -2459,12 +2441,12 @@ dependencies = [ [[package]] name = "prettyplease" -version = "0.2.19" +version = "0.2.20" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5ac2cf0f2e4f42b49f5ffd07dae8d746508ef7526c13940e5f524012ae6c6550" +checksum = "5f12335488a2f3b0a83b14edad48dca9879ce89b2edd10e80237e4e852dd645e" dependencies = [ - "proc-macro2 1.0.81", - "syn 2.0.60", + "proc-macro2 1.0.82", + "syn 2.0.61", ] [[package]] @@ -2487,9 +2469,9 @@ dependencies = [ [[package]] name = "proc-macro2" -version = "1.0.81" +version = "1.0.82" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3d1597b0c024618f09a9c3b8655b7e430397a36d23fdafec26d6965e9eec3eba" +checksum = "8ad3d49ab951a01fbaafe34f2ec74122942fe18a3f9814c3268f1bb72042131b" dependencies = [ "unicode-ident", ] @@ -2521,7 +2503,7 @@ dependencies = [ "prost", "prost-types", "regex", - "syn 2.0.60", + "syn 2.0.61", "tempfile", ] @@ -2533,9 +2515,9 @@ checksum = "19de2de2a00075bf566bee3bd4db014b11587e84184d3f7a791bc17f1a8e9e48" dependencies = [ "anyhow", "itertools 0.12.1", - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", - "syn 2.0.60", + "syn 2.0.61", ] [[package]] @@ -2582,7 +2564,7 @@ version = "1.0.36" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0fa76aaf39101c457836aec0ce2316dbdc3ab723cdda1c6bd4e6ad4208acaca7" dependencies = [ - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", ] [[package]] @@ -2846,12 +2828,12 @@ checksum = "d428f8247852f894ee1be110b375111b586d4fa431f6c46e64ba5a0dcccbe605" dependencies = [ "cfg-if", "glob", - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", "regex", "relative-path", "rustc_version", - "syn 2.0.60", + "syn 2.0.61", "unicode-ident", ] @@ -2863,12 +2845,12 @@ checksum = "04a9df72cc1f67020b0d63ad9bfe4a323e459ea7eb68e03bd9824db49f9a4c25" dependencies = [ "cfg-if", "glob", - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", "regex", "relative-path", "rustc_version", - "syn 2.0.60", + "syn 2.0.61", "unicode-ident", ] @@ -2999,15 +2981,15 @@ dependencies = [ [[package]] name = "rustversion" -version = "1.0.15" +version = "1.0.16" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "80af6f9131f277a45a3fba6ce8e2258037bb0477a67e610d3c1fe046ab31de47" +checksum = "092474d1a01ea8278f69e6a358998405fae5b8b963ddaeb2b0b04a128bf1dfb0" [[package]] name = "ryu" -version = "1.0.17" +version = "1.0.18" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e86697c916019a8588c99b5fac3cead74ec0b4b819707a682fd4d23fa0ce1ba1" +checksum = "f3cb5ba0dc43242ce17de99c180e96db90b235b8a9fdc9543c96d2209116bd9f" [[package]] name = "same-file" @@ -3068,9 +3050,9 @@ dependencies = [ [[package]] name = "semver" -version = "1.0.22" +version = "1.0.23" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "92d43fe69e652f3df9bdc2b85b2854a0825b86e4fb76bc44d945137d053639ca" +checksum = "61697e0a1c7e512e84a621326239844a24d8207b4669b41bc18b32ea5cbf988b" [[package]] name = "serde" @@ -3087,9 +3069,9 @@ version = "1.0.200" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "856f046b9400cee3c8c94ed572ecdb752444c24528c035cd35882aad6f492bcb" dependencies = [ - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", - "syn 2.0.60", + "syn 2.0.61", ] [[package]] @@ -3149,9 +3131,9 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "65569b702f41443e8bc8bbb1c5779bd0450bbe723b56198980e80ec45780bce2" dependencies = [ "darling", - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", - "syn 2.0.60", + "syn 2.0.61", ] [[package]] @@ -3340,18 +3322,18 @@ version = "1.0.109" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "72b64191b275b66ffe2469e8af2c1cfe3bafa67b529ead792a6d0160888b4237" dependencies = [ - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", "unicode-ident", ] [[package]] name = "syn" -version = "2.0.60" +version = "2.0.61" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "909518bc7b1c9b779f1bbf07f2929d35af9f0f37e47c6e9ef7f9dddc1e1821f3" +checksum = "c993ed8ccba56ae856363b1845da7266a7cb78e1d146c8a32d54b45a8b831fc9" dependencies = [ - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", "unicode-ident", ] @@ -3430,17 +3412,6 @@ dependencies = [ "winapi-util", ] -[[package]] -name = "test-env-log" -version = "0.2.8" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "877189d680101869f65ef94168105d6c188b3a143c13a2d42cf8a09c4c704f8a" -dependencies = [ - "proc-macro2 1.0.81", - "quote 1.0.36", - "syn 1.0.109", -] - [[package]] name = "test-log" version = "0.2.16" @@ -3458,9 +3429,9 @@ version = "0.2.16" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5999e24eaa32083191ba4e425deb75cdf25efefabe5aaccb7446dd0d4122a3f5" dependencies = [ - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", - "syn 2.0.60", + "syn 2.0.61", ] [[package]] @@ -3474,22 +3445,22 @@ dependencies = [ [[package]] name = "thiserror" -version = "1.0.59" +version = "1.0.60" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f0126ad08bff79f29fc3ae6a55cc72352056dfff61e3ff8bb7129476d44b23aa" +checksum = "579e9083ca58dd9dcf91a9923bb9054071b9ebbd800b342194c9feb0ee89fc18" dependencies = [ "thiserror-impl", ] [[package]] name = "thiserror-impl" -version = "1.0.59" +version = "1.0.60" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d1cd413b5d558b4c5bf3680e324a6fa5014e7b7c067a51e69dbdf47eb7148b66" +checksum = "e2470041c06ec3ac1ab38d0356a6119054dedaea53e12fbefc0de730a1c08524" dependencies = [ - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", - "syn 2.0.60", + "syn 2.0.61", ] [[package]] @@ -3510,9 +3481,7 @@ checksum = "5dfd88e563464686c916c7e46e623e520ddc6d79fa6641390f2e3fa86e83e885" dependencies = [ "deranged", "itoa", - "libc", "num-conv", - "num_threads", "powerfmt", "serde", "time-core", @@ -3585,9 +3554,9 @@ version = "2.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5b8a1e28f2deaa14e508979454cb3a223b10b938b45af148bc0986de36f1923b" dependencies = [ - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", - "syn 2.0.60", + "syn 2.0.61", ] [[package]] @@ -3727,10 +3696,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "be4ef6dd70a610078cb4e338a0f79d06bc759ff1b22d2120c2ff02ae264ba9c2" dependencies = [ "prettyplease", - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "prost-build", "quote 1.0.36", - "syn 2.0.60", + "syn 2.0.61", ] [[package]] @@ -3777,27 +3746,15 @@ dependencies = [ "tracing-core", ] -[[package]] -name = "tracing-appender" -version = "0.2.3" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3566e8ce28cc0a3fe42519fc80e6b4c943cc4c8cef275620eb8dac2d3d4e06cf" -dependencies = [ - "crossbeam-channel", - "thiserror", - "time", - "tracing-subscriber", -] - [[package]] name = "tracing-attributes" version = "0.1.27" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "34704c8d6ebcbc939824180af020566b01a7c01f80641264eba0999f6c2b6be7" dependencies = [ - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", - "syn 2.0.60", + "syn 2.0.61", ] [[package]] @@ -3834,7 +3791,6 @@ dependencies = [ "sharded-slab", "smallvec", "thread_local", - "time", "tracing", "tracing-core", "tracing-log", @@ -4008,7 +3964,7 @@ version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d257817081c7dffcdbab24b9e62d2def62e2ff7d00b1c20062551e6cccc145ff" dependencies = [ - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", ] @@ -4065,9 +4021,9 @@ dependencies = [ "bumpalo", "log", "once_cell", - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", - "syn 2.0.60", + "syn 2.0.61", "wasm-bindgen-shared", ] @@ -4099,9 +4055,9 @@ version = "0.2.92" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e94f17b526d0a461a191c78ea52bbce64071ed5c04c9ffe424dcb38f74171bb7" dependencies = [ - "proc-macro2 1.0.81", + "proc-macro2 1.0.82", "quote 1.0.36", - "syn 2.0.60", + "syn 2.0.61", "wasm-bindgen-backend", "wasm-bindgen-shared", ] @@ -4135,25 +4091,6 @@ dependencies = [ "wasm-bindgen", ] -[[package]] -name = "webmachine-rust" -version = "0.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "38bc755d931618136f84cef66f29eb5658b96af8289bcf60f96db8acb41f01dd" -dependencies = [ - "chrono", - "futures", - "hex", - "http 0.2.12", - "hyper 0.14.28", - "itertools 0.10.5", - "lazy_static", - "maplit", - "serde", - "serde_json", - "tracing", -] - [[package]] name = "winapi" version = "0.3.9" diff --git a/rust/Cargo.toml b/rust/Cargo.toml index 8025d6c49..6b307a417 100644 --- a/rust/Cargo.toml +++ b/rust/Cargo.toml @@ -3,6 +3,8 @@ members = [ "pact_*" ] exclude = [ + "pact_mock_server", + "pact_mock_server_cli", "pact_wasm", "pact_cli" ] diff --git a/rust/README.md b/rust/README.md index 4da218c5a..6e6a2b7f8 100644 --- a/rust/README.md +++ b/rust/README.md @@ -10,6 +10,8 @@ This project provides a Pact implementation written in Rust. It supports the [V3 and [V4 Pact specification](https://github.com/pact-foundation/pact-specification/tree/version-4) and provides shared libraries that can be used in other languages via foreign function interfaces (FFI). +Note: The mock server crates have moved to https://github.com/pact-foundation/pact-core-mock-server. + ## Installing / Getting started ### Rust Projects @@ -56,16 +58,13 @@ This is a library that provides the Pact functions for matching requests and res This is a library that implements exported functions using C bindings for use in foreign languages. -### [pact_mock_server](./pact_mock_server) +### [pact_mock_server](https://github.com/pact-foundation/pact-core-mock-server/pact_mock_server) -This is a library that provides an in-process mock server for Pact client tests. It uses the [pact_matching](./pact_matching) -library. +Moved to https://github.com/pact-foundation/pact-core-mock-server. -### [pact_mock_server_cli](./pact_mock_server_cli) +### [pact_mock_server_cli](https://github.com/pact-foundation/pact-core-mock-server/pact_mock_server_cli) -This module provides a command line executable that provides a standalone pact mock server and commands for controlling -the mock servers. It uses the [libpact_mock_server](./pact_mock_server) and [libpact_matching](./pact_matching) -libraries. +Moved to https://github.com/pact-foundation/pact-core-mock-server. ### [pact_consumer](./pact_consumer) @@ -111,8 +110,6 @@ Rust crate documentation is published to the Rust documentation site. * [pact_consumer](https://docs.rs/pact_consumer/) * [pact_matching](https://docs.rs/pact_matching/) * [pact_ffi](https://docs.rs/pact_ffi/) -* [pact_mock_server](https://docs.rs/pact_mock_server/) -* [pact_mock_server_cli](https://docs.rs/pact_mock_server_cli/) * [pact_models](https://docs.rs/pact_models/) * [pact_verifier](https://docs.rs/pact_verifier/) * [pact_verifier_cli](https://docs.rs/pact_verifier_cli/) diff --git a/rust/pact_consumer/Cargo.toml b/rust/pact_consumer/Cargo.toml index 705b63840..ef416ce5d 100644 --- a/rust/pact_consumer/Cargo.toml +++ b/rust/pact_consumer/Cargo.toml @@ -30,7 +30,7 @@ itertools = "0.12.1" lazy_static = "1.4.0" maplit = "1.0.2" pact_matching = { version = "~1.2.2", path = "../pact_matching", default-features = false } -pact_mock_server = { version = "~1.2.6", path = "../pact_mock_server", default-features = false } +pact_mock_server = { version = "~1.2.6", default-features = false } pact_models = { version = "~1.2.0", default-features = false } pact-plugin-driver = { version = "~0.6.1", optional = true, default-features = false } regex = "1.10.4" diff --git a/rust/pact_ffi/Cargo.toml b/rust/pact_ffi/Cargo.toml index ee256cab0..d88bbb918 100644 --- a/rust/pact_ffi/Cargo.toml +++ b/rust/pact_ffi/Cargo.toml @@ -31,7 +31,7 @@ maplit = "1.0.2" multipart = { version = "0.18.0", default-features = false, features = ["client", "mock"] } onig = { version = "6.4.0", default-features = false } pact_matching = { version = "~1.2.2", path = "../pact_matching" } -pact_mock_server = { version = "~1.2.6", path = "../pact_mock_server" } +pact_mock_server = { version = "~1.2.6" } pact_models = { version = "~1.2.0" } pact-plugin-driver = { version = "~0.6.1" } pact_verifier = { version = "~1.2.0", path = "../pact_verifier" } diff --git a/rust/pact_mock_server/CHANGELOG.md b/rust/pact_mock_server/CHANGELOG.md deleted file mode 100644 index 4bba284c6..000000000 --- a/rust/pact_mock_server/CHANGELOG.md +++ /dev/null @@ -1,715 +0,0 @@ -To generate the log, run `git log --pretty='* %h - %s (%an, %ad)' TAGNAME..HEAD .` replacing TAGNAME and HEAD as appropriate. - -# 1.2.6 - Maintenance Release - -* 30e994fd - chore(pact_mock_server): Upgrade pact-plugin-driver to 0.6.0 (Ronald Holshausen, Tue Apr 16 15:03:40 2024 +1000) -* a945a380 - chore(pact_mock_server): Upgrade dependencies (Ronald Holshausen, Tue Apr 16 15:00:03 2024 +1000) -* d6125b75 - chore(pact_matching): Bump minor version (Ronald Holshausen, Tue Apr 16 10:16:44 2024 +1000) -* 23a9a60d - bump version to 1.2.6 (Ronald Holshausen, Fri Mar 15 15:07:14 2024 +1100) - -# 1.2.5 - Maintenance Release - -* 9311d1be - chore(pact_mock_server): Update dependencies (Ronald Holshausen, Fri Mar 15 14:34:13 2024 +1100) -* a52e0ee9 - chore: Upgrade pact_matching to 1.1.10 (Ronald Holshausen, Wed Feb 7 13:20:45 2024 +1100) -* 24a26cca - chore: Update pact_models to 1.1.18 (Ronald Holshausen, Wed Feb 7 10:53:22 2024 +1100) -* 73578350 - chore: use local pact_models (JP-Ellis, Tue Feb 6 10:51:09 2024 +1100) -* 95cbe5a9 - fix: Upgrade pact-plugin-driver to 0.5.1 (Ronald Holshausen, Wed Jan 31 19:56:04 2024 +1100) -* 4325dcab - chore(pact_mock_server): Upgrade dependencies (Ronald Holshausen, Sat Jan 20 18:57:03 2024 +1100) -* ca4256fe - bump version to 1.2.5 (Ronald Holshausen, Sat Jan 20 18:34:05 2024 +1100) - -# 1.2.4 - Maintenance Release - -* e552bdce - chore: Upgrade pact_matching to 1.1.9 (Ronald Holshausen, Sat Jan 20 15:13:13 2024 +1100) -* 7b087acf - chore: Upgrade pact-plugin-driver to 0.5.0 (Ronald Holshausen, Sat Jan 20 14:49:21 2024 +1100) -* b735df9d - chore: Upgrade pact_models to 1.1.17 (Ronald Holshausen, Sat Jan 20 13:54:03 2024 +1100) -* 1a4bcd27 - chore: Upgrade pact_matching to 1.1.8 (Ronald Holshausen, Fri Jan 19 18:24:54 2024 +1100) -* 944613df - fix: regression - upgrade pact_models to 1.1.16 #359 (Ronald Holshausen, Fri Jan 19 14:52:36 2024 +1100) -* 403c0af1 - chore: Upgrade pact_models to 1.1.14 #355 (Ronald Holshausen, Tue Jan 16 10:31:12 2024 +1100) -* dfd13760 - chore: Upgrade pact_models to 1.1.13 #355 (Ronald Holshausen, Tue Jan 16 07:42:33 2024 +1100) -* 713e4098 - chore: Upgrade pact-plugin-driver to 0.4.6 (Ronald Holshausen, Thu Dec 14 17:04:59 2023 +1100) -* 3f0ae7f1 - chore: Upgrade pact_matching to 1.1.7 (Ronald Holshausen, Tue Nov 14 03:10:25 2023 +1100) -* 826758a6 - chore: Upgrade pact_models to 1.1.12 (Ronald Holshausen, Mon Nov 13 17:25:21 2023 +1100) -* 04bad264 - chore: Upgrade pact_matching to 1.1.6 (Ronald Holshausen, Fri Sep 22 11:03:38 2023 +1000) -* 43fe7b61 - bump version to 1.2.4 (Ronald Holshausen, Tue Aug 29 09:19:03 2023 +1000) - -# 1.2.3 - Maintenance Release - -* 3ec99c41 - chore: Upgrade pact_matching to 1.1.5 (Ronald Holshausen, Fri Aug 18 15:40:02 2023 +1000) -* e4da3e42 - chore: Upgrade pact_models to 1.1.11 (Ronald Holshausen, Mon Aug 7 13:59:34 2023 +1000) -* 24ed7835 - chore: Upgrade pact-models to 1.1.10 (Ronald Holshausen, Fri Aug 4 16:11:24 2023 +1000) -* 9f059907 - bump version to 1.2.3 (Ronald Holshausen, Thu Jul 27 14:41:03 2023 +1000) - -# 1.2.2 - Bugfix Release - -* 8f88192e - chore: Upgrade pact_matching to 1.1.4 (Ronald Holshausen, Thu Jul 27 14:35:27 2023 +1000) -* 4a01919a - chore: Upgrade pact_models to 1.1.9 (Ronald Holshausen, Thu Jul 27 10:24:00 2023 +1000) -* c2aad1ac - chore: Add support for datetime, xml, multipart and plugins crate features (Ronald Holshausen, Wed Jul 12 11:15:37 2023 +1000) -* 80b3aba8 - bump version to 1.2.2 (Ronald Holshausen, Tue Jul 11 14:41:05 2023 +1000) - -# 1.2.1 - Bugfix Release - -* 3cd0417c - chore: Add crate features to readme and module docs (Ronald Holshausen, Tue Jul 11 14:24:40 2023 +1000) -* 0f40fdd8 - chore: Add a crate feature to enable TLS support (Ronald Holshausen, Tue Jul 11 14:19:27 2023 +1000) -* 4f8a55cf - chore: Add support for datetime, xml, multipart and plugins crate features (Ronald Holshausen, Tue Jul 11 12:19:13 2023 +1000) -* 348eb3f3 - chore: Upgrade pact_matcing to 1.1.3 (Ronald Holshausen, Tue Jul 11 11:38:26 2023 +1000) -* f2ae77ba - chore: Upgrade pact-plugin-driver to 0.4.5 (Ronald Holshausen, Mon Jul 10 17:15:20 2023 +1000) -* b18b9dff - chore: Upgrade pact_matching to 1.1.2 (Ronald Holshausen, Mon Jul 10 16:42:27 2023 +1000) -* 1deca59a - chore: Upgrade pact_models to 1.1.8 (Ronald Holshausen, Mon Jul 10 16:15:43 2023 +1000) -* 2662cdfc - chore: Upgrade pact_models to 1.1.7 (Ronald Holshausen, Thu Jul 6 10:27:25 2023 +1000) -* 445ea1ee - fix: Header matching rules should be looked up in a case-insenstive way (Ronald Holshausen, Wed Jun 28 15:21:32 2023 +1000) -* e95ae4d0 - chore: Upgrade pact_models to 1.1.6 (Ronald Holshausen, Thu Jun 22 15:40:55 2023 +1000) -* 244f1fdb - feat(compatibility-suite): Implemented scenarios for no provider state callback configured + request filters (Ronald Holshausen, Fri Jun 16 11:36:30 2023 +1000) -* 8771ba5c - bump version to 1.2.1 (Ronald Holshausen, Wed Jun 14 15:53:22 2023 +1000) - -# 1.2.0 - Fixes a deadlock with mock server JSON results - -* 834f77cc - chore: Upgrade pact_mock_server to 1.2.0 (Ronald Holshausen, Wed Jun 14 15:22:11 2023 +1000) -* e58aa917 - fix: no need to wrap the Pact for a mock server in a mutex (mock server is already behind a mutex) as this can cause deadlocks #274 (Ronald Holshausen, Wed Jun 14 13:26:54 2023 +1000) -* bc68ed7f - chore: Upgrade pact_models to 1.1.4 (Ronald Holshausen, Thu Jun 1 10:22:38 2023 +1000) -* 317f85b1 - feat(mockserver): Make request received and response returned more explicit in the logs (Ronald Holshausen, Tue May 30 11:50:16 2023 +1000) -* 37673fac - fix: correct tests after upgrading pact_models (Ronald Holshausen, Mon May 29 15:13:44 2023 +1000) -* 397c837f - chore: Upgrade pact_models to 1.1.3 (fixes MockServerURL generator) (Ronald Holshausen, Mon May 29 15:12:22 2023 +1000) -* 8156751f - bump version to 1.1.1 (Ronald Holshausen, Tue May 23 14:01:55 2023 +1000) - -# 1.1.0 - Update Pact models to 1.1 (breaking change) - -* 56103f6c - Revert "update changelog for release 1.1.0" (Ronald Holshausen, Tue May 23 13:58:03 2023 +1000) -* e3b5793f - chore: correct dependencies (Ronald Holshausen, Tue May 23 13:56:26 2023 +1000) -* 94d46cee - update changelog for release 1.1.0 (Ronald Holshausen, Tue May 23 13:54:08 2023 +1000) -* 8e9bd503 - chore: Upgrade pact_mock_server to 1.1.0 (Ronald Holshausen, Tue May 23 12:20:01 2023 +1000) -* 8f27f9bd - chore: Upgrade pact-plugin-driver to 0.4.4 (Ronald Holshausen, Tue May 23 11:55:23 2023 +1000) -* ac2e24da - chore: Use "Minimum version, with restricted compatibility range" for all Pact crate versions (Ronald Holshausen, Tue May 23 11:46:52 2023 +1000) -* 6df4670c - chore: Upgrade pact_matching to 1.1.1 (Ronald Holshausen, Tue May 23 11:32:51 2023 +1000) -* 54887690 - chore: Bump pact_matching to 1.1 (Ronald Holshausen, Tue May 23 11:13:14 2023 +1000) -* 261ecf47 - fix: Add RefUnwindSafe trait bound to all Pact and Interaction uses (Ronald Holshausen, Mon May 15 13:59:31 2023 +1000) -* 6494c2a4 - bump version to 1.0.3 (Ronald Holshausen, Tue Apr 18 13:24:05 2023 +1000) - -# 1.0.2 - Bugfix Release - -* 0bcba082 - chore: Upgrade pact_matching to 1.0.8 (Ronald Holshausen, Tue Apr 18 13:14:38 2023 +1000) -* 6c14abfd - chore: Upgrade pact_models to 1.0.13 (Ronald Holshausen, Tue Apr 18 13:00:01 2023 +1000) -* ce16d43f - chore: Upgrade pact-plugin-driver to 0.4.2 (supports auto-installing known plugins) (Ronald Holshausen, Tue Apr 18 11:49:52 2023 +1000) -* 10bf1a48 - chore: Upgrade pact_models to 1.0.12 (fixes generators hash function) (Ronald Holshausen, Mon Apr 17 10:31:09 2023 +1000) -* 84b9d9e9 - fix: Upgrade pact models to 1.0.11 (fixes generated key for V4 Pacts) (Ronald Holshausen, Fri Apr 14 17:10:58 2023 +1000) -* 669f7812 - chore: Upgrade pact_models to 1.0.10 (Ronald Holshausen, Thu Apr 13 15:32:34 2023 +1000) -* 779a59f0 - fix: Upgrade pact-plugin-driver to 0.4.1 (fixes an issue introduced in 0.4.0 with shared channels to plugins) (Ronald Holshausen, Wed Apr 5 17:01:18 2023 +1000) -* efa2ef69 - bump version to 1.0.2 (Ronald Holshausen, Tue Apr 4 15:33:09 2023 +1000) - -# 1.0.1 - Bugfix Release - -* 3951f0b8 - chore: Update dependencies (Ronald Holshausen, Tue Apr 4 15:18:41 2023 +1000) -* 30dad6d4 - fix: mock servers were shutting plugins down twice when shutting down (Ronald Holshausen, Tue Apr 4 15:15:13 2023 +1000) -* 126cf462 - chore: Upgrade pact_matching to 1.0.7 (Ronald Holshausen, Tue Apr 4 15:12:28 2023 +1000) -* 6f0c4b2f - feat: Upgrade pact-plugin-driver to 0.4.0 which uses a shared gRPC channel to each plugin (Ronald Holshausen, Tue Apr 4 14:32:36 2023 +1000) -* 11c701b4 - fix: Upgrade pact_matching to 1.0.6 (fixes some issues with matching HTTP headers) (Ronald Holshausen, Wed Mar 15 14:54:54 2023 +1100) -* e96bc54e - fix: Upgrade pact_models to 1.0.9 (fixes issues with headers) (Ronald Holshausen, Wed Mar 15 14:31:00 2023 +1100) -* f7e0b669 - chore: Upgrade pact_models to 1.0.8 (Ronald Holshausen, Wed Mar 15 12:19:22 2023 +1100) -* 57728a01 - chore: update pact-plugin-driver to 0.3.3 (Ronald Holshausen, Tue Mar 14 17:19:20 2023 +1100) -* 8c64edec - bump version to 1.0.1 (Ronald Holshausen, Thu Feb 16 14:53:46 2023 +1100) - -# 1.0.0 - Maintenance Release - -* 0676047e - chore: Upgrade pact-plugin-driver to 0.3.2 (Ronald Holshausen, Thu Feb 16 12:09:46 2023 +1100) -* 7589b9b0 - chore: Bump pact_mock_server version to 1.0.0 (Ronald Holshausen, Fri Feb 10 14:43:53 2023 +1100) -* 019bd2fe - chore: Upgrade pact_matching to 1.0.5 (Ronald Holshausen, Wed Feb 8 13:53:15 2023 +1100) -* 1e7331f1 - fix: Upgrade plugin driver to 0.3.1 (Ronald Holshausen, Wed Feb 8 13:28:07 2023 +1100) -* 0f4178e5 - chore: Upgrade pact_matching to 1.0.4 (Ronald Holshausen, Mon Feb 6 15:40:43 2023 +1100) -* 0b70060f - chore: Upgrade pact-plugin-driver and base64 crates (supports message metadata) (Ronald Holshausen, Mon Feb 6 14:56:29 2023 +1100) -* c1b22f1c - chore: Upgrade pact_matching to 1.0.3 (Ronald Holshausen, Wed Jan 11 15:19:29 2023 +1100) -* 7d84d941 - chore: Upgrade pact_models to 1.0.4 (Ronald Holshausen, Wed Jan 11 14:33:13 2023 +1100) -* 1bdb1054 - chore: Upgrade pact_models to 1.0.3 #239 (Ronald Holshausen, Thu Dec 22 15:37:53 2022 +1100) -* 899ff48d - bump version to 0.9.8 (Ronald Holshausen, Mon Dec 19 15:45:50 2022 +1100) - -# 0.9.7 - Support generators in plugins - -* e827f591 - chore: Upgrade pact_matching to 1.0.2 (Ronald Holshausen, Mon Dec 19 15:30:14 2022 +1100) -* 21821045 - chore: Update mock server to start_mock_server_v2 (Ronald Holshausen, Fri Dec 16 16:49:32 2022 +1100) -* 5fbb0d6a - feat: Upgrade plugin driver to 0.2.2 (supports passing a test context to support generators) (Ronald Holshausen, Fri Dec 16 16:38:03 2022 +1100) -* 1ab47c6f - chore: Upgrade Tokio to latest (Ronald Holshausen, Fri Dec 16 16:31:31 2022 +1100) -* fb2f4204 - chore: Upgrade pact_matching to 1.0.1 (Ronald Holshausen, Wed Dec 14 17:03:31 2022 +1100) -* 8be00f0c - chore: Upgrade pact-plugin-driver to 0.2.1 (Ronald Holshausen, Wed Dec 14 14:55:32 2022 +1100) -* ae2bc7f3 - bump version to 0.9.7 (Ronald Holshausen, Mon Dec 12 09:27:54 2022 +1100) - -# 0.9.6 - Support plugins generating interaction content - -* e7a1b9f2 - chore: Upgrade pact_matching to 1.0 and plugin driver to 0.2 (Ronald Holshausen, Fri Dec 9 17:29:33 2022 +1100) -* daef9669 - bump version to 0.9.6 (Ronald Holshausen, Mon Nov 28 14:42:59 2022 +1100) - -# 0.9.5 - Maintenance Release - -* 2802fffd - chore: Upgrade pact_matching to 0.12.15 (Ronald Holshausen, Mon Nov 28 14:29:43 2022 +1100) -* c9721fd5 - chore: Upgrade pact_models to 1.0.1 and pact-plugin-driver to 0.1.16 (Ronald Holshausen, Mon Nov 28 14:10:53 2022 +1100) -* e8e75db1 - chore: correct the pact_mock_server readme #227 (Ronald Holshausen, Thu Nov 10 10:30:58 2022 +1100) -* c953f66e - bump version to 0.9.5 (Ronald Holshausen, Mon Nov 7 11:43:22 2022 +1100) - -# 0.9.4 - Bugfix Release - -* 014d76d1 - chore: Upgrade all dependencies (Ronald Holshausen, Mon Nov 7 11:38:59 2022 +1100) -* 123060e3 - chore: Upgrade pact_matching to 0.12.14 (Ronald Holshausen, Mon Nov 7 11:34:36 2022 +1100) -* 577824e7 - fix: Upgrade pact_models to 1.0 and pact-plugin-driver to 0.1.15 to fix cyclic dependency issue (Ronald Holshausen, Mon Nov 7 11:14:20 2022 +1100) -* e1f985ad - chore: Upgrade pact_models to 0.4.6 and pact-plugin-driver to 0.1.14 (Ronald Holshausen, Fri Nov 4 16:38:36 2022 +1100) -* 6ad00a5d - fix: Update onig to latest master to fix Regex Matcher Fails On Valid Inputs #214 (Ronald Holshausen, Fri Nov 4 15:23:50 2022 +1100) -* 86d32ddf - fix(cors): source allowed origin from origin header, add credentials (Matt Fellows, Sun Oct 30 21:59:35 2022 +1100) -* 965a1c41 - fix: Upgrade plugin driver to 0.1.13 (fixes issue loading plugin when there are multiple versions for the same plugin) (Ronald Holshausen, Wed Oct 5 17:29:37 2022 +1100) -* 02d9e2cb - chore: Upgrade pact matching crate to 0.12.12 (Ronald Holshausen, Wed Sep 28 10:11:11 2022 +1000) -* 60b2b642 - chore: Upgrade pact-plugin-driver to 0.1.12 (Ronald Holshausen, Mon Sep 12 17:44:13 2022 +1000) -* 57a8ad7d - fix: Consumer DSL needs to increment plugin access to avoid plugin shutting down when mock server starts (Ronald Holshausen, Thu Sep 8 11:54:33 2022 +1000) -* fcab3016 - chore: Upgrade pact-plugin-driver to 0.1.11 (Ronald Holshausen, Thu Sep 8 11:28:52 2022 +1000) -* ac4fe73f - chore: fix to release scripts (Ronald Holshausen, Wed Sep 7 10:51:01 2022 +1000) -* f8db90d2 - fix: Upgrade pact_models to 0.4.5 - fixes FFI bug with generators for request paths (Ronald Holshausen, Fri Aug 26 11:44:08 2022 +1000) -* 1b1c77e6 - chore: cleanup some compiler warnings (Ronald Holshausen, Thu Aug 18 16:06:43 2022 +1000) -* 12c437c1 - bump version to 0.9.4 (Ronald Holshausen, Thu Aug 18 15:59:58 2022 +1000) - -# 0.9.3 - Maintenance Release - -* fa832ec1 - chore: cleanup some deprecation warnings (Ronald Holshausen, Thu Aug 18 15:57:02 2022 +1000) -* 1d5fb787 - chore: Upgrade pact_matching to 0.12.11 (Ronald Holshausen, Thu Aug 18 15:07:23 2022 +1000) -* 32a70382 - chore: Upgrade pact_models (0.4.4), plugin driver (0.1.10), tracing and tracing core crates (Ronald Holshausen, Thu Aug 18 14:41:52 2022 +1000) -* a57c19fc - bump version to 0.9.3 (Ronald Holshausen, Mon Aug 15 17:35:20 2022 +1000) - -# 0.9.2 - Maintenance Release - -* 78c05f29 - feat: add metric call when the mock server is shutdown via FFI function (Ronald Holshausen, Thu Aug 11 17:50:29 2022 +1000) -* 7b6a919b - chore: Upgrade pact_matching crate to 0.12.10 (Ronald Holshausen, Wed Aug 10 12:37:11 2022 +1000) -* 33b04eee - chore: cleanup some deprecation warnings (Ronald Holshausen, Wed Aug 10 10:34:58 2022 +1000) -* 195ad07b - chore: Updated dependant crates (uuid, simplelog) (Ronald Holshausen, Wed Aug 10 10:22:07 2022 +1000) -* 49232caa - chore: Update pact plugin driver to 0.1.9 (Ronald Holshausen, Wed Aug 10 10:14:42 2022 +1000) -* a3fe5e7f - chore: Update pact models to 0.4.2 (Ronald Holshausen, Wed Aug 10 10:10:41 2022 +1000) -* 9a6c846f - chore: Upgrade pact_matching to 0.12.9 (Ronald Holshausen, Fri Jun 10 15:46:07 2022 +1000) -* d6a22c6e - bump version to 0.9.2 (Ronald Holshausen, Mon May 30 12:00:40 2022 +1000) - -# 0.9.1 - Bugfix Release - -* bcddbcfb - chore: Upgrade pact_matching to 0.12.8 (Ronald Holshausen, Mon May 30 11:52:26 2022 +1000) -* 80256458 - chore: Upgrade pact-plugin-driver to 0.1.8 (Ronald Holshausen, Mon May 30 11:36:54 2022 +1000) -* 873f0c93 - fix(ffi): resources were not freed correctly when the mock server is provided by a plugin (Ronald Holshausen, Mon May 30 11:05:20 2022 +1000) -* b8ae4569 - bump version to 0.9.1 (Ronald Holshausen, Mon May 23 14:15:44 2022 +1000) - -# 0.9.0 - support for mock servers from plugin - -* 4f198f10 - feat: support for mock servers from plugins (Ronald Holshausen, Fri May 20 15:59:49 2022 +1000) -* d9b9fe72 - chore: Upgrade pact-plugin-driver to 0.1.7 (Ronald Holshausen, Fri May 20 15:56:23 2022 +1000) -* ac6b0058 - bump version to 0.8.12 (Ronald Holshausen, Wed May 11 16:55:52 2022 +1000) - -# 0.8.11 - Maintenance Release - -* c7bc0b68 - chore: switch from logging crate to tracing crate (Ronald Holshausen, Wed May 11 16:50:32 2022 +1000) -* 5c426547 - chore: Upgrade crate dependencies (Ronald Holshausen, Wed May 11 16:23:17 2022 +1000) -* 08f28e4a - chore: Upgrade pact_matching to 0.12.7 (Ronald Holshausen, Wed May 11 15:57:36 2022 +1000) -* 37bfc5de - chore: Upgrade pact-plugin-driver to 0.1.6 (Ronald Holshausen, Wed May 11 11:56:23 2022 +1000) -* 020b5715 - chore: upgrade pact_models to 0.4.1 (Ronald Holshausen, Wed May 11 11:36:57 2022 +1000) -* 10bab6c4 - bump version to 0.8.11 (Ronald Holshausen, Wed Apr 27 15:02:42 2022 +1000) - -# 0.8.10 - Maintenance Release - -* bcae77b4 - chore: upgrade pact_matching to 0.12.6 (Ronald Holshausen, Wed Apr 27 14:29:26 2022 +1000) -* dba7252e - chore: Upgrade pact-plugin-driver to 0.1.5 (Ronald Holshausen, Tue Apr 26 13:56:22 2022 +1000) -* 688e49e7 - chore: Upgrade pact-plugin-driver to 0.1.4 (Ronald Holshausen, Fri Apr 22 14:47:01 2022 +1000) -* cdf72b05 - feat: forward provider details to plugin when verifying (Ronald Holshausen, Fri Apr 22 14:12:34 2022 +1000) -* 2395143a - feat: forward verification to plugin for transports provided by the plugin (Ronald Holshausen, Fri Apr 22 12:02:05 2022 +1000) -* 6a8fd482 - bump version to 0.8.10 (Ronald Holshausen, Wed Apr 13 15:47:42 2022 +1000) - -# 0.8.9 - Maintenance Release - -* 0df06dd2 - chore: Upgrade pact_matching to 0.12.5 (Ronald Holshausen, Wed Apr 13 15:38:49 2022 +1000) -* d043f6c7 - chore: upgrade pact_models to 0.3.3 (Ronald Holshausen, Wed Apr 13 15:24:33 2022 +1000) -* eee09ba6 - chore: Upgrade pact-plugin-driver to 0.1.3 (Ronald Holshausen, Wed Apr 13 14:07:36 2022 +1000) -* 73ae0ef0 - fix: Upgrade reqwest to 0.11.10 to resolve #156 (Ronald Holshausen, Wed Apr 13 13:31:55 2022 +1000) -* ffeca2e2 - chore: update to the latest plugin driver (Ronald Holshausen, Wed Apr 13 13:08:25 2022 +1000) -* 89027c87 - chore: update pact_matching (0.12.4) and pact_mock_server (0.8.8) (Ronald Holshausen, Thu Mar 24 14:09:45 2022 +1100) -* 482bd719 - bump version to 0.8.9 (Ronald Holshausen, Thu Mar 24 14:06:16 2022 +1100) - -# 0.8.8 - Maintenance Release - -* 9baf03a9 - chore: use the published version of the plugin driver (Ronald Holshausen, Thu Mar 24 13:36:01 2022 +1100) -* 345b0011 - feat: support mock servers provided from plugins (Ronald Holshausen, Mon Mar 21 15:59:46 2022 +1100) -* e3505a2d - bump version to 0.8.8 (Ronald Holshausen, Fri Mar 4 14:14:25 2022 +1100) - -# 0.8.7 - Maintenance Release - -* 8894fdfd - chore: update pact_matching to 0.12.3 (Ronald Holshausen, Fri Mar 4 14:09:17 2022 +1100) -* 8e864502 - chore: update all dependencies (Ronald Holshausen, Fri Mar 4 13:29:59 2022 +1100) -* b7cfa9d4 - bump version to 0.8.7 (Ronald Holshausen, Mon Jan 17 16:39:00 2022 +1100) - -# 0.8.6 - Bugfix Release - -* 5e4c68ef - chore: update pact matching to 0.12.2 (Ronald Holshausen, Mon Jan 17 16:29:21 2022 +1100) -* 80b241c5 - chore: Upgrade plugin driver crate to 0.0.17 (Ronald Holshausen, Mon Jan 17 11:22:48 2022 +1100) -* 4f1ecff2 - chore: Upgrade pact-models to 0.2.7 (Ronald Holshausen, Mon Jan 17 10:53:26 2022 +1100) -* c2089645 - fix: log crate version must be fixed across all crates (including plugin driver) (Ronald Holshausen, Fri Jan 14 16:10:50 2022 +1100) -* b33ce2fa - bump version to 0.8.6 (Ronald Holshausen, Tue Jan 4 12:43:22 2022 +1100) - -# 0.8.5 - Maintenance Release - -* 8259c12a - chore: update pact_models 0.2.6, pact_matching 0.12.1, pact-plugin-driver 0.0.16 (Ronald Holshausen, Tue Jan 4 12:38:26 2022 +1100) -* 9c2810ad - chore: Upgrade pact-plugin-driver to 0.0.15 (Ronald Holshausen, Fri Dec 31 15:12:56 2021 +1100) -* 0a6e7d9d - refactor: Convert MatchingContext to a trait and use DocPath instead of string slices (Ronald Holshausen, Wed Dec 29 14:24:39 2021 +1100) -* d8332686 - bump version to 0.8.5 (Ronald Holshausen, Thu Dec 23 13:19:14 2021 +1100) - -# 0.8.4 - Maintenance Release - -* 52bc1735 - chore: update pact_matching crate to 0.11.5 (Ronald Holshausen, Thu Dec 23 13:12:08 2021 +1100) -* 5479a634 - chore: Update pact_models (0.2.4) and pact-plugin-driver (0.0.14) (Ronald Holshausen, Thu Dec 23 12:57:02 2021 +1100) -* fc0a8360 - chore: update pact_matching to 0.11.4 (Ronald Holshausen, Mon Dec 20 12:19:36 2021 +1100) -* 8911d5b0 - chore: update to latest plugin driver crate (metrics fixes) (Ronald Holshausen, Mon Dec 20 12:11:35 2021 +1100) -* 71708291 - bump version to 0.8.4 (Ronald Holshausen, Wed Dec 15 13:20:28 2021 +1100) - -# 0.8.3 - Maintenance Release - -* 84355d3d - chore: Upgrade rustls in the mock server to 0.20.2 (Ronald Holshausen, Wed Dec 15 12:32:28 2021 +1100) -* 4f1ba7d9 - chore: update to the latest plugin driver (Ronald Holshausen, Tue Dec 14 13:55:02 2021 +1100) -* e21879f7 - bump version to 0.8.3 (Ronald Holshausen, Wed Nov 17 15:08:23 2021 +1100) - -# 0.8.2 - Support setting pact spec version on the mock servers - -* 9cfe897a - feat(mock server): default pact spec to V3 if unknown (Ronald Holshausen, Wed Nov 17 14:53:19 2021 +1100) -* 5d4a09c6 - feat: store the pact specification version with the mock server (Ronald Holshausen, Wed Nov 17 14:46:56 2021 +1100) -* fc5be202 - fix: update to latest driver crate (Ronald Holshausen, Tue Nov 16 16:19:02 2021 +1100) -* 33891ccb - bump version to 0.8.2 (Ronald Holshausen, Tue Nov 16 12:17:47 2021 +1100) - -# 0.8.1 - Support for using plugins via FFI - -* 5d974c4a - chore: update to latest models and plugin driver crates (Ronald Holshausen, Tue Nov 16 11:56:53 2021 +1100) -* 2027537d - refactor: update FFI to use V4 models internally (Ronald Holshausen, Mon Nov 8 16:44:39 2021 +1100) -* 400a1231 - chore: drop beta from pact_verifier version (Ronald Holshausen, Thu Nov 4 15:56:22 2021 +1100) -* 01dbf7b5 - bump version to 0.8.1 (Ronald Holshausen, Thu Nov 4 15:36:31 2021 +1100) - -# 0.8.0 - Pact V4 release - -* fc4580b8 - chore: drop beta from pact_mock_server version (Ronald Holshausen, Thu Nov 4 15:28:51 2021 +1100) -* bd2bd0ec - chore: drop beta from pact_matching version (Ronald Holshausen, Wed Nov 3 13:28:35 2021 +1100) -* 296b4370 - chore: update project to Rust 2021 edition (Ronald Holshausen, Fri Oct 22 10:44:48 2021 +1100) -* a561f883 - chore: use the non-beta models crate (Ronald Holshausen, Thu Oct 21 18:10:27 2021 +1100) -* 5532c730 - bump version to 0.8.0-beta.5 (Ronald Holshausen, Tue Oct 19 17:26:58 2021 +1100) - -# 0.8.0-beta.4 - Bugfix Release - -* 918e5beb - fix: update to latest models and plugin driver crates (Ronald Holshausen, Tue Oct 19 17:09:48 2021 +1100) -* 3819522d - chore: update to the latest matching and mock server crates (Ronald Holshausen, Tue Oct 19 11:34:18 2021 +1100) -* ece992af - bump version to 0.8.0-beta.4 (Ronald Holshausen, Tue Oct 19 11:27:07 2021 +1100) - -# 0.8.0-beta.3 - Support matching synchronous request/response messages - -* aa434ba3 - chore: update to latest driver crate (Ronald Holshausen, Tue Oct 19 11:09:46 2021 +1100) -* df386c8a - chore: use the published version of pact-plugin-driver (Ronald Holshausen, Mon Oct 18 13:41:36 2021 +1100) -* 2b4b7cc3 - feat(plugins): Support matching synchronous request/response messages (Ronald Holshausen, Fri Oct 15 16:01:50 2021 +1100) -* d69b0617 - bump version to 0.8.0-beta.3 (Ronald Holshausen, Tue Oct 12 16:31:49 2021 +1100) - -# 0.8.0-beta.2 - Support synchronous messages - -* 9bbbb52e - chore: bump pact matching crate version (Ronald Holshausen, Tue Oct 12 16:24:01 2021 +1100) -* b7018002 - Revert "update changelog for release 0.8.0-beta.2" (Ronald Holshausen, Tue Oct 12 16:09:49 2021 +1100) -* 9319f650 - update changelog for release 0.8.0-beta.2 (Ronald Holshausen, Tue Oct 12 16:05:18 2021 +1100) -* 3dbd609a - chore: bump version of pact-plugin-driver (Ronald Holshausen, Tue Oct 12 15:59:53 2021 +1100) -* d0bfb8a8 - feat: Support consumer tests with synchronous messages (Ronald Holshausen, Tue Oct 12 15:51:08 2021 +1100) -* 35ff0993 - feat: record the version of the lib that created the pact in the metadata (Ronald Holshausen, Tue Oct 12 14:52:43 2021 +1100) -* 3df879d4 - bump version to 0.8.0-beta.2 (Ronald Holshausen, Wed Oct 6 12:30:24 2021 +1100) - -# 0.8.0-beta.1 - Fixes from master + Plugin support (driver version 0.0.3) - -* dfabfac0 - chore: use the published version of the models crate (Ronald Holshausen, Wed Oct 6 12:24:04 2021 +1100) -* 2c47023c - chore: pin plugin driver version to 0.0.3 (Ronald Holshausen, Wed Oct 6 11:21:07 2021 +1100) -* 288e2168 - chore: use the published version of the plugin driver lib (Ronald Holshausen, Tue Oct 5 15:36:06 2021 +1100) -* 6d23796f - feat(plugins): support each key and each value matchers (Ronald Holshausen, Wed Sep 29 11:10:46 2021 +1000) -* 6f20282d - Merge branch 'master' into feat/plugins (Ronald Holshausen, Tue Sep 28 14:51:34 2021 +1000) -* 54615e1b - bump version to 0.7.22 (Ronald Holshausen, Tue Sep 28 13:41:40 2021 +1000) -* 97c8de3c - update changelog for release 0.7.21 (Ronald Holshausen, Tue Sep 28 13:39:32 2021 +1000) -* df715cd5 - feat: support native TLS. Fixes #144 (Matt Fellows, Mon Sep 20 13:00:33 2021 +1000) -* ee3212a8 - refactor(plugins): do not expose the catalogue statics, but rather a function to initialise it (Ronald Holshausen, Tue Sep 14 15:13:12 2021 +1000) -* b71dcabf - refactor(plugins): rename ContentTypeOverride -> ContentTypeHint (Ronald Holshausen, Tue Sep 14 15:08:52 2021 +1000) -* e63ade0d - bump version to 0.8.0-beta.1 (Ronald Holshausen, Mon Sep 13 11:53:04 2021 +1000) - -# 0.7.21 - support native TLS certs - -* df715cd5 - feat: support native TLS. Fixes #144 (Matt Fellows, Mon Sep 20 13:00:33 2021 +1000) -* c9165bd3 - bump version to 0.7.21 (Ronald Holshausen, Tue Aug 17 10:37:33 2021 +1000) - -# 0.8.0-beta.0 - Support for plugins with mock server - -* fd6f8f40 - chore: Bump pact_mock_server version to 0.8.0-beta.0 (Ronald Holshausen, Mon Sep 13 11:46:11 2021 +1000) -* 716809f6 - chore: Get CI build passing (Ronald Holshausen, Fri Sep 10 14:55:46 2021 +1000) -* 4aaaafd8 - feat(plugins): Support non-blocking mock server in consumer tests + shutting down plugins when mock servers shutdown (Ronald Holshausen, Fri Sep 10 13:20:01 2021 +1000) -* b77498c8 - chore: fix tests after updating plugin API (Ronald Holshausen, Fri Sep 3 16:48:18 2021 +1000) -* e8ae81b3 - refactor: matching req/res with plugins requires data from the pact and interaction (Ronald Holshausen, Thu Sep 2 11:57:50 2021 +1000) -* b9aa7ecb - feat(Plugins): allow plugins to override text/binary format of the interaction content (Ronald Holshausen, Mon Aug 30 10:48:04 2021 +1000) -* eb34b011 - chore: use the published version of pact-plugin-driver (Ronald Holshausen, Mon Aug 23 15:48:55 2021 +1000) -* 0c5cede2 - chore: bump models crate to 0.2 (Ronald Holshausen, Mon Aug 23 12:56:14 2021 +1000) -* e3a2660f - chore: fix tests after updating test builders to be async (Ronald Holshausen, Fri Aug 20 12:41:10 2021 +1000) -* 779f099c - feat(plugins): Got generators from plugin working (Ronald Holshausen, Thu Aug 19 17:20:47 2021 +1000) -* b75fea5d - Merge branch 'master' into feat/plugins (Ronald Holshausen, Wed Aug 18 12:27:41 2021 +1000) -* c9165bd3 - bump version to 0.7.21 (Ronald Holshausen, Tue Aug 17 10:37:33 2021 +1000) -* 2662241e - feat(plugins): Call out to plugins when comparing content owned by the plugin during verification (Ronald Holshausen, Fri Aug 13 14:29:30 2021 +1000) -* 60869969 - feat(plugins): Add core features to the plugin catalogue (Ronald Holshausen, Thu Aug 12 13:00:41 2021 +1000) - -# 0.7.20 - Refactor - -* 9baa714d - chore: bump minor version of matching crate (Ronald Holshausen, Fri Jul 23 14:03:20 2021 +1000) -* 533c9e1f - chore: bump minor version of the Pact models crate (Ronald Holshausen, Fri Jul 23 13:15:32 2021 +1000) -* 3dccf866 - refacfor: moved the pact structs to the models crate (Ronald Holshausen, Sun Jul 18 16:58:14 2021 +1000) -* e8046d84 - refactor: moved interaction structs to the models crate (Ronald Holshausen, Sun Jul 18 14:36:03 2021 +1000) -* cf00f528 - bump version to 0.7.20 (Ronald Holshausen, Sun Jul 11 17:11:29 2021 +1000) - -# 0.7.19 - Refactor: Moved structs to models crate - -* e2e10241 - refactor: moved Request and Response structs to the models crate (Ronald Holshausen, Wed Jul 7 18:09:36 2021 +1000) -* 9e8b01d7 - refactor: move HttpPart struct to models crate (Ronald Holshausen, Wed Jul 7 15:59:34 2021 +1000) -* 01ff9877 - refactor: moved matching rules and generators to models crate (Ronald Holshausen, Sun Jul 4 17:17:30 2021 +1000) -* c3c22ea8 - Revert "refactor: moved matching rules and generators to models crate (part 1)" (Ronald Holshausen, Wed Jun 23 14:37:46 2021 +1000) -* 53bb86c4 - Merge branch 'release-verifier' (Ronald Holshausen, Wed Jun 23 13:59:59 2021 +1000) -* 3a02d1eb - bump version to 0.7.19 (Ronald Holshausen, Wed Jun 23 13:25:12 2021 +1000) -* d3406650 - refactor: moved matching rules and generators to models crate (part 1) (Ronald Holshausen, Wed Jun 23 12:58:30 2021 +1000) - -# 0.7.18 - accumulating log entries + bugfix - -* b4e26844 - fix: reqwest is dyn linked to openssl by default, which causes a SIGSEGV on alpine linux (Ronald Holshausen, Tue Jun 1 14:21:31 2021 +1000) -* 68f8f84e - chore: skip failing tests in alpine to get the build going (Ronald Holshausen, Tue Jun 1 13:47:20 2021 +1000) -* 17beef62 - feat: support accumulating log entries per running mock server (Ronald Holshausen, Mon May 31 15:09:20 2021 +1000) -* 0fc54642 - bump version to 0.7.18 (Ronald Holshausen, Sun May 30 17:36:27 2021 +1000) - -# 0.7.17 - V4 features + bugfixes/enhancements - -* 735c9e7 - chore: bump pact_matching to 0.9 (Ronald Holshausen, Sun Apr 25 13:50:18 2021 +1000) -* fb373b4 - chore: bump version to 0.0.2 (Ronald Holshausen, Sun Apr 25 13:40:52 2021 +1000) -* d010630 - chore: cleanup deprecation and compiler warnings (Ronald Holshausen, Sun Apr 25 12:23:30 2021 +1000) -* 3dd610a - refactor: move structs and code dealing with bodies to a seperate package (Ronald Holshausen, Sun Apr 25 11:20:47 2021 +1000) -* a725ab1 - feat(V4): added synchronous request/response message formats (Ronald Holshausen, Sat Apr 24 16:05:12 2021 +1000) -* e588bb2 - fix: clippy violation: using `clone` on a double-reference (Ronald Holshausen, Sat Apr 24 12:52:58 2021 +1000) -* 80b7148 - feat(V4): Updated consumer DSL to set comments + mock server initial support for V4 pacts (Ronald Holshausen, Fri Apr 23 17:58:10 2021 +1000) -* 4bcd94f - refactor: moved OptionalBody and content types to pact models crate (Ronald Holshausen, Thu Apr 22 14:01:56 2021 +1000) -* 220fb5e - refactor: move the PactSpecification enum to the pact_models crate (Ronald Holshausen, Thu Apr 22 11:18:26 2021 +1000) -* a0f6a1d - refactor: Use Anyhow instead of `io::Result` (Caleb Stepanian, Wed Apr 7 16:17:35 2021 -0400) -* 97ac20d - bump version to 0.7.17 (Ronald Holshausen, Sun Mar 14 14:41:36 2021 +1100) - -# 0.7.16 - Bugfix Release - -* 5a529fd - feat: add ability of mock server to expose metrics #94 (Ronald Holshausen, Sun Mar 14 11:41:16 2021 +1100) -* e81482e - chore: correct import (Ronald Holshausen, Tue Feb 9 16:27:38 2021 +1100) -* b23c845 - chore: cleanup some debug logging (Ronald Holshausen, Tue Feb 9 16:18:34 2021 +1100) -* 7f054e8 - fix: correctly assemble UTF-8 percent encoded query parameters (Ronald Holshausen, Tue Feb 9 14:02:04 2021 +1100) -* 2002b67 - bump version to 0.7.16 (Ronald Holshausen, Mon Feb 8 15:44:20 2021 +1100) - -# 0.7.15 - use a file system lock when merging pact files - -* eae1b16 - chore: fix clippy errors (Ronald Holshausen, Mon Feb 8 14:57:42 2021 +1100) -* 9976e80 - feat: added read locks and a mutex guard to reading and writing pacts (Ronald Holshausen, Mon Feb 8 11:58:52 2021 +1100) -* 61e16ed - feat: use a file system lock when merging pact files (Ronald Holshausen, Sun Feb 7 17:00:29 2021 +1100) -* 49a3cf2 - refactor: use bytes crate instead of vector of bytes for body content (Ronald Holshausen, Sun Feb 7 14:43:40 2021 +1100) -* e43fdb8 - chore: upgrade maplit, itertools (Audun Halland, Mon Jan 11 05:30:10 2021 +0100) -* 45ae48e - bump version to 0.7.15 (Ronald Holshausen, Mon Jan 11 10:05:50 2021 +1100) - -# 0.7.14 - Updated dependencies - -* 4a70bef - chore: upgrade expectest to 0.12 (Audun Halland, Sat Jan 9 11:29:29 2021 +0100) -* 1ac3548 - chore: upgrade env_logger to 0.8 (Audun Halland, Sat Jan 9 09:50:27 2021 +0100) -* 9a8a63f - chore: upgrade quickcheck (Audun Halland, Sat Jan 9 08:46:51 2021 +0100) -* 3a6945e - chore: Upgrade reqwest to 0.11 and hence tokio to 1.0 (Ronald Holshausen, Wed Jan 6 15:34:47 2021 +1100) -* 598352b - bump version to 0.7.14 (Ronald Holshausen, Tue Jan 5 13:04:25 2021 +1100) - -# 0.7.13 - Upgrade Tokio to 1.0 - -* ef76f38 - chore: cleanup compiler warnings (Ronald Holshausen, Tue Jan 5 10:10:39 2021 +1100) -* 4636982 - chore: update other crates to use Tokio 1.0 (Ronald Holshausen, Mon Jan 4 17:26:59 2021 +1100) -* 211a4fc - chore: got code compiling, which is 90% of the battle (Ronald Holshausen, Mon Jan 4 10:45:27 2021 +1100) -* 62454d5 - chore: upgrade tokio and hyper (Ronald Holshausen, Sun Jan 3 12:22:38 2021 +1100) -* 5dddde1 - bump version to 0.7.13 (Ronald Holshausen, Thu Dec 31 12:40:46 2020 +1100) - -# 0.7.12 - Mockserver URL and array contains generators - -* f2086d8 - chore: cleanup warnings (Ronald Holshausen, Tue Dec 29 15:46:46 2020 +1100) -* 528c9b5 - chore: skip test that fails intermittently on Windows (Ronald Holshausen, Tue Dec 29 14:52:38 2020 +1100) -* 6491ce9 - chore: add longer sleep for test failing on windows (Ronald Holshausen, Tue Dec 29 14:38:45 2020 +1100) -* 5e56ecb - refactor: support generators associated with array contains matcher variants (Ronald Holshausen, Tue Dec 29 11:46:56 2020 +1100) -* 5058a2d - feat: include the mockserver URL and port in the verification context (Ronald Holshausen, Fri Nov 20 16:43:10 2020 +1100) -* 118daa1 - feat: when merging pact files, upcast to the higher spec version (Ronald Holshausen, Thu Nov 19 18:09:13 2020 +1100) -* 08852e4 - bump version to 0.7.12 (Ronald Holshausen, Tue Nov 17 16:45:35 2020 +1100) - -# 0.7.11 - Support provider state injected values - -* 13ce2f2 - fix: introduce GeneratorTestMode and restrict provider state generator to the provider side (Ronald Holshausen, Mon Nov 16 15:00:01 2020 +1100) -* 0a10c7c - bump version to 0.7.11 (Ronald Holshausen, Fri Oct 30 12:18:53 2020 +1100) - -# 0.7.10 - Bugfix Release - -* 326d02d - fix: jsdom does not support access-control-allow-headers: * for CORS pre-flight responses (Ronald Holshausen, Fri Oct 30 11:54:03 2020 +1100) -* a732c41 - bump version to 0.7.10 (Ronald Holshausen, Fri Oct 16 11:25:56 2020 +1100) - -# 0.7.9 - arrayContains matcher - -* 2fb0c6e - fix: fix the build after refactoring the pact write function (Ronald Holshausen, Wed Oct 14 11:07:57 2020 +1100) -* f334a4f - refactor: introduce a MatchingContext into all matching functions + delgate to matchers for collections (Ronald Holshausen, Mon Oct 12 14:06:00 2020 +1100) -* 7fbc731 - chore: bump minor version of matching lib (Ronald Holshausen, Fri Oct 9 10:42:33 2020 +1100) -* 172f505 - chore: cleaned up some compiler warnings (Ronald Holshausen, Thu Oct 8 15:02:49 2020 +1100) -* facc898 - refactor: moved the shutdown code to a method in mock server crate (Ronald Holshausen, Sun Oct 4 11:56:10 2020 +1100) -* 44e7414 - fix: access-control-allow-methods header was duplicated (Ronald Holshausen, Thu Oct 1 15:29:14 2020 +1000) -* d3c5cf2 - feat: add all the CORS headers (Ronald Holshausen, Wed Sep 30 13:19:31 2020 +1000) -* 584aa08 - bump version to 0.7.9 (Ronald Holshausen, Mon Sep 28 12:06:28 2020 +1000) - -# 0.7.8 - CORS pre-flight requests - -* 7e68e4c - feat: enable CORS behaviour based on the mock server config (Ronald Holshausen, Mon Sep 28 11:42:23 2020 +1000) -* bdbfccc - refactor: update mock server CLI to be async (Ronald Holshausen, Sun Sep 27 13:12:51 2020 +1000) -* 29ba743 - feat: add a mock server config struct (Ronald Holshausen, Thu Sep 24 10:30:59 2020 +1000) -* 2e662a6 - feat: handle CORS pre-flight requests in the mock server (Ronald Holshausen, Wed Sep 23 17:59:32 2020 +1000) -* 2676b51 - bump version to 0.7.8 (Ronald Holshausen, Mon Sep 14 16:55:22 2020 +1000) - -# 0.7.7 - Updated to latest pact matching crate - -* 6cba6ad - feat: implemented basic message verification with the verifier cli (Ronald Holshausen, Mon Sep 14 13:48:27 2020 +1000) -* 2d44ffd - chore: bump minor version of the matching crate (Ronald Holshausen, Mon Sep 14 12:06:37 2020 +1000) -* 814c416 - refactor: added a trait for interactions, renamed Interaction to RequestResponseInteraction (Ronald Holshausen, Sun Sep 13 17:09:41 2020 +1000) -* a05bcbb - refactor: renamed Pact to RequestResponsePact (Ronald Holshausen, Sun Sep 13 12:45:34 2020 +1000) -* 1682eda - bump version to 0.7.7 (Ronald Holshausen, Sun Aug 23 14:47:38 2020 +1000) - -# 0.7.6 - Implemented provider state generator - -* e9955c4 - chore: update to latest matching crate (Ronald Holshausen, Sun Aug 23 14:41:42 2020 +1000) -* 8499b7d - chore: fix link in readme #72 (Ronald Holshausen, Sat Aug 22 15:38:08 2020 +1000) -* da53bac - fix: return the most relevant response from the mock server #69 (Ronald Holshausen, Tue Jul 21 16:10:54 2020 +1000) -* 420f5e2 - Merge pull request #70 from pact-foundation/fix/v2-pacts (Ronald Holshausen, Tue Jul 21 09:46:05 2020 +1000) -* d7632cb - fix: write_pact_file was always serialising a v3 pact even if the spec version was set to 2 (Matt Fellows, Tue Jul 21 09:42:30 2020 +1000) -* b242eb1 - refactor: changed the remaining uses of the old content type methods (Ronald Holshausen, Sun Jun 28 17:11:51 2020 +1000) -* ed207a7 - chore: updated readmes for docs site (Ronald Holshausen, Sun Jun 28 10:04:09 2020 +1000) -* 3d44484 - bump version to 0.7.6 (Ronald Holshausen, Wed Jun 24 10:48:13 2020 +1000) -* f123357 - chore: bump to latest matching crate (Ronald Holshausen, Wed Jun 24 10:43:01 2020 +1000) - -# 0.7.5 - Updated XML Matching - -* a15edea - chore: try set the content type on the body if known (Ronald Holshausen, Tue Jun 23 16:53:32 2020 +1000) -* b4fe61f - bump version to 0.7.5 (Ronald Holshausen, Sun May 24 11:56:22 2020 +1000) - -# 0.7.4 - multi-part form post bodies - -* ce94df9 - feat: cleaned up the logging of request matches (Ronald Holshausen, Sun May 24 11:17:08 2020 +1000) -* bea787c - chore: bump matching crate version to 0.6.0 (Ronald Holshausen, Sat May 23 17:56:04 2020 +1000) -* 2d11c17 - chore: set version of patch matching crate to 0.5.14 (Ronald Holshausen, Fri May 15 16:33:21 2020 +1000) -* a4b2a6a - bump version to 0.7.4 (Ronald Holshausen, Tue May 12 12:40:50 2020 +1000) - -# 0.7.3 - matching of binary payloads - -* 4a28e7c - chore: add debug log entry when request does not match (Ronald Holshausen, Tue May 12 11:59:02 2020 +1000) -* 708db47 - feat: implement matching of binary payloads (application/octet-stream) (Ronald Holshausen, Fri May 8 15:52:03 2020 +1000) -* 754a483 - chore: updated itertools to latest (Ronald Holshausen, Wed May 6 15:49:27 2020 +1000) -* 215eb67 - bump version to 0.7.3 (Ronald Holshausen, Tue May 5 16:53:48 2020 +1000) - -# 0.7.2 - TLS suppport + bugfixes - -* d85f28c - fix: mock server matching requests with headers with multiple values (Ronald Holshausen, Tue May 5 15:23:11 2020 +1000) -* da885a3 - feat: add support for TLS with the mock server #65 (Ronald Holshausen, Thu Apr 30 16:41:30 2020 +1000) -* 34103aa - bump version to 0.7.2 (Ronald Holshausen, Fri Apr 24 10:45:24 2020 +1000) - -# 0.7.1 - Changes to support C++ DSL - -* 43de9c3 - chore: update matching library to latest (Ronald Holshausen, Fri Apr 24 10:20:55 2020 +1000) -* 5f8d0a0 - feat: handle bodies with embedded matchers and generators (Ronald Holshausen, Thu Apr 23 12:25:05 2020 +1000) -* 734723d - chore: increase timeout for test on Appveyor (Ronald Holshausen, Fri Apr 17 09:06:55 2020 +1000) -* a0b2c7b - chore: add a wait for test on Appveyor (Ronald Holshausen, Thu Apr 16 14:42:46 2020 +1000) -* 7e89ca9 - chore: update matching crate to latest (Ronald Holshausen, Thu Apr 16 14:06:02 2020 +1000) -* 9ff6f20 - chore: cleaned up some debug logging (Ronald Holshausen, Tue Apr 7 12:10:12 2020 +1000) -* f9b690e - bump version to 0.7.1 (Ronald Holshausen, Sun Jan 19 11:30:42 2020 +1100) - -# 0.7.0 - Convert to async/await - -* cf452f5 - chore: bump minor version (Ronald Holshausen, Sun Jan 19 11:18:03 2020 +1100) -* 2b85b71 - chore: dump pact matching crate to 0.5.8 (Ronald Holshausen, Sun Jan 19 11:15:07 2020 +1100) -* cb4c560 - Upgrade tokio to 0.2.9 (Audun Halland, Fri Jan 10 00:13:02 2020 +0100) -* 3dec6ff - Upgrade tokio to 0.2.6 (Audun Halland, Tue Dec 31 07:40:14 2019 +0100) -* 6747a98 - pact_mock_server: Try to fix windows test fail by awaiting the server shutdown (Audun Halland, Thu Dec 19 23:39:07 2019 +0100) -* fda11e4 - Merge remote-tracking branch 'upstream/master' into async-await (Audun Halland, Tue Dec 17 02:13:58 2019 +0100) -* 65a4452 - chore: set min matching lib version to 0.5.7 (Ronald Holshausen, Sat Dec 14 17:09:03 2019 +1100) -* b6dda08 - bump version to 0.6.3 (Ronald Holshausen, Sat Dec 14 17:07:50 2019 +1100) -* 23a652d - pact_verifier: Implement hyper requests for provider/state change (Audun Halland, Thu Dec 12 11:46:50 2019 +0100) -* 6a43f82 - Cut down tokio features to the bone (Audun Halland, Wed Dec 11 22:15:03 2019 +0100) -* 353cb5b - pact_mock_server: Use std future trait instead of futures-rs (Audun Halland, Wed Dec 11 21:56:05 2019 +0100) -* 2136306 - pact_mock_server: Pass all tests (Audun Halland, Wed Dec 11 01:08:24 2019 +0100) -* 6699bc8 - pact_mock_server: Make it all compile with async/await (Audun Halland, Wed Dec 11 00:32:49 2019 +0100) -* 42f72f2 - mock_server: Convert hyper_server to async await. Use 4 space indent (Audun Halland, Wed Dec 11 00:13:15 2019 +0100) - -# 0.6.2 - Rust 2018 edition - -* 8bfeb0b - pact_mock_server: Remove extern crate from lib.rs (Audun Halland, Sun Nov 17 22:53:52 2019 +0100) -* 713cd6a - Explicit edition 2018 in Cargo.toml files (Audun Halland, Sat Nov 16 23:55:37 2019 +0100) -* 924452f - 2018 edition autofix "cargo fix --edition" (Audun Halland, Sat Nov 16 22:27:42 2019 +0100) -* 99fdde2 - bump version to 0.6.2 (Ronald Holshausen, Sat Sep 28 14:19:43 2019 +1000) - -# 0.6.1 - Bugfix Release - -* 37d89dd - chore: use the latest matching lib (Ronald Holshausen, Sat Sep 28 14:04:55 2019 +1000) -* eef3d97 - feat: added some tests for publishing verification results to the pact broker #44 (Ronald Holshausen, Sun Sep 22 16:44:52 2019 +1000) -* 1110b47 - feat: implemented publishing verification results to the pact broker #44 (Ronald Holshausen, Sun Sep 22 13:53:27 2019 +1000) -* 2488ab9 - Merge branch 'master' of https://github.com/pact-foundation/pact-reference (milleniumbug, Wed Sep 18 11:32:03 2019 +0200) -* cb30a2f - feat: added the ProviderStateGenerator as a generator type (Ronald Holshausen, Sun Sep 8 16:29:46 2019 +1000) -* bdcf655 - bump version to 0.6.1 (Ronald Holshausen, Sat Sep 7 12:29:06 2019 +1000) -* adf1a97 - fix: correct the release script (Ronald Holshausen, Sat Sep 7 12:28:22 2019 +1000) -* b48ee72 - Provide public API for passing in a listener address and post (milleniumbug, Thu Sep 5 15:20:37 2019 +0200) - -# 0.6.0 - moved the ffi functions into the ffi module - -* e4355d5 - refactor: removed the ffi suffix from the exported functions (Ronald Holshausen, Sat Sep 7 10:36:19 2019 +1000) -* 9abde6c - refactor: moved the ffi functions into the ffi module (Ronald Holshausen, Sat Sep 7 10:16:54 2019 +1000) -* 097d045 - refactor: added a mock server ffi module and bumped the mock server minor version (Ronald Holshausen, Sat Sep 7 09:39:27 2019 +1000) -* 3adf21d - bump version to 0.5.2 (Ronald Holshausen, Sun Aug 11 15:03:24 2019 +1000) - -# 0.5.1 - support headers with multiple values - -* 1971e2a - chore: remove the p-macro crate (Ronald Holshausen, Sun Aug 11 14:51:24 2019 +1000) -* 63c180f - chore: set the version of the matching lib top 0.5.3 (Ronald Holshausen, Sun Aug 11 14:48:03 2019 +1000) -* b5c7842 - fix: corrected some spelling (Ronald Holshausen, Sun Aug 11 14:31:42 2019 +1000) -* 152682e - chore: cleanup crates and warnings (Ronald Holshausen, Sun Aug 11 14:28:02 2019 +1000) -* f0c0d07 - feat: support headers with multiple values (Ronald Holshausen, Sat Aug 10 17:01:10 2019 +1000) -* 2057f2c - fix: correct the release scripts (Ronald Holshausen, Sat Jul 27 16:07:13 2019 +1000) -* ba7f7e1 - bump version to 0.5.1 (Ronald Holshausen, Sat Jul 27 15:59:52 2019 +1000) - -# 0.5.0 - Upgrade to non-blocking Hyper 0.12 - -* d842100 - chore: bump component versions to 0.5.0 (Ronald Holshausen, Sat Jul 27 15:44:51 2019 +1000) -* a7c674a - fix: remove duplicated line (Ronald Holshausen, Sat Jul 27 15:41:00 2019 +1000) -* ee8a898 - Rewrite server matches sync from mpsc queue to Arc>. Avoids awkward synchronization (Audun Halland, Tue Jul 23 02:10:55 2019 +0200) -* 5ea7815 - Merge remote-tracking branch 'upstream/master' into hyper_upgrade_merge (Audun Halland, Tue Jul 23 01:46:51 2019 +0200) -* 2826bb0 - Make pact_mock_server_cli use ServerManager (Audun Halland, Tue Jul 23 01:40:46 2019 +0200) -* 47ab6d0 - Upgrade tokio to 0.1.22 everywhere (Audun Halland, Mon Jul 22 23:47:09 2019 +0200) -* 4df2797 - Rename API function again (Audun Halland, Mon Jul 22 23:38:11 2019 +0200) -* 7f7dcb0 - Don't expose tokio Runtime inside the libraries (Audun Halland, Mon Jul 22 02:18:52 2019 +0200) -* 2230be9 - bump version to 0.4.2 (Ronald Holshausen, Sun Jun 30 16:23:22 2019 +1000) -* 0223d31 - Remove warning about unused macros in production code (Audun Halland, Sun May 12 10:57:35 2019 +0200) -* 0e83d41 - Comment the use of PACT_FILE_MUTEX (Audun Halland, Sun May 12 10:55:55 2019 +0200) -* 9c1d5a3 - Fix missing documentation (Audun Halland, Sun May 12 10:48:58 2019 +0200) -* 522e7ba - Set runtime::Builder core_threads instead of blocking_threads (Audun Halland, Sun May 12 10:36:54 2019 +0200) -* a0dc885 - Shut down MockServer without consuming self, by putting shutdown_tx in an Option (Audun Halland, Sun May 12 10:28:27 2019 +0200) -* 16cc6b6 - Run pact_verifier tests in async mode + pact write lock (Audun Halland, Sun May 12 04:05:08 2019 +0200) -* 39d231d - pact_consumer async support (untested) (Audun Halland, Sun May 12 03:45:05 2019 +0200) -* 2b34371 - Refactor MockServer; move to separate file (Audun Halland, Sun May 12 02:51:22 2019 +0200) -* cd2ef48 - Rename server.rs to hyper_server.rs (Audun Halland, Sun May 12 02:04:00 2019 +0200) -* ab1ff4d - Remove unused import (Audun Halland, Sun May 12 01:44:24 2019 +0200) -* 9e34c33 - Make the old tests in tests.rs work (Audun Halland, Sun May 12 01:42:22 2019 +0200) -* 32b52cd - Manager should not block waiting for match requests. (Audun Halland, Sun May 12 01:19:10 2019 +0200) -* 71dc054 - A failing test for mock server on current_thread runtime (Audun Halland, Sat May 11 22:57:12 2019 +0200) -* 56768ff - Move pact_mock_server_async into pact_mock_server, making it the official implementation (Audun Halland, Sat May 11 22:04:38 2019 +0200) - -# 0.4.1 - pact matchig version to 0.5.0 - -* 61a6b7f - chore: updated release script (Ronald Holshausen, Sun Jun 30 16:15:49 2019 +1000) -* f8fa0d8 - chore: Bump pact matchig version to 0.5.0 (Ronald Holshausen, Sat Jan 5 19:25:53 2019 +1100) -* 386ab52 - fix: corrected the release scripts to check for a version parameter (Ronald Holshausen, Sun Apr 8 13:44:57 2018 +1000) -* 736a6a4 - bump version to 0.4.1 (Ronald Holshausen, Sat Apr 7 14:29:37 2018 +1000) - -# 0.4.0 - First V3 specification release - -* 398edaf - Upgrade UUID library to latest (Ronald Holshausen, Sat Apr 7 12:29:58 2018 +1000) -* 691b14c - Merge branch 'master' into v3-spec (Ronald Holshausen, Sun Mar 4 17:10:14 2018 +1100) -* 6597141 - WIP - start of implementation of applying generators to the bodies (Ronald Holshausen, Sun Mar 4 17:01:11 2018 +1100) -* 3d01d6e - Merge pull request #31 from andrewspinks/master (Ronald Holshausen, Sun Mar 4 14:18:21 2018 +1100) -* 542b7a3 - Add release script for building an apple universal binary (required for iOS). (Andrew Spinks, Wed Dec 13 11:24:53 2017 +0900) -* 41f1729 - Return a String instead of a serde_json value (Eduard Litau, Mon Dec 4 23:32:19 2017 +0100) -* a76bb5a - Cleaned up all the compiler warnings (Ronald Holshausen, Sun Nov 19 11:29:47 2017 +1100) -* efb17a1 - When there is no content type, default to text/plain (Ronald Holshausen, Sun Nov 19 10:58:17 2017 +1100) -* c4d424b - Wired in the generated request/response into the mock server and verifier (Ronald Holshausen, Tue Nov 7 16:27:01 2017 +1100) -* 13558d6 - Basic generators working (Ronald Holshausen, Tue Nov 7 10:56:55 2017 +1100) -* 7fef36b - Merge branch 'v2-spec' into v3-spec (Ronald Holshausen, Sat Nov 4 12:49:07 2017 +1100) -* ed20d42 - bump version to 0.3.2 (Ronald Holshausen, Fri Nov 3 12:24:46 2017 +1100) -* a905bed - Cleaned up some compiler warnings (Ronald Holshausen, Sun Oct 22 12:26:09 2017 +1100) -* 940a0e3 - Reverted hyper to 0.9.x (Ronald Holshausen, Sun Oct 22 12:01:17 2017 +1100) -* 00dc75a - Bump version to 0.4.0 (Ronald Holshausen, Sun Oct 22 10:46:48 2017 +1100) -* 184127a - Merge branch 'v2-spec' into v3-spec (Ronald Holshausen, Sun Oct 22 10:32:31 2017 +1100) -* e82ee08 - Merge branch 'v2-spec' into v3-spec (Ronald Holshausen, Mon Oct 16 09:24:11 2017 +1100) -* 64ff667 - Upgraded the mock server implemenation to use Hyper 0.11.2 (Ronald Holshausen, Wed Sep 6 12:56:47 2017 +1000) -* e5a93f3 - Merge branch 'master' into v3-spec (Ronald Holshausen, Sun Aug 20 09:53:48 2017 +1000) -* bb46822 - update the mock server to support the V3 format matchers (Ronald Holshausen, Sun Nov 13 16:44:30 2016 +1100) -* 8797c6c - First successful build after merge from master (Ronald Holshausen, Sun Oct 23 11:59:55 2016 +1100) -* 639ac22 - fixes after merge in from master (Ronald Holshausen, Sun Oct 23 10:45:54 2016 +1100) -* 7361688 - moved missing files after merge from master (Ronald Holshausen, Sun Oct 23 10:19:31 2016 +1100) -* 49e45f7 - Merge branch 'master' into v3-spec (Ronald Holshausen, Sun Oct 23 10:10:40 2016 +1100) - -# 0.3.1 - Bugfixes plus changes for running with docker - -* 5606c0c - Refactored the remaining exported functions into an exported rust one and a FFI one (Ronald Holshausen, Wed Nov 1 11:06:48 2017 +1100) -* dab7fb9 - Renamed the exported functions and refactored what the create_mock_server was doing into a new function (Ronald Holshausen, Wed Nov 1 09:30:07 2017 +1100) -* 24e3f73 - Converted OptionalBody::Present to take a Vec #19 (Ronald Holshausen, Sun Oct 22 18:04:46 2017 +1100) -* a56b6a6 - Change the column heading to verification state in the mock server list output #24 (Ronald Holshausen, Sun Oct 22 15:15:30 2017 +1100) -* 814fe12 - Modify AssafKatz3's implementation to scan for next available port from a base port number #15 (Ronald Holshausen, Sun Oct 22 14:40:13 2017 +1100) -* 37abe19 - Pulled in changes from https://github.com/AssafKatz3/pact-reference.git #14 (Assaf Katz, Mon Sep 25 12:28:17 2017 +0300) -* c8595cc - Correct the paths in the release scripts for pact_mock_server_cli (Ronald Holshausen, Fri Oct 20 10:48:03 2017 +1100) -* e11bff6 - Correct the paths in the release script after changing to cargo workspace (Ronald Holshausen, Fri Oct 20 10:33:44 2017 +1100) -* 654e875 - bump version to 0.3.1 (Ronald Holshausen, Fri Oct 20 09:50:46 2017 +1100) - -# 0.3.0 - Backported matching rules from V3 branch - -* aff5b6c - Added cargo update after to release script after bumping the version (Ronald Holshausen, Fri Oct 20 09:41:09 2017 +1100) -* d990729 - Some code cleanup #20 (Ronald Holshausen, Wed Oct 18 16:32:37 2017 +1100) -* c983c63 - Bump versions to 0.3.0 (Ronald Holshausen, Wed Oct 18 13:54:46 2017 +1100) -* 941d0de - Backported the matching rules from the V3 branch #20 (Ronald Holshausen, Mon Oct 31 16:41:03 2016 +1100) -* 06e92e5 - Refer to local libs using version+paths (Eric Kidd, Tue Oct 3 06:22:23 2017 -0400) -* 7afd258 - Update all the cargo manifest versions and commit the cargo lock files (Ronald Holshausen, Wed May 17 10:37:44 2017 +1000) -* 0f22f14 - bump version to 0.2.3 (Ronald Holshausen, Wed May 17 09:57:56 2017 +1000) -* 7d93682 - Move linux specific bits out of the release script (Ronald Holshausen, Wed May 17 09:56:31 2017 +1000) -* adc1505 - Move linux specific bits out of the release script (Ronald Holshausen, Wed May 17 08:50:12 2017 +1000) - -# 0.2.2 - Bugfix Release - -* be8c299 - Cleanup unused BTreeMap usages and use remote pact dependencies (Anthony Damtsis, Mon May 15 17:09:14 2017 +1000) -* a59fb98 - Migrate remaining pact modules over to serde (Anthony Damtsis, Mon May 15 16:59:04 2017 +1000) -* 84867ac - bump version to 0.2.2 (Ronald Holshausen, Sun Oct 9 16:31:07 2016 +1100) - -# 0.2.1 - Changes required for verifying V2 pacts - -* 770010a - update projects to use the published pact matching lib (Ronald Holshausen, Sun Oct 9 16:25:15 2016 +1100) -* 574e072 - upadte versions for V2 branch and fix an issue with loading JSON bodies encoded as a string (Ronald Holshausen, Sun Oct 9 15:31:57 2016 +1100) -* a21973a - Get the build passing after merge from V1.1 branch (Ronald Holshausen, Sun Oct 9 13:47:09 2016 +1100) -* 341607c - Merge branch 'v1.1-spec' into v2-spec (Ronald Holshausen, Sun Oct 9 12:10:12 2016 +1100) -* 797c9b9 - correct the URLs to the repos (Ronald Holshausen, Sat Oct 8 17:10:56 2016 +1100) -* ca29349 - bump version to 0.1.2 (Ronald Holshausen, Sat Oct 8 17:09:57 2016 +1100) - -# 0.1.1 - Changes required for verifying V1.1 pacts - -* a54abd7 - update the dependencies (Ronald Holshausen, Sat Oct 8 17:01:35 2016 +1100) -* a46dabb - update all references to V1 spec after merge (Ronald Holshausen, Sat Oct 8 16:20:51 2016 +1100) -* 63ae7e4 - get project compiling after merge from V1 branch (Ronald Holshausen, Sat Oct 8 15:53:22 2016 +1100) -* 1d6d4f8 - Merge branch 'v1-spec' into v1.1-spec (Ronald Holshausen, Sat Oct 8 15:44:25 2016 +1100) -* 04d9e5f - update the docs for the pact consumer library (Ronald Holshausen, Mon Sep 26 23:06:19 2016 +1000) -* 7dd04e6 - update the release scripts to point the docs to docs.rs (Ronald Holshausen, Mon Sep 26 21:49:35 2016 +1000) -* d8ef338 - bump version to 0.0.3 (Ronald Holshausen, Mon Sep 26 21:48:37 2016 +1000) - -# 0.2.0 - V2 specification implementation - -* ea9644d - added some V2 matcher tests (Ronald Holshausen, Wed Jul 13 13:35:24 2016 +1000) -* 0e75490 - link to 0.2.0 of the matching library and updated the rust docs (Ronald Holshausen, Tue Jul 12 14:10:02 2016 +1000) -* 534e7a1 - updated readmes and bump versions for the V2 implementation (Ronald Holshausen, Wed Jun 29 10:38:32 2016 +1000) -* f235684 - bump version to 0.1.1 (Ronald Holshausen, Tue Jun 28 21:25:58 2016 +1000) - -# 0.1.0 - V1.1 Specification Implementation - -* 1e7ab5a - use the V1.1 matching library (Ronald Holshausen, Tue Jun 28 21:17:01 2016 +1000) -* 140526d - Implement V1.1 matching (Ronald Holshausen, Tue Jun 28 15:58:35 2016 +1000) -* 4224875 - update readmes and bump versions for V1.1 implementation (Ronald Holshausen, Tue Jun 28 15:05:39 2016 +1000) -* 91d6d62 - removed the v1 from the project path, will use a git branch instead (Ronald Holshausen, Mon Jun 27 22:09:32 2016 +1000) - -# 0.0.2 - Fixes required for verifing pacts - -* a0954f9 - prepare for release (Ronald Holshausen, Mon Sep 26 21:32:05 2016 +1000) -* 40c9e02 - exclude IntelliJ files from publishing (Ronald Holshausen, Mon Sep 26 21:22:35 2016 +1000) -* c3a8a30 - renamed the pact_matching and pact_mock_server directories (Ronald Holshausen, Sun Sep 18 11:07:32 2016 +1000) - -# 0.0.1 - Feature Release - -* 21ca473 - add changelog to libpact_mock_server (Ronald Holshausen, Mon Jun 27 14:59:49 2016 +1000) -* 60077b4 - release script needs to be executable (Ronald Holshausen, Mon Jun 27 14:54:14 2016 +1000) -* 6712635 - added release script for libpact_mock_server (Ronald Holshausen, Mon Jun 27 14:10:20 2016 +1000) -* 0f7965a - updated README for libpact_mock_server (Ronald Holshausen, Mon Jun 27 13:36:37 2016 +1000) -* 518e14a - If the mock server has been shutdown, return a 401 Not Implemented (Ronald Holshausen, Sun Jun 26 11:04:58 2016 +1000) -* 6234bbd - implemented delete on the master server to shut a mock server down (Ronald Holshausen, Sat Jun 25 16:59:39 2016 +1000) -* 4c60f07 - replace rustful with webmachine (Ronald Holshausen, Thu Jun 16 17:31:11 2016 +1000) -* 44daccc - add an optional port number to start the mock server with (Ronald Holshausen, Wed Jun 15 12:40:51 2016 +1000) -* 60bbae5 - handle the result from setting up the logger framework (Ronald Holshausen, Fri Jun 10 11:21:10 2016 +1000) -* 4b8a98a - upgrade hyper to latest version in the mock server library (Ronald Holshausen, Thu Jun 9 21:50:22 2016 +1000) -* b769277 - also add static library as an artifact (Ronald Holshausen, Thu Jun 9 21:22:26 2016 +1000) -* 1c0c7cd - remove rustful from the mock server library (Ronald Holshausen, Thu Jun 9 21:09:32 2016 +1000) -* 7dc4b52 - implemented merging of pact files when writing (Ronald Holshausen, Thu Jun 9 17:34:02 2016 +1000) -* 34fd827 - implement a write_pact exported function to the mock server library (Ronald Holshausen, Thu Jun 9 12:15:01 2016 +1000) -* 769f840 - update the mock server cli readme (Ronald Holshausen, Wed Jun 8 16:05:56 2016 +1000) -* 5f99bb3 - links in readmes are relative to the file they are in (Ronald Holshausen, Wed Jun 8 11:58:05 2016 +1000) -* 0178f8b - change the link to the javascript examples (Ronald Holshausen, Wed Jun 8 11:55:32 2016 +1000) -* 2ba2a08 - correct the link to the javascript examples (Ronald Holshausen, Wed Jun 8 11:46:32 2016 +1000) -* e0130c5 - small tweaks to the libpact_mock_server library readme (Ronald Holshausen, Wed Jun 8 10:46:08 2016 +1000) -* 801f24c - update the github readmes to point to the published rust docs (Ronald Holshausen, Wed Jun 8 10:42:30 2016 +1000) -* 1577eeb - bump the version of libpact_mock_server (Ronald Holshausen, Wed Jun 1 21:59:48 2016 +1000) - -# 0.0.0 - First Release diff --git a/rust/pact_mock_server/Cargo.toml b/rust/pact_mock_server/Cargo.toml deleted file mode 100644 index ccd74eee7..000000000 --- a/rust/pact_mock_server/Cargo.toml +++ /dev/null @@ -1,55 +0,0 @@ -[package] -name = "pact_mock_server" -version = "1.2.7" -authors = ["Ronald Holshausen "] -edition = "2021" -description = "Pact-Rust support library that implements in process mock server" -homepage = "https://www.pact.io" -repository = "https://github.com/pact-foundation/pact-reference/blob/master/rust/pact_mock_server" -readme = "README.md" -keywords = ["testing", "pact", "cdc", "mockserver"] -license = "MIT" -exclude = [ - "*.iml" -] - -[features] -default = ["datetime", "xml", "plugins", "multipart", "tls"] -datetime = ["pact_models/datetime", "pact-plugin-driver?/datetime", "pact_matching/datetime"] # Support for date/time matchers and expressions -xml = ["pact_models/xml", "pact-plugin-driver?/xml", "pact_matching/xml"] # support for matching XML documents -plugins = ["dep:pact-plugin-driver", "pact_matching/plugins"] -multipart = ["pact_matching/multipart"] # suport for MIME multipart bodies -tls = ["dep:hyper-rustls", "dep:rustls", "dep:rustls-pemfile", "dep:tokio-rustls"] - -[dependencies] -anyhow = "1.0.82" -bytes = "1.6.0" -futures = "0.3.30" -hyper = { version = "0.14.28", features = ["full"] } -hyper-rustls = { version = "0.24.2", optional = true } -itertools = "0.12.1" -lazy_static = "1.4.0" -maplit = "1.0.2" -pact_matching = { version = "~1.2.2", path = "../pact_matching", default-features = false } -pact_models = { version = "~1.2.0", default-features = false } -pact-plugin-driver = { version = "~0.6.1", optional = true, default-features = false } -rustls = { version = "~0.21.10", optional = true } -rustls-pemfile = { version = "1.0.4", optional = true } -serde = { version = "1.0.197", features = ["derive"] } -serde_json = "1.0.115" -thiserror = "1.0.58" -tokio = { version = "1.37.0", features = ["full"] } -tokio-rustls = { version = "~0.24.1", optional = true } -tracing = "0.1.40" -tracing-core = "0.1.32" -url = "2.5.0" -uuid = { version = "1.8.0", features = ["v4"] } - -[dev-dependencies] -quickcheck = "1.0.3" -expectest = "0.12.0" -reqwest = { version = "0.12.3", default-features = false, features = ["rustls-tls-native-roots", "blocking", "json"] } -env_logger = "0.11.3" -test-log = "0.2.15" -test-env-log = "0.2.8" -tracing-subscriber = "0.3.18" diff --git a/rust/pact_mock_server/README.md b/rust/pact_mock_server/README.md index fd2cbc632..2ed5b3122 100644 --- a/rust/pact_mock_server/README.md +++ b/rust/pact_mock_server/README.md @@ -1,48 +1,3 @@ # Pact Mock Server library -This library implements the in-process mock server for matching HTTP requests and generating responses from a pact file. -It implements the [V3 Pact specification](https://github.com/pact-foundation/pact-specification/tree/version-3) -and [V4 Pact specification](https://github.com/pact-foundation/pact-specification/tree/version-4). - -[Online rust docs](https://docs.rs/pact_mock_server/latest/pact_mock_server/) - -All the exported functions using C bindings for controlling the mock server are now found in the [pact_ffi module](https://github.com/pact-foundation/pact-reference/tree/master/rust/pact_ffi). - -## [create_mock_server](https://docs.rs/pact_mock_server/latest/pact_mock_server/fn.create_mock_server.html) - -Creates a mock server. Requires the pact JSON as a string as well as the port for the mock server to run on. A value of -0 for the port will result in a port being allocated by the operating system. The port of the mock server is returned. - -## [mock_server_matched](https://docs.rs/pact_mock_server/latest/pact_mock_server/fn.mock_server_matched.html) - -Simple function that returns a boolean value given the port number of the mock service. This value will be true if all -the expectations of the pact that the mock server was created with have been met. It will return false if any request did -not match, an un-recognised request was received or an expected request was not received. - -## [mock_server_mismatches](https://docs.rs/pact_mock_server/latest/pact_mock_server/fn.mock_server_mismatches.html) - -This returns all the mismatches, un-expected requests and missing requests in JSON format, given the port number of the -mock server. - -## [shutdown_mock_server](https://docs.rs/pact_mock_server/latest/pact_mock_server/fn.shutdown_mock_server.html) - -Shuts down the mock server with the provided port. Returns a boolean value to indicate if the mock server was successfully shut down. - -## [write_pact_file](https://docs.rs/pact_mock_server/latest/pact_mock_server/fn.write_pact_file.html) - -Trigger a mock server to write out its pact file. This function should be called if all the consumer tests have passed. -The directory to write the file to is passed as the second parameter. If None is passed in, the current working -directory is used. If overwrite is true, the file will be overwritten with the contents of the current pact. Otherwise -it will be merged with any existing pact file. - -Returns Ok if the pact file was successfully written. Returns an Err if the file can not be written, or there is no -mock server running on that port. - -## Crate features -All features are enabled by default - -* `datetime`: Enables support of date and time expressions and generators. -* `xml`: Enables support for parsing XML documents. -* `plugins`: Enables support for using plugins. -* `multipart`: Enables support for MIME multipart bodies. -* `tls`: Enables support for mock servers using TLS. This will add the following dependencies: hyper-rustls, rustls, rustls-pemfile, tokio-rustls. +Moved to https://github.com/pact-foundation/pact-core-mock-server/pact_mock_server diff --git a/rust/pact_mock_server/release.groovy b/rust/pact_mock_server/release.groovy deleted file mode 100755 index feac4d3b5..000000000 --- a/rust/pact_mock_server/release.groovy +++ /dev/null @@ -1,113 +0,0 @@ -#!/usr/bin/env groovy -@Grab(group = 'com.github.zafarkhaja', module = 'java-semver', version = '0.9.0') -import com.github.zafarkhaja.semver.Version - -def executeOnShell(String command, Closure closure = null) { - executeOnShell(command, new File(System.properties.'user.dir'), closure) -} - -def executeOnShell(String command, File workingDir, Closure closure = null) { - println command - def processBuilder = new ProcessBuilder(['sh', '-c', command]) - .directory(workingDir) - if (closure) { - processBuilder.redirectErrorStream(true) - } else { - processBuilder.inheritIO() - } - def process = processBuilder.start() - if (closure) { - process.inputStream.eachLine closure - } - process.waitFor() - if (process.exitValue() > 0) { - System.exit(process.exitValue()) - } -} - -void ask(String prompt, String defaultValue = 'Y', Closure cl) { - def promptValue = System.console().readLine(prompt + ' ').trim() - if (promptValue.empty) { - promptValue = defaultValue - } - if (promptValue.toUpperCase() == 'Y') { - cl.call() - } -} - -executeOnShell 'git pull' - -ask('Execute Build?: [Y]') { - executeOnShell 'cargo clean' - executeOnShell 'cargo build' - executeOnShell 'cargo test' -} - -def projectProps = new File('Cargo.toml').text -def versionMatch = projectProps =~ /(?m)version\s*=\s*"(.*)"/ -def version = versionMatch[0][1] - -def prevTag = 'git describe --abbrev=0 --tags --match=libpact_mock_server-*'.execute().text.trim() -def changelog = [] -executeOnShell("git log --pretty='* %h - %s (%an, %ad)' ${prevTag}..HEAD .".toString()) { - println it - changelog << it -} - -def releaseDesc = System.console().readLine('Describe this release: [Bugfix Release]').trim() -if (releaseDesc.empty) { - releaseDesc = 'Bugfix Release' -} - -def releaseVer = System.console().readLine("What is the version for this release?: [$version]").trim() -if (releaseVer.empty) { - releaseVer = version -} - -ask('Update Changelog?: [Y]') { - def changeLogFile = new File('CHANGELOG.md') - def changeLogFileLines = changeLogFile.readLines() - changeLogFile.withPrintWriter() { p -> - p.println(changeLogFileLines[0]) - - p.println() - p.println("# $releaseVer - $releaseDesc") - p.println() - changelog.each { - p.println(it) - } - - changeLogFileLines[1..-1].each { - p.println(it) - } - } - - executeOnShell("git add CHANGELOG.md") - executeOnShell("git commit -m 'update changelog for release $releaseVer'") - executeOnShell("git status") - executeOnShell("git diff HEAD^..HEAD") -} - -ask('Tag and Push commits?: [Y]') { - executeOnShell 'git push' - executeOnShell("git tag libpact_mock_server-v${releaseVer}") - executeOnShell 'git push --tags' -} - -ask('Publish library to crates.io?: [Y]') { - executeOnShell 'cargo package' - executeOnShell 'cargo publish' -} - -def nextVer = Version.valueOf(releaseVer).incrementPatchVersion() -ask("Bump version to $nextVer?: [Y]") { - executeOnShell "sed -i -e 's/^version = \"${releaseVer}\"/version = \"${nextVer}\"/' Cargo.toml" - executeOnShell("cargo update") - executeOnShell("git add Cargo.toml") - executeOnShell("git add ../Cargo.lock") - executeOnShell("git diff --cached") - ask("Commit and push this change?: [Y]") { - executeOnShell("git commit -m 'bump version to $nextVer'") - executeOnShell("git push") - } -} diff --git a/rust/pact_mock_server/src/hyper_server.rs b/rust/pact_mock_server/src/hyper_server.rs deleted file mode 100644 index a64e38977..000000000 --- a/rust/pact_mock_server/src/hyper_server.rs +++ /dev/null @@ -1,523 +0,0 @@ -use std::borrow::BorrowMut; -use std::collections::HashMap; -#[cfg(feature = "tls")] use std::io; -use std::net::SocketAddr; -#[cfg(feature = "tls")] use std::pin::Pin; -use std::sync::{Arc, Mutex}; - -#[cfg(feature = "tls")] use futures::prelude::*; -#[cfg(feature = "tls")] use futures::StreamExt; -#[cfg(feature = "tls")] use futures::task::{Context, Poll}; -use hyper::{Body, Error, Response, Server}; -use hyper::http::header::{HeaderName, HeaderValue}; -use hyper::http::response::Builder as ResponseBuilder; -use hyper::service::make_service_fn; -use hyper::service::service_fn; -use maplit::*; -use pact_models::bodies::OptionalBody; -use pact_models::generators::GeneratorTestMode; -use pact_models::http_parts::HttpPart; -use pact_models::pact::Pact; -use pact_models::query_strings::parse_query_string; -use pact_models::v4::http_parts::HttpRequest; -#[cfg(feature = "tls")] use rustls::ServerConfig; -use serde_json::json; -#[cfg(feature = "tls")] use tokio::net::{TcpListener, TcpStream}; -#[cfg(feature = "tls")] use tokio_rustls::server::TlsStream; -#[cfg(feature = "tls")] use tokio_rustls::TlsAcceptor; -use tracing::{debug, error, info, trace, warn}; - -use pact_matching::logging::LOG_ID; - -use crate::matching::{match_request, MatchResult}; -use crate::mock_server::MockServer; - -#[derive(Debug, Clone)] -enum InteractionError { - RequestHeaderEncodingError, - RequestBodyError, - ResponseHeaderEncodingError, - ResponseBodyError -} - -fn extract_path(uri: &hyper::Uri) -> String { - uri.path_and_query() - .map(|path_and_query| path_and_query.path()) - .unwrap_or("/") - .into() -} - -fn extract_query_string(uri: &hyper::Uri) -> Option>>> { - debug!("Extracting query from uri {:?}", uri); - uri.path_and_query() - .and_then(|path_and_query| { - trace!("path_and_query -> {:?}", path_and_query); - path_and_query.query() - }) - .and_then(|query| parse_query_string(query)) -} - -fn extract_headers(headers: &hyper::HeaderMap) -> Result>>, InteractionError> { - if !headers.is_empty() { - let result: Result>, InteractionError> = headers.keys() - .map(|name| -> Result<(String, Vec), InteractionError> { - let values = headers.get_all(name); - let parsed_vals: Vec> = values.iter() - .map(|val| val.to_str() - .map(|v| v.to_string()) - .map_err(|err| { - warn!("Failed to parse HTTP header value: {}", err); - InteractionError::RequestHeaderEncodingError - }) - ).collect(); - if parsed_vals.iter().find(|val| val.is_err()).is_some() { - Err(InteractionError::RequestHeaderEncodingError) - } else { - Ok((name.as_str().into(), parsed_vals.iter().cloned() - .map(|val| val.unwrap_or_default()) - .flat_map(|val| val.split(",").map(|v| v.to_string()).collect::>()) - .map(|val| val.trim().to_string()) - .collect())) - } - }) - .collect(); - - result.map(|map| Some(map)) - } else { - Ok(None) - } -} - -fn extract_body(bytes: bytes::Bytes, request: &HttpRequest) -> OptionalBody { - if bytes.len() > 0 { - OptionalBody::Present(bytes, request.content_type(), None) - } else { - OptionalBody::Empty - } -} - -async fn hyper_request_to_pact_request(req: hyper::Request) -> Result { - let method = req.method().to_string(); - let path = extract_path(req.uri()); - let query = extract_query_string(req.uri()); - let headers = extract_headers(req.headers())?; - - let body_bytes = hyper::body::to_bytes(req.into_body()) - .await - .map_err(|_| InteractionError::RequestBodyError)?; - - let request = HttpRequest { - method, - path, - query, - headers, - .. HttpRequest::default() - }; - - Ok(HttpRequest { - body: extract_body(body_bytes, &request), - .. request.clone() - }) -} - -fn set_hyper_headers(builder: &mut ResponseBuilder, headers: &Option>>) -> Result<(), InteractionError> { - let hyper_headers = builder.headers_mut().unwrap(); - match headers { - Some(header_map) => { - for (k, v) in header_map { - for val in v { - // FIXME?: Headers are not sent in "raw" mode. - // Names are converted to lower case and values are parsed. - hyper_headers.append( - HeaderName::from_bytes(k.as_bytes()) - .map_err(|err| { - error!("Invalid header name '{}' ({})", k, err); - InteractionError::ResponseHeaderEncodingError - })?, - val.parse::() - .map_err(|err| { - error!("Invalid header value '{}': '{}' ({})", k, val, err); - InteractionError::ResponseHeaderEncodingError - })? - ); - } - } - }, - _ => {} - } - Ok(()) -} - -fn error_body(request: &HttpRequest, error: &String) -> String { - let body = json!({ "error" : format!("{} : {:?}", error, request) }); - body.to_string() -} - -async fn match_result_to_hyper_response( - request: &HttpRequest, - match_result: MatchResult, - mock_server: Arc> -) -> Result, InteractionError> { - let (context, cors_preflight) = { - let ms = mock_server.lock().unwrap(); - ( - hashmap!{ - "mockServer" => json!({ - "url": ms.url(), - "port": ms.port - }) - }, - ms.config.cors_preflight - ) - }; - - let origin = match request.headers.clone() { - Some(ref h) => h.iter() - .find(|kv| kv.0.to_lowercase() == "origin") - .map(|kv| kv.1.clone().join(", ")).unwrap_or("*".to_string()), - None => "*".to_string() - }; - - match match_result { - MatchResult::RequestMatch(_, ref response, _) => { - debug!("Test context = {:?}", context); - let response = pact_matching::generate_response(response, &GeneratorTestMode::Consumer, &context).await; - info!("Request matched, sending response"); - if response.has_text_body() { - debug!( - " - ---------------------------------------------------------------------------------------- - status: {} - headers: {:?} - body: {} '{}' - ---------------------------------------------------------------------------------------- - ", response.status, response.headers, response.body, response.body.display_string() - ); - } else { - debug!( - " - ---------------------------------------------------------------------------------------- - status: {} - headers: {:?} - body: {} - ---------------------------------------------------------------------------------------- - ", response.status, response.headers, response.body - ); - } - - let mut builder = Response::builder() - .status(response.status) - .header(hyper::header::ACCESS_CONTROL_ALLOW_ORIGIN, &origin) - .header(hyper::header::ACCESS_CONTROL_ALLOW_HEADERS, "*") - .header(hyper::header::ACCESS_CONTROL_ALLOW_METHODS, "GET, HEAD, POST, PUT, DELETE, CONNECT, OPTIONS, TRACE, PATCH") - .header(hyper::header::ACCESS_CONTROL_EXPOSE_HEADERS, "Location, Link") - .header(hyper::header::ACCESS_CONTROL_ALLOW_CREDENTIALS, "true"); - - set_hyper_headers(&mut builder, &response.headers)?; - - builder.body(match response.body { - OptionalBody::Present(ref s, _, _) => Body::from(s.clone()), - _ => Body::empty() - }) - .map_err(|_| InteractionError::ResponseBodyError) - }, - _ => { - debug!("Request did not match: {}", match_result); - if cors_preflight && request.method.to_uppercase() == "OPTIONS" { - info!("Responding to CORS pre-flight request"); - let cors_headers = match request.headers.clone() { - Some(ref h) => h.iter() - .find(|kv| kv.0.to_lowercase() == "access-control-request-headers") - .map(|kv| kv.1.clone().join(", ") + ", *").unwrap_or("*".to_string()), - None => "*".to_string() - }; - - Response::builder() - .status(204) - .header(hyper::header::ACCESS_CONTROL_ALLOW_ORIGIN, &origin) - .header(hyper::header::ACCESS_CONTROL_ALLOW_METHODS, "GET, HEAD, POST, PUT, DELETE, CONNECT, OPTIONS, TRACE, PATCH") - .header(hyper::header::ACCESS_CONTROL_ALLOW_HEADERS, cors_headers) - .header(hyper::header::ACCESS_CONTROL_EXPOSE_HEADERS, "Location, Link") - .header(hyper::header::ACCESS_CONTROL_ALLOW_CREDENTIALS, "true") - .body(Body::empty()) - .map_err(|_| InteractionError::ResponseBodyError) - } else { - Response::builder() - .status(500) - .header(hyper::header::ACCESS_CONTROL_ALLOW_ORIGIN, "*") - .header(hyper::header::CONTENT_TYPE, "application/json; charset=utf-8") - .header("X-Pact", match_result.match_key()) - .body(Body::from(error_body(&request, &match_result.match_key()))) - .map_err(|_| InteractionError::ResponseBodyError) - } - } - } -} - -async fn handle_request( - req: hyper::Request, - pact: Arc, - matches: Arc>>, - mock_server: Arc> -) -> Result, InteractionError> { - debug!("Creating pact request from hyper request"); - - { - let mut guard = mock_server.lock().unwrap(); - let mock_server = guard.borrow_mut(); - mock_server.metrics.requests = mock_server.metrics.requests + 1; - mock_server.metrics.requests_by_path.entry(req.uri().path().to_string()) - .and_modify(|e| *e += 1) - .or_insert(1); - } - - let pact_request = hyper_request_to_pact_request(req).await?; - info!("Received request {} {}", pact_request.method, pact_request.path); - if pact_request.has_text_body() { - debug!( - " - ---------------------------------------------------------------------------------------- - method: {} - path: {} - query: {:?} - headers: {:?} - body: {} '{}' - ---------------------------------------------------------------------------------------- - ", - pact_request.method, pact_request.path, pact_request.query, pact_request.headers, - pact_request.body, pact_request.body.display_string() - ); - } else { - debug!( - " - ---------------------------------------------------------------------------------------- - method: {} - path: {} - query: {:?} - headers: {:?} - body: {} - ---------------------------------------------------------------------------------------- - ", - pact_request.method, pact_request.path, pact_request.query, pact_request.headers, - pact_request.body - ); - } - - // This unwrap is safe, as all pact models can be upgraded to V4 format - let v4_pact = pact.as_v4_pact().unwrap(); - let match_result = match_request(&pact_request, &v4_pact).await; - - matches.lock().unwrap().push(match_result.clone()); - - match_result_to_hyper_response(&pact_request, match_result, mock_server).await -} - -// TODO: Should instead use some form of X-Pact headers -fn handle_mock_request_error(result: Result, InteractionError>) -> Result, Error> { - match result { - Ok(response) => Ok(response), - Err(error) => { - let response = match error { - InteractionError::RequestHeaderEncodingError => Response::builder() - .status(400) - .body(Body::from("Found an invalid header encoding")), - InteractionError::RequestBodyError => Response::builder() - .status(500) - .body(Body::from("Could not process request body")), - InteractionError::ResponseBodyError => Response::builder() - .status(500) - .body(Body::from("Could not process response body")), - InteractionError::ResponseHeaderEncodingError => Response::builder() - .status(500) - .body(Body::from("Could not set response header")) - }; - Ok(response.unwrap()) - } - } -} - -// Create and bind the server, but do not start it. -// Returns a future that drives the server. -// The reason that the function itself is still async (even if it performs -// no async operations) is that it needs a tokio context to be able to call try_bind. -pub(crate) async fn create_and_bind( - pact: Box, - addr: SocketAddr, - shutdown: impl std::future::Future, - matches: Arc>>, - mock_server: Arc>, - mock_server_id: &String -) -> Result<(impl std::future::Future, SocketAddr), hyper::Error> { - let pact = pact.arced(); - let ms_id = Arc::new(mock_server_id.clone()); - - let server = Server::try_bind(&addr)? - .serve(make_service_fn(move |_| { - let pact = pact.clone(); - let matches = matches.clone(); - let mock_server = mock_server.clone(); - let mock_server_id = ms_id.clone(); - - LOG_ID.scope(mock_server_id.to_string(), async move { - Ok::<_, hyper::Error>( - service_fn(move |req| { - let pact = pact.clone(); - let matches = matches.clone(); - let mock_server = mock_server.clone(); - let mock_server_id = mock_server_id.clone(); - - LOG_ID.scope(mock_server_id.to_string(), async move { - handle_mock_request_error( - handle_request(req, pact, matches, mock_server).await - ) - }) - }) - ) - }) - })); - - let socket_addr = server.local_addr(); - - Ok(( - // This is the future that drives the server: - async { - let _ = server - .with_graceful_shutdown(shutdown) - .await; - }, - socket_addr - )) -} - -// Taken from https://github.com/ctz/hyper-rustls/blob/master/examples/server.rs -#[cfg(feature = "tls")] -struct HyperAcceptor { - stream: Pin, io::Error>> + Send>> -} - -#[cfg(feature = "tls")] -impl hyper::server::accept::Accept for HyperAcceptor { - type Conn = TlsStream; - type Error = io::Error; - - fn poll_accept( - mut self: Pin<&mut Self>, - cx: &mut Context, - ) -> Poll>> { - self.as_mut().stream.poll_next_unpin(cx) - } -} - -#[cfg(feature = "tls")] -pub(crate) async fn create_and_bind_tls( - pact: Box, - addr: SocketAddr, - shutdown: impl std::future::Future, - matches: Arc>>, - tls_cfg: ServerConfig, - mock_server: Arc> -) -> Result<(impl std::future::Future, SocketAddr), io::Error> { - let tcp = TcpListener::bind(&addr).await?; - let socket_addr = tcp.local_addr()?; - let tls_acceptor = Arc::new(TlsAcceptor::from(Arc::new(tls_cfg))); - let tls_stream = stream::unfold((Arc::new(tcp), tls_acceptor.clone()), |(listener, acceptor)| { - async move { - let (socket, _) = listener.accept().await.map_err(|err| { - error!("Failed to accept TLS connection - {:?}", err); - err - }).ok()?; - let stream = acceptor.accept(socket); - Some((stream.await, (listener.clone(), acceptor.clone()))) - } - }); - - let pact = pact.arced(); - let server = Server::builder(HyperAcceptor { - stream: tls_stream.boxed() - }) - .serve(make_service_fn(move |_| { - let pact = pact.clone(); - let matches = matches.clone(); - let mock_server = mock_server.clone(); - - async { - Ok::<_, hyper::Error>( - service_fn(move |req| { - let pact = pact.clone(); - let matches = matches.clone(); - let mock_server = mock_server.clone(); - - async { - handle_mock_request_error( - handle_request(req, pact, matches, mock_server).await - ) - } - }) - ) - } - })); - - Ok(( - // This is the future that drives the server: - async { - let _ = server - .with_graceful_shutdown(shutdown) - .await; - }, - socket_addr - )) -} - -#[cfg(test)] -mod tests { - use expectest::expect; - use expectest::prelude::*; - use hyper::header::{ACCEPT, CONTENT_TYPE, USER_AGENT}; - use hyper::HeaderMap; - use pact_models::prelude::RequestResponsePact; - - use super::*; - - #[tokio::test] - async fn can_fetch_results_on_current_thread() { - let (shutdown_tx, shutdown_rx) = futures::channel::oneshot::channel(); - let matches = Arc::new(Mutex::new(vec![])); - - let (future, _) = create_and_bind( - RequestResponsePact::default().boxed(), - ([0, 0, 0, 0], 0 as u16).into(), - async { - shutdown_rx.await.ok(); - }, - matches.clone(), - Arc::new(Mutex::new(MockServer::default())), - &String::default() - ).await.unwrap(); - - let join_handle = tokio::task::spawn(future); - - shutdown_tx.send(()).unwrap(); - - // Server has shut down, now flush the server future from runtime - join_handle.await.unwrap(); - - // 0 matches have been produced - let all_matches = matches.lock().unwrap().clone(); - assert_eq!(all_matches, vec![]); - } - - #[test] - fn handle_hyper_headers_with_multiple_values() { - let mut headers = HeaderMap::new(); - headers.append(ACCEPT, "application/xml, application/json".parse().unwrap()); - headers.append(USER_AGENT, "test".parse().unwrap()); - headers.append(USER_AGENT, "test2".parse().unwrap()); - headers.append(CONTENT_TYPE, "text/plain".parse().unwrap()); - let result = extract_headers(&headers); - expect!(result).to(be_ok().value(Some(hashmap! { - "accept".to_string() => vec!["application/xml".to_string(), "application/json".to_string()], - "user-agent".to_string() => vec!["test".to_string(), "test2".to_string()], - "content-type".to_string() => vec!["text/plain".to_string()] - }))); - } -} diff --git a/rust/pact_mock_server/src/lib.rs b/rust/pact_mock_server/src/lib.rs deleted file mode 100644 index 6fb61c38a..000000000 --- a/rust/pact_mock_server/src/lib.rs +++ /dev/null @@ -1,499 +0,0 @@ -//! The `pact_mock_server` crate provides the in-process mock server for mocking HTTP requests -//! and generating responses based on a pact file. It implements the -//! [V3 Pact specification](https://github.com/pact-foundation/pact-specification/tree/version-3) -//! and [V4 Pact specification](https://github.com/pact-foundation/pact-specification/tree/version-4). -//! -//! The exported functions using C bindings for controlling the mock server now live in the `pact_mock_server_ffi` -//! crate. -//! -//! ## Crate features -//! All features are enabled by default -//! -//! * `datetime`: Enables support of date and time expressions and generators. -//! * `xml`: Enables support for parsing XML documents. -//! * `plugins`: Enables support for using plugins. -//! * `multipart`: Enables support for MIME multipart bodies. -//! * `tls`: Enables support for mock servers using TLS. This will add the following dependencies: hyper-rustls, rustls, rustls-pemfile, tokio-rustls. - -#![warn(missing_docs)] - -#[cfg(feature = "plugins")] use std::path::PathBuf; -use std::sync::Mutex; - -#[cfg(feature = "plugins")] use anyhow::anyhow; -use itertools::Either; -#[cfg(feature = "plugins")] use itertools::Itertools; -use lazy_static::*; -#[cfg(feature = "plugins")] use maplit::hashmap; -use pact_models::pact::{load_pact_from_json, Pact}; -#[cfg(feature = "plugins")] use pact_models::pact::{ReadWritePact, write_pact}; -#[cfg(feature = "plugins")] use pact_models::PactSpecification; -#[cfg(feature = "plugins")] use pact_plugin_driver::catalogue_manager; -#[cfg(feature = "plugins")] use pact_plugin_driver::catalogue_manager::{ - CatalogueEntry, - CatalogueEntryProviderType, - CatalogueEntryType, - register_core_entries -}; -#[cfg(feature = "plugins")] use pact_plugin_driver::plugin_manager::get_mock_server_results; -#[cfg(feature = "tls")] use rustls::ServerConfig; -use serde_json::json; -#[allow(unused_imports)] use tracing::{error, info, warn}; -use uuid::Uuid; - -use crate::mock_server::{MockServer, MockServerConfig}; -use crate::server_manager::{PluginMockServer, ServerManager}; - -pub mod matching; -pub mod mock_server; -pub mod server_manager; -mod hyper_server; -#[cfg(feature = "tls")] pub mod tls; -mod utils; - -/// Mock server errors -#[derive(thiserror::Error, Debug)] -pub enum MockServerError { - /// Invalid Pact Json - #[error("Invalid Pact JSON")] - InvalidPactJson, - /// Failed to start the mock server - #[error("Failed to start the mock server")] - MockServerFailedToStart -} - -lazy_static! { - /// - /// A global thread-safe, "init-on-demand" reference to a server manager. - /// When the server manager is initialized, it starts a separate thread on which - /// to serve requests. - /// - pub static ref MANAGER: Mutex> = Mutex::new(Option::None); -} - -#[cfg(feature = "plugins")] -lazy_static! { -/// Mock server entries to add to the plugin catalogue - static ref MOCK_SERVER_CATALOGUE_ENTRIES: Vec = { - let mut entries = vec![]; - entries.push(CatalogueEntry { - entry_type: CatalogueEntryType::TRANSPORT, - provider_type: CatalogueEntryProviderType::CORE, - plugin: None, - key: "http".to_string(), - values: hashmap!{} - }); - entries.push(CatalogueEntry { - entry_type: CatalogueEntryType::TRANSPORT, - provider_type: CatalogueEntryProviderType::CORE, - plugin: None, - key: "https".to_string(), - values: hashmap!{} - }); - entries - }; -} - -/// Sets up all the core catalogue entries for mock servers -pub fn configure_core_catalogue() { - #[cfg(feature = "plugins")] register_core_entries(MOCK_SERVER_CATALOGUE_ENTRIES.as_ref()); -} - -/// Starts a mock server with the given ID, pact and port number. The ID needs to be unique. A port -/// number of 0 will result in an auto-allocated port by the operating system. Returns the port -/// that the mock server is running on wrapped in a `Result`. -/// -/// * `id` - Unique ID for the mock server. -/// * `pact` - Pact model to use for the mock server. -/// * `addr` - Socket address that the server should listen on. -/// -/// # Errors -/// -/// An error with a message will be returned in the following conditions: -/// -/// - If a mock server is not able to be started -pub fn start_mock_server( - id: String, - pact: Box, - addr: std::net::SocketAddr -) -> Result { - start_mock_server_with_config(id, pact, addr, MockServerConfig::default()) -} - -/// Starts a mock server with the given ID, pact and port number. The ID needs to be unique. A port -/// number of 0 will result in an auto-allocated port by the operating system. Returns the port -/// that the mock server is running on wrapped in a `Result`. -/// -/// * `id` - Unique ID for the mock server. -/// * `pact` - Pact model to use for the mock server. -/// * `addr` - Socket address that the server should listen on. -/// * `config` - Configuration for the mock server -/// -/// # Errors -/// -/// An error with a message will be returned in the following conditions: -/// -/// - If a mock server is not able to be started -pub fn start_mock_server_with_config( - id: String, - pact: Box, - addr: std::net::SocketAddr, - config: MockServerConfig -) -> Result { - configure_core_catalogue(); - pact_matching::matchers::configure_core_catalogue(); - - MANAGER.lock().unwrap() - .get_or_insert_with(ServerManager::new) - .start_mock_server_with_addr(id, pact, addr, config) - .map(|addr| addr.port() as i32) -} - -/// Starts a TLS mock server with the given ID, pact and port number. The ID needs to be unique. A port -/// number of 0 will result in an auto-allocated port by the operating system. Returns the port -/// that the mock server is running on wrapped in a `Result`. -/// -/// * `id` - Unique ID for the mock server. -/// * `pact` - Pact model to use for the mock server. -/// * `addr` - Socket address that the server should listen on. -/// * `tls` - TLS config. -/// -/// # Errors -/// -/// An error with a message will be returned in the following conditions: -/// -/// - If a mock server is not able to be started -#[cfg(feature = "tls")] -pub fn start_tls_mock_server( - id: String, - pact: Box, - addr: std::net::SocketAddr, - tls: &ServerConfig -) -> Result { - start_tls_mock_server_with_config(id, pact, addr, tls, MockServerConfig::default()) -} - -/// Starts a TLS mock server with the given ID, pact and port number. The ID needs to be unique. A port -/// number of 0 will result in an auto-allocated port by the operating system. Returns the port -/// that the mock server is running on wrapped in a `Result`. -/// -/// * `id` - Unique ID for the mock server. -/// * `pact` - Pact model to use for the mock server. -/// * `addr` - Socket address that the server should listen on. -/// * `tls` - TLS config. -/// * `config` - Configuration for the mock server -/// -/// # Errors -/// -/// An error with a message will be returned in the following conditions: -/// -/// - If a mock server is not able to be started -#[cfg(feature = "tls")] -pub fn start_tls_mock_server_with_config( - id: String, - pact: Box, - addr: std::net::SocketAddr, - tls: &ServerConfig, - config: MockServerConfig -) -> Result { - configure_core_catalogue(); - pact_matching::matchers::configure_core_catalogue(); - - MANAGER.lock().unwrap() - .get_or_insert_with(ServerManager::new) - .start_tls_mock_server_with_addr(id, pact, addr, tls, config) - .map(|addr| addr.port() as i32) -} - -/// Starts a mock server for the provided transport. The ID needs to be unique. A port -/// number of 0 will result in an auto-allocated port by the operating system. Returns the port -/// that the mock server is running on wrapped in a `Result`. -/// -/// * `id` - Unique ID for the mock server. -/// * `pact` - Pact model to use for the mock server. -/// * `addr` - Socket address that the server should listen on. -/// * `transport` - Transport to use for the mock server. -/// * `config` - Configuration for the mock server. Transport specific configuration must be specified in the `transport_config` field. -/// -/// Requires the plugins feature to be enabled. -/// -/// # Errors -/// -/// An error will be returned if the mock server is not able to be started or the transport is not known. -#[cfg(feature = "plugins")] -pub fn start_mock_server_for_transport( - id: String, - pact: Box, - addr: std::net::SocketAddr, - transport: &str, - config: MockServerConfig -) -> anyhow::Result { - configure_core_catalogue(); - pact_matching::matchers::configure_core_catalogue(); - - let key = format!("transport/{}", transport); - let transport_entry = catalogue_manager::lookup_entry(key.as_str()) - .ok_or_else(|| anyhow!("Transport '{}' is not a known transport", transport))?; - - MANAGER.lock().unwrap() - .get_or_insert_with(ServerManager::new) - .start_mock_server_for_transport(id, pact, addr, &transport_entry, config) - .map(|addr| addr.port() as i32) -} - -/// Creates a mock server. Requires the pact JSON as a string as well as the port for the mock -/// server to run on. A value of 0 for the port will result in a -/// port being allocated by the operating system. The port of the mock server is returned. -/// -/// * `pact_json` - Pact in JSON format -/// * `addr` - Socket address to listen on -pub fn create_mock_server( - pact_json: &str, - addr: std::net::SocketAddr -) -> anyhow::Result { - configure_core_catalogue(); - pact_matching::matchers::configure_core_catalogue(); - - match serde_json::from_str(pact_json) { - Ok(pact_json) => { - let pact = load_pact_from_json("", &pact_json)?; - start_mock_server(Uuid::new_v4().to_string(), pact, addr) - .map_err(|err| { - error!("Could not start mock server: {}", err); - MockServerError::MockServerFailedToStart.into() - }) - }, - Err(err) => { - error!("Could not parse pact json: {}", err); - Err(MockServerError::InvalidPactJson.into()) - } - } -} - -/// Creates a TLS mock server. Requires the pact JSON as a string as well as the port for the mock -/// server to run on. A value of 0 for the port will result in a -/// port being allocated by the operating system. The port of the mock server is returned. -/// -/// * `pact_json` - Pact in JSON format -/// * `addr` - Socket address to listen on -/// * `tls` - TLS config -#[cfg(feature = "tls")] -pub fn create_tls_mock_server( - pact_json: &str, - addr: std::net::SocketAddr, - tls: &ServerConfig -) -> anyhow::Result { - match serde_json::from_str(pact_json) { - Ok(pact_json) => { - let pact = load_pact_from_json("", &pact_json)?; - start_tls_mock_server(Uuid::new_v4().to_string(), pact, addr, tls) - .map_err(|err| { - error!("Could not start mock server: {}", err); - MockServerError::MockServerFailedToStart.into() - }) - }, - Err(err) => { - error!("Could not parse pact json: {}", err); - Err(MockServerError::InvalidPactJson.into()) - } - } -} - -/// Function to check if a mock server has matched all its requests. The port number is -/// passed in, and if all requests have been matched, true is returned. False is returned if there -/// is no mock server on the given port, or if any request has not been successfully matched. -/// -/// Note that for mock servers provided by plugins, if the call to the plugin fails, a value of false -/// will also be returned. -pub fn mock_server_matched(mock_server_port: i32) -> bool { - MANAGER.lock().unwrap() - .get_or_insert_with(ServerManager::new) - .find_mock_server_by_port(mock_server_port as u16, &|_server_manager, _, mock_server| { - match mock_server { - Either::Left(mock_server) => mock_server.mismatches().is_empty(), - Either::Right(_plugin_mock_server) => { - #[cfg(feature = "plugins")] - { - let results = _server_manager.exec_async(get_mock_server_results(&_plugin_mock_server.mock_server_details)); - match results { - Ok(results) => results.is_empty(), - Err(err) => { - error!("Request to plugin to get matching results failed - {}", err); - false - } - } - } - - #[cfg(not(feature = "plugins"))] - { - error!("Plugin mock server support requires the plugins feature to be enabled"); - false - } - } - } - }) - .unwrap_or(false) -} - -/// Gets all the mismatches from a mock server in JSON format. The port number of the mock -/// server is passed in, and the results are returned in JSON format as a String. -/// -/// If there is no mock server with the provided port number, `None` is returned. -/// -/// For mock servers provided by plugins, if the call to the plugin fails, a JSON value with an -/// error attribute will be returned. -pub fn mock_server_mismatches(mock_server_port: i32) -> Option { - MANAGER.lock().unwrap() - .get_or_insert_with(ServerManager::new) - .find_mock_server_by_port(mock_server_port as u16, &|_manager, _, mock_server| { - match mock_server { - Either::Left(mock_server) => { - let mismatches = mock_server.mismatches().iter() - .map(|mismatch| mismatch.to_json() ) - .collect::>(); - json!(mismatches).to_string() - } - Either::Right(_plugin_mock_server) => { - #[cfg(feature = "plugins")] - { - let results = _manager.exec_async(get_mock_server_results(&_plugin_mock_server.mock_server_details)); - match results { - Ok(results) => { - json!(results.iter().map(|item| { - json!({ - "path": item.path, - "error": item.error, - "mismatches": item.mismatches.iter().map(|mismatch| { - json!({ - "expected": mismatch.expected, - "actual": mismatch.actual, - "mismatch": mismatch.mismatch, - "path": mismatch.path, - "diff": mismatch.diff.clone().unwrap_or_default() - }) - }).collect_vec() - }) - }).collect_vec()) - }, - Err(err) => { - error!("Request to plugin to get matching results failed - {}", err); - json!({ "error": format!("Request to plugin to get matching results failed - {}", err) }) - } - }.to_string() - } - - #[cfg(not(feature = "plugins"))] - { - error!("Plugin mock server support requires the plugins feature to be enabled"); - json!({ "error": "Plugin mock server support requires the plugins feature to be enabled" }).to_string() - } - } - } - }) -} - -/// Write Pact File Errors -pub enum WritePactFileErr { - /// IO Error occurred - IOError, - /// No mock server was running on the port - NoMockServer -} - -/// Trigger a mock server to write out its pact file. This function should -/// be called if all the consumer tests have passed. The directory to write the file to is passed -/// as the second parameter. If `None` is passed in, the current working directory is used. -/// If overwrite is true, the file will be overwritten with the contents of the current pact. -/// Otherwise it will be merged with any existing pact file. -/// -/// Returns `Ok` if the pact file was successfully written. Returns an `Err` if the file can -/// not be written, or there is no mock server running on that port. -pub fn write_pact_file( - mock_server_port: i32, - directory: Option, - overwrite: bool -) -> Result<(), WritePactFileErr> { - let opt_result = MANAGER.lock().unwrap() - .get_or_insert_with(ServerManager::new) - .find_mock_server_by_port(mock_server_port as u16, &|_, _, ms| { - match ms { - Either::Left(mock_server) => { - mock_server.write_pact(&directory, overwrite) - .map(|_| ()) - .map_err(|err| { - error!("Failed to write pact to file - {}", err); - WritePactFileErr::IOError - }) - } - Either::Right(_plugin_mock_server) => { - #[cfg(feature = "plugins")] - { - let mut pact = _plugin_mock_server.pact.clone(); - pact.add_md_version("mockserver", option_env!("CARGO_PKG_VERSION").unwrap_or("unknown")); - let pact_file_name = pact.default_file_name(); - let filename = match directory { - Some(ref path) => { - let mut path = PathBuf::from(path); - path.push(pact_file_name); - path - }, - None => PathBuf::from(pact_file_name) - }; - - info!("Writing pact out to '{}'", filename.display()); - match write_pact(pact.boxed(), filename.as_path(), PactSpecification::V4, overwrite) { - Ok(_) => Ok(()), - Err(err) => { - warn!("Failed to write pact to file - {}", err); - Err(WritePactFileErr::IOError) - } - } - } - - #[cfg(not(feature = "plugins"))] - { - error!("Plugin mock server support requires the plugins feature to be enabled"); - Err(WritePactFileErr::NoMockServer) - } - } - } - }); - - match opt_result { - Some(result) => result, - None => { - error!("No mock server running on port {}", mock_server_port); - Err(WritePactFileErr::NoMockServer) - } - } -} - -/// Shuts down the mock server with the provided port. Returns a boolean value to indicate if -/// the mock server was successfully shut down. -pub fn shutdown_mock_server(mock_server_port: i32) -> bool { - MANAGER.lock().unwrap() - .get_or_insert_with(ServerManager::new) - .shutdown_mock_server_by_port(mock_server_port as u16) -} - -/// Find a mock server by port number and and map it using supplied function if found. Returns the -/// result of the function call wrapped in a Some. Returns a None if the mock server was not found. -pub fn find_mock_server_by_port( - port: u16, - f: &dyn Fn(&ServerManager, &String, Either<&MockServer, &PluginMockServer>) -> R -) -> Option { - MANAGER.lock().unwrap() - .get_or_insert_with(ServerManager::new) - .find_mock_server_by_port(port, f) -} - -/// Shuts down the mock server with the provided ID. Returns a boolean value to indicate if -/// the mock server was successfully shut down. -pub fn shutdown_mock_server_by_id(id: &str) -> bool { - MANAGER.lock().unwrap() - .get_or_insert_with(ServerManager::new) - .shutdown_mock_server_by_id(id.to_string()) -} - -#[cfg(test)] -mod tests; diff --git a/rust/pact_mock_server/src/matching.rs b/rust/pact_mock_server/src/matching.rs deleted file mode 100644 index 86ed189f3..000000000 --- a/rust/pact_mock_server/src/matching.rs +++ /dev/null @@ -1,147 +0,0 @@ -//! -//! The matching module defines how a request is matched -//! against a list of potential interactions. -//! - -use std::fmt::{Debug, Display, Formatter}; - -use futures::prelude::*; -use itertools::Itertools; -use serde_json::json; - -use pact_matching::{Mismatch, RequestMatchResult}; -use pact_models::interaction::Interaction; -use pact_models::PactSpecification; -use pact_models::prelude::Pact; -use pact_models::prelude::v4::SynchronousHttp; -use pact_models::v4::http_parts::{HttpRequest, HttpResponse}; -use pact_models::v4::V4InteractionType; -use pact_models::v4::pact::V4Pact; - -/// Enum to define a match result -#[derive(Debug, Clone, PartialEq)] -pub enum MatchResult { - /// Match result where the request was successfully matched. Stores the expected request, - /// response returned and the actual request that was received. - RequestMatch(HttpRequest, HttpResponse, HttpRequest), - /// Match result where there were a number of mismatches. Stores the expected and actual requests, - /// and all the mismatches. - RequestMismatch(HttpRequest, HttpRequest, Vec), - /// Match result where the request was not expected - RequestNotFound(HttpRequest), - /// Match result where an expected request was not received - MissingRequest(HttpRequest) -} - -impl MatchResult { - /// Returns the match key for this mismatch - pub fn match_key(&self) -> String { - match self { - &MatchResult::RequestMatch(_, _, _) => "Request-Matched", - &MatchResult::RequestMismatch(_, _, _) => "Request-Mismatch", - &MatchResult::RequestNotFound(_) => "Unexpected-Request", - &MatchResult::MissingRequest(_) => "Missing-Request" - }.to_string() - } - - /// Returns true if this match result is a `RequestMatch` - pub fn matched(&self) -> bool { - match self { - &MatchResult::RequestMatch(_, _, _) => true, - _ => false - } - } - - /// Returns true if this is an unexpected OPTIONS request - pub fn cors_preflight(&self) -> bool { - match self { - MatchResult::RequestNotFound(req) => req.method == "OPTIONS", - _ => false - } - } - - /// Converts this match result to a `Value` struct - pub fn to_json(&self) -> serde_json::Value { - match self { - MatchResult::RequestMatch(_, _, _) => json!({ "type" : "request-match"}), - MatchResult::RequestMismatch(request, _, mismatches) => mismatches_to_json(request, mismatches), - MatchResult::RequestNotFound(req) => json!({ - "type": "request-not-found", - "method": req.method, - "path": req.path, - "request": req.as_v3_request().to_json(&PactSpecification::V3) - }), - MatchResult::MissingRequest(request) => json!({ - "type": "missing-request", - "method": request.method, - "path": request.path, - "request": request.as_v3_request().to_json(&PactSpecification::V3) - }) - } - } -} - -impl Display for MatchResult { - fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result { - match self { - MatchResult::RequestMatch(request, _, _) => { - write!(f, "Request matched OK - {}", request) - }, - MatchResult::RequestMismatch(request, _, mismatches) => { - write!(f, "Request did not match - {}", request)?; - for (i, mismatch) in mismatches.iter().enumerate() { - write!(f, " {}) {}", i, mismatch)?; - } - Ok(()) - }, - MatchResult::RequestNotFound(request) => { - write!(f, "Request was not expected - {}", request) - }, - MatchResult::MissingRequest(request) => { - write!(f, "Request was not received - {}", request) - } - } - } -} - -fn mismatches_to_json(request: &HttpRequest, mismatches: &Vec) -> serde_json::Value { - json!({ - "type" : "request-mismatch", - "method" : request.method, - "path" : request.path, - "mismatches" : mismatches.iter().map(|m| m.to_json()).collect::() - }) -} - -/// -/// Matches a request against a list of interactions -/// -pub async fn match_request( - req: &HttpRequest, - pact: &V4Pact, -) -> MatchResult { - let interactions = pact.filter_interactions(V4InteractionType::Synchronous_HTTP); - let match_results = futures::stream::iter(interactions) - .filter(|i| future::ready(i.is_request_response())) - .then(|i| async move { - let interaction = i.as_v4_http().unwrap(); - (interaction.clone(), pact_matching::match_request(interaction.request.clone(), - req.clone(), &pact.boxed(), &i).await) - }).collect::>().await; - let mut sorted = match_results.iter().sorted_by(|(_, i1), (_, i2)| { - Ord::cmp(&i2.score(), &i1.score()) - }); - match sorted.next() { - Some((interaction, result)) => { - let request_response_interaction = interaction.as_v4_http().unwrap(); - if result.all_matched() { - MatchResult::RequestMatch(request_response_interaction.request, request_response_interaction.response, req.clone()) - } else if result.method_or_path_mismatch() { - MatchResult::RequestNotFound(req.clone()) - } else { - MatchResult::RequestMismatch(request_response_interaction.request, req.clone(), result.mismatches()) - } - }, - None => MatchResult::RequestNotFound(req.clone()) - } -} diff --git a/rust/pact_mock_server/src/mock_server.rs b/rust/pact_mock_server/src/mock_server.rs deleted file mode 100644 index 729650a62..000000000 --- a/rust/pact_mock_server/src/mock_server.rs +++ /dev/null @@ -1,408 +0,0 @@ -//! -//! This module defines the external interface for controlling one particular -//! instance of a mock server. -//! - -use std::cell::RefCell; -use std::collections::HashMap; -use std::ffi::CString; -use std::ops::DerefMut; -use std::path::PathBuf; -use std::sync::{Arc, Mutex}; -use pact_models::json_utils::json_to_string; - -use pact_models::pact::{Pact, write_pact}; -use pact_models::PactSpecification; -use pact_models::sync_pact::RequestResponsePact; -use pact_models::v4::http_parts::HttpRequest; -#[cfg(feature = "tls")] use rustls::ServerConfig; -use serde::{Deserialize, Serialize}; -use serde_json::{json, Value}; -use tracing::{debug, info, trace, warn}; - -use crate::hyper_server; -use crate::matching::MatchResult; -use crate::utils::json_to_bool; - -/// Mock server configuration -#[derive(Debug, Default, Clone, PartialEq)] -pub struct MockServerConfig { - /// If CORS Pre-Flight requests should be responded to - pub cors_preflight: bool, - /// Pact specification to use - pub pact_specification: PactSpecification, - /// Configuration required for the transport used - pub transport_config: HashMap -} - -impl MockServerConfig { - /// Convert a JSON value into a config struct. This method is tolerant of invalid JSON formats. - pub fn from_json(value: &Value) -> MockServerConfig { - let mut config = MockServerConfig::default(); - - if let Value::Object(map) = value { - for (k, v) in map { - if k == "corsPreflight" { - config.cors_preflight = json_to_bool(v).unwrap_or_default(); - } else if k == "pactSpecification" { - config.pact_specification = PactSpecification::from(json_to_string(v)); - } else { - config.transport_config.insert(k.clone(), v.clone()); - } - } - } - - config - } -} - -/// Mock server scheme -#[derive(Debug, Clone)] -pub enum MockServerScheme { - /// HTTP - HTTP, - /// HTTPS - HTTPS -} - -impl Default for MockServerScheme { - fn default() -> Self { - MockServerScheme::HTTP - } -} - -impl ToString for MockServerScheme { - fn to_string(&self) -> String { - match self { - MockServerScheme::HTTP => "http".into(), - MockServerScheme::HTTPS => "https".into() - } - } -} - -/// Metrics for the mock server -#[derive(Debug, Default, Clone, Serialize, Deserialize, Eq, PartialEq)] -pub struct MockServerMetrics { - /// Total requests - pub requests: usize, - /// Total requests by path - pub requests_by_path: HashMap -} - -/// Struct to represent the "foreground" part of mock server -#[derive(Debug)] -pub struct MockServer { - /// Mock server unique ID - pub id: String, - /// Scheme the mock server is using - pub scheme: MockServerScheme, - /// Port the mock server is running on - pub port: Option, - /// Address the mock server is bound to - pub address: Option, - /// List of resources that need to be cleaned up when the mock server completes - #[deprecated(since = "0.9.1", note = "Resources should be stored on the mock server manager entry")] - pub resources: Vec, - /// Pact that this mock server is based on - pub pact: Box, - /// Receiver of match results - matches: Arc>>, - /// Shutdown signal - shutdown_tx: RefCell>>, - /// Mock server config - pub config: MockServerConfig, - /// Metrics collected by the mock server - pub metrics: MockServerMetrics, - /// Pact spec version to use - pub spec_version: PactSpecification -} - -impl MockServer { - /// Create a new mock server, consisting of its state (self) and its executable server future. - pub async fn new( - id: String, - pact: Box, - addr: std::net::SocketAddr, - config: MockServerConfig - ) -> Result<(Arc>, impl std::future::Future), String> { - let (shutdown_tx, shutdown_rx) = futures::channel::oneshot::channel(); - let matches = Arc::new(Mutex::new(vec![])); - - #[allow(deprecated)] - let mock_server = Arc::new(Mutex::new(MockServer { - id: id.clone(), - port: None, - address: None, - scheme: MockServerScheme::HTTP, - resources: vec![], - pact: pact.boxed(), - matches: matches.clone(), - shutdown_tx: RefCell::new(Some(shutdown_tx)), - config: config.clone(), - metrics: MockServerMetrics::default(), - spec_version: pact_specification(config.pact_specification, pact.specification_version()) - })); - - let (future, socket_addr) = hyper_server::create_and_bind( - pact, - addr, - async { - shutdown_rx.await.ok(); - }, - matches, - mock_server.clone(), - &id - ) - .await - .map_err(|err| format!("Could not start server: {}", err))?; - - { - let mut ms = mock_server.lock().unwrap(); - ms.deref_mut().port = Some(socket_addr.port()); - ms.deref_mut().address = Some(socket_addr.ip().to_string()); - - debug!("Started mock server on {}:{}", socket_addr.ip(), socket_addr.port()); - } - - Ok((mock_server.clone(), future)) - } - - /// Create a new TLS mock server, consisting of its state (self) and its executable server future. - #[cfg(feature = "tls")] - pub async fn new_tls( - id: String, - pact: Box, - addr: std::net::SocketAddr, - tls: &ServerConfig, - config: MockServerConfig - ) -> Result<(Arc>, impl std::future::Future), String> { - let (shutdown_tx, shutdown_rx) = futures::channel::oneshot::channel(); - let matches = Arc::new(Mutex::new(vec![])); - - #[allow(deprecated)] - let mock_server = Arc::new(Mutex::new(MockServer { - id: id.clone(), - port: None, - address: None, - scheme: MockServerScheme::HTTPS, - resources: vec![], - pact: pact.boxed(), - matches: matches.clone(), - shutdown_tx: RefCell::new(Some(shutdown_tx)), - config: config.clone(), - metrics: MockServerMetrics::default(), - spec_version: pact_specification(config.pact_specification, pact.specification_version()) - })); - - let (future, socket_addr) = hyper_server::create_and_bind_tls( - pact, - addr, - async { - shutdown_rx.await.ok(); - }, - matches, - tls.clone(), - mock_server.clone() - ).await.map_err(|err| format!("Could not start server: {}", err))?; - - { - let mut ms = mock_server.lock().unwrap(); - ms.deref_mut().port = Some(socket_addr.port()); - ms.deref_mut().address = Some(socket_addr.ip().to_string()); - - debug!("Started mock server on {}:{}", socket_addr.ip(), socket_addr.port()); - } - - Ok((mock_server.clone(), future)) - } - - /// Send the shutdown signal to the server - pub fn shutdown(&mut self) -> Result<(), String> { - let shutdown_future = &mut *self.shutdown_tx.borrow_mut(); - match shutdown_future.take() { - Some(sender) => { - match sender.send(()) { - Ok(()) => { - debug!("Mock server {} shutdown - {:?}", self.id, self.metrics); - Ok(()) - }, - Err(_) => Err("Problem sending shutdown signal to mock server".into()) - } - }, - _ => Err("Mock server already shut down".into()) - } - } - - /// Converts this mock server to a `Value` struct - pub fn to_json(&self) -> serde_json::Value { - json!({ - "id" : self.id.clone(), - "port" : self.port.unwrap_or_default() as u64, - "address" : self.address.clone().unwrap_or_default(), - "scheme" : self.scheme.to_string(), - "provider" : self.pact.provider().name.clone(), - "status" : if self.mismatches().is_empty() { "ok" } else { "error" }, - "metrics" : self.metrics - }) - } - - /// Returns all collected matches - pub fn matches(&self) -> Vec { - self.matches.lock().unwrap().clone() - } - - /// Returns all the mismatches that have occurred with this mock server - pub fn mismatches(&self) -> Vec { - let matches = self.matches(); - let mismatches = matches.iter() - .filter(|m| !m.matched() && !m.cors_preflight()) - .cloned(); - let requests: Vec = matches.iter().map(|m| { - match m { - MatchResult::RequestMatch(request, _, _) => Some(request), - MatchResult::RequestMismatch(request, _, _) => Some(request), - MatchResult::RequestNotFound(_) => None, - MatchResult::MissingRequest(_) => None - } - }).filter(|o| o.is_some()) - .map(|o| o.unwrap().clone()) - .collect(); - - let interactions = self.pact.interactions(); - let missing = interactions.iter() - .map(|i| i.as_v4_http().unwrap().request) - .filter(|req| !requests.contains(req)) - .map(|req| MatchResult::MissingRequest(req.clone())); - mismatches.chain(missing).collect() - } - - /// Mock server writes its pact out to the provided directory - pub fn write_pact(&self, output_path: &Option, overwrite: bool) -> anyhow::Result<()> { - trace!("write_pact: output_path = {:?}, overwrite = {}", output_path, overwrite); - let pact = if self.pact.is_v4() { - let mut v4_pact = self.pact.as_v4_pact().unwrap_or_default(); - v4_pact.add_md_version("mockserver", option_env!("CARGO_PKG_VERSION").unwrap_or("unknown")); - for interaction in &mut v4_pact.interactions { - interaction.set_transport(Some("http".to_string())); - } - v4_pact.boxed() - } else { - let mut pact = self.pact.boxed(); - pact.add_md_version("mockserver", option_env!("CARGO_PKG_VERSION").unwrap_or("unknown")); - pact - }; - - let pact_file_name = pact.default_file_name(); - let filename = match *output_path { - Some(ref path) => { - let mut path = PathBuf::from(path); - path.push(pact_file_name); - path - }, - None => PathBuf::from(pact_file_name) - }; - - info!("Writing pact out to '{}'", filename.display()); - let specification = match self.spec_version { - PactSpecification::Unknown => PactSpecification::V3, - _ => self.spec_version - }; - match write_pact(pact, filename.as_path(), specification, overwrite) { - Ok(_) => Ok(()), - Err(err) => { - warn!("Failed to write pact to file - {}", err); - Err(err) - } - } - } - - /// Returns the URL of the mock server - pub fn url(&self) -> String { - let addr = self.address.clone().unwrap_or_else(|| "127.0.0.1".to_string()); - match self.port { - Some(port) => format!("{}://{}:{}", self.scheme.to_string(), - if addr == "0.0.0.0" { "127.0.0.1" } else { addr.as_str() }, port), - None => "error(port is not set)".to_string() - } - } -} - -fn pact_specification(spec1: PactSpecification, spec2: PactSpecification) -> PactSpecification { - match spec1 { - PactSpecification::Unknown => spec2, - _ => spec1 - } -} - -impl Clone for MockServer { - /// Make a clone all of the MockServer fields. - /// Note that the clone of the original server cannot be shut down directly. - #[allow(deprecated)] - fn clone(&self) -> MockServer { - MockServer { - id: self.id.clone(), - port: self.port, - address: self.address.clone(), - scheme: self.scheme.clone(), - resources: vec![], - pact: self.pact.boxed(), - matches: self.matches.clone(), - shutdown_tx: RefCell::new(None), - config: self.config.clone(), - metrics: self.metrics.clone(), - spec_version: self.spec_version - } - } -} - -impl Default for MockServer { - #[allow(deprecated)] - fn default() -> Self { - MockServer { - id: "".to_string(), - scheme: Default::default(), - port: None, - address: None, - resources: vec![], - pact: Box::new(RequestResponsePact::default()), - matches: Arc::new(Mutex::new(vec![])), - shutdown_tx: RefCell::new(None), - config: Default::default(), - metrics: Default::default(), - spec_version: Default::default() - } - } -} - -#[cfg(test)] -mod tests { - use expectest::prelude::*; - use maplit::hashmap; - use pact_models::PactSpecification; - use serde_json::{json, Value}; - - use crate::MockServerConfig; - - #[test] - fn test_mock_server_config_from_json() { - expect!(MockServerConfig::from_json(&Value::Null)).to(be_equal_to(MockServerConfig::default())); - expect!(MockServerConfig::from_json(&Value::Array(vec![]))).to(be_equal_to(MockServerConfig::default())); - expect!(MockServerConfig::from_json(&Value::String("s".into()))).to(be_equal_to(MockServerConfig::default())); - expect!(MockServerConfig::from_json(&Value::Bool(true))).to(be_equal_to(MockServerConfig::default())); - expect!(MockServerConfig::from_json(&json!(12334))).to(be_equal_to(MockServerConfig::default())); - - expect!(MockServerConfig::from_json(&json!({ - "corsPreflight": true, - "pactSpecification": "V4", - "tlsKey": "key", - "tlsCertificate": "cert" - }))).to(be_equal_to(MockServerConfig { - cors_preflight: true, - pact_specification: PactSpecification::V4, - transport_config: hashmap! { - "tlsKey".to_string() => json!("key"), - "tlsCertificate".to_string() => json!("cert") - } - })); - } -} diff --git a/rust/pact_mock_server/src/server_manager.rs b/rust/pact_mock_server/src/server_manager.rs deleted file mode 100644 index e8b42321c..000000000 --- a/rust/pact_mock_server/src/server_manager.rs +++ /dev/null @@ -1,449 +0,0 @@ -//! -//! This module defines a manager for holding multiple instances of mock servers. -//! - -use std::collections::BTreeMap; -use std::ffi::CString; -#[cfg(feature = "plugins")] use std::future::Future; -use std::net::SocketAddr; -#[cfg(feature = "plugins")] use std::net::ToSocketAddrs; -use std::sync::{Arc, Mutex}; - -use anyhow::anyhow; -use itertools::Either; -#[cfg(feature = "plugins")] use maplit::hashmap; -use pact_models::pact::Pact; -#[cfg(feature = "plugins")] use pact_models::prelude::v4::V4Pact; -#[cfg(feature = "plugins")] use pact_plugin_driver::catalogue_manager::{CatalogueEntry, CatalogueEntryProviderType}; -#[cfg(feature = "plugins")] use pact_plugin_driver::mock_server::MockServerDetails; -#[cfg(feature = "tls")] use rustls::ServerConfig; -#[cfg(not(feature = "plugins"))] use serde::{Deserialize, Serialize}; -use tracing::{debug, error, trace}; -#[cfg(feature = "plugins")] use url::Url; - -use crate::mock_server::{MockServer, MockServerConfig}; - -/// Mock server that has been provided by a plugin -#[derive(Debug, Clone)] -#[cfg(feature = "plugins")] -pub struct PluginMockServer { - /// Details of the running mock server - pub mock_server_details: MockServerDetails, - /// Catalogue entry for the transport - pub catalogue_entry: CatalogueEntry, - /// Pact for this mock server - pub pact: V4Pact -} - -/// Mock server that has been provided by a plugin (dummy struct) -#[derive(Debug, Clone)] -#[cfg(not(feature = "plugins"))] -pub struct PluginMockServer {} - -/// Dummy Catalogue entry -#[derive(Clone, Debug, Deserialize, Serialize, PartialEq, Eq)] -#[cfg(not(feature = "plugins"))] -pub struct CatalogueEntry {} - -struct ServerEntry { - /// Either a local mock server or a plugin provided one - mock_server: Either>, PluginMockServer>, - /// Port the mock server is running on - port: u16, - /// List of resources that need to be cleaned up when the mock server completes - pub resources: Vec, - join_handle: Option> -} - -/// Struct to represent many mock servers running in a background thread -pub struct ServerManager { - runtime: tokio::runtime::Runtime, - mock_servers: BTreeMap, -} - -impl ServerManager { - /// Construct a new ServerManager for scheduling several instances of mock servers - /// on one tokio runtime. - pub fn new() -> ServerManager { - ServerManager { - runtime: tokio::runtime::Builder::new_multi_thread() - .worker_threads(1) - .enable_all() - .build() - .unwrap(), - mock_servers: BTreeMap::new() - } - } - - /// Start a new server on the runtime - pub fn start_mock_server_with_addr( - &mut self, - id: String, - pact: Box, - addr: SocketAddr, - config: MockServerConfig - ) -> Result { - let (mock_server, future) = - self.runtime.block_on(MockServer::new(id.clone(), pact, addr, config))?; - - let port = { mock_server.lock().unwrap().port.clone() }; - self.mock_servers.insert( - id, - ServerEntry { - mock_server: Either::Left(mock_server), - port: port.unwrap_or_else(|| addr.port()), - resources: vec![], - join_handle: Some(self.runtime.spawn(future)) - }, - ); - - match port { - Some(port) => Ok(SocketAddr::new(addr.ip(), port)), - None => Ok(addr) - } - } - - /// Start a new TLS server on the runtime - #[cfg(feature = "tls")] - pub fn start_tls_mock_server_with_addr( - &mut self, - id: String, - pact: Box, - addr: SocketAddr, - tls_config: &ServerConfig, - config: MockServerConfig - ) -> Result { - let (mock_server, future) = - self.runtime.block_on(MockServer::new_tls(id.clone(), pact, addr, tls_config, config))?; - - let port = { mock_server.lock().unwrap().port.clone() }; - self.mock_servers.insert( - id, - ServerEntry { - mock_server: Either::Left(mock_server), - port: port.unwrap_or_else(|| addr.port()), - resources: vec![], - join_handle: Some(self.runtime.spawn(future)) - } - ); - - match port { - Some(port) => Ok(SocketAddr::new(addr.ip(), port)), - None => Ok(addr) - } - } - - /// Start a new server on the runtime - pub fn start_mock_server( - &mut self, - id: String, - pact: Box, - port: u16, - config: MockServerConfig - ) -> Result { - self.start_mock_server_with_addr(id, pact, ([0, 0, 0, 0], port as u16).into(), config) - .map(|addr| addr.port()) - } - - /// Start a new server on the runtime, returning the future - pub async fn start_mock_server_nonblocking( - &mut self, - id: String, - pact: Box, - port: u16, - config: MockServerConfig - ) -> Result { - let addr= ([0, 0, 0, 0], port as u16).into(); - let (mock_server, future) = MockServer::new(id.clone(), pact, addr, config).await?; - - let port = { mock_server.lock().unwrap().port.clone() }; - self.mock_servers.insert( - id, - ServerEntry { - mock_server: Either::Left(mock_server), - port: port.unwrap_or_else(|| addr.port()), - resources: vec![], - join_handle: Some(self.runtime.spawn(future)) - }, - ); - - port.ok_or_else(|| "Started mock server has no port".to_string()) - } - - /// Start a new TLS server on the runtime - #[cfg(feature = "tls")] - pub fn start_tls_mock_server( - &mut self, - id: String, - pact: Box, - port: u16, - tls: &ServerConfig, - config: MockServerConfig - ) -> Result { - self.start_tls_mock_server_with_addr(id, pact, ([0, 0, 0, 0], port as u16).into(), tls, config) - .map(|addr| addr.port()) - } - - /// Start a new mock server for the provided transport on the runtime. Returns the socket address - /// that the server is running on. - #[allow(unused_variables)] - pub fn start_mock_server_for_transport( - &mut self, - id: String, - pact: Box, - addr: SocketAddr, - transport: &CatalogueEntry, - config: MockServerConfig - ) -> anyhow::Result { - #[cfg(feature = "plugins")] - { - if transport.provider_type == CatalogueEntryProviderType::PLUGIN { - let mut v4_pact = pact.as_v4_pact()?; - for interaction in v4_pact.interactions.iter_mut() { - if let None = interaction.transport() { - interaction.set_transport(transport.key.split("/").last().map(|i| i.to_string())); - } - } - let mock_server_config = pact_plugin_driver::mock_server::MockServerConfig { - output_path: None, - host_interface: Some(addr.ip().to_string()), - port: addr.port() as u32, - tls: false - }; - let test_context = hashmap! {}; - let result = self.runtime.block_on( - pact_plugin_driver::plugin_manager::start_mock_server_v2(transport, v4_pact.boxed(), - mock_server_config, test_context) - )?; - self.mock_servers.insert( - id, - ServerEntry { - mock_server: Either::Right(PluginMockServer { - mock_server_details: result.clone(), - catalogue_entry: transport.clone(), - pact: v4_pact - }), - port: result.port as u16, - resources: vec![], - join_handle: None - } - ); - - let url = Url::parse(&result.base_url)?; - (url.host_str().unwrap_or_default(), result.port as u16).to_socket_addrs()?.next() - .ok_or_else(|| anyhow!("Could not parse the result from the plugin as a socket address")) - } else { - self.start_mock_server_with_addr(id, pact, addr, config) - .map_err(|err| anyhow!(err)) - } - } - #[cfg(not(feature = "plugins"))] - { - self.start_mock_server_with_addr(id, pact, addr, config) - .map_err(|err| anyhow!(err)) - } - } - - /// Shut down a server by its id. This function will only shut down a local mock server, not one - /// provided by a plugin. - pub fn shutdown_mock_server_by_id(&mut self, id: String) -> bool { - match self.mock_servers.remove(&id) { - Some(entry) => match entry.mock_server { - Either::Left(mock_server) => { - let mut ms = mock_server.lock().unwrap(); - debug!("Shutting down mock server with ID {} - {:?}", id, ms.metrics); - match ms.shutdown() { - Ok(()) => { - self.runtime.block_on(entry.join_handle.unwrap()).unwrap(); - true - } - Err(_) => false, - } - } - Either::Right(_plugin_mock_server) => { - #[cfg(feature = "plugins")] - { - match self.runtime.block_on(pact_plugin_driver::plugin_manager::shutdown_mock_server(&_plugin_mock_server.mock_server_details)) { - Ok(_) => true, - Err(err) => { - error!("Failed to shutdown plugin mock server with ID {} - {}", id, err); - false - } - } - } - #[cfg(not(feature = "plugins"))] - { - error!("Plugins require the plugin feature to be enabled"); - false - } - } - }, - None => false, - } - } - - /// Shut down a server by its local port number - pub fn shutdown_mock_server_by_port(&mut self, port: u16) -> bool { - debug!("Shutting down mock server with port {}", port); - let result = self - .mock_servers - .iter() - .find_map(|(id, entry)| { - if entry.port == port { - Some(id.clone()) - } else { - None - } - }); - - if let Some(id) = result { - self.shutdown_mock_server_by_id(id) - } else { - false - } - } - - /// Find mock server by id, and map it using supplied function if found. - pub fn find_mock_server_by_id( - &self, - id: &String, - f: &dyn Fn(&ServerManager, Either<&MockServer, &PluginMockServer>) -> R - ) -> Option { - match self.mock_servers.get(id) { - Some(entry) => match &entry.mock_server { - Either::Left(mock_server) => { - let inner = mock_server.lock().unwrap(); - Some(f(self, Either::Left(&inner))) - } - Either::Right(plugin_mock_server) => Some(f(self, Either::Right(plugin_mock_server))) - } - None => None, - } - } - - /// Find a mock server by port number and and map it using supplied function if found. - pub fn find_mock_server_by_port( - &mut self, - port: u16, - f: &dyn Fn(&ServerManager, &String, Either<&MockServer, &PluginMockServer>) -> R - ) -> Option { - let entry = { - self.mock_servers - .iter() - .find(|(_id, entry)| entry.port == port) - .map(|(id, entry)| (id.clone(), &entry.mock_server)) - }; - match entry { - Some((id, entry)) => match entry { - Either::Left(mock_server) => { - let inner = mock_server.lock().unwrap(); - Some(f(self, &id, Either::Left(&inner))) - } - Either::Right(plugin_mock_server) => Some(f(self, &id, Either::Right(plugin_mock_server))) - } - None => None, - } - } - - /// Find a mock server by port number and apply a mutating operation on it if successful. This will - /// only work for locally managed mock servers, not mock servers provided by plugins. - pub fn find_mock_server_by_port_mut( - &mut self, - port: u16, - f: &dyn Fn(&mut MockServer) -> R, - ) -> Option { - match self - .mock_servers - .iter_mut() - .find(|(_id, entry)| entry.port == port) - { - Some((_id, entry)) => match &mut entry.mock_server { - Either::Left(mock_server) => { - Some(f(&mut mock_server.lock().unwrap())) - } - Either::Right(_) => None - } - None => None, - } - } - - /// Map all the running mock servers This will only work for locally managed mock servers, - /// not mock servers provided by plugins. - pub fn map_mock_servers(&self, f: F) -> Vec - where F: Fn(&MockServer) -> R { - let mut results = vec![]; - for (id, entry) in self.mock_servers.iter() { - trace!(?id, "mock server entry"); - if let Either::Left(mock_server) = &entry.mock_server { - trace!(?id, "Waiting on lock for mock server"); - let guard = mock_server.lock().unwrap(); - trace!(?id, "Got access to mock server, invoking callback"); - results.push(f(&guard)); - } - } - trace!("returning results"); - return results; - } - - /// Execute a future on the Tokio runtime for the service manager - #[cfg(feature = "plugins")] - pub(crate) fn exec_async(&self, future: impl Future) -> OUT { - self.runtime.block_on(future) - } - - /// Store a string that needs to be cleaned up when the mock server terminates - pub fn store_mock_server_resource(&mut self, port: u16, s: CString) -> bool { - if let Some((_, entry)) = self.mock_servers - .iter_mut() - .find(|(_id, entry)| entry.port == port) { - entry.resources.push(s); - true - } else { - false - } - } -} - -#[cfg(test)] -mod tests { - use std::{thread, time}; - use std::net::TcpStream; - - use env_logger; - use pact_models::sync_pact::RequestResponsePact; - - use super::*; - - #[test] - #[cfg(not(target_os = "windows"))] - fn manager_should_start_and_shutdown_mock_server() { - let _ = env_logger::builder().is_test(true).try_init(); - let mut manager = ServerManager::new(); - let start_result = manager.start_mock_server("foobar".into(), - RequestResponsePact::default().boxed(), - 0, MockServerConfig::default()); - - assert!(start_result.is_ok()); - let server_port = start_result.unwrap(); - - // Server should be up - assert!(TcpStream::connect(("127.0.0.1", server_port)).is_ok()); - - // Should be able to read matches without blocking - let matches = - manager.find_mock_server_by_port_mut(server_port, &|mock_server| mock_server.matches()); - assert_eq!(matches, Some(vec![])); - - let stopped = manager.shutdown_mock_server_by_port(server_port); - assert!(stopped); - - // The tokio runtime is now out of tasks - drop(manager); - - let millis = time::Duration::from_millis(100); - thread::sleep(millis); - - // Server should be down - assert!(TcpStream::connect(("127.0.0.1", server_port)).is_err()); - } -} diff --git a/rust/pact_mock_server/src/tests.rs b/rust/pact_mock_server/src/tests.rs deleted file mode 100644 index f8f79961f..000000000 --- a/rust/pact_mock_server/src/tests.rs +++ /dev/null @@ -1,295 +0,0 @@ -#[cfg(feature = "plugins")] use std::net::SocketAddr; -use expectest::expect; -use expectest::prelude::*; -use maplit::*; -use reqwest::header::ACCEPT; - -use pact_matching::Mismatch; -use pact_models::bodies::OptionalBody; -use pact_models::matchingrules; -use pact_models::matchingrules::MatchingRule; -use pact_models::prelude::v4::{SynchronousHttp, V4Pact}; -use pact_models::v4::http_parts::{HttpRequest, HttpResponse}; - -use crate::matching::{match_request, MatchResult}; - -use super::*; -use pact_models::v4::interaction::V4Interaction; - -#[tokio::test] -async fn match_request_returns_a_match_for_identical_requests() { - let request = HttpRequest::default(); - let interaction = SynchronousHttp { request: request.clone(), .. SynchronousHttp::default() }; - let interactions = vec![interaction.boxed_v4()]; - let pact = V4Pact { interactions, .. V4Pact::default() }; - let result = match_request(&request, &pact).await; - expect!(result).to(be_equal_to(MatchResult::RequestMatch(interaction.request.clone(), - interaction.response.clone(), request.clone()))); -} - -#[tokio::test] -async fn match_request_returns_a_not_found_for_no_interactions() { - let request = HttpRequest::default(); - let interactions = vec![]; - let pact = V4Pact { interactions, .. V4Pact::default() }; - let result = match_request(&request, &pact).await; - expect!(result).to(be_equal_to(MatchResult::RequestNotFound(request))); -} - -#[tokio::test] -async fn match_request_returns_a_match_for_multiple_identical_requests() { - let request = HttpRequest::default(); - let interaction = SynchronousHttp { request: request.clone(), .. SynchronousHttp::default() }; - let interaction2 = SynchronousHttp { - description: "test2".to_string(), - request: request.clone(), - ..SynchronousHttp::default() - }; - let interactions = vec![ - interaction.boxed_v4(), - interaction2.boxed_v4() - ]; - let pact = V4Pact { interactions, .. V4Pact::default() }; - let result = match_request(&request, &pact).await; - expect!(result).to(be_equal_to( - MatchResult::RequestMatch(interaction.request, interaction.response, request.clone()))); -} - -#[tokio::test] -async fn match_request_returns_a_match_for_multiple_requests() { - let request = HttpRequest { method: "GET".to_string(), .. HttpRequest::default() }; - let request2 = HttpRequest { method: "POST".to_string(), path: "/post".to_string(), .. HttpRequest::default() }; - let interaction = SynchronousHttp { request: request.clone(), .. SynchronousHttp::default() }; - let interaction2 = SynchronousHttp { - description: "test2".to_string(), - request: request2.clone(), - ..SynchronousHttp::default() - }; - let interactions = vec![ - interaction.boxed_v4(), - interaction2.boxed_v4() - ]; - let pact = V4Pact { interactions, .. V4Pact::default() }; - let result = match_request(&request, &pact).await; - expect!(result).to(be_equal_to( - MatchResult::RequestMatch(interaction.request, interaction.response, request.clone()))); -} - -#[tokio::test] -async fn match_request_returns_a_mismatch_for_incorrect_request() { - let request = HttpRequest::default(); - let expected_request = HttpRequest { query: Some(hashmap!{ "QueryA".to_string() => vec![Some("Value A".to_string())] }), - .. HttpRequest::default() }; - let interaction = SynchronousHttp { - request: expected_request, - ..SynchronousHttp::default() - }; - let interactions = vec![ - interaction.boxed_v4() - ]; - let pact = V4Pact { interactions, .. V4Pact::default() }; - let result = match_request(&request, &pact).await; - expect!(result.match_key()).to(be_equal_to("Request-Mismatch".to_string())); -} - -#[tokio::test] -async fn match_request_returns_request_not_found_if_method_or_path_do_not_match() { - let request = HttpRequest { method: "GET".to_string(), path: "/path".to_string(), .. HttpRequest::default() }; - let expected_request = HttpRequest { method: "POST".to_string(), path: "/otherpath".to_string(), - .. HttpRequest::default() }; - let interaction = SynchronousHttp { - request: expected_request, - ..SynchronousHttp::default() - }; - let interactions = vec![ - interaction.boxed_v4() - ]; - let pact = V4Pact { interactions, .. V4Pact::default() }; - let result = match_request(&request, &pact).await; - expect!(result).to(be_equal_to(MatchResult::RequestNotFound(request))); -} - -#[tokio::test] -async fn match_request_returns_the_most_appropriate_mismatch_for_multiple_requests() { - let request = HttpRequest { method: "GET".to_string(), path: "/".to_string(), body: OptionalBody::Present("This is a body".into(), None, None), - .. HttpRequest::default() }; - let request2 = HttpRequest { method: "GET".to_string(), path: "/".to_string(), query: Some(hashmap!{ - "QueryA".to_string() => vec![Some("Value A".to_string())] - }), body: OptionalBody::Present("This is a body".into(), None, None), - .. HttpRequest::default() }; - let request3 = HttpRequest { method: "GET".to_string(), path: "/".to_string(), query: Some(hashmap!{ - "QueryA".to_string() => vec![Some("Value A".to_string())] - }), body: OptionalBody::Missing, .. HttpRequest::default() }; - let interaction = SynchronousHttp { description: "test".to_string(), request: request.clone(), .. SynchronousHttp::default() }; - let interaction2 = SynchronousHttp { description: "test2".to_string(), request: request2.clone(), .. SynchronousHttp::default() }; - let interactions = vec![interaction.boxed_v4(), interaction2.boxed_v4()]; - let pact = V4Pact { interactions, .. V4Pact::default() }; - let result = match_request(&request3, &pact).await; - expect!(result).to(be_equal_to(MatchResult::RequestMismatch(interaction2.request, request3.clone(), - vec![Mismatch::BodyMismatch { path: "/".to_string(), expected: Some("This is a body".into()), actual: None, - mismatch: "Expected body \'This is a body\' but was missing".to_string() }]))); -} - -#[tokio::test] -async fn match_request_supports_v2_matchers() { - let request = HttpRequest { method: "GET".to_string(), path: "/".to_string(), - headers: Some(hashmap!{ "Content-Type".to_string() => vec!["application/json".to_string()] }), body: OptionalBody::Present( - r#" - { - "a": 100, - "b": "one hundred" - } - "#.into(), None, None - ), .. HttpRequest::default() }; - let expected_request = HttpRequest { method: "GET".to_string(), path: "/".to_string(), - headers: Some(hashmap!{ "Content-Type".to_string() => vec!["application/json".to_string()] }), - body: OptionalBody::Present( - r#" - { - "a": 1000, - "b": "One Thousand" - } - "#.into(), None, None - ), matching_rules: matchingrules!{ - "body" => { - "$.*" => [ MatchingRule::Type ] - } - }, - .. HttpRequest::default() - }; - let interaction = SynchronousHttp { request: expected_request, .. SynchronousHttp::default() }; - let interactions = vec![interaction.boxed_v4()]; - let pact = V4Pact { interactions, .. V4Pact::default() }; - let result = match_request(&request, &pact).await; - expect!(result).to(be_equal_to( - MatchResult::RequestMatch(interaction.request, interaction.response, request.clone()))); -} - -#[tokio::test] -async fn match_request_supports_v2_matchers_with_xml() { - let request = HttpRequest { method: "GET".to_string(), path: "/".to_string(), query: None, - headers: Some(hashmap!{ "Content-Type".to_string() => vec!["application/xml".to_string()] }), body: OptionalBody::Present( - r#" - helloworld - "#.into(), None, None - ), .. HttpRequest::default() }; - let expected_request = HttpRequest { method: "GET".to_string(), path: "/".to_string(), query: None, - headers: Some(hashmap!{ "Content-Type".to_string() => vec!["application/xml".to_string()] }), - body: OptionalBody::Present( - r#" - hellomars - "#.into(), None, None - ), matching_rules: matchingrules!{ - "body" => { - "$.foo['#text']" => [ MatchingRule::Regex("[a-z]+".into()) ] - } - }, - .. HttpRequest::default() - }; - let interaction = SynchronousHttp { request: expected_request, .. SynchronousHttp::default() }; - let interactions = vec![interaction.boxed_v4()]; - let pact = V4Pact { interactions, .. V4Pact::default() }; - let result = match_request(&request, &pact).await; - expect!(result).to(be_equal_to( - MatchResult::RequestMatch(interaction.request, interaction.response, request.clone()))); -} - -#[test_log::test] -fn match_request_with_header_with_multiple_values() { - let pact = V4Pact { - interactions: vec![ - SynchronousHttp { - request: HttpRequest { - headers: Some(hashmap! { - "accept".to_string() => vec!["application/hal+json".to_string(), "application/json".to_string()] - }), - .. HttpRequest::default() - }, - .. SynchronousHttp::default() - }.boxed_v4() - ], - .. V4Pact::default() - }; - let mut manager = ServerManager::new(); - let id = "match_request_with_header_with_multiple_values".to_string(); - let port = manager.start_mock_server(id.clone(), pact.boxed(), 0, MockServerConfig::default()).unwrap(); - - let client = reqwest::blocking::Client::new(); - let response = client.get(format!("http://127.0.0.1:{}", port).as_str()) - .header(ACCEPT, "application/hal+json, application/json").send(); - - let mismatches = manager.find_mock_server_by_id(&id, &|_, ms| { - ms.unwrap_left().mismatches() - }); - manager.shutdown_mock_server_by_port(port); - - expect!(mismatches).to(be_some().value(vec![])); - expect!(response.unwrap().status()).to(be_equal_to(200)); -} - -#[tokio::test] -async fn match_request_with_more_specific_request() { - let request1 = HttpRequest { path: "/animals/available".into(), .. HttpRequest::default() }; - let request2 = HttpRequest { path: "/animals/available".into(), headers: Some(hashmap! { - "Authorization".to_string() => vec!["Bearer token".to_string()] - }), - .. HttpRequest::default() }; - let interaction1 = SynchronousHttp { - description: "test_more_general_request".into(), - request: request1.clone(), - response: HttpResponse { status: 401, .. HttpResponse::default() }, - .. SynchronousHttp::default() - }; - let interaction2 = SynchronousHttp { - description: "test_more_specific_request".into(), - request: request2.clone(), - response: HttpResponse { status: 200, .. HttpResponse::default() }, - .. SynchronousHttp::default() - }; - - let expected = interaction1.clone(); - let interactions = vec![interaction1.boxed_v4(), interaction2.boxed_v4()]; - let pact = V4Pact { interactions, .. V4Pact::default() }; - let result1 = match_request(&request1.clone(), &pact).await; - expect!(result1).to(be_equal_to( - MatchResult::RequestMatch(expected.request, expected.response, request1.clone()))); - - let expected = interaction2.clone(); - let result2 = match_request(&request2.clone(), &pact).await; - expect!(result2).to(be_equal_to( - MatchResult::RequestMatch(expected.request, expected.response, request2.clone()))); -} - -#[test] -#[cfg(feature = "plugins")] -fn basic_mock_server_test() { - let pact = V4Pact { - interactions: vec![ - SynchronousHttp { - request: HttpRequest { - headers: Some(hashmap! { - "accept".to_string() => vec!["application/json".to_string()] - }), - .. HttpRequest::default() - }, - .. SynchronousHttp::default() - }.boxed_v4() - ], - .. V4Pact::default() - }; - let id = "basic_mock_server_test".to_string(); - let addr: SocketAddr = "127.0.0.1:0".parse().unwrap(); - let port = start_mock_server_for_transport(id.clone(), pact.boxed(), addr, "http", MockServerConfig::default()).unwrap(); - - let client = reqwest::blocking::Client::new(); - let response = client.get(format!("http://127.0.0.1:{}", port).as_str()) - .header(ACCEPT, "application/json").send(); - - let all_matched = mock_server_matched(port); - let mismatches = mock_server_mismatches(port); - shutdown_mock_server(port); - - expect!(all_matched).to(be_true()); - expect!(mismatches).to(be_some().value("[]")); - expect!(response.unwrap().status()).to(be_equal_to(200)); -} diff --git a/rust/pact_mock_server/src/tls.rs b/rust/pact_mock_server/src/tls.rs deleted file mode 100644 index 6bdf1d173..000000000 --- a/rust/pact_mock_server/src/tls.rs +++ /dev/null @@ -1,185 +0,0 @@ -//! TLS support structs - -// Copyright (c) 2018 Sean McArthur (https://github.com/seanmonstar/warp/blob/master/src/tls.rs) -// -// Permission is hereby granted, free of charge, to any person obtaining a copy -// of this software and associated documentation files (the "Software"), to deal -// in the Software without restriction, including without limitation the rights -// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell -// copies of the Software, and to permit persons to whom the Software is -// furnished to do so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included in -// all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, -// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN -// THE SOFTWARE. - -use std::fs::File; -use std::io::{self, BufReader, Cursor, Read}; -use std::path::{Path, PathBuf}; - -use rustls::{Certificate, PrivateKey}; -use rustls_pemfile::{certs, pkcs8_private_keys, rsa_private_keys}; -use tokio_rustls::rustls::ServerConfig; - -/// Represents errors that can occur building the TlsConfig -#[derive(Debug)] -pub enum TlsConfigError { - /// IO Error - Io(io::Error), - /// An Error parsing the Certificate - CertParseError(io::Error), - /// An Error parsing a Pkcs8 key - Pkcs8ParseError, - /// An Error parsing a Rsa key - RsaParseError, - /// An error from an empty key - EmptyKey, - /// An error from an invalid key - InvalidKey(rustls::Error), -} - -impl std::fmt::Display for TlsConfigError { - fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { - match self { - TlsConfigError::Io(err) => err.fmt(f), - TlsConfigError::CertParseError(err) => write!(f, "certificate parse error, {}", err), - TlsConfigError::Pkcs8ParseError => write!(f, "pkcs8 parse error"), - TlsConfigError::RsaParseError => write!(f, "rsa parse error"), - TlsConfigError::EmptyKey => write!(f, "key contains no private key"), - TlsConfigError::InvalidKey(err) => write!(f, "key contains an invalid key, {}", err), - } - } -} - -impl std::error::Error for TlsConfigError {} - -/// Builder to set the configuration for the Tls server. -pub struct TlsConfigBuilder { - cert: Box, - key: Box, -} - -impl std::fmt::Debug for TlsConfigBuilder { - fn fmt(&self, f: &mut ::std::fmt::Formatter) -> ::std::fmt::Result { - f.debug_struct("TlsConfigBuilder").finish() - } -} - -impl TlsConfigBuilder { - /// Create a new TlsConfigBuilder - pub fn new() -> TlsConfigBuilder { - TlsConfigBuilder { - key: Box::new(io::empty()), - cert: Box::new(io::empty()), - } - } - - /// sets the Tls key via File Path, returns `TlsConfigError::IoError` if the file cannot be open - pub fn key_path(mut self, path: impl AsRef) -> Self { - self.key = Box::new(LazyFile { - path: path.as_ref().into(), - file: None, - }); - self - } - - /// sets the Tls key via bytes slice - pub fn key(mut self, key: &[u8]) -> Self { - self.key = Box::new(Cursor::new(Vec::from(key))); - self - } - - /// Specify the file path for the TLS certificate to use. - pub fn cert_path(mut self, path: impl AsRef) -> Self { - self.cert = Box::new(LazyFile { - path: path.as_ref().into(), - file: None, - }); - self - } - - /// sets the Tls certificate via bytes slice - pub fn cert(mut self, cert: &[u8]) -> Self { - self.cert = Box::new(Cursor::new(Vec::from(cert))); - self - } - - /// Build the TLS configuration - pub fn build(mut self) -> Result { - let mut cert_rdr = BufReader::new(self.cert); - let cert = certs(&mut cert_rdr) - .map_err(TlsConfigError::CertParseError)? - .iter() - .map(|data| Certificate(data.clone())) - .collect(); - - let key = { - // convert it to Vec to allow reading it again if key is RSA - let mut key_vec = Vec::new(); - self.key - .read_to_end(&mut key_vec) - .map_err(TlsConfigError::Io)?; - - if key_vec.is_empty() { - return Err(TlsConfigError::EmptyKey); - } - - let mut pkcs8 = pkcs8_private_keys(&mut key_vec.as_slice()) - .map_err(|_| TlsConfigError::Pkcs8ParseError)?; - - if !pkcs8.is_empty() { - PrivateKey(pkcs8.remove(0)) - } else { - let mut rsa = rsa_private_keys(&mut key_vec.as_slice()) - .map_err(|_| TlsConfigError::RsaParseError)?; - - if !rsa.is_empty() { - PrivateKey(rsa.remove(0)) - } else { - return Err(TlsConfigError::EmptyKey); - } - } - }; - - let config = ServerConfig::builder() - .with_safe_defaults() - .with_no_client_auth() - .with_single_cert(cert, key) - .map_err(|err| TlsConfigError::InvalidKey(err))?; - Ok(config) - } -} - -struct LazyFile { - path: PathBuf, - file: Option, -} - -impl LazyFile { - fn lazy_read(&mut self, buf: &mut [u8]) -> io::Result { - if self.file.is_none() { - self.file = Some(File::open(&self.path)?); - } - - self.file.as_mut().unwrap().read(buf) - } -} - -impl Read for LazyFile { - fn read(&mut self, buf: &mut [u8]) -> io::Result { - self.lazy_read(buf).map_err(|err| { - let kind = err.kind(); - io::Error::new( - kind, - format!("error reading file ({:?}): {}", self.path.display(), err), - ) - }) - } -} diff --git a/rust/pact_mock_server/src/utils.rs b/rust/pact_mock_server/src/utils.rs deleted file mode 100644 index 8096f1ad7..000000000 --- a/rust/pact_mock_server/src/utils.rs +++ /dev/null @@ -1,11 +0,0 @@ -//! Utility functions needed for mock server support - -use serde_json::Value; - -/// Unpack a JSON boolean value, returning a None if the JSON value is not a boolean -pub(crate) fn json_to_bool(value: &Value) -> Option { - match value { - Value::Bool(b) => Some(*b), - _ => None - } -} diff --git a/rust/pact_mock_server_cli/.dockerignore b/rust/pact_mock_server_cli/.dockerignore deleted file mode 100644 index 2f7896d1d..000000000 --- a/rust/pact_mock_server_cli/.dockerignore +++ /dev/null @@ -1 +0,0 @@ -target/ diff --git a/rust/pact_mock_server_cli/CHANGELOG.md b/rust/pact_mock_server_cli/CHANGELOG.md deleted file mode 100644 index 5e635aacb..000000000 --- a/rust/pact_mock_server_cli/CHANGELOG.md +++ /dev/null @@ -1,470 +0,0 @@ -To generate the log, run `git log --pretty='* %h - %s (%an, %ad)' TAGNAME..HEAD .` replacing TAGNAME and HEAD as appropriate. - -# 1.0.5 - Maintenance Release - -* 2f974fc4 - chore(pact_mock_server_cli): Update dependencies (Ronald Holshausen, Fri Mar 15 15:15:40 2024 +1100) -* ffffa61d - chore: Upgrade pact_mock_server to 1.2.5 (Ronald Holshausen, Fri Mar 15 15:13:04 2024 +1100) -* 6406e9ae - refactor(release): Rename OSX to MacOS (Ronald Holshausen, Fri Mar 15 14:28:06 2024 +1100) -* 7732a637 - chore(ci): refactor release pipeline (JP-Ellis, Mon Feb 26 17:54:18 2024 +1100) -* 41faa544 - chore: Lock clap crate to 4.4 as 4.5 requires Rust 1.75 (Ronald Holshausen, Mon Feb 12 15:16:18 2024 +1100) -* 8d197959 - chore: fixup path to aarch64-unknown-linux-musl artifact (Yousaf Nabi, Thu Feb 8 21:13:21 2024 +0000) -* 9196efe4 - feat: verifier/mock_server clis - build for musl (Yousaf Nabi, Thu Feb 8 20:36:10 2024 +0000) -* a52e0ee9 - chore: Upgrade pact_matching to 1.1.10 (Ronald Holshausen, Wed Feb 7 13:20:45 2024 +1100) -* 24a26cca - chore: Update pact_models to 1.1.18 (Ronald Holshausen, Wed Feb 7 10:53:22 2024 +1100) -* 73578350 - chore: use local pact_models (JP-Ellis, Tue Feb 6 10:51:09 2024 +1100) -* 113470ca - chore: Update release script (Ronald Holshausen, Sat Jan 20 19:19:40 2024 +1100) -* ba1f77a9 - bump version to 1.0.5 (Ronald Holshausen, Sat Jan 20 19:18:42 2024 +1100) - -# 1.0.4 - Maintenance Release - -* 0496fb75 - chore(pact_mock_server_cli): Upgrade dependencies (Ronald Holshausen, Sat Jan 20 19:06:50 2024 +1100) -* def5685c - chore: Upgrade pact_mock_server to 1.2.4 (Ronald Holshausen, Sat Jan 20 18:56:26 2024 +1100) -* 6fa097a5 - Merge branch 'master' into ci/cargo_clean (Ronald Holshausen, Thu Jan 25 10:22:25 2024 +1100) -* 36390097 - Merge pull request #371 from YOU54F/chore/renable_verifier_aarch64_linux (Ronald Holshausen, Thu Jan 25 09:59:53 2024 +1100) -* 00402ba4 - chore: migrate target/artifacts to release_artifacts to avoid cargo clean loss (Yousaf Nabi, Wed Jan 24 15:26:18 2024 +0000) -* 22331310 - ci: cargo clean prior to cross build (Yousaf Nabi, Wed Jan 24 15:24:10 2024 +0000) -* c412829f - feat: build aarch64-pc-windows-msvc target (ffi/mock_server/verifier) (Yousaf Nabi, Wed Jan 24 12:01:50 2024 +0000) -* a2ba1cd5 - fix: pin cross to 0.2.5 for glibc 2.23 (Yousaf Nabi, Wed Jan 24 11:54:22 2024 +0000) -* e552bdce - chore: Upgrade pact_matching to 1.1.9 (Ronald Holshausen, Sat Jan 20 15:13:13 2024 +1100) -* b735df9d - chore: Upgrade pact_models to 1.1.17 (Ronald Holshausen, Sat Jan 20 13:54:03 2024 +1100) -* 1a4bcd27 - chore: Upgrade pact_matching to 1.1.8 (Ronald Holshausen, Fri Jan 19 18:24:54 2024 +1100) -* 944613df - fix: regression - upgrade pact_models to 1.1.16 #359 (Ronald Holshausen, Fri Jan 19 14:52:36 2024 +1100) -* 403c0af1 - chore: Upgrade pact_models to 1.1.14 #355 (Ronald Holshausen, Tue Jan 16 10:31:12 2024 +1100) -* dfd13760 - chore: Upgrade pact_models to 1.1.13 #355 (Ronald Holshausen, Tue Jan 16 07:42:33 2024 +1100) -* 3f0ae7f1 - chore: Upgrade pact_matching to 1.1.7 (Ronald Holshausen, Tue Nov 14 03:10:25 2023 +1100) -* 826758a6 - chore: Upgrade pact_models to 1.1.12 (Ronald Holshausen, Mon Nov 13 17:25:21 2023 +1100) -* 04bad264 - chore: Upgrade pact_matching to 1.1.6 (Ronald Holshausen, Fri Sep 22 11:03:38 2023 +1000) -* d592cd8b - chore: Upgrade pact_mock_server to 1.2.3 (Ronald Holshausen, Tue Aug 29 09:25:14 2023 +1000) -* 3ec99c41 - chore: Upgrade pact_matching to 1.1.5 (Ronald Holshausen, Fri Aug 18 15:40:02 2023 +1000) -* e4da3e42 - chore: Upgrade pact_models to 1.1.11 (Ronald Holshausen, Mon Aug 7 13:59:34 2023 +1000) -* 24ed7835 - chore: Upgrade pact-models to 1.1.10 (Ronald Holshausen, Fri Aug 4 16:11:24 2023 +1000) -* 0586fcf1 - chore: Upgrade pact_mock_server to 1.2.2 (Ronald Holshausen, Thu Jul 27 14:45:02 2023 +1000) -* 8f88192e - chore: Upgrade pact_matching to 1.1.4 (Ronald Holshausen, Thu Jul 27 14:35:27 2023 +1000) -* 4a01919a - chore: Upgrade pact_models to 1.1.9 (Ronald Holshausen, Thu Jul 27 10:24:00 2023 +1000) -* c2aad1ac - chore: Add support for datetime, xml, multipart and plugins crate features (Ronald Holshausen, Wed Jul 12 11:15:37 2023 +1000) -* a3726bb8 - bump version to 1.0.4 (Ronald Holshausen, Tue Jul 11 15:12:25 2023 +1000) - -# 1.0.3 - Maintenance release - -* de1f04e7 - chore: Update readme (Ronald Holshausen, Tue Jul 11 15:07:02 2023 +1000) -* 66d010fb - chore: Add support for datetime, xml, multipart. plugins and tls crate features (Ronald Holshausen, Tue Jul 11 15:04:13 2023 +1000) -* e07ca36c - chore: Upgrade pact_mock_server to 1.2.1 (Ronald Holshausen, Tue Jul 11 14:47:17 2023 +1000) -* 348eb3f3 - chore: Upgrade pact_matcing to 1.1.3 (Ronald Holshausen, Tue Jul 11 11:38:26 2023 +1000) -* b18b9dff - chore: Upgrade pact_matching to 1.1.2 (Ronald Holshausen, Mon Jul 10 16:42:27 2023 +1000) -* 1deca59a - chore: Upgrade pact_models to 1.1.8 (Ronald Holshausen, Mon Jul 10 16:15:43 2023 +1000) -* 2662cdfc - chore: Upgrade pact_models to 1.1.7 (Ronald Holshausen, Thu Jul 6 10:27:25 2023 +1000) -* e95ae4d0 - chore: Upgrade pact_models to 1.1.6 (Ronald Holshausen, Thu Jun 22 15:40:55 2023 +1000) -* 5331f99e - bump version to 1.0.3 (Ronald Holshausen, Wed Jun 14 16:19:39 2023 +1000) - -# 1.0.2 - Fixes a deadlock caused when getting mock server JSON - -* 834f77cc - chore: Upgrade pact_mock_server to 1.2.0 (Ronald Holshausen, Wed Jun 14 15:22:11 2023 +1000) -* 41147cf5 - chore(pact_mock_server_cli): Upgrade Clap to v4 (Ronald Holshausen, Wed Jun 14 15:01:45 2023 +1000) -* fc4ddeb7 - chore(pact_mock_server_cli): Add actions to all Clap args (Ronald Holshausen, Wed Jun 14 14:03:44 2023 +1000) -* e58aa917 - fix: no need to wrap the Pact for a mock server in a mutex (mock server is already behind a mutex) as this can cause deadlocks #274 (Ronald Holshausen, Wed Jun 14 13:26:54 2023 +1000) -* d6775858 - chore(pact_mock_server_cli): Fix all the Clap deprecation warnings (Ronald Holshausen, Tue Jun 13 17:16:03 2023 +1000) -* 17a81361 - chore(pact_mock_server_cli): Switch to using tracing crate (Ronald Holshausen, Tue Jun 13 14:42:52 2023 +1000) -* 2047ce09 - bump version to 1.0.2 (Ronald Holshausen, Tue Jun 13 11:35:52 2023 +1000) - -# 1.0.1 - Adds aarch64 osx binary + bug fixes - -* 2a21bc0e - chore: correct the pact_matching version (Ronald Holshausen, Tue Jun 13 11:31:32 2023 +1000) -* 666535ab - Revert "update changelog for release 1.0.1" (Ronald Holshausen, Tue Jun 13 11:30:16 2023 +1000) -* cf2914ec - update changelog for release 1.0.1 (Ronald Holshausen, Tue Jun 13 11:28:38 2023 +1000) -* bc68ed7f - chore: Upgrade pact_models to 1.1.4 (Ronald Holshausen, Thu Jun 1 10:22:38 2023 +1000) -* 397c837f - chore: Upgrade pact_models to 1.1.3 (fixes MockServerURL generator) (Ronald Holshausen, Mon May 29 15:12:22 2023 +1000) -* 8e9bd503 - chore: Upgrade pact_mock_server to 1.1.0 (Ronald Holshausen, Tue May 23 12:20:01 2023 +1000) -* ac2e24da - chore: Use "Minimum version, with restricted compatibility range" for all Pact crate versions (Ronald Holshausen, Tue May 23 11:46:52 2023 +1000) -* 6df4670c - chore: Upgrade pact_matching to 1.1.1 (Ronald Holshausen, Tue May 23 11:32:51 2023 +1000) -* 54887690 - chore: Bump pact_matching to 1.1 (Ronald Holshausen, Tue May 23 11:13:14 2023 +1000) -* 261ecf47 - fix: Add RefUnwindSafe trait bound to all Pact and Interaction uses (Ronald Holshausen, Mon May 15 13:59:31 2023 +1000) -* 6a71b12d - chore: Upgrade pact_mock_server to 1.0.2 (Ronald Holshausen, Tue Apr 18 13:30:21 2023 +1000) -* 0bcba082 - chore: Upgrade pact_matching to 1.0.8 (Ronald Holshausen, Tue Apr 18 13:14:38 2023 +1000) -* 6c14abfd - chore: Upgrade pact_models to 1.0.13 (Ronald Holshausen, Tue Apr 18 13:00:01 2023 +1000) -* ce16d43f - chore: Upgrade pact-plugin-driver to 0.4.2 (supports auto-installing known plugins) (Ronald Holshausen, Tue Apr 18 11:49:52 2023 +1000) -* 10bf1a48 - chore: Upgrade pact_models to 1.0.12 (fixes generators hash function) (Ronald Holshausen, Mon Apr 17 10:31:09 2023 +1000) -* 84b9d9e9 - fix: Upgrade pact models to 1.0.11 (fixes generated key for V4 Pacts) (Ronald Holshausen, Fri Apr 14 17:10:58 2023 +1000) -* 669f7812 - chore: Upgrade pact_models to 1.0.10 (Ronald Holshausen, Thu Apr 13 15:32:34 2023 +1000) -* a7349c74 - feat: pact_mock_server_cli aarch64 osx (Yousaf Nabi, Wed Apr 12 12:29:14 2023 +0100) -* b81d1d86 - bump version to 1.0.1 (Ronald Holshausen, Wed Apr 5 09:27:43 2023 +1000) - -# 1.0.0 - Maintenance Release - -* bb314a73 - chore(pact_mock_server_cli): Upgrade clap to v3 (Ronald Holshausen, Wed Apr 5 09:06:54 2023 +1000) -* 7e99decf - chore: add CLI tests (Ronald Holshausen, Tue Apr 4 16:33:28 2023 +1000) -* d2c8752e - chore: Update dependencies (Ronald Holshausen, Tue Apr 4 15:47:50 2023 +1000) -* 81a9b306 - chore: Upgrade pact_mock_server to 1.0.1 (Ronald Holshausen, Tue Apr 4 15:40:20 2023 +1000) -* 126cf462 - chore: Upgrade pact_matching to 1.0.7 (Ronald Holshausen, Tue Apr 4 15:12:28 2023 +1000) -* 11c701b4 - fix: Upgrade pact_matching to 1.0.6 (fixes some issues with matching HTTP headers) (Ronald Holshausen, Wed Mar 15 14:54:54 2023 +1100) -* e96bc54e - fix: Upgrade pact_models to 1.0.9 (fixes issues with headers) (Ronald Holshausen, Wed Mar 15 14:31:00 2023 +1100) -* f7e0b669 - chore: Upgrade pact_models to 1.0.8 (Ronald Holshausen, Wed Mar 15 12:19:22 2023 +1100) -* 7589b9b0 - chore: Bump pact_mock_server version to 1.0.0 (Ronald Holshausen, Fri Feb 10 14:43:53 2023 +1100) -* 019bd2fe - chore: Upgrade pact_matching to 1.0.5 (Ronald Holshausen, Wed Feb 8 13:53:15 2023 +1100) -* 0f4178e5 - chore: Upgrade pact_matching to 1.0.4 (Ronald Holshausen, Mon Feb 6 15:40:43 2023 +1100) -* c1b22f1c - chore: Upgrade pact_matching to 1.0.3 (Ronald Holshausen, Wed Jan 11 15:19:29 2023 +1100) -* 7d84d941 - chore: Upgrade pact_models to 1.0.4 (Ronald Holshausen, Wed Jan 11 14:33:13 2023 +1100) -* e4a44252 - chore: removed the quicktest for port validation as it fails from time to time (Ronald Holshausen, Mon Jan 9 09:45:01 2023 +1100) -* 33f39f2c - chore: removed the quicktest for port validation as it fails from time to time (Ronald Holshausen, Mon Jan 9 09:35:16 2023 +1100) -* 1bdb1054 - chore: Upgrade pact_models to 1.0.3 #239 (Ronald Holshausen, Thu Dec 22 15:37:53 2022 +1100) -* 81e55220 - chore: Upgrade pact_mock_server to 0.9.7 (Ronald Holshausen, Mon Dec 19 16:04:55 2022 +1100) -* e827f591 - chore: Upgrade pact_matching to 1.0.2 (Ronald Holshausen, Mon Dec 19 15:30:14 2022 +1100) -* fb2f4204 - chore: Upgrade pact_matching to 1.0.1 (Ronald Holshausen, Wed Dec 14 17:03:31 2022 +1100) -* 9be00044 - chore: Upgrade pact_mock_server to 0.9.6 (Ronald Holshausen, Mon Dec 12 10:06:25 2022 +1100) -* e7a1b9f2 - chore: Upgrade pact_matching to 1.0 and plugin driver to 0.2 (Ronald Holshausen, Fri Dec 9 17:29:33 2022 +1100) -* 246c0730 - chore: Upgrade pact_mock_server to 0.9.5 (Ronald Holshausen, Mon Nov 28 14:52:37 2022 +1100) -* 2802fffd - chore: Upgrade pact_matching to 0.12.15 (Ronald Holshausen, Mon Nov 28 14:29:43 2022 +1100) -* c9721fd5 - chore: Upgrade pact_models to 1.0.1 and pact-plugin-driver to 0.1.16 (Ronald Holshausen, Mon Nov 28 14:10:53 2022 +1100) -* a3110bd6 - chore: Upgrade pact_mock_server to 0.9.4 (Ronald Holshausen, Mon Nov 7 11:50:05 2022 +1100) -* 123060e3 - chore: Upgrade pact_matching to 0.12.14 (Ronald Holshausen, Mon Nov 7 11:34:36 2022 +1100) -* 577824e7 - fix: Upgrade pact_models to 1.0 and pact-plugin-driver to 0.1.15 to fix cyclic dependency issue (Ronald Holshausen, Mon Nov 7 11:14:20 2022 +1100) -* e1f985ad - chore: Upgrade pact_models to 0.4.6 and pact-plugin-driver to 0.1.14 (Ronald Holshausen, Fri Nov 4 16:38:36 2022 +1100) -* 6ad00a5d - fix: Update onig to latest master to fix Regex Matcher Fails On Valid Inputs #214 (Ronald Holshausen, Fri Nov 4 15:23:50 2022 +1100) -* 02d9e2cb - chore: Upgrade pact matching crate to 0.12.12 (Ronald Holshausen, Wed Sep 28 10:11:11 2022 +1000) -* ac4fe73f - chore: fix to release scripts (Ronald Holshausen, Wed Sep 7 10:51:01 2022 +1000) -* f8db90d2 - fix: Upgrade pact_models to 0.4.5 - fixes FFI bug with generators for request paths (Ronald Holshausen, Fri Aug 26 11:44:08 2022 +1000) -* 9d1e8e89 - chore: Upgrade pact_mock_server to 0.9.3 (Ronald Holshausen, Thu Aug 18 16:03:38 2022 +1000) -* 1d5fb787 - chore: Upgrade pact_matching to 0.12.11 (Ronald Holshausen, Thu Aug 18 15:07:23 2022 +1000) -* 32a70382 - chore: Upgrade pact_models (0.4.4), plugin driver (0.1.10), tracing and tracing core crates (Ronald Holshausen, Thu Aug 18 14:41:52 2022 +1000) -* 98c5e2db - chore: correct pact_mock_server_cli docker file (Ronald Holshausen, Tue Aug 16 10:31:50 2022 +1000) -* f2e3d9ff - bump version to 0.7.9 (Ronald Holshausen, Tue Aug 16 10:15:14 2022 +1000) - -# 0.7.8 - Maintenance Release - -* a41fe69c - chore: Upgrade pact_mock_server to 0.9.2 (Ronald Holshausen, Mon Aug 15 17:40:09 2022 +1000) -* e3bef155 - feat: Add ARM64 (aarch64) linux targets to the release build #160 (Ronald Holshausen, Mon Aug 15 16:13:22 2022 +1000) -* 7b6a919b - chore: Upgrade pact_matching crate to 0.12.10 (Ronald Holshausen, Wed Aug 10 12:37:11 2022 +1000) -* 195ad07b - chore: Updated dependant crates (uuid, simplelog) (Ronald Holshausen, Wed Aug 10 10:22:07 2022 +1000) -* a3fe5e7f - chore: Update pact models to 0.4.2 (Ronald Holshausen, Wed Aug 10 10:10:41 2022 +1000) -* fcbee0c2 - fix: rust/pact_mock_server_cli/Dockerfile to reduce vulnerabilities (snyk-bot, Thu Jul 7 11:09:31 2022 +0000) -* 9a6c846f - chore: Upgrade pact_matching to 0.12.9 (Ronald Holshausen, Fri Jun 10 15:46:07 2022 +1000) -* f42026d5 - chore: Upgrade pact_mock_server to 0.9.1 (Ronald Holshausen, Mon May 30 12:09:06 2022 +1000) -* bcddbcfb - chore: Upgrade pact_matching to 0.12.8 (Ronald Holshausen, Mon May 30 11:52:26 2022 +1000) -* 26bb612b - chore: changes required for 0.9.0 of mock server crate (Ronald Holshausen, Fri May 20 16:00:41 2022 +1000) -* d9b9fe72 - chore: Upgrade pact-plugin-driver to 0.1.7 (Ronald Holshausen, Fri May 20 15:56:23 2022 +1000) -* f8471bb7 - chore: switch from log crate to tracing crate (Ronald Holshausen, Fri May 13 13:47:18 2022 +1000) -* f6b942da - chore: Upgrade pact_mock_server to 0.8.11 (Ronald Holshausen, Wed May 11 17:00:46 2022 +1000) -* 08f28e4a - chore: Upgrade pact_matching to 0.12.7 (Ronald Holshausen, Wed May 11 15:57:36 2022 +1000) -* 020b5715 - chore: upgrade pact_models to 0.4.1 (Ronald Holshausen, Wed May 11 11:36:57 2022 +1000) -* 563ae9fc - chore: Upgrade pact_mock_server to 0.8.10 (Ronald Holshausen, Wed Apr 27 15:06:50 2022 +1000) -* bcae77b4 - chore: upgrade pact_matching to 0.12.6 (Ronald Holshausen, Wed Apr 27 14:29:26 2022 +1000) -* cdf72b05 - feat: forward provider details to plugin when verifying (Ronald Holshausen, Fri Apr 22 14:12:34 2022 +1000) -* 2395143a - feat: forward verification to plugin for transports provided by the plugin (Ronald Holshausen, Fri Apr 22 12:02:05 2022 +1000) -* 1e8ae855 - chore: Upgrade pact_mock_server to 0.8.9 (Ronald Holshausen, Wed Apr 13 15:49:03 2022 +1000) -* 0df06dd2 - chore: Upgrade pact_matching to 0.12.5 (Ronald Holshausen, Wed Apr 13 15:38:49 2022 +1000) -* d043f6c7 - chore: upgrade pact_models to 0.3.3 (Ronald Holshausen, Wed Apr 13 15:24:33 2022 +1000) -* 73ae0ef0 - fix: Upgrade reqwest to 0.11.10 to resolve #156 (Ronald Holshausen, Wed Apr 13 13:31:55 2022 +1000) -* 89027c87 - chore: update pact_matching (0.12.4) and pact_mock_server (0.8.8) (Ronald Holshausen, Thu Mar 24 14:09:45 2022 +1100) -* 345b0011 - feat: support mock servers provided from plugins (Ronald Holshausen, Mon Mar 21 15:59:46 2022 +1100) -* eb92d665 - fix: rust/pact_mock_server_cli/Dockerfile to reduce vulnerabilities (snyk-bot, Thu Mar 17 22:20:08 2022 +0000) -* 5a4a8a1c - chore: update pact_mock_server to 0.8.7 (Ronald Holshausen, Fri Mar 4 14:24:23 2022 +1100) -* 8894fdfd - chore: update pact_matching to 0.12.3 (Ronald Holshausen, Fri Mar 4 14:09:17 2022 +1100) -* 8e864502 - chore: update all dependencies (Ronald Holshausen, Fri Mar 4 13:29:59 2022 +1100) -* d1bdd132 - chore: use docker builder image that supports Rust 2021 (Ronald Holshausen, Tue Jan 25 11:46:54 2022 +1100) -* e22067be - bump version to 0.7.8 (Ronald Holshausen, Tue Jan 25 11:17:43 2022 +1100) - -# 0.7.7 - Maintenance Release - -* 10c9b842 - chore: Upgrade pact_mock_server to 0.8.6 (Ronald Holshausen, Mon Jan 17 16:57:31 2022 +1100) -* 5e4c68ef - chore: update pact matching to 0.12.2 (Ronald Holshausen, Mon Jan 17 16:29:21 2022 +1100) -* 4f1ecff2 - chore: Upgrade pact-models to 0.2.7 (Ronald Holshausen, Mon Jan 17 10:53:26 2022 +1100) -* c2089645 - fix: log crate version must be fixed across all crates (including plugin driver) (Ronald Holshausen, Fri Jan 14 16:10:50 2022 +1100) -* 0a6e7d9d - refactor: Convert MatchingContext to a trait and use DocPath instead of string slices (Ronald Holshausen, Wed Dec 29 14:24:39 2021 +1100) -* 4d088317 - chore: Update pact_mock_server crate to 0.8.4 (Ronald Holshausen, Thu Dec 23 13:24:15 2021 +1100) -* 52bc1735 - chore: update pact_matching crate to 0.11.5 (Ronald Holshausen, Thu Dec 23 13:12:08 2021 +1100) -* 5479a634 - chore: Update pact_models (0.2.4) and pact-plugin-driver (0.0.14) (Ronald Holshausen, Thu Dec 23 12:57:02 2021 +1100) -* fc0a8360 - chore: update pact_matching to 0.11.4 (Ronald Holshausen, Mon Dec 20 12:19:36 2021 +1100) -* 631167fa - chore: update to latest mock server crate (Ronald Holshausen, Wed Nov 17 15:13:32 2021 +1100) -* 5d4a09c6 - feat: store the pact specification version with the mock server (Ronald Holshausen, Wed Nov 17 14:46:56 2021 +1100) -* 5d974c4a - chore: update to latest models and plugin driver crates (Ronald Holshausen, Tue Nov 16 11:56:53 2021 +1100) -* fc4580b8 - chore: drop beta from pact_mock_server version (Ronald Holshausen, Thu Nov 4 15:28:51 2021 +1100) -* bd2bd0ec - chore: drop beta from pact_matching version (Ronald Holshausen, Wed Nov 3 13:28:35 2021 +1100) -* 296b4370 - chore: update project to Rust 2021 edition (Ronald Holshausen, Fri Oct 22 10:44:48 2021 +1100) -* a561f883 - chore: use the non-beta models crate (Ronald Holshausen, Thu Oct 21 18:10:27 2021 +1100) -* a3d321cb - chore: update to latest mock server crate (Ronald Holshausen, Tue Oct 19 17:28:24 2021 +1100) -* 46a404c0 - chore: update to latest pact matching crate (Ronald Holshausen, Tue Oct 19 17:20:27 2021 +1100) -* 918e5beb - fix: update to latest models and plugin driver crates (Ronald Holshausen, Tue Oct 19 17:09:48 2021 +1100) -* 3819522d - chore: update to the latest matching and mock server crates (Ronald Holshausen, Tue Oct 19 11:34:18 2021 +1100) -* df386c8a - chore: use the published version of pact-plugin-driver (Ronald Holshausen, Mon Oct 18 13:41:36 2021 +1100) -* 1dc6f543 - chore: bump pact_mock_server version (Ronald Holshausen, Tue Oct 12 16:36:51 2021 +1100) -* 9bbbb52e - chore: bump pact matching crate version (Ronald Holshausen, Tue Oct 12 16:24:01 2021 +1100) -* 1eb37c13 - chore: use the published version of the models crate (Ronald Holshausen, Thu Oct 7 10:49:11 2021 +1100) -* ddc64246 - chore: use the published version of the models crate (Ronald Holshausen, Wed Oct 6 12:40:52 2021 +1100) -* 6d23796f - feat(plugins): support each key and each value matchers (Ronald Holshausen, Wed Sep 29 11:10:46 2021 +1000) -* 6f20282d - Merge branch 'master' into feat/plugins (Ronald Holshausen, Tue Sep 28 14:51:34 2021 +1000) -* 5599fe38 - bump version to 0.7.7 (Ronald Holshausen, Tue Sep 28 13:48:12 2021 +1000) -* b71dcabf - refactor(plugins): rename ContentTypeOverride -> ContentTypeHint (Ronald Holshausen, Tue Sep 14 15:08:52 2021 +1000) -* 03ebe632 - Merge branch 'master' into feat/plugins (Ronald Holshausen, Mon Sep 13 12:01:13 2021 +1000) -* fd6f8f40 - chore: Bump pact_mock_server version to 0.8.0-beta.0 (Ronald Holshausen, Mon Sep 13 11:46:11 2021 +1000) -* 716809f6 - chore: Get CI build passing (Ronald Holshausen, Fri Sep 10 14:55:46 2021 +1000) -* ceb1c35f - Merge branch 'master' into feat/plugins (Ronald Holshausen, Tue Sep 7 10:07:45 2021 +1000) -* b9aa7ecb - feat(Plugins): allow plugins to override text/binary format of the interaction content (Ronald Holshausen, Mon Aug 30 10:48:04 2021 +1000) -* 0c5cede2 - chore: bump models crate to 0.2 (Ronald Holshausen, Mon Aug 23 12:56:14 2021 +1000) - -# 0.7.6 - support native TLS certs - -* df715cd5 - feat: support native TLS. Fixes #144 (Matt Fellows, Mon Sep 20 13:00:33 2021 +1000) -* 971b980e - chore: fix clippy warnings (Ronald Holshausen, Fri Sep 10 17:31:16 2021 +1000) -* 9baa714d - chore: bump minor version of matching crate (Ronald Holshausen, Fri Jul 23 14:03:20 2021 +1000) -* 533c9e1f - chore: bump minor version of the Pact models crate (Ronald Holshausen, Fri Jul 23 13:15:32 2021 +1000) -* 47177971 - Revert "chore: pin the pact_mock_server_cli dependencies" (Ronald Holshausen, Wed Jul 21 15:53:47 2021 +1000) -* 3dbb2b1c - bump version to 0.7.6 (Ronald Holshausen, Wed Jul 21 15:49:42 2021 +1000) - -# 0.7.5 - Bugfix Release - -* 15e5d587 - chore: pin the pact_mock_server_cli dependencies (Ronald Holshausen, Wed Jul 21 15:14:08 2021 +1000) -* c958c24a - Revert "update changelog for release 0.7.5" (Ronald Holshausen, Wed Jul 21 15:07:34 2021 +1000) -* 4193beb8 - update changelog for release 0.7.5 (Ronald Holshausen, Wed Jul 21 14:01:09 2021 +1000) -* 3dccf866 - refacfor: moved the pact structs to the models crate (Ronald Holshausen, Sun Jul 18 16:58:14 2021 +1000) -* ed73b98a - chore: fix compiler warnings (Ronald Holshausen, Wed Jul 7 13:54:53 2021 +1000) -* 5c670814 - refactor: move expression_parser to pact_models crate (Ronald Holshausen, Fri Jun 11 10:51:51 2021 +1000) -* 6932c6d5 - Revert "chore: remove unused imports" (Ronald Holshausen, Sat Jun 5 16:26:52 2021 +1000) -* b4e26844 - fix: reqwest is dyn linked to openssl by default, which causes a SIGSEGV on alpine linux (Ronald Holshausen, Tue Jun 1 14:21:31 2021 +1000) -* 913b7b17 - chore: correct CLI docker release files (Ronald Holshausen, Tue Jun 1 11:25:28 2021 +1000) -* 13221ad9 - chore: Mock server CLI release build was overwriting the Windows exe with the SHA checksum (Ronald Holshausen, Sun May 30 18:30:44 2021 +1000) -* 11885733 - bump version to 0.7.5 (Ronald Holshausen, Sun May 30 18:08:28 2021 +1000) - -# 0.7.4 - Upgraded crates + V4 features - -* 62a653c - chore: remove unused imports (Matt Fellows, Thu May 27 23:40:27 2021 +1000) -* 4224088 - chore: add shasums to all release artifacts (Matt Fellows, Wed May 5 15:18:31 2021 +1000) -* 735c9e7 - chore: bump pact_matching to 0.9 (Ronald Holshausen, Sun Apr 25 13:50:18 2021 +1000) -* fb373b4 - chore: bump version to 0.0.2 (Ronald Holshausen, Sun Apr 25 13:40:52 2021 +1000) -* d010630 - chore: cleanup deprecation and compiler warnings (Ronald Holshausen, Sun Apr 25 12:23:30 2021 +1000) -* a725ab1 - feat(V4): added synchronous request/response message formats (Ronald Holshausen, Sat Apr 24 16:05:12 2021 +1000) -* 728465d - fix: clippy violation - caused a compiler error (Ronald Holshausen, Sat Apr 24 13:07:32 2021 +1000) -* e3d48a0 - chore: cleanup some clippy voilations (Ronald Holshausen, Sat Apr 24 12:57:14 2021 +1000) -* 80b7148 - feat(V4): Updated consumer DSL to set comments + mock server initial support for V4 pacts (Ronald Holshausen, Fri Apr 23 17:58:10 2021 +1000) -* 220fb5e - refactor: move the PactSpecification enum to the pact_models crate (Ronald Holshausen, Thu Apr 22 11:18:26 2021 +1000) -* 9976e80 - feat: added read locks and a mutex guard to reading and writing pacts (Ronald Holshausen, Mon Feb 8 11:58:52 2021 +1100) -* 49a3cf2 - refactor: use bytes crate instead of vector of bytes for body content (Ronald Holshausen, Sun Feb 7 14:43:40 2021 +1100) -* 4afa86a - fix: add callback timeout option for verifcation callbacks (Ronald Holshausen, Sat Feb 6 12:27:32 2021 +1100) -* e43fdb8 - chore: upgrade maplit, itertools (Audun Halland, Mon Jan 11 05:30:10 2021 +0100) -* 5e5c320 - chore: upgrade rand, rand_regex (Audun Halland, Sat Jan 9 09:33:13 2021 +0100) -* 4a70bef - chore: upgrade expectest to 0.12 (Audun Halland, Sat Jan 9 11:29:29 2021 +0100) -* 3a28a6c - chore: upgrade regex, chrono-tz (Audun Halland, Sat Jan 9 11:12:49 2021 +0100) -* afeb679 - chore: upgrade simplelog (Audun Halland, Sat Jan 9 10:55:08 2021 +0100) -* 9a8a63f - chore: upgrade quickcheck (Audun Halland, Sat Jan 9 08:46:51 2021 +0100) -* 39fc84d - chore: upgrade http to get rid of bytes 0.5.6 (Audun Halland, Sat Jan 9 07:18:50 2021 +0100) -* 3a6945e - chore: Upgrade reqwest to 0.11 and hence tokio to 1.0 (Ronald Holshausen, Wed Jan 6 15:34:47 2021 +1100) -* 3bef361 - chore: add apt clean to docker file (Ronald Holshausen, Tue Jan 5 13:31:31 2021 +1100) -* b9ba322 - bump version to 0.7.4 (Ronald Holshausen, Tue Jan 5 13:13:50 2021 +1100) - -# 0.7.3 - Add TLS (self-signed) option - -* 773b4b1 - fix: pinning version of webmachine until reqwest is updated (Ronald Holshausen, Tue Jan 5 12:41:05 2021 +1100) -* 76f052b - feat: add self-signed tls option to mockserver cli (to test TLS with Tokio 1.0) (Ronald Holshausen, Tue Jan 5 11:39:53 2021 +1100) -* 3d531b3 - bump version to 0.7.3 (Ronald Holshausen, Thu Dec 31 13:11:40 2020 +1100) -* d85e9ee - chore: correct changelog (Ronald Holshausen, Thu Dec 31 13:06:58 2020 +1100) - -# 0.7.2 - support generators associated with array contains matcher variants - -* 56a13d3: update pact_matching and pact_mock_server crates to latest -* bfba4bd - bump version to 0.7.2 (Ronald Holshausen, Fri Oct 16 11:50:58 2020 +1100) - -# 0.7.1 - arrayContains matcher + text/xml content type - -* 2fb0c6e - fix: fix the build after refactoring the pact write function (Ronald Holshausen, Wed Oct 14 11:07:57 2020 +1100) -* 7fbc731 - chore: bump minor version of matching lib (Ronald Holshausen, Fri Oct 9 10:42:33 2020 +1100) -* 7232e89 - feat: Add initial V4 models and example pact files (Ronald Holshausen, Tue Oct 6 09:13:21 2020 +1100) -* eb0389c - bump version to 0.7.1 (Ronald Holshausen, Mon Sep 28 12:17:05 2020 +1000) - -# 0.7.0 - Async changes (using Hyper 0.13) + CORS pre-flight support - -* 7e68e4c - feat: enable CORS behaviour based on the mock server config (Ronald Holshausen, Mon Sep 28 11:42:23 2020 +1000) -* 4eb9188 - chore: cleanup warnings (Ronald Holshausen, Mon Sep 28 10:30:42 2020 +1000) -* d0b84f9 - refactor: remove the use of lazy_static (Ronald Holshausen, Sun Sep 27 17:08:58 2020 +1000) -* bdbfccc - refactor: update mock server CLI to be async (Ronald Holshausen, Sun Sep 27 13:12:51 2020 +1000) -* 7fd4dd2 - refactor: update the mock server CLI to use webmachine 0.2 and hyper 0.13 (Ronald Holshausen, Sun Sep 27 09:39:23 2020 +1000) -* 29ba743 - feat: add a mock server config struct (Ronald Holshausen, Thu Sep 24 10:30:59 2020 +1000) -* 2e662a6 - feat: handle CORS pre-flight requests in the mock server (Ronald Holshausen, Wed Sep 23 17:59:32 2020 +1000) -* 2d44ffd - chore: bump minor version of the matching crate (Ronald Holshausen, Mon Sep 14 12:06:37 2020 +1000) -* a05bcbb - refactor: renamed Pact to RequestResponsePact (Ronald Holshausen, Sun Sep 13 12:45:34 2020 +1000) -* ed207a7 - chore: updated readmes for docs site (Ronald Holshausen, Sun Jun 28 10:04:09 2020 +1000) -* 56258d7 - bump version to 0.6.3 (Ronald Holshausen, Wed Jun 24 11:01:06 2020 +1000) - -# 0.6.2 - Updated XML Matching - -* 218239c - chore: update to latest matching crate (Ronald Holshausen, Wed Jun 24 10:53:35 2020 +1000) - -# 0.6.1 - Updated crates - -* 98d7abb - chore: update GH action to build pact_mock_server_cli (Ronald Holshausen, Wed May 27 14:55:14 2020 +1000) -* bea787c - chore: bump matching crate version to 0.6.0 (Ronald Holshausen, Sat May 23 17:56:04 2020 +1000) -* 411f697 - chore: correct some clippy warnings (Ronald Holshausen, Wed Apr 29 16:49:36 2020 +1000) -* f84e672 - chore: update mock server library to latest (Ronald Holshausen, Fri Apr 24 11:00:34 2020 +1000) -* 43de9c3 - chore: update matching library to latest (Ronald Holshausen, Fri Apr 24 10:20:55 2020 +1000) -* 1651af1 - fix: upgrade uuid crate (Ronald Holshausen, Thu Apr 23 14:56:34 2020 +1000) -* d457221 - chore: update dependant crates to use mock server lib 0.7.0 (Ronald Holshausen, Sun Jan 19 11:31:21 2020 +1100) -* 8a0c5c2 - fix: docker file needs to be able to build Oniguruma lib (Ronald Holshausen, Sat Dec 14 19:23:45 2019 +1100) -* e1a0f16 - bump version to 0.6.1 (Ronald Holshausen, Sat Dec 14 17:32:50 2019 +1100) - -# 0.6.0 - Bugfix Release - -* d2908af - chore: bump minor version (Ronald Holshausen, Sat Dec 14 17:15:41 2019 +1100) -* 2d95535 - pact_mock_server_cli: Remove extern crate from main.rs (Audun Halland, Sun Nov 17 23:10:10 2019 +0100) -* abc2a36 - pact_mock_server_cli: Upgrade log, simplelog (Audun Halland, Sun Nov 17 23:01:50 2019 +0100) -* 713cd6a - Explicit edition 2018 in Cargo.toml files (Audun Halland, Sat Nov 16 23:55:37 2019 +0100) -* 924452f - 2018 edition autofix "cargo fix --edition" (Audun Halland, Sat Nov 16 22:27:42 2019 +0100) -* 097d045 - refactor: added a mock server ffi module and bumped the mock server minor version (Ronald Holshausen, Sat Sep 7 09:39:27 2019 +1000) -* f79b033 - chore: update terminal support in release scripts (Ronald Holshausen, Sat Aug 24 12:25:28 2019 +1000) -* da1956a - chore: bump the version of the matching lib (Ronald Holshausen, Sat Aug 24 12:06:51 2019 +1000) -* c5e55ab - bump version to 0.5.2 (Ronald Holshausen, Sat Aug 24 11:29:20 2019 +1000) - -# 0.5.1 - support headers with multiple values - -* 5b22076 - fix: docker release script (Ronald Holshausen, Sat Jul 27 16:52:12 2019 +1000) -* 2e59235 - bump version to 0.5.1 (Ronald Holshausen, Sat Jul 27 16:36:51 2019 +1000) - -# 0.5.0 - Upgrade to non-blocking Hyper 0.12 - -* d842100 - chore: bump component versions to 0.5.0 (Ronald Holshausen, Sat Jul 27 15:44:51 2019 +1000) -* 2826bb0 - Make pact_mock_server_cli use ServerManager (Audun Halland, Tue Jul 23 01:40:46 2019 +0200) -* 4df2797 - Rename API function again (Audun Halland, Mon Jul 22 23:38:11 2019 +0200) -* f8fa0d8 - chore: Bump pact matchig version to 0.5.0 (Ronald Holshausen, Sat Jan 5 19:25:53 2019 +1100) -* 074569a - feat: Add a parameter for the server key to the start command #26 (Ronald Holshausen, Sun Apr 8 18:24:36 2018 +1000) -* 40ad75b - feat: Add a command to shut the master mock server down #26 (Ronald Holshausen, Sun Apr 8 18:15:08 2018 +1000) -* e5af1b0 - fix: global options no longer incorrectly display a warning about being provided twice #27 (Ronald Holshausen, Sun Apr 8 16:11:41 2018 +1000) -* 3c33294 - fix: Only print errors in the CLI to STDERR #28 (Ronald Holshausen, Sun Apr 8 15:57:56 2018 +1000) -* 386ab52 - fix: corrected the release scripts to check for a version parameter (Ronald Holshausen, Sun Apr 8 13:44:57 2018 +1000) -* 6c2d6c8 - chore: added docker release scripts for the CLIs (Ronald Holshausen, Sun Apr 8 13:44:18 2018 +1000) -* a45d5f8 - fix: corrected the docker build for the mock server cli #14 (Ronald Holshausen, Sun Apr 8 12:52:53 2018 +1000) -* 6343607 - fix: CLI was reporting incorrect pact specification version (Ronald Holshausen, Sun Apr 8 12:36:56 2018 +1000) -* 9ea039f - bump version to 0.4.1 (Ronald Holshausen, Sat Apr 7 14:55:59 2018 +1000) - -# 0.4.0 - First V3 specification release - -* 398edaf - Upgrade UUID library to latest (Ronald Holshausen, Sat Apr 7 12:29:58 2018 +1000) -* 7fef36b - Merge branch 'v2-spec' into v3-spec (Ronald Holshausen, Sat Nov 4 12:49:07 2017 +1100) -* a306b12 - bump version to 0.3.2 (Ronald Holshausen, Fri Nov 3 14:07:07 2017 +1100) -* 940a0e3 - Reverted hyper to 0.9.x (Ronald Holshausen, Sun Oct 22 12:01:17 2017 +1100) -* fbe35d8 - Compiling after merge from v2-spec (Ronald Holshausen, Sun Oct 22 11:39:46 2017 +1100) -* 00dc75a - Bump version to 0.4.0 (Ronald Holshausen, Sun Oct 22 10:46:48 2017 +1100) -* 184127a - Merge branch 'v2-spec' into v3-spec (Ronald Holshausen, Sun Oct 22 10:32:31 2017 +1100) -* e82ee08 - Merge branch 'v2-spec' into v3-spec (Ronald Holshausen, Mon Oct 16 09:24:11 2017 +1100) -* 64ff667 - Upgraded the mock server implemenation to use Hyper 0.11.2 (Ronald Holshausen, Wed Sep 6 12:56:47 2017 +1000) -* e5a93f3 - Merge branch 'master' into v3-spec (Ronald Holshausen, Sun Aug 20 09:53:48 2017 +1000) -* 639ac22 - fixes after merge in from master (Ronald Holshausen, Sun Oct 23 10:45:54 2016 +1100) -* 49e45f7 - Merge branch 'master' into v3-spec (Ronald Holshausen, Sun Oct 23 10:10:40 2016 +1100) -* a7533dc - updated the mockserver lib and cli to generate V3 pacts (Ronald Holshausen, Thu Aug 4 22:13:20 2016 +1000) -* 539eb48 - updated all the readmes and cargo manefests for v3 (Ronald Holshausen, Tue Jul 19 15:46:18 2016 +1000) - -# 0.3.1 - Bugfixes plus changes for running with docker - -* cdf01f3 - Add a docker file for the pact mock server cli (Ronald Holshausen, Fri Nov 3 11:51:01 2017 +1100) -* a56b6a6 - Change the column heading to verification state in the mock server list output #24 (Ronald Holshausen, Sun Oct 22 15:15:30 2017 +1100) -* 814fe12 - Modify AssafKatz3's implementation to scan for next available port from a base port number #15 (Ronald Holshausen, Sun Oct 22 14:40:13 2017 +1100) -* 37abe19 - Pulled in changes from https://github.com/AssafKatz3/pact-reference.git #14 (Assaf Katz, Mon Sep 25 12:28:17 2017 +0300) -* 9cda328 - bump version to 0.3.1 (Ronald Holshausen, Fri Oct 20 11:01:04 2017 +1100) - -# 0.3.0 - Backported the matching rules from the V3 branch - -* c8595cc - Correct the paths in the release scripts for pact_mock_server_cli (Ronald Holshausen, Fri Oct 20 10:48:03 2017 +1100) -* ac94388 - Tests are now all passing #20 (Ronald Holshausen, Thu Oct 19 15:14:25 2017 +1100) -* c983c63 - Bump versions to 0.3.0 (Ronald Holshausen, Wed Oct 18 13:54:46 2017 +1100) -* 06e92e5 - Refer to local libs using version+paths (Eric Kidd, Tue Oct 3 06:22:23 2017 -0400) -* 7afd258 - Update all the cargo manifest versions and commit the cargo lock files (Ronald Holshausen, Wed May 17 10:37:44 2017 +1000) -* be8c299 - Cleanup unused BTreeMap usages and use remote pact dependencies (Anthony Damtsis, Mon May 15 17:09:14 2017 +1000) -* a59fb98 - Migrate remaining pact modules over to serde (Anthony Damtsis, Mon May 15 16:59:04 2017 +1000) -* c5f9c27 - bump version to 0.2.4 (Ronald Holshausen, Sun Apr 23 17:39:49 2017 +1000) - -# 0.2.3 - Bugfix Release - -* 224ad98 - Change no-console-log to no-term-log and use a simple logger if it is set #6 (Ronald Holshausen, Sun Apr 23 17:19:53 2017 +1000) -* cec2358 - bump version to 0.2.3 (Ronald Holshausen, Fri Apr 21 14:33:13 2017 +1000) - -# 0.2.2 - Bugfix Release - -* 53074cf - Merge branch 'v1.1-spec' into v2-spec (Ronald Holshausen, Fri Apr 21 14:17:05 2017 +1000) -* 01fa713 - bump version to 0.1.3 (Ronald Holshausen, Fri Apr 21 14:08:58 2017 +1000) -* e4b59e5 - update changelog for release 0.1.2 (Ronald Holshausen, Fri Apr 21 14:05:14 2017 +1000) -* 07b1827 - Merge branch 'v1-spec' into v1.1-spec (Ronald Holshausen, Fri Apr 21 13:39:50 2017 +1000) -* da4e32f - bump version to 0.0.3 (Ronald Holshausen, Fri Apr 21 13:31:18 2017 +1000) -* 9b4b5fb - update changelog for release 0.0.2 (Ronald Holshausen, Fri Apr 21 13:27:54 2017 +1000) -* 2276cd0 - upgraded simple log crate and added cli options to disable file or console logging #6 (Ronald Holshausen, Fri Apr 21 13:15:27 2017 +1000) -* ea5cec8 - bump version to 0.2.2 (Ronald Holshausen, Sun Oct 9 16:43:59 2016 +1100) -* 0b83b06 - correct the displayed help for the pact_mock_server_cli (Ronald Holshausen, Sat Oct 8 17:29:19 2016 +1100) - -# 0.1.2 - Bugfix Release - -* 07b1827 - Merge branch 'v1-spec' into v1.1-spec (Ronald Holshausen, Fri Apr 21 13:39:50 2017 +1000) -* da4e32f - bump version to 0.0.3 (Ronald Holshausen, Fri Apr 21 13:31:18 2017 +1000) -* 9b4b5fb - update changelog for release 0.0.2 (Ronald Holshausen, Fri Apr 21 13:27:54 2017 +1000) -* 2276cd0 - upgraded simple log crate and added cli options to disable file or console logging #6 (Ronald Holshausen, Fri Apr 21 13:15:27 2017 +1000) -* 91d1216 - bump version to 0.1.2 (Ronald Holshausen, Sat Oct 8 17:49:20 2016 +1100) -* 0b83b06 - correct the displayed help for the pact_mock_server_cli (Ronald Holshausen, Sat Oct 8 17:29:19 2016 +1100) - -# 0.0.2 - Bugfix Release - -* 2276cd0 - upgraded simple log crate and added cli options to disable file or console logging #6 (Ronald Holshausen, Fri Apr 21 13:15:27 2017 +1000) -* 0b83b06 - correct the displayed help for the pact_mock_server_cli (Ronald Holshausen, Sat Oct 8 17:29:19 2016 +1100) -* 04d9e5f - update the docs for the pact consumer library (Ronald Holshausen, Mon Sep 26 23:06:19 2016 +1000) -* 40c9e02 - exclude IntelliJ files from publishing (Ronald Holshausen, Mon Sep 26 21:22:35 2016 +1000) -* c1d97a0 - correct the repository paths in the cargo manifests (Ronald Holshausen, Tue Jun 28 14:52:46 2016 +1000) -* 91d6d62 - removed the v1 from the project path, will use a git branch instead (Ronald Holshausen, Mon Jun 27 22:09:32 2016 +1000) - -# 0.2.1 - Changes required for verifying V2 pacts - -* e3eebbd - update projects to use the published pact mock server library (Ronald Holshausen, Sun Oct 9 16:36:25 2016 +1100) -* 770010a - update projects to use the published pact matching lib (Ronald Holshausen, Sun Oct 9 16:25:15 2016 +1100) -* a21973a - Get the build passing after merge from V1.1 branch (Ronald Holshausen, Sun Oct 9 13:47:09 2016 +1100) -* 341607c - Merge branch 'v1.1-spec' into v2-spec (Ronald Holshausen, Sun Oct 9 12:10:12 2016 +1100) -* 91d1216 - bump version to 0.1.2 (Ronald Holshausen, Sat Oct 8 17:49:20 2016 +1100) -* 0d324a8 - bump version to 0.2.1 (Ronald Holshausen, Wed Jul 13 14:26:40 2016 +1000) -* 377b372 - update changelog for release 0.2.0 (Ronald Holshausen, Wed Jul 13 14:22:15 2016 +1000) -* 7ed156e - updated project for the V2 spec release (Ronald Holshausen, Wed Jul 13 14:19:12 2016 +1000) -* 22b0bb9 - fix for failing build (Ronald Holshausen, Tue Jul 12 16:59:56 2016 +1000) -* 534e7a1 - updated readmes and bump versions for the V2 implementation (Ronald Holshausen, Wed Jun 29 10:38:32 2016 +1000) - -# 0.1.1 - Changes required for verifying V1.1 pacts - -* 28928ef - correct the displayed help for the pact_mock_server_cli (Ronald Holshausen, Sat Oct 8 17:29:19 2016 +1100) -* 3ca2df8 - update dependencies (Ronald Holshausen, Sat Oct 8 17:22:48 2016 +1100) -* a46dabb - update all references to V1 spec after merge (Ronald Holshausen, Sat Oct 8 16:20:51 2016 +1100) -* 1d6d4f8 - Merge branch 'v1-spec' into v1.1-spec (Ronald Holshausen, Sat Oct 8 15:44:25 2016 +1100) -* 04d9e5f - update the docs for the pact consumer library (Ronald Holshausen, Mon Sep 26 23:06:19 2016 +1000) -* 40c9e02 - exclude IntelliJ files from publishing (Ronald Holshausen, Mon Sep 26 21:22:35 2016 +1000) -* efe036c - bump version to 0.1.1 (Ronald Holshausen, Tue Jun 28 21:54:59 2016 +1000) -* c1d97a0 - correct the repository paths in the cargo manifests (Ronald Holshausen, Tue Jun 28 14:52:46 2016 +1000) - -# 0.2.0 - V2 Specification Implementation - -* 7ed156e - updated project for the V2 spec release (Ronald Holshausen, Wed Jul 13 14:19:12 2016 +1000) -* 22b0bb9 - fix for failing build (Ronald Holshausen, Tue Jul 12 16:59:56 2016 +1000) -* 534e7a1 - updated readmes and bump versions for the V2 implementation (Ronald Holshausen, Wed Jun 29 10:38:32 2016 +1000) -* efe036c - bump version to 0.1.1 (Ronald Holshausen, Tue Jun 28 21:54:59 2016 +1000) - -# 0.1.0 - V1.1 Specification Implementation - -* f91bb6e - use the published versions of the matching and mock server libraries (Ronald Holshausen, Tue Jun 28 21:38:21 2016 +1000) -* 140526d - Implement V1.1 matching (Ronald Holshausen, Tue Jun 28 15:58:35 2016 +1000) -* 4224875 - update readmes and bump versions for V1.1 implementation (Ronald Holshausen, Tue Jun 28 15:05:39 2016 +1000) -* 91d6d62 - removed the v1 from the project path, will use a git branch instead (Ronald Holshausen, Mon Jun 27 22:09:32 2016 +1000) - -# 0.0.1 - Feature Release - -* 18c009b - added changelog (Ronald Holshausen, Mon Jun 27 19:42:26 2016 +1000) -* 78126ab - no point publishing the rust docs as pact_mock_server_cli is not a library (Ronald Holshausen, Mon Jun 27 19:38:56 2016 +1000) -* 8867836 - correct the release script (Ronald Holshausen, Mon Jun 27 19:36:46 2016 +1000) -* aa2d2dd - added release script for pact_mock_server_cli (Ronald Holshausen, Mon Jun 27 17:20:38 2016 +1000) -* 2a78f40 - updated the README for the pact_mock_server_cli (Ronald Holshausen, Mon Jun 27 17:01:16 2016 +1000) -* 3f77f3f - update pact_mock_server_cli to depend on libpact_mock_server from crates.io (Ronald Holshausen, Mon Jun 27 15:50:15 2016 +1000) -* 3b6bf66 - fix the project deps for the travis build (Ronald Holshausen, Mon Jun 27 14:46:19 2016 +1000) -* f7d9960 - implemented the shutdown mock server command (Ronald Holshausen, Sun Jun 26 15:05:40 2016 +1000) -* f91b9fd - compile against the published webmachine crate (Ronald Holshausen, Sun Jun 26 13:14:34 2016 +1000) -* b7635b8 - correctly handle the status codes from the master mock server (Ronald Holshausen, Sun Jun 26 10:49:47 2016 +1000) -* 6234bbd - implemented delete on the master server to shut a mock server down (Ronald Holshausen, Sat Jun 25 16:59:39 2016 +1000) -* ec23a8b - use a Hyper Handler instead of a closure as it is easier to be thread safe (Ronald Holshausen, Fri Jun 24 16:30:28 2016 +1000) -* dd850bc - Got POST to main resource working with webmachine (Ronald Holshausen, Thu Jun 23 13:01:25 2016 +1000) -* b5b41ee - got GET to main resource working with webmachine (Ronald Holshausen, Thu Jun 23 11:30:10 2016 +1000) -* 079fdd4 - correct the webmachine-rust reference (Ronald Holshausen, Thu Jun 16 19:35:39 2016 +1000) -* 4c60f07 - replace rustful with webmachine (Ronald Holshausen, Thu Jun 16 17:31:11 2016 +1000) -* 44daccc - add an optional port number to start the mock server with (Ronald Holshausen, Wed Jun 15 12:40:51 2016 +1000) -* 0cfc690 - add the webmachine project as a dependency (Ronald Holshausen, Thu Jun 9 22:26:16 2016 +1000) -* 7dc4b52 - implemented merging of pact files when writing (Ronald Holshausen, Thu Jun 9 17:34:02 2016 +1000) -* 34fd827 - implement a write_pact exported function to the mock server library (Ronald Holshausen, Thu Jun 9 12:15:01 2016 +1000) -* dcde5dc - add a newline at the end of the help for people with crazy terminal settings (Ronald Holshausen, Thu Jun 9 11:12:16 2016 +1000) -* 511d7a1 - bump version of pact mock server cli (Ronald Holshausen, Wed Jun 8 20:27:53 2016 +1000) -* 5157386 - add rustdoc comment to the cli main file (Ronald Holshausen, Wed Jun 8 20:01:12 2016 +1000) - - -# 0.0.0 - First Release diff --git a/rust/pact_mock_server_cli/Cargo.toml b/rust/pact_mock_server_cli/Cargo.toml deleted file mode 100644 index 86f9732ba..000000000 --- a/rust/pact_mock_server_cli/Cargo.toml +++ /dev/null @@ -1,55 +0,0 @@ -[package] -name = "pact_mock_server_cli" -version = "1.0.6" -authors = ["Ronald Holshausen "] -edition = "2021" -description = "Standalone pact mock server for consumer pact tests" -homepage = "https://www.pact.io" -repository = "https://github.com/pact-foundation/pact-reference/blob/master/rust/pact_mock_server_cli" -readme = "README.md" -keywords = ["testing", "pact", "cdc", "mockserver"] -license = "MIT" -exclude = [ - "*.iml" -] - -[features] -default = ["datetime", "xml", "plugins", "multipart", "tls"] -datetime = ["pact_models/datetime", "pact_matching/datetime", "pact_mock_server/datetime"] # Support for date/time matchers and expressions -xml = ["pact_models/xml", "pact_matching/xml", "pact_mock_server/xml"] # support for matching XML documents -plugins = ["pact_matching/plugins", "pact_mock_server/plugins"] -multipart = ["pact_matching/multipart", "pact_mock_server/multipart"] # suport for MIME multipart bodies -tls = ["pact_mock_server/tls"] - -[dependencies] -anyhow = "1.0.75" -clap = { version = "~4.4.11", features = ["cargo"] } -futures = "0.3.29" -http = "0.2.9" -hyper = "0.14.28" -maplit = "1.0.2" -itertools = "0.12.0" -log = "0.4.20" -lazy_static = "1.4.0" -pact_matching = { version = "~1.2.2", path = "../pact_matching", default-features = false } -pact_mock_server = { version = "~1.2.6", path = "../pact_mock_server", default-features = false } -pact_models = { version = "~1.2.0", default-features = false } -rand = "0.8.5" -regex = "1.10.2" -reqwest = { version = "0.11.23", default-features = false, features = ["rustls-tls-native-roots", "blocking", "json"] } -serde_json = "1.0.108" -tokio = { version = "1.35.1", features = ["full"] } -tracing = "0.1.40" -tracing-appender = "0.2.3" -tracing-core = "0.1.32" -tracing-subscriber = { version = "0.3.18", features = ["env-filter", "local-time", "tracing-log"] } -url = "2.5.0" -uuid = { version = "1.6.1", features = ["v4"] } -webmachine-rust = "0.3.0" - -[dev-dependencies] -quickcheck = "1" -expectest = "0.12.0" -trycmd = "0.15.0" -test-log = "0.2.14" -env_logger = "0.11.3" diff --git a/rust/pact_mock_server_cli/Dockerfile b/rust/pact_mock_server_cli/Dockerfile deleted file mode 100644 index ab2737fd0..000000000 --- a/rust/pact_mock_server_cli/Dockerfile +++ /dev/null @@ -1,22 +0,0 @@ -ARG ARCH= -FROM rust:1-alpine3.15 AS builder -ARG BIN_ARCH=x86_64 -ARG VERSION=1.0.5 - -RUN apk --no-cache add wget -RUN wget -O pact_mock_server_cli.gz https://github.com/pact-foundation/pact-reference/releases/download/pact_mock_server_cli-v${VERSION}/pact_mock_server_cli-linux-${BIN_ARCH}.gz -RUN gunzip pact_mock_server_cli.gz -RUN chmod +x pact_mock_server_cli - - -# Now, we need to build our _real_ Docker container, copying in the executable. -FROM ${ARCH}alpine:3.16 -RUN apk --no-cache add ca-certificates -COPY --from=builder \ - /pact_mock_server_cli \ - /usr/local/bin/ - -EXPOSE 8080 9000-9020 - -ENTRYPOINT ["/usr/local/bin/pact_mock_server_cli"] -CMD ["start", "--base-port", "9000"] diff --git a/rust/pact_mock_server_cli/README.md b/rust/pact_mock_server_cli/README.md index 1df6ab941..eac3acea9 100644 --- a/rust/pact_mock_server_cli/README.md +++ b/rust/pact_mock_server_cli/README.md @@ -1,491 +1,3 @@ # Standalone Pact Mock Server -This project provides both a restful web api and command line interface to run pact mock servers. It is a single -executable binary and is able to manage multiple mock servers. The lifecycle of each mock server can be controlled by the -restful web api or through the command line interface. It implements the [V3 Pact specification](https://github.com/pact-foundation/pact-specification/tree/version-3). - -[Online rust docs](https://docs.rs/pact_mock_server_cli/) - -## Command line interface - -The mock server is bundles as a single binary executable `pact_mock_server_cli`. Running this with out any options displays -the standard help. - -```console,ignore -$ ./pact_mock_server_cli --help -./pact_mock_server_cli v1.0.0 -Standalone Pact mock server - -USAGE: - pact_mock_server_cli [FLAGS] [OPTIONS] - -FLAGS: - --help Prints help information - --no-file-log Do not log to an output file - --no-term-log Use a simple logger instead of the term based one - -v, --version Prints version information - -OPTIONS: - -h, --host hostname the master mock server runs on (defaults to localhost) - -l, --loglevel Log level for mock servers to write to the log file (defaults to info) [possible - values: error, warn, info, debug, trace, none] - -p, --port port the master mock server runs on (defaults to 8080) - -SUBCOMMANDS: - create Creates a new mock server from a pact file - help Prints this message or the help of the given subcommand(s) - list Lists all the running mock servers - shutdown Shutdown the mock server by id or port number, releasing all its resources - shutdown-master Performs a graceful shutdown of the master server (displayed when it started) - start Starts the master mock server - verify Verify the mock server by id or port number, and generate a pact file if all ok - - -``` - -### Options - -The following options are available for all subcommands: - -#### Host: -h, --host - -This sets the host the master mock server runs on. By default this will be localhost. - -#### Port: -p, --port - -This sets the port that the master mock server runs on. By default this will be 8080. The start command will start the -master server using this port. - -#### Log level: -l, --loglevel - -This sets the log level that the CLI and mock servers log at. It defaults to info. Valid values are: error, warn, -info, debug, trace, none. - -### Sub-commands - -#### help - -This prints either the main help or the help for a sub-command. - -#### start - -This starts the master mock server. This server needs to be running for the other sub-commands to work. - -```console -$ ./pact_mock_server_cli help start -Starts the master mock server - -Usage: pact_mock_server_cli start [OPTIONS] - -Options: - --help Print help and exit - -o, --output the directory where to write files to (defaults to current directory) - --base-port the base port number that mock server ports will be allocated from. If not specified, ports will be randomly assigned by the OS. - -v, --version Print version information and exit - -p, --port port the master mock server runs on (defaults to 8080) - --server-key the server key to use to authenticate shutdown requests (defaults to a random generated one) - -h, --host hostname the master mock server runs on (defaults to localhost) - -l, --loglevel Log level for mock servers to write to the log file (defaults to info) [possible values: error, warn, info, debug, trace, none] - --no-term-log Turns off using terminal ANSI escape codes - --no-file-log Do not log to an output file - - -``` - -##### Options - -###### Output directory: -o, --output - -This sets the output directory that log files and pact files are written to. It defaults to the current working directory. - -##### Example - -```console,ignore -$ ./pact_mock_server_cli start -l debug -o logs/ -15:40:08 [DEBUG] hyper::server: threads = 10 -15:40:08 [INFO] pact_mock_server_cli::server: Server started on port 8080 -``` - -#### create - -This creates a new pact mock server managed by the master server from a pact file. The ID and port of the mock server -will be displayed. - -Note, the tls option will only be available if the tls create feature is enabled. - -```console -$ ./pact_mock_server_cli help create -Creates a new mock server from a pact file - -Usage: pact_mock_server_cli create [OPTIONS] --file - -Options: - -f, --file the pact file to define the mock server - --help Print help and exit - -c, --cors-preflight Handle CORS pre-flight requests - -v, --version Print version information and exit - -p, --port port the master mock server runs on (defaults to 8080) - --tls Enable TLS with the mock server (will use a self-signed certificate) - -h, --host hostname the master mock server runs on (defaults to localhost) - -l, --loglevel Log level for mock servers to write to the log file (defaults to info) [possible values: error, warn, info, debug, trace, none] - --no-term-log Turns off using terminal ANSI escape codes - --no-file-log Do not log to an output file - - -``` - -##### Options - -###### Pact File: -f, --file - -This option specifies the pact file to base the mock server on. It is a mandatory option. - -##### Example - -```console,ignore -$ ./pact_mock_server_cli create -f ../../../libpact_matching/tests/pact.json -15:43:47 [INFO] pact_mock_server_cli::create_mock: Creating mock server from file ../../../libpact_matching/tests/pact.json -Mock server "7d1bf906d0ff42528f2d7d794dd19c5b" started on port 52943 -``` - -#### list - -Lists out all running mock servers with their ID, port, provider name and status. - -```console -$ ./pact_mock_server_cli list --help -Lists all the running mock servers - -Usage: pact_mock_server_cli list [OPTIONS] - -Options: - --help Print help and exit - -v, --version Print version information and exit - -p, --port port the master mock server runs on (defaults to 8080) - -h, --host hostname the master mock server runs on (defaults to localhost) - -l, --loglevel Log level for mock servers to write to the log file (defaults to info) [possible values: error, warn, info, debug, trace, none] - --no-term-log Turns off using terminal ANSI escape codes - --no-file-log Do not log to an output file - - -``` - -##### Example - -```console,ignore -$ ./pact_mock_server_cli list -Mock Server Id Port Provider Status -7d1bf906d0ff42528f2d7d794dd19c5b 52943 Alice Service error -``` - -#### verify - -This checks that the mock server, specified by ID or port number, has met all the expectations of the pact file. If all -expectations have been met, the pact file will be written out to the output directory that was specified with the start -sub-command. If there is any errors, no pact file will be written and the errors displayed to the console. - -```console -$ ./pact_mock_server_cli verify --help -Verify the mock server by id or port number, and generate a pact file if all ok - -Usage: pact_mock_server_cli verify [OPTIONS] - -Options: - --help - Print help and exit - -i, --mock-server-id - the ID of the mock server - -m, --mock-server-port - the port number of the mock server - -v, --version - Print version information and exit - -p, --port - port the master mock server runs on (defaults to 8080) - -h, --host - hostname the master mock server runs on (defaults to localhost) - -l, --loglevel - Log level for mock servers to write to the log file (defaults to info) [possible values: error, warn, info, debug, trace, none] - --no-term-log - Turns off using terminal ANSI escape codes - --no-file-log - Do not log to an output file - - -``` - -##### Options - -###### Mock server ID: -i, --mock-server-id - -The ID of the mock server to verify. Either this option or the mock server port option must be provided. - -###### Mock server Port: -m, --mock-server-port - -The port number of the mock server to verify. Either this option or the mock server ID option must be provided. - -##### Example - -In the case of a mock server that has issues: - -```console,ignore -$ ./pact_mock_server_cli verify -m 52943 -Mock server 7d1bf906d0ff42528f2d7d794dd19c5b/52943 failed verification with 1 errors - -0 - Expected request was not received - {"method":"GET","path":"/mallory","query":"name=ron&status=good"} -``` - -and for a mock server that has matched all requests: - -```console,ignore -$ ./pact_mock_server_cli verify -m 52943 -Mock server 7d1bf906d0ff42528f2d7d794dd19c5b/52943 verified ok -``` - -#### shutdown - -Shutdown the mock server by id or port number, releasing all its resources. - -```console -$ ./pact_mock_server_cli help shutdown -Shutdown the mock server by id or port number, releasing all its resources - -Usage: pact_mock_server_cli shutdown [OPTIONS] - -Options: - --help - Print help and exit - -i, --mock-server-id - the ID of the mock server - -m, --mock-server-port - the port number of the mock server - -v, --version - Print version information and exit - -p, --port - port the master mock server runs on (defaults to 8080) - -h, --host - hostname the master mock server runs on (defaults to localhost) - -l, --loglevel - Log level for mock servers to write to the log file (defaults to info) [possible values: error, warn, info, debug, trace, none] - --no-term-log - Turns off using terminal ANSI escape codes - --no-file-log - Do not log to an output file - - -``` - -##### Options - -###### Mock server ID: -i, --mock-server-id - -The ID of the mock server to shutdown. Either this option or the mock server port option must be provided. - -###### Mock server Port: -m, --mock-server-port - -The port number of the mock server to shutdown. Either this option or the mock server ID option must be provided. - -##### Example - -```console,ignore -$ ./pact_mock_server_cli shutdown -i 3a94a472d04849048b78109e288702d0 -Mock server with id '3a94a472d04849048b78109e288702d0' shutdown ok -``` - -## Restful JSON API - -The master mock server provides a restful JSON API, and this API is what the command line sub-commands use to -communicate and control the master server. - -### End points - -#### GET / - -This returns a list of all running mock servers managed by this master server. - -example request: - -```ignore -GET http://localhost:8080/ HTTP/1.1 -``` - -example response: - -```json -{ - "mockServers": [ - { - "id": "7d1bf906d0ff42528f2d7d794dd19c5b", - "port": 52943, - "provider": "Alice Service", - "status": "ok" - } - ] -} -``` - -#### POST / - -This creates a new mock server from a pact file that must be present as JSON in the body. Returns the details of the mock server -in the response. - -example request: - -```ignore -POST http://localhost:8080/ HTTP/1.1 -Content-Type: application/json -``` - -payload: - -```json -{ - "provider": { - "name": "Alice Service" - }, - "consumer": { - "name": "Consumer" - }, - "interactions": [ - { - "description": "a retrieve Mallory request", - "request": { - "method": "GET", - "path": "/mallory", - "query": "name=ron&status=good" - }, - "response": { - "status": 200, - "headers": { - "Content-Type": "text/html" - }, - "body": "\"That is some good Mallory.\"" - } - } - ] -} -``` - -example response: - -```json -{ - "mockServer": { - "id": "81c3483901e647ba8f545f2842d09cba", - "port": 58276 - } -} -``` - -#### Response codes - -##### 200 OK - -This is returned when if the mock server was created successfully. - -##### 422 Unprocessable Entity - -This is returned if the pact JSON could not be parsed or the mock server could not be started. - -#### GET /mockserver/:id - -Returns details of the mock server with `:id`, which can be either a mockserver ID or port number. - -example request: - -```ignore -GET http://localhost:8080/mockserver/33218 HTTP/1.1 -``` - -example response: - -```json -{ - "id": "3201b3e2f04f402c83b374a077f8f8dd", - "port": 33218, - "provider": "Alice Service", - "status": "error" -} -``` - -#### Response codes - -##### 200 OK - -This is returned with a valid mockserver. - -##### 404 Not Found - -This is returned if no mock server was found with the given ID or port number. - -#### POST /mockserver/:id/verify - -This checks that the mock server, specified by ID or port number, has met all the expectations of the pact file. If all -expectations have been met, the pact file will be written out to the output directory that was specified with the start -sub-command. If any mismatched requests where received by the mock server, they will be returned. - -example request: - -```ignore -POST http://localhost:8080/mockserver/33218/verify HTTP/1.1 -``` - -#### Response codes - -##### 204 No Content - -This is returned when all expectations have been successfully met and the pact file has been written out to the output directory. - -##### 422 Unprocessable Entity - -This is returned if any expectations have not been met, or any unrecognised requests where received. The details are -returned in the body. - -example response: - -```json -{ - "mismatches": [ - { - "method": "GET", - "path": "/mallory", - "request": { - "method": "GET", - "path": "/mallory", - "query": "name=ron&status=good" - }, - "type": "missing-request" - } - ], - "mockServer": { - "id": "3201b3e2f04f402c83b374a077f8f8dd", - "port": 33218, - "provider": "Alice Service", - "status": "error" - } -} -``` - -##### 404 Not Found - -This is returned if the ID or port number did not correspond to a running mock server or the pact file could not be -written. - -#### DELETE /mockserver/:id - -Shuts down the mock server with `:id`, which can be either a mockserver ID or port number. - -example request: - -```ignore -DELETE http://localhost:8080/mockserver/33218 HTTP/1.1 -``` - -#### Response codes - -##### 204 No Content - -This is returned when the mock server has been shutdown. - -##### 404 Not Found - -This is returned if no mock server was found with the given ID or port number. +Moved to https://github.com/pact-foundation/pact-core-mock-server/pact_mock_server_cli diff --git a/rust/pact_mock_server_cli/release-docker.sh b/rust/pact_mock_server_cli/release-docker.sh deleted file mode 100755 index 50564cf66..000000000 --- a/rust/pact_mock_server_cli/release-docker.sh +++ /dev/null @@ -1,29 +0,0 @@ -#!/bin/bash - -set -e - -if [ "" = "$1" ]; then - echo "Usage: " - echo " ./release-docker.sh version" - exit 1 -fi - -# AMD64 -docker build . -t pactfoundation/pact-ref-mock-server:$1-amd64 --platform linux/amd64 \ - --build-arg ARCH=amd64/ --build-arg BIN_ARCH=x86_64 --build-arg VERSION=$1 -docker push pactfoundation/pact-ref-mock-server:$1-amd64 - -# ARM64V8 -docker build . -t pactfoundation/pact-ref-mock-server:$1-arm64v8 --platform linux/arm64 \ - --build-arg ARCH=arm64v8/ --build-arg BIN_ARCH=aarch64 --build-arg VERSION=$1 -docker push pactfoundation/pact-ref-mock-server:$1-arm64v8 - -# Create Manifest -docker manifest create pactfoundation/pact-ref-mock-server:$1 \ - --amend pactfoundation/pact-ref-mock-server:$1-amd64 \ - --amend pactfoundation/pact-ref-mock-server:$1-arm64v8 -docker manifest push pactfoundation/pact-ref-mock-server:$1 -docker manifest create pactfoundation/pact-ref-mock-server:latest \ - --amend pactfoundation/pact-ref-mock-server:$1-amd64 \ - --amend pactfoundation/pact-ref-mock-server:$1-arm64v8 -docker manifest push pactfoundation/pact-ref-mock-server:latest diff --git a/rust/pact_mock_server_cli/release-linux.sh b/rust/pact_mock_server_cli/release-linux.sh deleted file mode 100755 index 4b27b7344..000000000 --- a/rust/pact_mock_server_cli/release-linux.sh +++ /dev/null @@ -1,43 +0,0 @@ -#!/bin/bash - -set -e -set -x - -RUST_DIR="$(cd -- "$(dirname "${BASH_SOURCE[0]}")/.." && pwd )" - -source "$RUST_DIR/scripts/gzip-and-sum.sh" -ARTIFACTS_DIR=${ARTIFACTS_DIR:-"$RUST_DIR/release_artifacts"} -mkdir -p "$ARTIFACTS_DIR" -export CARGO_TARGET_DIR=${CARO_TARGET_DIR:-"$RUST_DIR/target"} - -# All flags passed to this script are passed to cargo. -cargo_flags=( "$@" ) - -build_x86_64() { - sudo apt-get install -y musl-tools - cargo build --target=x86_64-unknown-linux-musl "${cargo_flags[@]}" - - if [[ "${cargo_flags[*]}" =~ "--release" ]]; then - gzip_and_sum \ - "$CARGO_TARGET_DIR/x86_64-unknown-linux-musl/release/pact_mock_server_cli" \ - "$ARTIFACTS_DIR/pact_mock_server_cli-linux-x86_64.gz" - fi -} - -install_cross() { - cargo install cross@0.2.5 -} - -build_aarch64() { - install_cross - cross build --target=aarch64-unknown-linux-musl "${cargo_flags[@]}" - - if [[ "${cargo_flags[*]}" =~ "--release" ]]; then - gzip_and_sum \ - "$CARGO_TARGET_DIR/aarch64-unknown-linux-musl/release/pact_mock_server_cli" \ - "$ARTIFACTS_DIR/pact_mock_server_cli-linux-aarch64.gz" - fi -} - -build_x86_64 -build_aarch64 diff --git a/rust/pact_mock_server_cli/release-macos.sh b/rust/pact_mock_server_cli/release-macos.sh deleted file mode 100755 index d9e77ff3f..000000000 --- a/rust/pact_mock_server_cli/release-macos.sh +++ /dev/null @@ -1,48 +0,0 @@ -#!/bin/bash - -set -e -set -x - -RUST_DIR="$(cd -- "$(dirname "${BASH_SOURCE[0]}")/.." && pwd )" - -source "$RUST_DIR/scripts/gzip-and-sum.sh" -ARTIFACTS_DIR=${ARTIFACTS_DIR:-"$RUST_DIR/release_artifacts"} -mkdir -p "$ARTIFACTS_DIR" -export CARGO_TARGET_DIR=${CARO_TARGET_DIR:-"$RUST_DIR/target"} - -# We target the oldest supported version of macOS. -export MACOSX_DEPLOYMENT_TARGET=${MACOSX_DEPLOYMENT_TARGET:-12} - -# All flags passed to this script are passed to cargo. -cargo_flags=( "$@" ) - -# Build the x86_64 darwin release -build_x86_64() { - cargo build --target x86_64-apple-darwin "${cargo_flags[@]}" - - if [[ "${cargo_flags[*]}" =~ "--release" ]]; then - gzip_and_sum \ - "$CARGO_TARGET_DIR/x86_64-apple-darwin/release/pact_mock_server_cli" \ - "$ARTIFACTS_DIR/pact_mock_server_cli-osx-x86_64.gz" - gzip_and_sum \ - "$CARGO_TARGET_DIR/x86_64-apple-darwin/release/pact_mock_server_cli" \ - "$ARTIFACTS_DIR/pact_mock_server_cli-macos-x86_64.gz" - fi -} - -# Build the aarch64 darwin release -build_aarch64() { - cargo build --target aarch64-apple-darwin "${cargo_flags[@]}" - - if [[ "${cargo_flags[*]}" =~ "--release" ]]; then - gzip_and_sum \ - "$CARGO_TARGET_DIR/aarch64-apple-darwin/release/pact_mock_server_cli" \ - "$ARTIFACTS_DIR/pact_mock_server_cli-osx-aarch64.gz" - gzip_and_sum \ - "$CARGO_TARGET_DIR/aarch64-apple-darwin/release/pact_mock_server_cli" \ - "$ARTIFACTS_DIR/pact_mock_server_cli-macos-aarch64.gz" - fi -} - -build_x86_64 -build_aarch64 diff --git a/rust/pact_mock_server_cli/release-win.sh b/rust/pact_mock_server_cli/release-win.sh deleted file mode 100644 index e6ebe3a2c..000000000 --- a/rust/pact_mock_server_cli/release-win.sh +++ /dev/null @@ -1,40 +0,0 @@ -#!/bin/bash - -set -e -set -x - -RUST_DIR="$(cd -- "$(dirname "${BASH_SOURCE[0]}")/.." && pwd )" - -source "$RUST_DIR/scripts/gzip-and-sum.sh" -ARTIFACTS_DIR=${ARTIFACTS_DIR:-"$RUST_DIR/release_artifacts"} -mkdir -p "$ARTIFACTS_DIR" -export CARGO_TARGET_DIR=${CARO_TARGET_DIR:-"$RUST_DIR/target"} - -# All flags passed to this script are passed to cargo. -cargo_flags=( "$@" ) - -# Build the x86_64 windows release -build_x86_64() { - cargo build --target x86_64-pc-windows-msvc "${cargo_flags[@]}" - - # If --release in cargo flags, then gzip and sum the release artifacts - if [[ "${cargo_flags[*]}" =~ "--release" ]]; then - gzip_and_sum \ - "$CARGO_TARGET_DIR/x86_64-pc-windows-msvc/release/pact_mock_server_cli.exe" \ - "$ARTIFACTS_DIR/pact_mock_server_cli-windows-x86_64.exe.gz" - fi -} - -# Build the aarch64 windows release -build_aarch64() { - cargo build --target aarch64-pc-windows-msvc "${cargo_flags[@]}" - - if [[ "${cargo_flags[*]}" =~ "--release" ]]; then - gzip_and_sum \ - "$CARGO_TARGET_DIR/aarch64-pc-windows-msvc/release/pact_mock_server_cli.exe" \ - "$ARTIFACTS_DIR/pact_mock_server_cli-windows-aarch64.exe.gz" - fi -} - -build_x86_64 -build_aarch64 \ No newline at end of file diff --git a/rust/pact_mock_server_cli/release.groovy b/rust/pact_mock_server_cli/release.groovy deleted file mode 100755 index 96d3c7560..000000000 --- a/rust/pact_mock_server_cli/release.groovy +++ /dev/null @@ -1,113 +0,0 @@ -#!/usr/bin/env groovy -@Grab(group = 'com.github.zafarkhaja', module = 'java-semver', version = '0.9.0') -import com.github.zafarkhaja.semver.Version - -def executeOnShell(String command, Closure closure = null) { - executeOnShell(command, new File(System.properties.'user.dir'), closure) -} - -def executeOnShell(String command, File workingDir, Closure closure = null) { - println command - def processBuilder = new ProcessBuilder(['sh', '-c', command]) - .directory(workingDir) - if (closure) { - processBuilder.redirectErrorStream(true) - } else { - processBuilder.inheritIO() - } - def process = processBuilder.start() - if (closure) { - process.inputStream.eachLine closure - } - process.waitFor() - if (process.exitValue() > 0) { - System.exit(process.exitValue()) - } -} - -void ask(String prompt, String defaultValue = 'Y', Closure cl) { - def promptValue = System.console().readLine(prompt + ' ').trim() - if (promptValue.empty) { - promptValue = defaultValue - } - if (promptValue.toUpperCase() == 'Y') { - cl.call() - } -} - -executeOnShell 'git pull' - -ask('Execute Build?: [Y]') { - executeOnShell 'cargo clean' - executeOnShell 'cargo build' - executeOnShell 'cargo test' -} - -def projectProps = new File('Cargo.toml').text -def versionMatch = projectProps =~ /(?m)version\s*=\s*"(.*)"/ -def version = versionMatch[0][1] - -def prevTag = 'git describe --abbrev=0 --tags --match=pact_mock_server_cli-*'.execute().text.trim() -def changelog = [] -executeOnShell("git log --pretty='* %h - %s (%an, %ad)' ${prevTag}..HEAD .".toString()) { - println it - changelog << it -} - -def releaseDesc = System.console().readLine('Describe this release: [Bugfix Release]').trim() -if (releaseDesc.empty) { - releaseDesc = 'Bugfix Release' -} - -def releaseVer = System.console().readLine("What is the version for this release?: [$version]").trim() -if (releaseVer.empty) { - releaseVer = version -} - -ask('Update Changelog?: [Y]') { - def changeLogFile = new File('CHANGELOG.md') - def changeLogFileLines = changeLogFile.readLines() - changeLogFile.withPrintWriter() { p -> - p.println(changeLogFileLines[0]) - - p.println() - p.println("# $releaseVer - $releaseDesc") - p.println() - changelog.each { - p.println(it) - } - - changeLogFileLines[1..-1].each { - p.println(it) - } - } - - executeOnShell("git add CHANGELOG.md") - executeOnShell("git commit -m 'update changelog for release $releaseVer'") - executeOnShell("git status") - executeOnShell("git diff HEAD^..HEAD") -} - -ask('Tag and Push commits?: [Y]') { - executeOnShell 'git push' - executeOnShell("git tag pact_mock_server_cli-v${releaseVer}") - executeOnShell 'git push --tags' -} - -ask('Publish library to crates.io?: [Y]') { - executeOnShell 'cargo package' - executeOnShell 'cargo publish' -} - -def nextVer = Version.valueOf(releaseVer).incrementPatchVersion() -ask("Bump version to $nextVer?: [Y]") { - executeOnShell "sed -i -e 's/^version = \"${releaseVer}\"/version = \"${nextVer}\"/' Cargo.toml" - executeOnShell("cargo update") - executeOnShell("git add Cargo.toml") - executeOnShell("git add ../Cargo.lock") - executeOnShell("git diff --cached") - ask("Commit and push this change?: [Y]") { - executeOnShell("git commit -m 'bump version to $nextVer'") - executeOnShell("git push") - } -} diff --git a/rust/pact_mock_server_cli/src/create_mock.rs b/rust/pact_mock_server_cli/src/create_mock.rs deleted file mode 100644 index 2bf1c3e9d..000000000 --- a/rust/pact_mock_server_cli/src/create_mock.rs +++ /dev/null @@ -1,78 +0,0 @@ -use std::path::Path; - -use clap::ArgMatches; -use itertools::Itertools; -use pact_models::pact::{Pact, ReadWritePact}; -use pact_models::sync_pact::RequestResponsePact; -use serde_json::Value; -use tracing::{debug, error, info}; - -use crate::handle_error; - -pub async fn create_mock_server(host: &str, port: u16, matches: &ArgMatches, usage: &str) -> Result<(), i32> { - let file = matches.get_one::("file").unwrap(); - info!("Creating mock server from file {}", file); - - match RequestResponsePact::read_pact(Path::new(file)) { - Ok(ref pact) => { - let mut args = vec![]; - if matches.get_flag("cors") { - info!("Setting mock server to handle CORS pre-flight requests"); - args.push("cors=true"); - } - if matches.get_flag("tls") { - info!("Setting mock server to use TLS"); - args.push("tls=true"); - } - let url = if args.is_empty() { - format!("http://{}:{}/", host, port) - } else { - format!("http://{}:{}/?{}", host, port, args.iter().join("&")) - }; - let client = reqwest::Client::new(); - let json = match pact.to_json(pact.specification_version()) { - Ok(json) => json, - Err(err) => { - crate::display_error(format!("Failed to send pact as JSON '{}': {}", file, err), usage); - } - }; - let resp = client.post(url.as_str()) - .json(&json) - .send().await; - match resp { - Ok(response) => { - if response.status().is_success() { - match response.json::().await { - Ok(json) => { - debug!("Got response from master server: {:?}", json); - let mock_server = json.get("mockServer") - .ok_or_else(|| handle_error("Invalid JSON received from master server - no mockServer attribute"))?; - let id = mock_server.get("id") - .ok_or_else(|| handle_error("Invalid JSON received from master server - mockServer has no id attribute"))? - .as_str().ok_or_else(|| handle_error("Invalid JSON received from master server - mockServer id attribute is not a string"))?; - let port = mock_server.get("port") - .ok_or_else(|| handle_error("Invalid JSON received from master server - mockServer has no port attribute"))? - .as_u64().ok_or_else(|| handle_error("Invalid JSON received from master server - mockServer port attribute is not a number"))?; - println!("Mock server {} started on port {}", id, port); - Ok(()) - }, - Err(err) => { - error!("Failed to parse JSON: {}", err); - crate::display_error(format!("Failed to parse JSON: {}", err), usage); - } - } - } else { - crate::display_error(format!("Master mock server returned an error: {}\n{}", - response.status(), response.text().await.unwrap_or_default()), usage); - } - } - Err(err) => { - crate::display_error(format!("Failed to connect to the master mock server '{}': {}", url, err), usage); - } - } - }, - Err(err) => { - crate::display_error(format!("Failed to load pact file '{}': {}", file, err), usage); - } - } -} diff --git a/rust/pact_mock_server_cli/src/list.rs b/rust/pact_mock_server_cli/src/list.rs deleted file mode 100644 index d918b7846..000000000 --- a/rust/pact_mock_server_cli/src/list.rs +++ /dev/null @@ -1,68 +0,0 @@ -use serde_json::{self, json, Value}; -use tracing::error; - -use crate::{display_error, handle_error}; - -fn json2string(json: Option<&Value>) -> String { - match json { - Some(v) => match *v { - Value::String(ref s) => s.clone(), - _ => v.to_string() - }, - None => String::new() - } -} - -#[allow(clippy::print_literal)] -pub async fn list_mock_servers(host: &str, port: u16, usage: &str) -> Result<(), i32> { - let client = reqwest::Client::new(); - let url = format!("http://{}:{}/", host, port); - let res = client.get(&url).send().await; - - match res { - Ok(result) => { - let status = result.status(); - if status.is_success() { - match result.json::().await { - Ok(json) => { - let mock_servers_json = json.get("mockServers") - .ok_or_else(|| handle_error("Invalid JSON received from master server - no mockServers attribute"))?; - let mock_servers = mock_servers_json.as_array() - .ok_or_else(|| handle_error("Invalid JSON received from master server - mockServers is not an array"))?; - let provider_len = mock_servers.iter().fold(0, |acc, ms| { - let unknown = &json!(""); - let provider = ms.get("provider").unwrap_or(unknown) - .as_str().unwrap_or(""); - if provider.len() > acc { - provider.len() - } else { - acc - } - }); - - println!("{0:36} {1:5} {2:3$} {4}", "Mock Server Id", "Port", - "Provider", provider_len, "Verification State"); - for ms in mock_servers { - let id = json2string(ms.get("id")); - let port = json2string(ms.get("port")); - let provider = json2string(ms.get("provider")); - let status = json2string(ms.get("status")); - println!("{0} {1} {2:3$} {4}", id, port, provider, provider_len, status); - }; - Ok(()) - }, - Err(err) => { - error!("Failed to parse JSON: {}\n", err); - display_error(format!("Failed to parse JSON: {}", err), usage); - } - } - } else { - let body = result.text().await.unwrap_or_default(); - display_error(format!("Master mock server returned an error: {}\n{}", status, body), usage); - } - }, - Err(err) => { - display_error(format!("Failed to connect to the master mock server '{}': {}", url, err), usage); - } - } -} diff --git a/rust/pact_mock_server_cli/src/main.rs b/rust/pact_mock_server_cli/src/main.rs deleted file mode 100644 index f95b0f0a1..000000000 --- a/rust/pact_mock_server_cli/src/main.rs +++ /dev/null @@ -1,353 +0,0 @@ -//! The `pact_mock_server` crate provides the CLI for the pact mock server for mocking HTTP requests -//! and generating responses based on a pact file. It implements the -//! [V3 Pact specification](https://github.com/pact-foundation/pact-specification/tree/version-3) -//! and [V4 Pact specification](https://github.com/pact-foundation/pact-specification/tree/version-4). - -#![warn(missing_docs)] - -use std::cell::RefCell; -use std::env; -use std::io; -use std::str::FromStr; -use std::sync::Mutex; - -use anyhow::anyhow; -use clap::{Arg, ArgAction, command, Command}; -use clap::error::ErrorKind; -use lazy_static::*; -use pact_models::PactSpecification; -use rand::distributions::Alphanumeric; -use rand::Rng; -use tracing_core::LevelFilter; -use tracing_subscriber::fmt::writer::MakeWriterExt; -use tracing_subscriber::FmtSubscriber; -use uuid::Uuid; - -use pact_mock_server::server_manager::ServerManager; - -pub(crate) fn display_error(error: String, usage: &str) -> ! { - eprintln!("ERROR: {}", error); - eprintln!(); - eprintln!("{}", usage); - panic!("{}", error) -} - -pub(crate) fn handle_error(error: &str) -> i32 { - eprintln!("ERROR: {}", error); - eprintln!(); - -100 -} - -mod server; -mod create_mock; -mod list; -mod verify; -mod shutdown; - -fn print_version() { - println!("pact mock server version : v{}", clap::crate_version!()); - println!("pact specification version: v{}", PactSpecification::V4.version_str()); -} - -fn setup_loggers( - level: &str, - command: &str, - output: Option<&str>, - no_file_log: bool, - no_term_log: bool -) -> anyhow::Result<()> { - let log_level = match level { - "none" => LevelFilter::OFF, - _ => LevelFilter::from_str(level).unwrap() - }; - - if command == "start" && !no_file_log { - let file_appender = tracing_appender::rolling::daily(output.unwrap_or("."), "pact_mock_server.log"); - let (non_blocking, _guard) = tracing_appender::non_blocking(file_appender); - let subscriber = FmtSubscriber::builder() - .with_max_level(log_level) - .with_writer(non_blocking.and(io::stdout)) - .with_thread_names(true) - .with_ansi(!no_term_log) - .finish(); - tracing::subscriber::set_global_default(subscriber) - } else { - let subscriber = FmtSubscriber::builder() - .with_max_level(log_level) - .with_thread_names(true) - .with_ansi(!no_term_log) - .finish(); - tracing::subscriber::set_global_default(subscriber) - }.map_err(|err| anyhow!(err)) -} - -fn integer_value(v: &str) -> Result { - v.parse::().map_err(|e| format!("'{}' is not a valid port value: {}", v, e) ) -} - -fn uuid_value(v: &str) -> Result { - Uuid::parse_str(v).map_err(|e| format!("'{}' is not a valid UUID value: {}", v, e) ) -} - -#[tokio::main] -async fn main() { - match handle_command_args().await { - Ok(_) => (), - Err(err) => std::process::exit(err) - } -} - -#[derive(Debug, Clone)] -pub(crate) struct ServerOpts { - pub output_path: Option, - pub base_port: Option, - pub server_key: String -} - -lazy_static!{ - pub(crate) static ref SERVER_OPTIONS: Mutex> = Mutex::new(RefCell::new(ServerOpts { - output_path: None, - base_port: None, - server_key: String::default() - })); - pub(crate) static ref SERVER_MANAGER: Mutex = Mutex::new(ServerManager::new()); -} - -async fn handle_command_args() -> Result<(), i32> { - let mut app = setup_args(); - - let usage = app.render_usage().to_string(); - let matches = app.try_get_matches(); - match matches { - Ok(ref matches) => { - let log_level = matches.get_one::("loglevel").map(|lvl| lvl.as_str()); - let no_file_log = matches.get_flag("no-file-log"); - let no_term_log = matches.get_flag("no-term-log"); - if let Err(err) = setup_loggers(log_level.unwrap_or("info"), - matches.subcommand_name().unwrap(), - matches.subcommand().map(|(name, args)| { - if name == "start" { - args.get_one::("output").map(|o| o.as_str()) - } else { - None - } - }).flatten(), - no_file_log, - no_term_log - ) { - eprintln!("WARN: Could not setup loggers: {}", err); - eprintln!(); - } - - let port = *matches.get_one::("port").unwrap_or(&8080); - let localhost = "localhost".to_string(); - let host = matches.get_one::("host").unwrap_or(&localhost); - - match matches.subcommand() { - Some(("start", sub_matches)) => { - let output_path = sub_matches.get_one::("output").map(|s| s.to_owned()); - let base_port = sub_matches.get_one::("base-port").cloned(); - let server_key = sub_matches.get_one::("server-key").map(|s| s.to_owned()) - .unwrap_or_else(|| rand::thread_rng().sample_iter(Alphanumeric).take(16).map(char::from).collect::()); - { - let inner = (*SERVER_OPTIONS).lock().unwrap(); - let mut options = inner.deref().borrow_mut(); - options.output_path = output_path; - options.base_port = base_port; - options.server_key = server_key; - } - server::start_server(port).await - }, - Some(("list", _)) => list::list_mock_servers(host, port, usage.as_str()).await, - Some(("create", sub_matches)) => create_mock::create_mock_server(host, port, sub_matches, usage.as_str()).await, - Some(("verify", sub_matches)) => verify::verify_mock_server(host, port, sub_matches, usage.as_str()).await, - Some(("shutdown", sub_matches)) => shutdown::shutdown_mock_server(host, port, sub_matches, usage.as_str()).await, - Some(("shutdown-master", sub_matches)) => shutdown::shutdown_master_server(host, port, sub_matches, usage.as_str()).await, - _ => Err(3) - } - }, - Err(ref err) => { - match err.kind() { - ErrorKind::DisplayHelp => { - println!("{}", err); - Ok(()) - }, - ErrorKind::DisplayVersion => { - print_version(); - println!(); - Ok(()) - }, - _ => { - err.exit() - } - } - } - } -} - -fn setup_args() -> Command { - #[allow(unused_mut)] - let mut create_command = Command::new("create") - .about("Creates a new mock server from a pact file") - .version(clap::crate_version!()) - .arg(Arg::new("file") - .short('f') - .long("file") - .action(ArgAction::Set) - .required(true) - .help("the pact file to define the mock server")) - .arg(Arg::new("cors") - .short('c') - .long("cors-preflight") - .action(ArgAction::SetTrue) - .help("Handle CORS pre-flight requests")); - - #[cfg(feature = "tls")] - { - create_command = create_command.arg(Arg::new("tls") - .long("tls") - .action(ArgAction::SetTrue) - .help("Enable TLS with the mock server (will use a self-signed certificate)")); - } - - command!() - .about("Standalone Pact mock server") - .disable_help_flag(true) - .arg_required_else_help(true) - .disable_version_flag(true) - .arg(Arg::new("help") - .long("help") - .action(ArgAction::Help) - .global(true) - .help("Print help and exit")) - .arg(Arg::new("version") - .short('v') - .long("version") - .action(ArgAction::Version) - .global(true) - .help("Print version information and exit")) - .arg(Arg::new("port") - .short('p') - .long("port") - .global(true) - .action(ArgAction::Set) - .value_parser(integer_value) - .help("port the master mock server runs on (defaults to 8080)")) - .arg(Arg::new("host") - .short('h') - .long("host") - .global(true) - .action(ArgAction::Set) - .help("hostname the master mock server runs on (defaults to localhost)")) - .arg(Arg::new("loglevel") - .short('l') - .long("loglevel") - .global(true) - .action(ArgAction::Set) - .value_parser(["error", "warn", "info", "debug", "trace", "none"]) - .help("Log level for mock servers to write to the log file (defaults to info)")) - .arg(Arg::new("no-term-log") - .long("no-term-log") - .global(true) - .action(ArgAction::SetTrue) - .help("Turns off using terminal ANSI escape codes")) - .arg(Arg::new("no-file-log") - .long("no-file-log") - .global(true) - .action(ArgAction::SetTrue) - .help("Do not log to an output file")) - .subcommand(Command::new("start") - .about("Starts the master mock server") - .version(clap::crate_version!()) - .arg(Arg::new("output") - .short('o') - .long("output") - .action(ArgAction::Set) - .help("the directory where to write files to (defaults to current directory)")) - .arg(Arg::new("base-port") - .long("base-port") - .action(ArgAction::Set) - .help("the base port number that mock server ports will be allocated from. If not specified, ports will be randomly assigned by the OS.") - .value_parser(integer_value)) - .arg(Arg::new("server-key") - .long("server-key") - .action(ArgAction::Set) - .help("the server key to use to authenticate shutdown requests (defaults to a random generated one)")) - ) - .subcommand(Command::new("list") - .about("Lists all the running mock servers") - .version(clap::crate_version!())) - .subcommand(create_command) - .subcommand(Command::new("verify") - .about("Verify the mock server by id or port number, and generate a pact file if all ok") - .version(clap::crate_version!()) - .arg(Arg::new("mock-server-id") - .short('i') - .long("mock-server-id") - .action(ArgAction::Set) - .required_unless_present("mock-server-port") - .conflicts_with("mock-server-port") - .help("the ID of the mock server") - .value_parser(uuid_value)) - .arg(Arg::new("mock-server-port") - .short('m') - .long("mock-server-port") - .action(ArgAction::Set) - .required_unless_present("mock-server-id") - .help("the port number of the mock server") - .value_parser(integer_value)) - ) - .subcommand(Command::new("shutdown") - .about("Shutdown the mock server by id or port number, releasing all its resources") - .version(clap::crate_version!()) - .arg(Arg::new("mock-server-id") - .short('i') - .long("mock-server-id") - .action(ArgAction::Set) - .required_unless_present("mock-server-port") - .conflicts_with("mock-server-port") - .help("the ID of the mock server") - .value_parser(uuid_value)) - .arg(Arg::new("mock-server-port") - .short('m') - .long("mock-server-port") - .action(ArgAction::Set) - .required_unless_present("mock-server-id") - .help("the port number of the mock server") - .value_parser(integer_value)) - ) - .subcommand(Command::new("shutdown-master") - .about("Performs a graceful shutdown of the master server (displayed when it started)") - .version(clap::crate_version!()) - .arg(Arg::new("server-key") - .short('k') - .long("server-key") - .action(ArgAction::Set) - .required(true) - .help("the server key of the master server")) - .arg(Arg::new("period") - .long("period") - .action(ArgAction::Set) - .help("the period of time in milliseconds to allow the server to shutdown (defaults to 100ms)") - .value_parser(integer_value)) - ) -} - -#[cfg(test)] -mod test { - use expectest::expect; - use expectest::prelude::*; - - use crate::{integer_value, setup_args}; - - #[test] - fn validates_integer_value() { - expect!(integer_value("1234")).to(be_ok()); - expect!(integer_value("1234x")).to(be_err()); - } - - #[test_log::test] - fn verify_cli() { - setup_args().debug_assert(); - } -} diff --git a/rust/pact_mock_server_cli/src/self-signed.cert b/rust/pact_mock_server_cli/src/self-signed.cert deleted file mode 100644 index 1778fa0fc..000000000 --- a/rust/pact_mock_server_cli/src/self-signed.cert +++ /dev/null @@ -1,29 +0,0 @@ ------BEGIN CERTIFICATE----- -MIIFCTCCAvGgAwIBAgIUONMSp5Utt78tmLuW0B8Nb9fZeXIwDQYJKoZIhvcNAQEL -BQAwFDESMBAGA1UEAwwJbG9jYWxob3N0MB4XDTIxMDEwNTAwMDgxOFoXDTMxMDEw -MzAwMDgxOFowFDESMBAGA1UEAwwJbG9jYWxob3N0MIICIjANBgkqhkiG9w0BAQEF -AAOCAg8AMIICCgKCAgEA4sS6reSVFOh/MDfruJX0dXBt4/iFadwKvTJeQBklvgtt -YbH/h3Cl1XQdhY5p4Xw1XWZ42l3QElmDRKhw3RtkBM/D0atXQQNVwgEti0U/QeN+ -esb//unZ2V7IkK/k2Tk5FGsBa2yuMu4Cj7dE9y7SBzAATmgFLWAmpcfthODnpBbW -Y4ceMB/ZBUGJ+S6vda5lnuk0LgvZx41wLlvLpS7Ea3cmnERHJG1HZh/LMbINjMYl -i1XNjPlpgAglXWizRx1INi3GlHI6xKfPIPYdUMWO5Q1Js6HGoD3fb9YOnGxiW6ks -RRMcqrKl02krmtiZ5V0u3Tlkqv6SLCpjvvsFsR98xj4stYAxZF8B4tpMJJdphyfZ -HJ2LkBigVtjPhYcjVUYuOiowS+7UYj1kyuR1ehyRXb4v7N+54JGuHzCuT+4tcslH -nqFJ/vDykYNdl2u/2+rVPyWY8JDcEb0yQ3wvRQ6X1nh4vj2+Pbn4HKL3dGvbFoL/ -uqP1kBw/sFuF2tYHQaJubYRzDlmng+SIsLIIEes1Etu7/WUXeSVr6KR2ZZFMOL85 -4w/Z+8fflcFrJVSWG0hmtL4OOCxSeDK51m+0JuGAAiukTx0F4/PEDTv1pZnTUO1+ -e2t4e9nrTZBnE4auuonbltwttGDRKSAeWZbvty7gkCtWys5HL5aQmd8SFHVqFVEC -AwEAAaNTMFEwHQYDVR0OBBYEFHzBeV21pWeOOrMCC5xAPrwQ6JLQMB8GA1UdIwQY -MBaAFHzBeV21pWeOOrMCC5xAPrwQ6JLQMA8GA1UdEwEB/wQFMAMBAf8wDQYJKoZI -hvcNAQELBQADggIBAFBwfUCuHl2cljND3JkHRXkcv22jgnmk/qNURE5z1gLTFq0q -33A1fiLYFhp0MweQefd/mh7N9OgTrJGV4bKThCkcZnAOEXiK3VVidxyVVTbU+grJ -qf54+FLD9bxlxBW2JN3Vz62EpoCoyZWNYt3Ltp2Y9iOuu7w9zWt013nIabA69VHk -RaRYPsIxfuBSWhqAt9qIeb81/FEISJeXa5hs5RHZ7nRgXoiU+4W8AnFrNwYW725g -zB0ZKMlPG2luPsUbckW82vxejgOG+hbr3vxsEx33NxeVbiNEwxlKfJQqjQ9bSueR -PPv4xVStYc+3iMxKr1KswOYrRGfMiVytPL34de0E7LbnKLqyQUHzZt+1uKdxJTrB -Ez/f4RagLLii/cVXKV/jYNI9nA7g08f3YTrRjcNkDd3i2Q1MU7wfWAjdft7NPdr/ -uMbyjpgCbdGAY9AknEuOlkpprvoAg9JkZngVziO5HFEvq9DL2hmUCpFY4s8XnWvp -TFagRuZVi3Gwsn4RTutkZR9S71jj6LRGwbaTSGirNEQneVt96u5WAOymsIuz8xxp -90RR8kJRUDUOp+hU1Y206zMjvLMx4mDbyvNsnk8dA0s3ReplgHK3InIp2HWYxKtx -2XUAdDll7HAzG1m7xXUOdC2RU4tdPqzb4dqZBv61ds7ivZ5RcK+4597mpRoJ ------END CERTIFICATE----- diff --git a/rust/pact_mock_server_cli/src/self-signed.key b/rust/pact_mock_server_cli/src/self-signed.key deleted file mode 100644 index ae78d8111..000000000 --- a/rust/pact_mock_server_cli/src/self-signed.key +++ /dev/null @@ -1,52 +0,0 @@ ------BEGIN PRIVATE KEY----- -MIIJQgIBADANBgkqhkiG9w0BAQEFAASCCSwwggkoAgEAAoICAQDixLqt5JUU6H8w -N+u4lfR1cG3j+IVp3Aq9Ml5AGSW+C21hsf+HcKXVdB2FjmnhfDVdZnjaXdASWYNE -qHDdG2QEz8PRq1dBA1XCAS2LRT9B4356xv/+6dnZXsiQr+TZOTkUawFrbK4y7gKP -t0T3LtIHMABOaAUtYCalx+2E4OekFtZjhx4wH9kFQYn5Lq91rmWe6TQuC9nHjXAu -W8ulLsRrdyacREckbUdmH8sxsg2MxiWLVc2M+WmACCVdaLNHHUg2LcaUcjrEp88g -9h1QxY7lDUmzocagPd9v1g6cbGJbqSxFExyqsqXTaSua2JnlXS7dOWSq/pIsKmO+ -+wWxH3zGPiy1gDFkXwHi2kwkl2mHJ9kcnYuQGKBW2M+FhyNVRi46KjBL7tRiPWTK -5HV6HJFdvi/s37ngka4fMK5P7i1yyUeeoUn+8PKRg12Xa7/b6tU/JZjwkNwRvTJD -fC9FDpfWeHi+Pb49ufgcovd0a9sWgv+6o/WQHD+wW4Xa1gdBom5thHMOWaeD5Iiw -sggR6zUS27v9ZRd5JWvopHZlkUw4vznjD9n7x9+VwWslVJYbSGa0vg44LFJ4MrnW -b7Qm4YACK6RPHQXj88QNO/WlmdNQ7X57a3h72etNkGcThq66iduW3C20YNEpIB5Z -lu+3LuCQK1bKzkcvlpCZ3xIUdWoVUQIDAQABAoICAGeIC/bScqIOF+uKzGsEw4xO -nU1ErJyNIrYIZfF7ybh/fRvqaVCLxJq0nbnZMEwLKk4PN8PyqsmF5qGVCZpZJAvy -U2PJh1eeTyv437NDFUNeuuMRMdVPLO/KD2XHeIMYVhAVXpuODeYgtjipIqp7zNYN -O0aQxTRXPq3XnoBZMki/SHg+OzEbiTiWGIkUoHTo/2pS7EjNjktGLt5reIlc1b5+ -srkLjzN5VOyyPVHeCcOov4Fi1iqzwE/86BpCb/9axho+QfiKQnyAZNeWpgG3gKrg -qzKA/K8yMG3d2+Pcs/dHQHf05tSkJYNk88yJcZG/PmMwDd7nxRK2871A2/Nm/c6k -YLmkKzhA1Izzucw7rT2VGzi86T2ko0bL535Ms4BEdORg6vBVqnzrgzOLRx/8eyo5 -cKKhtpoeaaDtsl4SaRrQWNkoqH2YEu9OPY/Eb6y+QCl4v7dTJHvq0IlpFGOQg6CZ -y3wK6BUD5RobTFDs34teydAnlkhrRHKDMxTpvnac+3OgIVdCekATUT8+TR0cgLEj -iYe0Iyh8p6waGkYUUHMSJ6ks2RfDiqCIPkqwIJ1AnkaNoFc0tWKU0yG4JuRHKNW0 -gNzRzFM6rDut6J+Tz9aHpMZALML19/XB5AB4CTth7Jcm7154ua3oDBQLYe0Z3aYj -KNxtBYrvsntmorH2xOYlAoIBAQD747NOQX31SuJpyCV2CMaS9AsrI1jf/RWwNNGk -QxME+ToxaUi5i7uskH5zP5CZzaAAywDkJf0oJi28NLAGRnFLiav23lkAP+cDzF9D -96/XuYzoiLmUAMoe89hjSw+l4b1unS4aVSu1G8E7abMpCQNPQwcLexd4PSMXDJfC -XxgMln8wPneXNqv53EEKfSgGo5NbtocAMCTFM1hQ7nAgWwzvza8bU7ULuQ+AFISQ -tPOZeGapb9tvCOW4gDfvA7/FAum5XFO0YH5pRdK2pN3e+QuWHOAsgMzyB6KSUQMT -iHUZIKttZNBxbtggvFMagegOWU/Fcnd/N7/lOD6ktOyGPNW/AoIBAQDmeBUwo0dX -htnmy0RtxxqWGlRpmnFD6A6b6MGOjRZoAaqGqBS3gWwe4Zo8kbbdC3et4jaYbiq+ -ChnCRWJvEy+28wqRAzjDOA6m2S7C1gf4M2gr0ljCSOWgEiX8eqhxhbAQIN3u9kBZ -ZEaGV7kFJVsPWPL/7HGg8reAktNzLgzTQ/XuG8yaZ061wuhY63RY3IB3Bf2qSvly -HCJ88DF7L/5ZB2dLaDJ8gjVcUzks/Feg3nvWkFc0Dgm6Lr+g6e3BJTGW1eU58Dna -0fQJTeSIpKyL7cT9js3lwEQgbEUi8Np5PlQZxxt2O1JpYbMNyxbrzPknrHWM5wBr -9BkQgf4O03jvAoIBAAsdhTAS28gTQeKBHoYS5RBfDI8exDE+LdLUwduJyjER/mtn -xfnKHMIErk/PokXnOQRP8P4gXweCh8oiWRIt0ZoPvTLrpOnJ6BvWzO1m5K+UVI9+ -WRIa5tBu2kGnck1TpNRYw0wOLhuT2fcRNwK8jxTUVF9BU0vPBtlhiODe6WTEz2AF -oalelEA2Y/hehYGlfj8x0stDVJwPI/qOSwxieDOs0+lUzEx0Iib4wNDR613+Xilj -8j74GYsGvXEirTe4ZS/0zwzKpUln92Bv7gqE2uoI5CuSk3iqtZXXVVdrUh+FvYra -RAh9Z7QqG1C0ItVfQ5Hm9zb58tHepYUHJtjVnmkCggEBANv+OEvrMAhuosVZtoIL -kmdBzt3XHNMzSe6tKUXHi2HQZVSQUOYx1mFL/Ixgk2tArQcAbhjm4EnzHk+BJ8rb -R6qdKLLvnllKw0GlAqvc3lKfz4o1CaC7MOWxLS1qcCuc70kV9oNJ8Hbj7yYByo0M -8XUe9SYyLuzxgxRqEwlZJcjskG6vfojMoCeEW4G1j6PbJ4113IOXebDhBlK4fKMY -VvPoy0MBvV94czMkBenZHlRiy1cvBO6dj893HFifs+GwfTt8BYles/saepX/Em0U -s9gGKQnYLNZoxx8j+oK14fXl9yV8F8yuJ6aMKfy6pbCEQjkKuFK9lnt10A8f5sGE -P2UCggEAZ95n3Ri+vUsmNmqib8rfaBB9tDjN+3yuC3sAgTCsaV4xdEBM6oAIQUsq -+W6vGVRIVKFXA6W1Vjl8aA8dryB+MYJgnYqXXdQUnXPR/9WQAy/tKq4tfgS0U7kl -fqln50OYBd/qYfMMLHFdDnydNJ0DsFaTqHYx67SWd7Z5Tgbt+Ipb0ZNTb1H9/jKC -1hoKbu/wjjlUwIX/Xwe6jqI6aj/+Q3iSXC3L+eQmTm1PRQ9F35e59Cevdy1Ygsfg -ZWwKZNTb9mRUnkIoUS8GiXU0jqmPCTsYg7r8XABRheYiYHWhRRTiMW1EX5vwJGS+ -vzRmCHvZ0fmtcu7nhdSrXYRcXUKHLw== ------END PRIVATE KEY----- diff --git a/rust/pact_mock_server_cli/src/server.rs b/rust/pact_mock_server_cli/src/server.rs deleted file mode 100644 index c25ff7cfc..000000000 --- a/rust/pact_mock_server_cli/src/server.rs +++ /dev/null @@ -1,408 +0,0 @@ -use std::{ - net::TcpListener, - process, - sync::mpsc, - thread, - time::Duration -}; -use std::convert::Infallible; -use std::net::{IpAddr, SocketAddr}; - -use futures::channel::oneshot::channel; -use hyper::server::Server; -use hyper::service::make_service_fn; -use itertools::Either; -use maplit::*; -use pact_models::pact::load_pact_from_json; -use pact_models::PactSpecification; -use serde_json::{self, json, Value}; -use tracing::{debug, error, info, trace}; -use uuid::Uuid; -use webmachine_rust::*; -use webmachine_rust::context::*; -use webmachine_rust::headers::*; - -use pact_mock_server::mock_server::{MockServer, MockServerConfig}; -#[cfg(feature = "tls")] use pact_mock_server::tls::TlsConfigBuilder; - -use crate::{SERVER_MANAGER, SERVER_OPTIONS, ServerOpts}; -use crate::verify; - -fn json_error(error: String) -> String { - let json_response = json!({ "error" : json!(error) }); - json_response.to_string() -} - -fn get_next_port(base_port: Option) -> u16 { - match base_port { - None => 0, - Some(p) => if p > 0 { - let mut port = p; - let mut listener = TcpListener::bind(("127.0.0.1", port)); - while listener.is_err() && port < p + 1000 { - port += 1; - listener = TcpListener::bind(("127.0.0.1", port)); - } - match listener { - Ok(listener) => listener.local_addr().unwrap().port(), - Err(_) => 0 - } - } else { - 0 - } - } -} - -fn start_provider(context: &mut WebmachineContext, options: ServerOpts) -> Result { - debug!("start_provider => {}", context.request.request_path); - match context.request.body { - Some(ref body) if !body.is_empty() => { - match serde_json::from_slice(body) { - Ok(ref json) => { - let pact = load_pact_from_json(&context.request.request_path, json) - .map_err(|err| { - error!("Failed to parse Pact JSON - {}", err); - 422_u16 - })?; - debug!("Loaded pact = {:?}", pact); - let mock_server_id = Uuid::new_v4().to_string(); - let config = MockServerConfig { - cors_preflight: query_param_set(context, "cors"), - pact_specification: PactSpecification::default(), - transport_config: Default::default() - }; - debug!("Mock server config = {:?}", config); - - #[allow(unused_assignments)] - let mut result = Err("No mock server started yet".to_string()); - #[cfg(feature = "tls")] - { - result = if query_param_set(context, "tls") { - debug!("Starting TLS mock server with id {}", &mock_server_id); - let key = include_str!("self-signed.key"); - let cert = include_str!("self-signed.cert"); - TlsConfigBuilder::new() - .key(key.as_bytes()) - .cert(cert.as_bytes()) - .build() - .map_err(|err| { - format!("Failed to setup TLS using self-signed certificate - {}", err) - }) - .and_then(|tls_config| { - let mut guard = SERVER_MANAGER.lock().unwrap(); - guard.start_tls_mock_server(mock_server_id.clone(), pact, get_next_port(options.base_port), &tls_config, config) - }) - } else { - debug!("Starting mock server with id {}", &mock_server_id); - let mut guard = SERVER_MANAGER.lock().unwrap(); - guard.start_mock_server(mock_server_id.clone(), pact, get_next_port(options.base_port), config) - }; - } - - #[cfg(not(feature = "tls"))] - { - debug!("Starting mock server with id {}", &mock_server_id); - let mut guard = SERVER_MANAGER.lock().unwrap(); - result = guard.start_mock_server(mock_server_id.clone(), pact, get_next_port(options.base_port), config); - } - - match result { - Ok(mock_server) => { - debug!("mock server started on port {}", mock_server); - let mock_server_json = json!({ - "id" : json!(mock_server_id), - "port" : json!(mock_server as i64), - }); - let json_response = json!({ "mockServer" : mock_server_json }); - context.response.body = Some(json_response.to_string().into_bytes()); - context.response.add_header("Location", - vec![HeaderValue::basic(format!("/mockserver/{}", mock_server_id).as_str())]); - Ok(true) - }, - Err(msg) => { - context.response.body = Some(json_error(format!("Failed to start mock server - {}", msg)).into_bytes()); - Err(422) - } - } - }, - Err(err) => { - log::error!("Failed to parse json body - {}", err); - context.response.body = Some(json_error(format!("Failed to parse json body - {}", err)).into_bytes()); - Err(422) - } - } - }, - _ => { - log::error!("No pact json was supplied"); - context.response.body = Some(json_error("No pact json was supplied".to_string()).into_bytes()); - Err(422) - } - } -} - -fn query_param_set(context: &mut WebmachineContext, name: &str) -> bool { - context.request.query.get(name) - .unwrap_or(&vec![]).first().unwrap_or(&String::default()) - .eq("true") -} - -pub fn verify_mock_server_request(context: &mut WebmachineContext) -> Result { - let id = context.metadata.get("id").cloned().unwrap_or_default(); - match verify::validate_id(&id, &SERVER_MANAGER) { - Ok(ms) => { - let mut map = btreemap!{ "mockServer" => ms.to_json() }; - let mismatches = ms.mismatches(); - if !mismatches.is_empty() { - map.insert("mismatches", json!(mismatches.iter() - .map(|m| m.to_json()).collect::>())); - context.response.body = Some(json!(map).to_string().into_bytes()); - Err(422) - } else { - let inner = SERVER_OPTIONS.lock().unwrap(); - let options = inner.borrow(); - match ms.write_pact(&options.output_path, false) { - Ok(_) => Ok(true), - Err(err) => { - map.insert("error", json!(format!("Failed to write pact to file - {}", err))); - context.response.body = Some(json!(map).to_string().into_bytes()); - Err(422) - } - } - } - }, - Err(_) => Err(422) - } -} - -fn shutdown_resource<'a>() -> WebmachineResource<'a> { - WebmachineResource { - allowed_methods: vec!["POST"], - forbidden: callback(&|context, _| { - let options = SERVER_OPTIONS.lock().unwrap(); - !context.request.has_header_value(&"Authorization".to_owned(), &format!("Bearer {}", options.borrow().server_key)) - }), - process_post: callback(&|context, _| { - let shutdown_period = match context.request.body { - Some(ref body) if !body.is_empty() => { - match serde_json::from_slice::(body) { - Ok(ref json) => match json.get("period") { - Some(val) => match val.clone() { - Value::Number(n) => Ok(n.as_u64().unwrap_or(100)), - _ => Ok(100) - }, - None => Ok(100) - }, - Err(err) => { - error!("Failed to parse json body - {}", err); - context.response.body = Some(json_error(format!("Failed to parse json body - {}", err)).into_bytes()); - Err(422) - } - } - } - _ => Ok(100) - }; - - match shutdown_period { - Ok(period) => { - // Need to work out how to do this as the webmachine has to have a static lifetime - // shutdown.send(()).unwrap_or_default(); - thread::spawn(move || { - info!("Scheduling master server to shutdown in {}ms", period); - thread::sleep(Duration::from_millis(period)); - info!("Shutting down"); - process::exit(0); - }); - Ok(true) - } - Err(err) => Err(err) - } - }), - ..WebmachineResource::default() - } -} - -fn mock_server_resource<'a>() -> WebmachineResource<'a> { - WebmachineResource { - allowed_methods: vec!["OPTIONS", "GET", "HEAD", "POST", "DELETE"], - resource_exists: callback(&|context, _| { - debug!("mock_server_resource -> resource_exists"); - let paths: Vec = context.request.request_path - .split('/') - .filter(|p| !p.is_empty()) - .map(|p| p.to_string()) - .collect(); - if !paths.is_empty() && paths.len() <= 2 { - match verify::validate_id(&paths[0].clone(), &SERVER_MANAGER) { - Ok(ms) => { - context.metadata.insert("id".to_string(), ms.id.clone()); - context.metadata.insert("port".to_string(), ms.port.unwrap_or_default().to_string()); - if paths.len() > 1 { - context.metadata.insert("subpath".to_string(), paths[1].clone()); - paths[1] == "verify" - } else { - true - } - } - Err(_) => false - } - } else { - false - } - }), - render_response: callback(&|context, _| { - debug!("mock_server_resource -> render_response"); - match context.metadata.get("subpath") { - None => { - let id = context.metadata.get("id").unwrap().clone(); - debug!("Mock server id = {}", id); - let response = { - let guard = SERVER_MANAGER.lock().unwrap(); - guard.find_mock_server_by_id(&id, &|_, ms| match ms { - Either::Left(ms) => (Some(ms.to_json().to_string()), None), - Either::Right(_plugin) => { - error!("Plugin mock servers are not currently supported"); - (None, Some(422)) - } - }) - }; - match response { - Some((res, Some(status))) => { - context.response.status = status; - res - } - Some((res, None)) => res, - None => None - } - } - Some(_) => { - context.response.status = 405; - None - } - } - }), - process_post: callback(&|context, _| { - debug!("mock_server_resource -> process_post"); - let subpath = context.metadata.get("subpath").unwrap().clone(); - if subpath == "verify" { - verify_mock_server_request(context) - } else { - Err(422) - } - }), - delete_resource: callback(&|context, _| { - debug!("mock_server_resource -> delete_resource"); - match context.metadata.get("subpath") { - None => { - let id = context.metadata.get("id").unwrap().clone(); - thread::spawn(move || { - if SERVER_MANAGER.lock().unwrap().shutdown_mock_server_by_id(id) { - Ok(true) - } else { - Err(404) - } - }).join().expect("Could not spawn thread to shut down mock server") - } - Some(_) => Err(405) - } - }), - ..WebmachineResource::default() - } -} - -fn dispatcher() -> WebmachineDispatcher<'static> { - WebmachineDispatcher { - routes: btreemap! { - "/" => WebmachineResource { - allowed_methods: vec!["OPTIONS", "GET", "HEAD", "POST"], - resource_exists: callback(&|context, _| { - debug!("main_resource -> resource_exists"); - context.request.request_path == "/" - }), - render_response: callback(&|_, _| { - debug!("main_resource -> render_response"); - let server_manager = SERVER_MANAGER.lock().unwrap(); - trace!("Unlocked server manager"); - let mock_servers = server_manager.map_mock_servers(MockServer::to_json); - trace!("Got mock server JSON"); - let json_response = json!({ "mockServers" : mock_servers }); - trace!("Returning response"); - Some(json_response.to_string()) - }), - process_post: callback(&|context, _| { - debug!("main_resource -> process_post"); - - let options = { - let inner = SERVER_OPTIONS.lock().unwrap(); - inner.clone().into_inner() - }; - - let (tx, rx) = mpsc::channel(); - let (tx2, rx2) = mpsc::channel(); - - if let Err(err) = tx.send(context.clone()) { - error!("Failed to send context to start new mock server - {:?}", err); - return Err(500) - } - let start_fn = move || { - let handle = thread::current(); - debug!("starting mock server on thread {}", handle.name().unwrap_or("")); - let mut ctx = rx.recv().unwrap(); - let result = start_provider(&mut ctx, options); - debug!("Result of starting mock server: {:?}", result.clone()); - match tx2.send(ctx) { - Ok(_) => result, - Err(err) => { - error!("Failed to send result back to main resource - {:?}", err); - Err(500) - } - } - }; - - match thread::spawn(start_fn).join() { - Ok(res) => { - debug!("Result of thread: {:?}", res); - let ctx = rx2.recv().unwrap(); - context.response = ctx.response; - res - }, - Err(err) => { - error!("Failed to spawn new thread to start new mock server - {:?}", err); - Err(500) - } - } - }), - .. WebmachineResource::default() - }, - "/mockserver" => mock_server_resource(), - "/shutdown" => shutdown_resource() - } - } -} - -pub async fn start_server(port: u16) -> Result<(), i32> { - let addr = SocketAddr::new(IpAddr::from([0, 0, 0, 0]), port); - let (_shutdown_tx, shutdown_rx) = channel::<()>(); - - let make_svc = make_service_fn(|_| async { - Ok::<_, Infallible>(dispatcher()) - }); - match Server::try_bind(&addr) { - Ok(server) => { - let server = server.serve(make_svc); - { - let inner = SERVER_OPTIONS.lock().unwrap(); - let options = inner.borrow(); - info!("Master server started on port {}", server.local_addr().port()); - info!("Server key: '{}'", options.server_key); - } - server.with_graceful_shutdown(async { shutdown_rx.await.unwrap_or_default() }).await.map_err(|err| { - error!("Received an error starting master server: {}", err); - 2 - }) - }, - Err(err) => { - error!("could not start master server: {}", err); - Err(1) - } - } -} diff --git a/rust/pact_mock_server_cli/src/shutdown.rs b/rust/pact_mock_server_cli/src/shutdown.rs deleted file mode 100644 index 0ed454da6..000000000 --- a/rust/pact_mock_server_cli/src/shutdown.rs +++ /dev/null @@ -1,65 +0,0 @@ -use clap::ArgMatches; -use http::StatusCode; -use serde_json::json; - -pub async fn shutdown_mock_server(host: &str, port: u16, matches: &ArgMatches, usage: &str) -> Result<(), i32> { - let mock_server_id = matches.get_one::("mock-server-id"); - let mock_server_port = matches.get_one::("mock-server-port"); - let (id, id_type) = match (mock_server_id, mock_server_port) { - (Some(id), _) => (id.clone(), "id"), - (_, Some(port)) => (port.to_string(), "port"), - _ => crate::display_error("Either an ID or port must be provided".to_string(), usage) - }; - - let client = reqwest::Client::new(); - let url = format!("http://{}:{}/mockserver/{}", host, port, id); - let resp = client.delete(&url).send().await; - match resp { - Ok(result) => { - if !result.status().is_success() { - match result.status() { - StatusCode::NOT_FOUND => { - println!("No mock server found with {} '{}', use the 'list' command to get a list of available mock servers.", id_type, id); - Err(3) - }, - _ => crate::display_error(format!("Unexpected response from master mock server '{}': {}", url, result.status()), usage) - } - } else { - println!("Mock server with {} '{}' shutdown ok", id_type, id); - Ok(()) - } - }, - Err(err) => { - crate::display_error(format!("Failed to connect to the master mock server '{}': {}", url, err), usage); - } - } -} - -pub async fn shutdown_master_server(host: &str, port: u16, matches: &ArgMatches, usage: &str) -> Result<(), i32> { - let client = reqwest::Client::new(); - let server_key = matches.get_one::("server-key").unwrap().to_owned(); - let shutdown_period = matches.get_one::("period").map(|val| val.parse::().unwrap_or(100)).unwrap_or(100); - let url = format!("http://{}:{}/shutdown", host, port); - let res = client.post(&url) - .bearer_auth(server_key) - .json(&json!({ "period": shutdown_period })) - .send().await; - match res { - Ok(result) => { - if !result.status().is_success() { - if result.status() == StatusCode::FORBIDDEN { - crate::display_error(format!("Invalid server key: got response {}", result.status()), usage) - } else { - crate::display_error(format!("Unexpected response from master mock server '{}': {}", - url, result.status()), usage) - } - } else { - println!("Master server shutting down ok"); - Ok(()) - } - }, - Err(err) => { - crate::display_error(format!("Failed to connect to the master mock server '{}': {}", url, err), usage); - } - } -} diff --git a/rust/pact_mock_server_cli/src/verify.rs b/rust/pact_mock_server_cli/src/verify.rs deleted file mode 100644 index f44ec93a4..000000000 --- a/rust/pact_mock_server_cli/src/verify.rs +++ /dev/null @@ -1,129 +0,0 @@ -use std::sync::Mutex; - -use clap::ArgMatches; -use http::StatusCode; -use pact_models::json_utils::json_to_string; -use serde_json::Value; -use tracing::error; - -use pact_mock_server::{ - mock_server::MockServer, - server_manager::ServerManager -}; - -use crate::handle_error; - -pub async fn verify_mock_server(host: &str, port: u16, matches: &ArgMatches, usage: &str) -> Result<(), i32> { - let mock_server_id = matches.get_one::("mock-server-id"); - let mock_server_port = matches.get_one::("mock-server-port"); - let (id, id_type) = match (mock_server_id, mock_server_port) { - (Some(id), _) => (id.clone(), "id"), - (_, Some(port)) => (port.to_string(), "port"), - _ => crate::display_error("Either an ID or port must be provided".to_string(), usage) - }; - - let client = reqwest::Client::new(); - let url = format!("http://{}:{}/mockserver/{}/verify", host, port, id); - let resp = client.post(&url) - .send().await; - match resp { - Ok(result) => { - let status = result.status(); - if !status.is_success() { - match status { - StatusCode::NOT_FOUND => { - println!("No mock server found with {} '{}', use the 'list' command to get a list of available mock servers.", id_type, id); - Err(3) - }, - StatusCode::UNPROCESSABLE_ENTITY => { - match result.text().await { - Ok(body) => { - match serde_json::from_str::(body.as_str()) { - Ok(json) => { - let mock_server = json.get("mockServer") - .ok_or_else(|| handle_error("Invalid JSON received from master server - no mockServer attribute"))?; - let id = mock_server.get("id") - .ok_or_else(|| handle_error("Invalid JSON received from master server - mockServer has no id attribute"))? - .as_str().ok_or_else(|| handle_error("Invalid JSON received from master server - mockServer id attribute is not a string"))?; - let port = mock_server.get("port") - .ok_or_else(|| handle_error("Invalid JSON received from master server - mockServer has no port attribute"))? - .as_u64().ok_or_else(|| handle_error("Invalid JSON received from master server - mockServer port attribute is not a number"))?; - display_verification_errors(id, port, &json); - Err(2) - }, - Err(err) => { - error!("Failed to parse JSON: {}\n{}", err, body); - crate::display_error(format!("Failed to parse JSON: {}\n{}", err, body), usage); - } - } - }, - Err(err) => { - error!("Failed to parse JSON: {}", err); - crate::display_error(format!("Failed to parse JSON: {}", err), usage); - } - } - }, - _ => crate::display_error(format!("Unexpected response from master mock server '{}': {}", url, result.status()), usage) - } - } else { - println!("Mock server with {} '{}' verified ok", id, id_type); - Ok(()) - } - }, - Err(err) => { - crate::display_error(format!("Failed to connect to the master mock server '{}': {}", url, err), usage); - } - } -} - -fn validate_port(port: u16, server_manager: &Mutex) -> Result { - server_manager.lock().unwrap() - .find_mock_server_by_port_mut(port, &|ms| { - ms.clone() - }) - .ok_or(format!("No mock server running with port '{}'", port)) -} - -fn validate_uuid(id: &str, server_manager: &Mutex) -> Result { - server_manager.lock().unwrap() - .find_mock_server_by_id(&id.to_string(), &|_, ms| { - ms.unwrap_left().clone() - }) - .ok_or(format!("No mock server running with id '{}'", id)) -} - -pub fn validate_id(id: &str, server_manager: &Mutex) -> Result { - if id.chars().all(|ch| ch.is_digit(10)) { - validate_port(id.parse::().unwrap(), server_manager) - } else { - validate_uuid(id, server_manager) - } -} - -fn display_verification_errors(id: &str, port: u64, json: &serde_json::Value) { - let mismatches = json.get("mismatches").unwrap().as_array().unwrap(); - println!("Mock server {}/{} failed verification with {} errors\n", id, port, mismatches.len()); - - for (i, mismatch) in mismatches.iter().enumerate() { - match json_to_string(mismatch.get("type").unwrap()).as_str() { - "missing-request" => { - let request = mismatch.get("request").unwrap(); - println!("{} - Expected request was not received - {}", i, request) - }, - "request-not-found" => { - let request = mismatch.get("request").unwrap(); - println!("{} - Received a request that was not expected - {}", i, request) - }, - "request-mismatch" => { - let path = mismatch.get("path").unwrap().to_string(); - let method = mismatch.get("method").unwrap().to_string(); - println!("{} - Received a request that did not match with expected - {} {}", i, method, path); - let request_mismatches = mismatch.get("mismatches").unwrap().as_array().unwrap(); - for request_mismatch in request_mismatches { - println!(" {}", request_mismatch.get("mismatch").unwrap().to_string()) - } - }, - _ => println!("{} - Unknown failure - {}", i, mismatch), - } - } -} diff --git a/rust/pact_mock_server_cli/tests/cli-tests.rs b/rust/pact_mock_server_cli/tests/cli-tests.rs deleted file mode 100644 index aa08c1320..000000000 --- a/rust/pact_mock_server_cli/tests/cli-tests.rs +++ /dev/null @@ -1,8 +0,0 @@ -#[test] -#[cfg(not(windows))] -fn cli_tests() { - trycmd::TestCases::new() - .case("tests/cmd/*.toml") - .insert_var("[CLIVERSION]", clap::crate_version!()).unwrap() - .case("README.md"); -} diff --git a/rust/pact_mock_server_cli/tests/cmd/create.stderr b/rust/pact_mock_server_cli/tests/cmd/create.stderr deleted file mode 100644 index e69de29bb..000000000 diff --git a/rust/pact_mock_server_cli/tests/cmd/create.stdout b/rust/pact_mock_server_cli/tests/cmd/create.stdout deleted file mode 100644 index 849dad630..000000000 --- a/rust/pact_mock_server_cli/tests/cmd/create.stdout +++ /dev/null @@ -1,16 +0,0 @@ -Creates a new mock server from a pact file - -Usage: pact_mock_server_cli create [OPTIONS] --file - -Options: - -f, --file the pact file to define the mock server - --help Print help and exit - -c, --cors-preflight Handle CORS pre-flight requests - -v, --version Print version information and exit - -p, --port port the master mock server runs on (defaults to 8080) - --tls Enable TLS with the mock server (will use a self-signed certificate) - -h, --host hostname the master mock server runs on (defaults to localhost) - -l, --loglevel Log level for mock servers to write to the log file (defaults to info) [possible values: error, warn, info, debug, trace, none] - --no-term-log Turns off using terminal ANSI escape codes - --no-file-log Do not log to an output file - diff --git a/rust/pact_mock_server_cli/tests/cmd/create.toml b/rust/pact_mock_server_cli/tests/cmd/create.toml deleted file mode 100644 index fe1883b3a..000000000 --- a/rust/pact_mock_server_cli/tests/cmd/create.toml +++ /dev/null @@ -1,2 +0,0 @@ -bin.name = "pact_mock_server_cli" -args = "create --help" diff --git a/rust/pact_mock_server_cli/tests/cmd/list.stderr b/rust/pact_mock_server_cli/tests/cmd/list.stderr deleted file mode 100644 index e69de29bb..000000000 diff --git a/rust/pact_mock_server_cli/tests/cmd/list.stdout b/rust/pact_mock_server_cli/tests/cmd/list.stdout deleted file mode 100644 index e7329b58e..000000000 --- a/rust/pact_mock_server_cli/tests/cmd/list.stdout +++ /dev/null @@ -1,13 +0,0 @@ -Lists all the running mock servers - -Usage: pact_mock_server_cli list [OPTIONS] - -Options: - --help Print help and exit - -v, --version Print version information and exit - -p, --port port the master mock server runs on (defaults to 8080) - -h, --host hostname the master mock server runs on (defaults to localhost) - -l, --loglevel Log level for mock servers to write to the log file (defaults to info) [possible values: error, warn, info, debug, trace, none] - --no-term-log Turns off using terminal ANSI escape codes - --no-file-log Do not log to an output file - diff --git a/rust/pact_mock_server_cli/tests/cmd/list.toml b/rust/pact_mock_server_cli/tests/cmd/list.toml deleted file mode 100644 index d921b5149..000000000 --- a/rust/pact_mock_server_cli/tests/cmd/list.toml +++ /dev/null @@ -1,2 +0,0 @@ -bin.name = "pact_mock_server_cli" -args = "list --help" diff --git a/rust/pact_mock_server_cli/tests/cmd/main.stderr b/rust/pact_mock_server_cli/tests/cmd/main.stderr deleted file mode 100644 index e69de29bb..000000000 diff --git a/rust/pact_mock_server_cli/tests/cmd/main.stdout b/rust/pact_mock_server_cli/tests/cmd/main.stdout deleted file mode 100644 index 173bb772e..000000000 --- a/rust/pact_mock_server_cli/tests/cmd/main.stdout +++ /dev/null @@ -1,22 +0,0 @@ -Standalone Pact mock server - -Usage: pact_mock_server_cli [OPTIONS] [COMMAND] - -Commands: - start Starts the master mock server - list Lists all the running mock servers - create Creates a new mock server from a pact file - verify Verify the mock server by id or port number, and generate a pact file if all ok - shutdown Shutdown the mock server by id or port number, releasing all its resources - shutdown-master Performs a graceful shutdown of the master server (displayed when it started) - help Print this message or the help of the given subcommand(s) - -Options: - --help Print help and exit - -v, --version Print version information and exit - -p, --port port the master mock server runs on (defaults to 8080) - -h, --host hostname the master mock server runs on (defaults to localhost) - -l, --loglevel Log level for mock servers to write to the log file (defaults to info) [possible values: error, warn, info, debug, trace, none] - --no-term-log Turns off using terminal ANSI escape codes - --no-file-log Do not log to an output file - diff --git a/rust/pact_mock_server_cli/tests/cmd/main.toml b/rust/pact_mock_server_cli/tests/cmd/main.toml deleted file mode 100644 index b47a251ee..000000000 --- a/rust/pact_mock_server_cli/tests/cmd/main.toml +++ /dev/null @@ -1,3 +0,0 @@ -bin.name = "pact_mock_server_cli" -args = "--help" -#status.code = 2 diff --git a/rust/pact_mock_server_cli/tests/cmd/shutdown.stderr b/rust/pact_mock_server_cli/tests/cmd/shutdown.stderr deleted file mode 100644 index e69de29bb..000000000 diff --git a/rust/pact_mock_server_cli/tests/cmd/shutdown.stdout b/rust/pact_mock_server_cli/tests/cmd/shutdown.stdout deleted file mode 100644 index ecfb1ab63..000000000 --- a/rust/pact_mock_server_cli/tests/cmd/shutdown.stdout +++ /dev/null @@ -1,24 +0,0 @@ -Shutdown the mock server by id or port number, releasing all its resources - -Usage: pact_mock_server_cli shutdown [OPTIONS] - -Options: - --help - Print help and exit - -i, --mock-server-id - the ID of the mock server - -m, --mock-server-port - the port number of the mock server - -v, --version - Print version information and exit - -p, --port - port the master mock server runs on (defaults to 8080) - -h, --host - hostname the master mock server runs on (defaults to localhost) - -l, --loglevel - Log level for mock servers to write to the log file (defaults to info) [possible values: error, warn, info, debug, trace, none] - --no-term-log - Turns off using terminal ANSI escape codes - --no-file-log - Do not log to an output file - diff --git a/rust/pact_mock_server_cli/tests/cmd/shutdown.toml b/rust/pact_mock_server_cli/tests/cmd/shutdown.toml deleted file mode 100644 index 892ce160a..000000000 --- a/rust/pact_mock_server_cli/tests/cmd/shutdown.toml +++ /dev/null @@ -1,2 +0,0 @@ -bin.name = "pact_mock_server_cli" -args = "shutdown --help" diff --git a/rust/pact_mock_server_cli/tests/cmd/start.stderr b/rust/pact_mock_server_cli/tests/cmd/start.stderr deleted file mode 100644 index e69de29bb..000000000 diff --git a/rust/pact_mock_server_cli/tests/cmd/start.stdout b/rust/pact_mock_server_cli/tests/cmd/start.stdout deleted file mode 100644 index 8d9eb0086..000000000 --- a/rust/pact_mock_server_cli/tests/cmd/start.stdout +++ /dev/null @@ -1,16 +0,0 @@ -Starts the master mock server - -Usage: pact_mock_server_cli start [OPTIONS] - -Options: - --help Print help and exit - -o, --output the directory where to write files to (defaults to current directory) - --base-port the base port number that mock server ports will be allocated from. If not specified, ports will be randomly assigned by the OS. - -v, --version Print version information and exit - -p, --port port the master mock server runs on (defaults to 8080) - --server-key the server key to use to authenticate shutdown requests (defaults to a random generated one) - -h, --host hostname the master mock server runs on (defaults to localhost) - -l, --loglevel Log level for mock servers to write to the log file (defaults to info) [possible values: error, warn, info, debug, trace, none] - --no-term-log Turns off using terminal ANSI escape codes - --no-file-log Do not log to an output file - diff --git a/rust/pact_mock_server_cli/tests/cmd/start.toml b/rust/pact_mock_server_cli/tests/cmd/start.toml deleted file mode 100644 index 997c2c45b..000000000 --- a/rust/pact_mock_server_cli/tests/cmd/start.toml +++ /dev/null @@ -1,2 +0,0 @@ -bin.name = "pact_mock_server_cli" -args = "start --help" diff --git a/rust/pact_mock_server_cli/tests/cmd/verify.stderr b/rust/pact_mock_server_cli/tests/cmd/verify.stderr deleted file mode 100644 index e69de29bb..000000000 diff --git a/rust/pact_mock_server_cli/tests/cmd/verify.stdout b/rust/pact_mock_server_cli/tests/cmd/verify.stdout deleted file mode 100644 index 9c680ef0d..000000000 --- a/rust/pact_mock_server_cli/tests/cmd/verify.stdout +++ /dev/null @@ -1,24 +0,0 @@ -Verify the mock server by id or port number, and generate a pact file if all ok - -Usage: pact_mock_server_cli verify [OPTIONS] - -Options: - --help - Print help and exit - -i, --mock-server-id - the ID of the mock server - -m, --mock-server-port - the port number of the mock server - -v, --version - Print version information and exit - -p, --port - port the master mock server runs on (defaults to 8080) - -h, --host - hostname the master mock server runs on (defaults to localhost) - -l, --loglevel - Log level for mock servers to write to the log file (defaults to info) [possible values: error, warn, info, debug, trace, none] - --no-term-log - Turns off using terminal ANSI escape codes - --no-file-log - Do not log to an output file - diff --git a/rust/pact_mock_server_cli/tests/cmd/verify.toml b/rust/pact_mock_server_cli/tests/cmd/verify.toml deleted file mode 100644 index b73e00b15..000000000 --- a/rust/pact_mock_server_cli/tests/cmd/verify.toml +++ /dev/null @@ -1,2 +0,0 @@ -bin.name = "pact_mock_server_cli" -args = "verify --help"