From f87eadf238d472ccc6ca8392cc45b91d7c84bfb3 Mon Sep 17 00:00:00 2001 From: "beltram.maldant" Date: Fri, 12 Mar 2021 16:48:17 +0100 Subject: [PATCH] feat: support 'urlPattern' --- README.md | 2 +- lib/src/model/request/query/mod.rs | 5 +-- lib/src/model/request/url/mod.rs | 10 +++-- lib/src/model/request/url/url_pattern.rs | 25 +++++++++++++ lib/tests/req/url/mod.rs | 1 + lib/tests/req/url/url_pattern.rs | 37 +++++++++++++++++++ lib/tests/stubs/req/url-pattern/all.json | 9 +++++ .../stubs/req/url-pattern/just-one-query.json | 9 +++++ lib/tests/stubs/req/url-pattern/just-url.json | 9 +++++ .../stubs/req/url-pattern/many-queries.json | 9 +++++ 10 files changed, 107 insertions(+), 9 deletions(-) create mode 100644 lib/src/model/request/url/url_pattern.rs create mode 100644 lib/tests/req/url/url_pattern.rs create mode 100644 lib/tests/stubs/req/url-pattern/all.json create mode 100644 lib/tests/stubs/req/url-pattern/just-one-query.json create mode 100644 lib/tests/stubs/req/url-pattern/just-url.json create mode 100644 lib/tests/stubs/req/url-pattern/many-queries.json diff --git a/README.md b/README.md index 77f2bed3..ab27c331 100644 --- a/README.md +++ b/README.md @@ -62,7 +62,7 @@ the latter. * [x] `url` * [x] `urlPath` * [x] `urlPathPattern` - * [ ] `urlPattern` + * [x] `urlPattern` * [x] headers * [x] `equalTo` * [x] `contains` diff --git a/lib/src/model/request/query/mod.rs b/lib/src/model/request/query/mod.rs index 82a64e6f..e780a5c8 100644 --- a/lib/src/model/request/query/mod.rs +++ b/lib/src/model/request/query/mod.rs @@ -10,10 +10,7 @@ use case::QueryCaseInsensitiveMatcher; use contains::QueryContainsMatcher; use matches::QueryRegexMatcher; -use super::{ - matcher::RequestMatcherDto, - super::request::MockRegistrable, -}; +use super::{matcher::RequestMatcherDto, super::request::MockRegistrable}; mod exact; mod case; diff --git a/lib/src/model/request/url/mod.rs b/lib/src/model/request/url/mod.rs index 55c6498a..9612091d 100644 --- a/lib/src/model/request/url/mod.rs +++ b/lib/src/model/request/url/mod.rs @@ -1,17 +1,16 @@ use std::convert::TryFrom; use serde::Deserialize; -use wiremock::{ - matchers::{PathExactMatcher, PathRegexMatcher}, - MockBuilder, -}; +use wiremock::{matchers::{PathExactMatcher, PathRegexMatcher}, MockBuilder}; use just_url::ExactPathAndQueryMatcher; +use url_pattern::UrlPatternMatcher; use super::MockRegistrable; mod url_path; mod url_path_pattern; +mod url_pattern; mod just_url; #[derive(Deserialize, Debug, Default)] @@ -35,6 +34,9 @@ impl MockRegistrable for HttpUrlDto { if let Ok(regex) = PathRegexMatcher::try_from(self) { mock = mock.and(regex); } + if let Ok(url_pattern_matcher) = UrlPatternMatcher::try_from(self) { + mock = mock.and(url_pattern_matcher); + } if let Ok(ExactPathAndQueryMatcher(path, queries)) = ExactPathAndQueryMatcher::try_from(self) { mock = mock.and(path); for query in queries { diff --git a/lib/src/model/request/url/url_pattern.rs b/lib/src/model/request/url/url_pattern.rs new file mode 100644 index 00000000..20804b74 --- /dev/null +++ b/lib/src/model/request/url/url_pattern.rs @@ -0,0 +1,25 @@ +use std::{convert::TryFrom, str::FromStr}; + +use regex::Regex; +use wiremock::{Match, Request}; + +use super::HttpUrlDto; + +pub struct UrlPatternMatcher(Regex); + +impl Match for UrlPatternMatcher { + fn matches(&self, req: &Request) -> bool { + self.0.is_match(req.url.as_str()) + } +} + +impl TryFrom<&HttpUrlDto> for UrlPatternMatcher { + type Error = anyhow::Error; + + fn try_from(http_url: &HttpUrlDto) -> anyhow::Result { + http_url.url_pattern.as_ref() + .and_then(|it| Regex::from_str(it).ok()) + .map(|it| Self(it)) + .ok_or_else(|| anyhow::Error::msg("No 'urlPattern'")) + } +} diff --git a/lib/tests/req/url/mod.rs b/lib/tests/req/url/mod.rs index 9218fbd2..37fc1cd0 100644 --- a/lib/tests/req/url/mod.rs +++ b/lib/tests/req/url/mod.rs @@ -1,3 +1,4 @@ pub mod url_path; +pub mod url_pattern; pub mod url_path_pattern; pub mod url_query; \ No newline at end of file diff --git a/lib/tests/req/url/url_pattern.rs b/lib/tests/req/url/url_pattern.rs new file mode 100644 index 00000000..33326c21 --- /dev/null +++ b/lib/tests/req/url/url_pattern.rs @@ -0,0 +1,37 @@ +use surf::get; + +use crate::utils::*; + +#[async_std::test] +async fn should_map_request_url_pattern_with_just_url() { + let srv = given("req/url-pattern/just-url"); + get(&srv.path("/api/pattern/abcd")).await.unwrap().assert_ok(); + get(&srv.path("/api/pattern/1234")).await.unwrap().assert_not_found(); +} + +#[async_std::test] +async fn should_map_request_url_pattern_with_just_one_query() { + let srv = given("req/url-pattern/just-one-query"); + get(&srv.path_query("/api/pattern", "one", "abcd")).await.unwrap().assert_ok(); + get(&srv.path_query("/api/pattern", "one", "1234")).await.unwrap().assert_not_found(); +} + +#[async_std::test] +async fn should_map_request_url_pattern_with_many_queries() { + let srv = given("req/url-pattern/many-queries"); + get(&srv.path_queries("/api/pattern", ("one", "abcd"), ("two", "abcd"))).await.unwrap().assert_ok(); + get(&srv.path_queries("/api/pattern", ("one", "1234"), ("two", "abcd"))).await.unwrap().assert_not_found(); + get(&srv.path_queries("/api/pattern", ("one", "abcd"), ("two", "1234"))).await.unwrap().assert_not_found(); + get(&srv.path_queries("/api/pattern", ("one", "1234"), ("two", "1234"))).await.unwrap().assert_not_found(); +} + +#[async_std::test] +async fn should_map_request_url_pattern_with_both_url_and_queries() { + let srv = given("req/url-pattern/all"); + get(&srv.path_queries("/api/pattern/abcd", ("one", "abcd"), ("two", "abcd"))).await.unwrap().assert_ok(); + get(&srv.path_queries("/api/pattern/1234", ("one", "abcd"), ("two", "abcd"))).await.unwrap().assert_not_found(); + get(&srv.path_queries("/api/pattern/abcd", ("one", "1234"), ("two", "abcd"))).await.unwrap().assert_not_found(); + get(&srv.path_queries("/api/pattern/abcd", ("one", "abcd"), ("two", "1234"))).await.unwrap().assert_not_found(); + get(&srv.path_queries("/api/pattern/abcd", ("one", "1234"), ("two", "1234"))).await.unwrap().assert_not_found(); + get(&srv.path_queries("/api/pattern/1234", ("one", "1234"), ("two", "1234"))).await.unwrap().assert_not_found(); +} diff --git a/lib/tests/stubs/req/url-pattern/all.json b/lib/tests/stubs/req/url-pattern/all.json new file mode 100644 index 00000000..ea33dc10 --- /dev/null +++ b/lib/tests/stubs/req/url-pattern/all.json @@ -0,0 +1,9 @@ +{ + "request": { + "urlPattern": "/api/pattern/([a-z]{4})\\?one=([a-z]{4})&two=([a-z]{4})", + "method": "GET" + }, + "response": { + "status": 200 + } +} \ No newline at end of file diff --git a/lib/tests/stubs/req/url-pattern/just-one-query.json b/lib/tests/stubs/req/url-pattern/just-one-query.json new file mode 100644 index 00000000..4635dc7e --- /dev/null +++ b/lib/tests/stubs/req/url-pattern/just-one-query.json @@ -0,0 +1,9 @@ +{ + "request": { + "urlPattern": "/api/pattern\\?one=([a-z]{4})", + "method": "GET" + }, + "response": { + "status": 200 + } +} \ No newline at end of file diff --git a/lib/tests/stubs/req/url-pattern/just-url.json b/lib/tests/stubs/req/url-pattern/just-url.json new file mode 100644 index 00000000..e51ab10d --- /dev/null +++ b/lib/tests/stubs/req/url-pattern/just-url.json @@ -0,0 +1,9 @@ +{ + "request": { + "urlPattern": "/api/pattern/([a-z]{4})", + "method": "GET" + }, + "response": { + "status": 200 + } +} \ No newline at end of file diff --git a/lib/tests/stubs/req/url-pattern/many-queries.json b/lib/tests/stubs/req/url-pattern/many-queries.json new file mode 100644 index 00000000..747e52f6 --- /dev/null +++ b/lib/tests/stubs/req/url-pattern/many-queries.json @@ -0,0 +1,9 @@ +{ + "request": { + "urlPattern": "/api/pattern\\?one=([a-z]{4})&two=([a-z]{4})", + "method": "GET" + }, + "response": { + "status": 200 + } +} \ No newline at end of file