mirror of
https://github.com/wiremock/WireMock.Net.git
synced 2026-02-24 17:55:01 +01:00
Compare commits
40 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
ed74871a26 | ||
|
|
cb66c04199 | ||
|
|
fd28ebdffa | ||
|
|
ce36daa326 | ||
|
|
b5a5f5e464 | ||
|
|
f5d624eeed | ||
|
|
799ea2d219 | ||
|
|
0f99e06acc | ||
|
|
9d0682bff6 | ||
|
|
cb1d2a5294 | ||
|
|
4b435faf0b | ||
|
|
5e7cb44525 | ||
|
|
444298c28c | ||
|
|
6f42aa99bc | ||
|
|
8a9ea1b843 | ||
|
|
dade24de37 | ||
|
|
6beaa631f4 | ||
|
|
282281aa7f | ||
|
|
4052a0ef3b | ||
|
|
2ca394b7f6 | ||
|
|
b04000bfdd | ||
|
|
93ab4e1853 | ||
|
|
80b5eaac6e | ||
|
|
a1dc2ba646 | ||
|
|
934c444902 | ||
|
|
83d178bdb5 | ||
|
|
d91b5d5831 | ||
|
|
43b96ce340 | ||
|
|
4d8cf43357 | ||
|
|
328e9090b1 | ||
|
|
a22b3bfbc5 | ||
|
|
29974c7ad4 | ||
|
|
660a09e656 | ||
|
|
fbecd3b119 | ||
|
|
b17840cea9 | ||
|
|
969b0da8e2 | ||
|
|
dc078b57ea | ||
|
|
8140b37095 | ||
|
|
2ad060bbd4 | ||
|
|
d758301e4f |
6
.editorconfig
Normal file
6
.editorconfig
Normal file
@@ -0,0 +1,6 @@
|
|||||||
|
[*]
|
||||||
|
indent_style = space
|
||||||
|
indent_size = 4
|
||||||
|
end_of_line = crlf
|
||||||
|
charset = utf-8
|
||||||
|
trim_trailing_whitespace = true
|
||||||
4
.github/FUNDING.yml
vendored
4
.github/FUNDING.yml
vendored
@@ -1,8 +1,8 @@
|
|||||||
# These are supported funding model platforms
|
# These are supported funding model platforms
|
||||||
|
|
||||||
github: # Replace with up to 4 GitHub Sponsors-enabled usernames e.g., [user1, user2]
|
github: [StefH]
|
||||||
patreon: # Replace with a single Patreon username
|
patreon: # Replace with a single Patreon username
|
||||||
open_collective: # Replace with a single Open Collective username
|
open_collective: # wiremocknet
|
||||||
ko_fi: # Replace with a single Ko-fi username
|
ko_fi: # Replace with a single Ko-fi username
|
||||||
tidelift: # Replace with a single Tidelift platform-name/package-name e.g., npm/babel
|
tidelift: # Replace with a single Tidelift platform-name/package-name e.g., npm/babel
|
||||||
community_bridge: # Replace with a single Community Bridge project-name e.g., cloud-foundry
|
community_bridge: # Replace with a single Community Bridge project-name e.g., cloud-foundry
|
||||||
|
|||||||
15
.github/workflows/CreateRelease.yml
vendored
Normal file
15
.github/workflows/CreateRelease.yml
vendored
Normal file
@@ -0,0 +1,15 @@
|
|||||||
|
name: CreateRelease
|
||||||
|
|
||||||
|
on:
|
||||||
|
push:
|
||||||
|
tags:
|
||||||
|
- "*.*.*"
|
||||||
|
|
||||||
|
jobs:
|
||||||
|
build:
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
steps:
|
||||||
|
- name: Checkout
|
||||||
|
uses: actions/checkout@v2
|
||||||
|
- name: Release
|
||||||
|
uses: softprops/action-gh-release@v1
|
||||||
60
CHANGELOG.md
60
CHANGELOG.md
@@ -1,3 +1,59 @@
|
|||||||
|
# 1.4.21 (16 September 2021)
|
||||||
|
- [#631](https://github.com/WireMock-Net/WireMock.Net/pull/631) - Add WireMock.org RestClient [feature] contributed by [StefH](https://github.com/StefH)
|
||||||
|
|
||||||
|
# 1.4.20 (06 August 2021)
|
||||||
|
- [#628](https://github.com/WireMock-Net/WireMock.Net/pull/628) - Fix issue with FluentBuilder [bug] contributed by [StefH](https://github.com/StefH)
|
||||||
|
- [#626](https://github.com/WireMock-Net/WireMock.Net/issues/626) - version 1.4.19 throws a lot of analyzer errors related to the BaseBuilder.cs [bug]
|
||||||
|
|
||||||
|
# 1.4.19 (04 August 2021)
|
||||||
|
- [#622](https://github.com/WireMock-Net/WireMock.Net/pull/622) - Add FluentBuilder for client models [feature] contributed by [StefH](https://github.com/StefH)
|
||||||
|
- [#625](https://github.com/WireMock-Net/WireMock.Net/pull/625) - Add NotNullOrEmptyMatcher [feature] contributed by [StefH](https://github.com/StefH)
|
||||||
|
- [#621](https://github.com/WireMock-Net/WireMock.Net/issues/621) - Fluent API for RestClient MappingModel creation [feature]
|
||||||
|
- [#624](https://github.com/WireMock-Net/WireMock.Net/issues/624) - Post request with "BodyAsBytes" is not matched by RegexMatcher [bug]
|
||||||
|
|
||||||
|
# 1.4.18 (10 July 2021)
|
||||||
|
- [#619](https://github.com/WireMock-Net/WireMock.Net/pull/619) - Update Handlebars.Net.Helpers.XPath to fix issue with 'xml version' contributed by [StefH](https://github.com/StefH)
|
||||||
|
- [#618](https://github.com/WireMock-Net/WireMock.Net/issues/618) - Trying to use attribute of the request object while creating response while mocking a soap service [bug]
|
||||||
|
|
||||||
|
# 1.4.17 (07 July 2021)
|
||||||
|
- [#617](https://github.com/WireMock-Net/WireMock.Net/pull/617) - Add support for Handlebars.Net.Helpers.Humanizer [feature] contributed by [StefH](https://github.com/StefH)
|
||||||
|
|
||||||
|
# 1.4.16 (05 June 2021)
|
||||||
|
- [#616](https://github.com/WireMock-Net/WireMock.Net/pull/616) - Upgrade Handlebars.Net.Helpers to 2.19 [feature] contributed by [StefH](https://github.com/StefH)
|
||||||
|
|
||||||
|
# 1.4.15 (19 May 2021)
|
||||||
|
- [#615](https://github.com/WireMock-Net/WireMock.Net/pull/615) - Add support for multiple webhooks [feature] contributed by [StefH](https://github.com/StefH)
|
||||||
|
- [#614](https://github.com/WireMock-Net/WireMock.Net/issues/614) - Is it possible to some how send multiple webhooks? [feature]
|
||||||
|
|
||||||
|
# 1.4.14 (11 May 2021)
|
||||||
|
- [#610](https://github.com/WireMock-Net/WireMock.Net/pull/610) - Fix some SonarCloud issues in UnitTests contributed by [StefH](https://github.com/StefH)
|
||||||
|
- [#611](https://github.com/WireMock-Net/WireMock.Net/pull/611) - Allow to add custom service registrations when using ASP.NET Core [feature] contributed by [starkpl](https://github.com/starkpl)
|
||||||
|
- [#612](https://github.com/WireMock-Net/WireMock.Net/pull/612) - Don't run SonarCloud tasks for PullRequests [feature] contributed by [StefH](https://github.com/StefH)
|
||||||
|
|
||||||
|
# 1.4.13 (26 April 2021)
|
||||||
|
- [#607](https://github.com/WireMock-Net/WireMock.Net/pull/607) - Bump System.Text.Encodings.Web from 4.5.0 to 4.5.1 in /examples/WireMock.Net.StandAlone.Net461 [dependencies] contributed by [dependabot[bot]](https://github.com/apps/dependabot)
|
||||||
|
- [#609](https://github.com/WireMock-Net/WireMock.Net/pull/609) - Add possibility to use settings to generate MappingModel models with wildcard path parameters. [feature] contributed by [StefH](https://github.com/StefH)
|
||||||
|
- [#608](https://github.com/WireMock-Net/WireMock.Net/issues/608) - Import from OpenApi generates model with path parameter narrowed in range (example value=42 instead of '*') [feature]
|
||||||
|
|
||||||
|
# 1.4.12 (22 April 2021)
|
||||||
|
- [#605](https://github.com/WireMock-Net/WireMock.Net/pull/605) - Bump System.Net.Http from 4.3.3 to 4.3.4 in /src/WireMock.Net [dependencies] contributed by [dependabot[bot]](https://github.com/apps/dependabot)
|
||||||
|
- [#606](https://github.com/WireMock-Net/WireMock.Net/pull/606) - Bump System.Net.Http from 4.3.3 to 4.3.4 in /examples/WireMock.Net.Service [dependencies] contributed by [dependabot[bot]](https://github.com/apps/dependabot)
|
||||||
|
|
||||||
|
# 1.4.11 (18 April 2021)
|
||||||
|
- [#604](https://github.com/WireMock-Net/WireMock.Net/pull/604) - Fix match logic for exact bytearray contributed by [StefH](https://github.com/StefH)
|
||||||
|
- [#601](https://github.com/WireMock-Net/WireMock.Net/issues/601) - Exact byte array request matching fails on specific byte arrays [bug]
|
||||||
|
|
||||||
|
# 1.4.10 (15 April 2021)
|
||||||
|
- [#603](https://github.com/WireMock-Net/WireMock.Net/pull/603) - Fix callback with Headers [bug] contributed by [StefH](https://github.com/StefH)
|
||||||
|
- [#602](https://github.com/WireMock-Net/WireMock.Net/issues/602) - Header not being returned when set in WithCallback [bug]
|
||||||
|
|
||||||
|
# 1.4.9 (31 March 2021)
|
||||||
|
- [#600](https://github.com/WireMock-Net/WireMock.Net/pull/600) - WithProxy() should save the new mapping [bug] contributed by [StefH](https://github.com/StefH)
|
||||||
|
|
||||||
|
# 1.4.8 (24 March 2021)
|
||||||
|
- [#591](https://github.com/WireMock-Net/WireMock.Net/pull/591) - Webhook [feature] contributed by [StefH](https://github.com/StefH)
|
||||||
|
- [#589](https://github.com/WireMock-Net/WireMock.Net/issues/589) - How to send a request to a specific URL after sending response [feature]
|
||||||
|
|
||||||
# 1.4.7 (21 March 2021)
|
# 1.4.7 (21 March 2021)
|
||||||
- [#594](https://github.com/WireMock-Net/WireMock.Net/pull/594) - Add possibility to the WithBody() to use IBodyData [feature] contributed by [StefH](https://github.com/StefH)
|
- [#594](https://github.com/WireMock-Net/WireMock.Net/pull/594) - Add possibility to the WithBody() to use IBodyData [feature] contributed by [StefH](https://github.com/StefH)
|
||||||
- [#595](https://github.com/WireMock-Net/WireMock.Net/pull/595) - Use Handlebars.Net.Helpers Version="2.1.2" [feature] contributed by [StefH](https://github.com/StefH)
|
- [#595](https://github.com/WireMock-Net/WireMock.Net/pull/595) - Use Handlebars.Net.Helpers Version="2.1.2" [feature] contributed by [StefH](https://github.com/StefH)
|
||||||
@@ -48,7 +104,6 @@
|
|||||||
- [#549](https://github.com/WireMock-Net/WireMock.Net/issues/549) - WithProxy(...) does not save the mappings to file [bug]
|
- [#549](https://github.com/WireMock-Net/WireMock.Net/issues/549) - WithProxy(...) does not save the mappings to file [bug]
|
||||||
|
|
||||||
# 1.3.8 (03 December 2020)
|
# 1.3.8 (03 December 2020)
|
||||||
- [#539](https://github.com/WireMock-Net/WireMock.Net/pull/539) - Support for partial JSON matching contributed by [gleb-osokin](https://github.com/gleb-osokin)
|
|
||||||
- [#542](https://github.com/WireMock-Net/WireMock.Net/pull/542) - Create dotnet-wiremock tool [feature] contributed by [StefH](https://github.com/StefH)
|
- [#542](https://github.com/WireMock-Net/WireMock.Net/pull/542) - Create dotnet-wiremock tool [feature] contributed by [StefH](https://github.com/StefH)
|
||||||
- [#543](https://github.com/WireMock-Net/WireMock.Net/pull/543) - Add support for .NET 5 [feature] contributed by [StefH](https://github.com/StefH)
|
- [#543](https://github.com/WireMock-Net/WireMock.Net/pull/543) - Add support for .NET 5 [feature] contributed by [StefH](https://github.com/StefH)
|
||||||
- [#544](https://github.com/WireMock-Net/WireMock.Net/pull/544) - Use Java 11 in Azure Pipelines (needed for SonarCloud) [feature] contributed by [StefH](https://github.com/StefH)
|
- [#544](https://github.com/WireMock-Net/WireMock.Net/pull/544) - Use Java 11 in Azure Pipelines (needed for SonarCloud) [feature] contributed by [StefH](https://github.com/StefH)
|
||||||
@@ -56,6 +111,9 @@
|
|||||||
- [#547](https://github.com/WireMock-Net/WireMock.Net/pull/547) - Fix Proxying with SSL and NetCoreApp3.1 [bug] contributed by [StefH](https://github.com/StefH)
|
- [#547](https://github.com/WireMock-Net/WireMock.Net/pull/547) - Fix Proxying with SSL and NetCoreApp3.1 [bug] contributed by [StefH](https://github.com/StefH)
|
||||||
- [#524](https://github.com/WireMock-Net/WireMock.Net/issues/524) - Proxying with SSL Not Working in .NET Core 3.1 [bug]
|
- [#524](https://github.com/WireMock-Net/WireMock.Net/issues/524) - Proxying with SSL Not Working in .NET Core 3.1 [bug]
|
||||||
|
|
||||||
|
# 1.3.7 (17 November 2020)
|
||||||
|
- [#539](https://github.com/WireMock-Net/WireMock.Net/pull/539) - Support for partial JSON matching contributed by [gleb-osokin](https://github.com/gleb-osokin)
|
||||||
|
|
||||||
# 1.3.6 (10 November 2020)
|
# 1.3.6 (10 November 2020)
|
||||||
- [#529](https://github.com/WireMock-Net/WireMock.Net/pull/529) - Add assertions for ClientIP, Url and ProxyUrl [feature] contributed by [akamud](https://github.com/akamud)
|
- [#529](https://github.com/WireMock-Net/WireMock.Net/pull/529) - Add assertions for ClientIP, Url and ProxyUrl [feature] contributed by [akamud](https://github.com/akamud)
|
||||||
- [#535](https://github.com/WireMock-Net/WireMock.Net/pull/535) - WithCallback should use also use enum HttpStatusCode [bug] contributed by [StefH](https://github.com/StefH)
|
- [#535](https://github.com/WireMock-Net/WireMock.Net/pull/535) - WithCallback should use also use enum HttpStatusCode [bug] contributed by [StefH](https://github.com/StefH)
|
||||||
|
|||||||
@@ -1,30 +1,36 @@
|
|||||||
<Project>
|
<Project>
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<MsBuildAllProjects>$(MsBuildAllProjects);$(MsBuildThisFileFullPath)</MsBuildAllProjects>
|
<MsBuildAllProjects>$(MsBuildAllProjects);$(MsBuildThisFileFullPath)</MsBuildAllProjects>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<VersionPrefix>1.4.7</VersionPrefix>
|
<VersionPrefix>1.4.21</VersionPrefix>
|
||||||
<PackageReleaseNotes>See CHANGELOG.md</PackageReleaseNotes>
|
<PackageReleaseNotes>See CHANGELOG.md</PackageReleaseNotes>
|
||||||
<PackageIconUrl>https://raw.githubusercontent.com/WireMock-Net/WireMock.Net/master/WireMock.Net-Logo.png</PackageIconUrl>
|
<PackageIcon>WireMock.Net-Logo.png</PackageIcon>
|
||||||
<PackageProjectUrl>https://github.com/WireMock-Net/WireMock.Net</PackageProjectUrl>
|
<PackageProjectUrl>https://github.com/WireMock-Net/WireMock.Net</PackageProjectUrl>
|
||||||
<PackageLicenseExpression>Apache-2.0</PackageLicenseExpression>
|
<PackageLicenseExpression>Apache-2.0</PackageLicenseExpression>
|
||||||
<RepositoryType>git</RepositoryType>
|
<PackageReleaseNotes>$([System.IO.File]::ReadAllText("$(MSBuildProjectDirectory)/../../PackageReleaseNotes.txt"))</PackageReleaseNotes>
|
||||||
<RepositoryUrl>https://github.com/WireMock-Net/WireMock.Net</RepositoryUrl>
|
<RepositoryType>git</RepositoryType>
|
||||||
<ApplicationIcon>../../WireMock.Net-Logo.ico</ApplicationIcon>
|
<RepositoryUrl>https://github.com/WireMock-Net/WireMock.Net</RepositoryUrl>
|
||||||
</PropertyGroup>
|
<ApplicationIcon>../../resources/WireMock.Net-Logo.ico</ApplicationIcon>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
<PropertyGroup Condition="'$(TF_BUILD)' == 'true'">
|
<PropertyGroup Condition="'$(TF_BUILD)' == 'true'">
|
||||||
<ContinuousIntegrationBuild>true</ContinuousIntegrationBuild>
|
<ContinuousIntegrationBuild>true</ContinuousIntegrationBuild>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<Choose>
|
<ItemGroup>
|
||||||
<!-- The environment variable `Prerelease` is set in the azure-pipelines.yml file. -->
|
<None Include="../../resources/WireMock.Net-Logo.png" Pack="true" PackagePath="" />
|
||||||
<When Condition=" '$(Prerelease)' != '' ">
|
<!--<None Include="../../PackageReadme.md" Pack="true" PackagePath=""/>-->
|
||||||
<PropertyGroup>
|
</ItemGroup>
|
||||||
<!-- Set the version to x.x.x.x-{Prerelease}-1{Build_BuildId} (this is same buildId as defined in the azure-pipelines.yml file). -->
|
|
||||||
<VersionSuffix>$(Prerelease)-1$(BUILD_BUILDID)</VersionSuffix>
|
<Choose>
|
||||||
</PropertyGroup>
|
<!-- The environment variable `Prerelease` is set in the azure-pipelines.yml file. -->
|
||||||
</When>
|
<When Condition=" '$(Prerelease)' != '' ">
|
||||||
</Choose>
|
<PropertyGroup>
|
||||||
|
<!-- Set the version to x.x.x.x-{Prerelease}-1{Build_BuildId} (this is same buildId as defined in the azure-pipelines.yml file). -->
|
||||||
|
<VersionSuffix>$(Prerelease)-1$(BUILD_BUILDID)</VersionSuffix>
|
||||||
|
</PropertyGroup>
|
||||||
|
</When>
|
||||||
|
</Choose>
|
||||||
</Project>
|
</Project>
|
||||||
|
|||||||
7
Generate-ReleaseNotes.cmd
Normal file
7
Generate-ReleaseNotes.cmd
Normal file
@@ -0,0 +1,7 @@
|
|||||||
|
rem https://github.com/StefH/GitHubReleaseNotes
|
||||||
|
|
||||||
|
SET version=1.4.21
|
||||||
|
|
||||||
|
GitHubReleaseNotes --output CHANGELOG.md --skip-empty-releases --exclude-labels question invalid doc duplicate --version %version%
|
||||||
|
|
||||||
|
GitHubReleaseNotes --output PackageReleaseNotes.txt --skip-empty-releases --exclude-labels question invalid doc duplicate --template PackageReleaseNotes.template --version %version%
|
||||||
@@ -1,3 +0,0 @@
|
|||||||
https://github.com/StefH/GitHubReleaseNotes
|
|
||||||
|
|
||||||
GitHubReleaseNotes --output CHANGELOG.md --skip-empty-releases --exclude-labels question invalid doc --version 1.4.7
|
|
||||||
6
PackageReleaseNotes.template
Normal file
6
PackageReleaseNotes.template
Normal file
@@ -0,0 +1,6 @@
|
|||||||
|
# {{releaseInfos.0.FriendlyName}} ({{formatDate releaseInfos.0.When "dd MMMM yyyy"}})
|
||||||
|
{{#each releaseInfos.0.issueInfos}}
|
||||||
|
- #{{Number}} {{Title}}{{#if Labels}} [{{join Labels ", "}}]{{/if}}
|
||||||
|
{{/each}}
|
||||||
|
|
||||||
|
The full release notes can be found here: https://github.com/WireMock-Net/WireMock.Net/blob/master/CHANGELOG.md
|
||||||
4
PackageReleaseNotes.txt
Normal file
4
PackageReleaseNotes.txt
Normal file
@@ -0,0 +1,4 @@
|
|||||||
|
# 1.4.21 (16 September 2021)
|
||||||
|
- #631 Add WireMock.org RestClient [feature]
|
||||||
|
|
||||||
|
The full release notes can be found here: https://github.com/WireMock-Net/WireMock.Net/blob/master/CHANGELOG.md
|
||||||
@@ -34,8 +34,11 @@ For more info, see also this WIKI page: [What is WireMock.Net](https://github.co
|
|||||||
| **WireMock.Net** | [](https://www.nuget.org/packages/WireMock.Net) | [](https://www.myget.org/feed/wiremock-net/package/nuget/WireMock.Net)
|
| **WireMock.Net** | [](https://www.nuget.org/packages/WireMock.Net) | [](https://www.myget.org/feed/wiremock-net/package/nuget/WireMock.Net)
|
||||||
| **WireMock.Net.StandAlone** | [](https://www.nuget.org/packages/WireMock.Net.StandAlone) | [](https://www.myget.org/feed/wiremock-net/package/nuget/WireMock.Net.StandAlone)
|
| **WireMock.Net.StandAlone** | [](https://www.nuget.org/packages/WireMock.Net.StandAlone) | [](https://www.myget.org/feed/wiremock-net/package/nuget/WireMock.Net.StandAlone)
|
||||||
| **WireMock.Net.FluentAssertions** | [](https://www.nuget.org/packages/WireMock.Net.FluentAssertions) | [](https://www.myget.org/feed/wiremock-net/package/nuget/WireMock.Net.FluentAssertions)
|
| **WireMock.Net.FluentAssertions** | [](https://www.nuget.org/packages/WireMock.Net.FluentAssertions) | [](https://www.myget.org/feed/wiremock-net/package/nuget/WireMock.Net.FluentAssertions)
|
||||||
| **WireMock.Net.RestClient** | [](https://www.nuget.org/packages/WireMock.Net.RestClient) | [](https://www.myget.org/feed/wiremock-net/package/nuget/WireMock.Net.RestClient)
|
|
||||||
| **WireMock.Net.Matchers.CSharpCode** | [](https://www.nuget.org/packages/WireMock.Net.Matchers.CSharpCode) | [](https://www.myget.org/feed/wiremock-net/package/nuget/WireMock.Net.Matchers.CSharpCode)
|
| **WireMock.Net.Matchers.CSharpCode** | [](https://www.nuget.org/packages/WireMock.Net.Matchers.CSharpCode) | [](https://www.myget.org/feed/wiremock-net/package/nuget/WireMock.Net.Matchers.CSharpCode)
|
||||||
|
| **WireMock.Net.OpenApiParser** | [](https://www.nuget.org/packages/WireMock.Net.OpenApiParser) | [](https://www.myget.org/feed/wiremock-net/package/nuget/WireMock.Net.OpenApiParser)
|
||||||
|
| **WireMock.Net.RestClient** | [](https://www.nuget.org/packages/WireMock.Net.RestClient) | [](https://www.myget.org/feed/wiremock-net/package/nuget/WireMock.Net.RestClient)
|
||||||
|
| **WireMock.Org.RestClient** | [](https://www.nuget.org/packages/WireMock.Org.RestClient) | [](https://www.myget.org/feed/wiremock-net/package/nuget/WireMock.Org.RestClient)
|
||||||
|
|
||||||
|
|
||||||
## Development
|
## Development
|
||||||
For the supported frameworks and build information, see [this](https://github.com/WireMock-Net/WireMock.Net/wiki/Development-Information) page.
|
For the supported frameworks and build information, see [this](https://github.com/WireMock-Net/WireMock.Net/wiki/Development-Information) page.
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
|
|
||||||
Microsoft Visual Studio Solution File, Format Version 12.00
|
Microsoft Visual Studio Solution File, Format Version 12.00
|
||||||
# Visual Studio Version 16
|
# Visual Studio Version 17
|
||||||
VisualStudioVersion = 16.0.30114.105
|
VisualStudioVersion = 17.0.31521.260
|
||||||
MinimumVisualStudioVersion = 10.0.40219.1
|
MinimumVisualStudioVersion = 10.0.40219.1
|
||||||
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "src", "src", "{8F890C6F-9ACC-438D-928A-AD61CDA862F2}"
|
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "src", "src", "{8F890C6F-9ACC-438D-928A-AD61CDA862F2}"
|
||||||
EndProject
|
EndProject
|
||||||
@@ -21,16 +21,15 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "examples", "examples", "{98
|
|||||||
EndProject
|
EndProject
|
||||||
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{7EFB2C5B-1BB2-4AAF-BC9F-216ED80C594D}"
|
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{7EFB2C5B-1BB2-4AAF-BC9F-216ED80C594D}"
|
||||||
ProjectSection(SolutionItems) = preProject
|
ProjectSection(SolutionItems) = preProject
|
||||||
|
.editorconfig = .editorconfig
|
||||||
.gitignore = .gitignore
|
.gitignore = .gitignore
|
||||||
azure-pipelines-ci-linux.yml = azure-pipelines-ci-linux.yml
|
|
||||||
azure-pipelines-ci.yml = azure-pipelines-ci.yml
|
|
||||||
azure-pipelines-linux.yml = azure-pipelines-linux.yml
|
|
||||||
azure-pipelines-nuget.yml = azure-pipelines-nuget.yml
|
|
||||||
build-info.md = build-info.md
|
build-info.md = build-info.md
|
||||||
CHANGELOG.md = CHANGELOG.md
|
CHANGELOG.md = CHANGELOG.md
|
||||||
Directory.Build.props = Directory.Build.props
|
Directory.Build.props = Directory.Build.props
|
||||||
GitHubReleaseNotes.txt = GitHubReleaseNotes.txt
|
Generate-ReleaseNotes.cmd = Generate-ReleaseNotes.cmd
|
||||||
nuget.config = nuget.config
|
nuget.config = nuget.config
|
||||||
|
PackageReleaseNotes.template = PackageReleaseNotes.template
|
||||||
|
PackageReleaseNotes.txt = PackageReleaseNotes.txt
|
||||||
README.md = README.md
|
README.md = README.md
|
||||||
EndProjectSection
|
EndProjectSection
|
||||||
EndProject
|
EndProject
|
||||||
@@ -82,7 +81,22 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "WireMock.Net.Matchers.CShar
|
|||||||
EndProject
|
EndProject
|
||||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "WireMock.Net.Console.Net472.Classic", "examples\WireMock.Net.Console.Net472.Classic\WireMock.Net.Console.Net472.Classic.csproj", "{6580580B-1EFD-4922-B0EC-FF290DB279EE}"
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "WireMock.Net.Console.Net472.Classic", "examples\WireMock.Net.Console.Net472.Classic\WireMock.Net.Console.Net472.Classic.csproj", "{6580580B-1EFD-4922-B0EC-FF290DB279EE}"
|
||||||
EndProject
|
EndProject
|
||||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "WireMock.Net.XamarinUI.Tests", "test\WireMock.Net.XamarinUI.Tests\WireMock.Net.XamarinUI.Tests.csproj", "{0DE14F1B-A51E-4B59-A87C-C6012DCD2844}"
|
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Actions", "Actions", "{1DAEFF47-D117-4E95-8B3E-4F7C8B92011A}"
|
||||||
|
ProjectSection(SolutionItems) = preProject
|
||||||
|
.github\workflows\CreateRelease.yml = .github\workflows\CreateRelease.yml
|
||||||
|
EndProjectSection
|
||||||
|
EndProject
|
||||||
|
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Azure Pipelines", "Azure Pipelines", "{5B64F6CA-BF6B-4F67-BB2A-9C47E441703E}"
|
||||||
|
ProjectSection(SolutionItems) = preProject
|
||||||
|
azure-pipelines-ci-linux.yml = azure-pipelines-ci-linux.yml
|
||||||
|
azure-pipelines-ci.yml = azure-pipelines-ci.yml
|
||||||
|
azure-pipelines-linux.yml = azure-pipelines-linux.yml
|
||||||
|
azure-pipelines-nuget.yml = azure-pipelines-nuget.yml
|
||||||
|
EndProjectSection
|
||||||
|
EndProject
|
||||||
|
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "WireMock.Org.RestClient", "src\WireMock.Org.RestClient\WireMock.Org.RestClient.csproj", "{08B29DB1-FEFE-408A-AD0A-6BA6DDC8D70F}"
|
||||||
|
EndProject
|
||||||
|
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "WireMock.Org.Abstractions", "src\WireMock.Org.Abstractions\WireMock.Org.Abstractions.csproj", "{3BA5109E-5F30-4CC2-B699-02EC82560AA6}"
|
||||||
EndProject
|
EndProject
|
||||||
Global
|
Global
|
||||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||||
@@ -206,14 +220,14 @@ Global
|
|||||||
{6580580B-1EFD-4922-B0EC-FF290DB279EE}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
{6580580B-1EFD-4922-B0EC-FF290DB279EE}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
{6580580B-1EFD-4922-B0EC-FF290DB279EE}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
{6580580B-1EFD-4922-B0EC-FF290DB279EE}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
{6580580B-1EFD-4922-B0EC-FF290DB279EE}.Release|Any CPU.Build.0 = Release|Any CPU
|
{6580580B-1EFD-4922-B0EC-FF290DB279EE}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
{0DE14F1B-A51E-4B59-A87C-C6012DCD2844}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
{08B29DB1-FEFE-408A-AD0A-6BA6DDC8D70F}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
{0DE14F1B-A51E-4B59-A87C-C6012DCD2844}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
{08B29DB1-FEFE-408A-AD0A-6BA6DDC8D70F}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
{0DE14F1B-A51E-4B59-A87C-C6012DCD2844}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
{08B29DB1-FEFE-408A-AD0A-6BA6DDC8D70F}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
{0DE14F1B-A51E-4B59-A87C-C6012DCD2844}.Release|Any CPU.Build.0 = Release|Any CPU
|
{08B29DB1-FEFE-408A-AD0A-6BA6DDC8D70F}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
{B6269AAC-170A-4346-8B9A-444DED3D9A44}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
{3BA5109E-5F30-4CC2-B699-02EC82560AA6}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
{B6269AAC-170A-4346-8B9A-444DED3D9A44}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
{3BA5109E-5F30-4CC2-B699-02EC82560AA6}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
{B6269AAC-170A-4346-8B9A-444DED3D9A44}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
{3BA5109E-5F30-4CC2-B699-02EC82560AA6}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
{B6269AAC-170A-4346-8B9A-444DED3D9A44}.Release|Any CPU.Build.0 = Release|Any CPU
|
{3BA5109E-5F30-4CC2-B699-02EC82560AA6}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
EndGlobalSection
|
EndGlobalSection
|
||||||
GlobalSection(SolutionProperties) = preSolution
|
GlobalSection(SolutionProperties) = preSolution
|
||||||
HideSolutionNode = FALSE
|
HideSolutionNode = FALSE
|
||||||
@@ -247,9 +261,11 @@ Global
|
|||||||
{40BF24B5-12E6-4610-9489-138798632E28} = {8F890C6F-9ACC-438D-928A-AD61CDA862F2}
|
{40BF24B5-12E6-4610-9489-138798632E28} = {8F890C6F-9ACC-438D-928A-AD61CDA862F2}
|
||||||
{3F8CF0AE-5F24-4A54-89E7-A3EE829DB5F8} = {985E0ADB-D4B4-473A-AA40-567E279B7946}
|
{3F8CF0AE-5F24-4A54-89E7-A3EE829DB5F8} = {985E0ADB-D4B4-473A-AA40-567E279B7946}
|
||||||
{B6269AAC-170A-4346-8B9A-444DED3D9A44} = {8F890C6F-9ACC-438D-928A-AD61CDA862F2}
|
{B6269AAC-170A-4346-8B9A-444DED3D9A44} = {8F890C6F-9ACC-438D-928A-AD61CDA862F2}
|
||||||
{B6269AAC-170A-4346-8B9A-444DED3D9A44} = {8F890C6F-9ACC-438D-928A-AD61CDA862F2}
|
|
||||||
{6580580B-1EFD-4922-B0EC-FF290DB279EE} = {985E0ADB-D4B4-473A-AA40-567E279B7946}
|
{6580580B-1EFD-4922-B0EC-FF290DB279EE} = {985E0ADB-D4B4-473A-AA40-567E279B7946}
|
||||||
{0DE14F1B-A51E-4B59-A87C-C6012DCD2844} = {0BB8B634-407A-4610-A91F-11586990767A}
|
{1DAEFF47-D117-4E95-8B3E-4F7C8B92011A} = {7EFB2C5B-1BB2-4AAF-BC9F-216ED80C594D}
|
||||||
|
{5B64F6CA-BF6B-4F67-BB2A-9C47E441703E} = {7EFB2C5B-1BB2-4AAF-BC9F-216ED80C594D}
|
||||||
|
{08B29DB1-FEFE-408A-AD0A-6BA6DDC8D70F} = {8F890C6F-9ACC-438D-928A-AD61CDA862F2}
|
||||||
|
{3BA5109E-5F30-4CC2-B699-02EC82560AA6} = {8F890C6F-9ACC-438D-928A-AD61CDA862F2}
|
||||||
EndGlobalSection
|
EndGlobalSection
|
||||||
GlobalSection(ExtensibilityGlobals) = postSolution
|
GlobalSection(ExtensibilityGlobals) = postSolution
|
||||||
SolutionGuid = {DC539027-9852-430C-B19F-FD035D018458}
|
SolutionGuid = {DC539027-9852-430C-B19F-FD035D018458}
|
||||||
|
|||||||
@@ -13,6 +13,9 @@
|
|||||||
<s:Boolean x:Key="/Default/UserDictionary/Words/=funcs/@EntryIndexedValue">True</s:Boolean>
|
<s:Boolean x:Key="/Default/UserDictionary/Words/=funcs/@EntryIndexedValue">True</s:Boolean>
|
||||||
<s:Boolean x:Key="/Default/UserDictionary/Words/=Heyenrath/@EntryIndexedValue">True</s:Boolean>
|
<s:Boolean x:Key="/Default/UserDictionary/Words/=Heyenrath/@EntryIndexedValue">True</s:Boolean>
|
||||||
<s:Boolean x:Key="/Default/UserDictionary/Words/=Jmes/@EntryIndexedValue">True</s:Boolean>
|
<s:Boolean x:Key="/Default/UserDictionary/Words/=Jmes/@EntryIndexedValue">True</s:Boolean>
|
||||||
|
<s:Boolean x:Key="/Default/UserDictionary/Words/=Raml/@EntryIndexedValue">True</s:Boolean>
|
||||||
<s:Boolean x:Key="/Default/UserDictionary/Words/=randomizer/@EntryIndexedValue">True</s:Boolean>
|
<s:Boolean x:Key="/Default/UserDictionary/Words/=randomizer/@EntryIndexedValue">True</s:Boolean>
|
||||||
<s:Boolean x:Key="/Default/UserDictionary/Words/=Stef/@EntryIndexedValue">True</s:Boolean>
|
<s:Boolean x:Key="/Default/UserDictionary/Words/=Stef/@EntryIndexedValue">True</s:Boolean>
|
||||||
|
<s:Boolean x:Key="/Default/UserDictionary/Words/=Webhook/@EntryIndexedValue">True</s:Boolean>
|
||||||
|
<s:Boolean x:Key="/Default/UserDictionary/Words/=Webhooks/@EntryIndexedValue">True</s:Boolean>
|
||||||
</wpf:ResourceDictionary>
|
</wpf:ResourceDictionary>
|
||||||
@@ -28,6 +28,7 @@ jobs:
|
|||||||
|
|
||||||
- task: SonarCloudPrepare@1
|
- task: SonarCloudPrepare@1
|
||||||
displayName: 'Prepare analysis on SonarCloud'
|
displayName: 'Prepare analysis on SonarCloud'
|
||||||
|
condition: and(succeeded(), ne(variables['Build.Reason'], 'PullRequest')) # Do not run for PullRequests
|
||||||
inputs:
|
inputs:
|
||||||
SonarCloud: SonarCloud
|
SonarCloud: SonarCloud
|
||||||
organization: wiremock-net
|
organization: wiremock-net
|
||||||
@@ -52,9 +53,11 @@ jobs:
|
|||||||
|
|
||||||
- task: SonarCloudAnalyze@1
|
- task: SonarCloudAnalyze@1
|
||||||
displayName: 'SonarCloud: Run Code Analysis'
|
displayName: 'SonarCloud: Run Code Analysis'
|
||||||
|
condition: and(succeeded(), ne(variables['Build.Reason'], 'PullRequest')) # Do not run for PullRequests
|
||||||
|
|
||||||
- task: SonarCloudPublish@1
|
- task: SonarCloudPublish@1
|
||||||
displayName: 'SonarCloud: Publish Quality Gate Result'
|
displayName: 'SonarCloud: Publish Quality Gate Result'
|
||||||
|
condition: and(succeeded(), ne(variables['Build.Reason'], 'PullRequest')) # Do not run for PullRequests
|
||||||
|
|
||||||
- task: whitesource.ws-bolt.bolt.wss.WhiteSource Bolt@19
|
- task: whitesource.ws-bolt.bolt.wss.WhiteSource Bolt@19
|
||||||
displayName: 'WhiteSource Bolt'
|
displayName: 'WhiteSource Bolt'
|
||||||
|
|||||||
@@ -22,6 +22,11 @@ namespace WireMock.Net.Client
|
|||||||
var settings1 = await api.GetSettingsAsync();
|
var settings1 = await api.GetSettingsAsync();
|
||||||
Console.WriteLine($"settings1 = {JsonConvert.SerializeObject(settings1)}");
|
Console.WriteLine($"settings1 = {JsonConvert.SerializeObject(settings1)}");
|
||||||
|
|
||||||
|
var settingsViaBuilder = new FluentBuilder.SettingsModelBuilder()
|
||||||
|
.WithGlobalProcessingDelay(1077)
|
||||||
|
.WithoutGlobalProcessingDelay()
|
||||||
|
.Build();
|
||||||
|
|
||||||
settings1.GlobalProcessingDelay = 1077;
|
settings1.GlobalProcessingDelay = 1077;
|
||||||
api.PostSettingsAsync(settings1).Wait();
|
api.PostSettingsAsync(settings1).Wait();
|
||||||
|
|
||||||
|
|||||||
@@ -3,12 +3,12 @@
|
|||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<OutputType>Exe</OutputType>
|
<OutputType>Exe</OutputType>
|
||||||
<TargetFramework>netcoreapp2.1</TargetFramework>
|
<TargetFramework>netcoreapp2.1</TargetFramework>
|
||||||
<ApplicationIcon>../../WireMock.Net-Logo.ico</ApplicationIcon>
|
<ApplicationIcon>../../resources/WireMock.Net-Logo.ico</ApplicationIcon>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<PackageReference Include="Newtonsoft.Json" Version="11.0.2" />
|
<PackageReference Include="Newtonsoft.Json" Version="11.0.2" />
|
||||||
<PackageReference Include="RestEase" Version="1.4.10" />
|
<PackageReference Include="RestEase" Version="1.5.5" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
|||||||
@@ -1,9 +1,8 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk">
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<OutputType>Exe</OutputType>
|
<OutputType>Exe</OutputType>
|
||||||
<TargetFramework>net5.0</TargetFramework>
|
<TargetFramework>net5.0</TargetFramework>
|
||||||
<ApplicationIcon>../../WireMock.Net-Logo.ico</ApplicationIcon>
|
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
|||||||
@@ -3,7 +3,7 @@
|
|||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<OutputType>Exe</OutputType>
|
<OutputType>Exe</OutputType>
|
||||||
<TargetFramework>netcoreapp1.1</TargetFramework>
|
<TargetFramework>netcoreapp1.1</TargetFramework>
|
||||||
<ApplicationIcon>../../WireMock.Net-Logo.ico</ApplicationIcon>
|
<ApplicationIcon>../../resources/WireMock.Net-Logo.ico</ApplicationIcon>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
|||||||
@@ -3,7 +3,7 @@
|
|||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<OutputType>Exe</OutputType>
|
<OutputType>Exe</OutputType>
|
||||||
<TargetFramework>netcoreapp2.1</TargetFramework>
|
<TargetFramework>netcoreapp2.1</TargetFramework>
|
||||||
<ApplicationIcon>../../WireMock.Net-Logo.ico</ApplicationIcon>
|
<ApplicationIcon>../../resources/WireMock.Net-Logo.ico</ApplicationIcon>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
|||||||
@@ -3,7 +3,7 @@
|
|||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<OutputType>Exe</OutputType>
|
<OutputType>Exe</OutputType>
|
||||||
<TargetFramework>netcoreapp3.1</TargetFramework>
|
<TargetFramework>netcoreapp3.1</TargetFramework>
|
||||||
<ApplicationIcon>../../WireMock.Net-Logo.ico</ApplicationIcon>
|
<ApplicationIcon>../../resources/WireMock.Net-Logo.ico</ApplicationIcon>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
|||||||
@@ -59,6 +59,7 @@ namespace WireMock.Net.ConsoleApplication
|
|||||||
//},
|
//},
|
||||||
PreWireMockMiddlewareInit = app => { System.Console.WriteLine($"PreWireMockMiddlewareInit : {app.GetType()}"); },
|
PreWireMockMiddlewareInit = app => { System.Console.WriteLine($"PreWireMockMiddlewareInit : {app.GetType()}"); },
|
||||||
PostWireMockMiddlewareInit = app => { System.Console.WriteLine($"PostWireMockMiddlewareInit : {app.GetType()}"); },
|
PostWireMockMiddlewareInit = app => { System.Console.WriteLine($"PostWireMockMiddlewareInit : {app.GetType()}"); },
|
||||||
|
AdditionalServiceRegistration = services => { System.Console.WriteLine($"AdditionalServiceRegistration : {services.GetType()}"); },
|
||||||
Logger = new WireMockConsoleLogger(),
|
Logger = new WireMockConsoleLogger(),
|
||||||
|
|
||||||
HandlebarsRegistrationCallback = (handlebarsContext, fileSystemHandler) =>
|
HandlebarsRegistrationCallback = (handlebarsContext, fileSystemHandler) =>
|
||||||
|
|||||||
@@ -33,7 +33,7 @@
|
|||||||
<WarningLevel>4</WarningLevel>
|
<WarningLevel>4</WarningLevel>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<ApplicationIcon>..\..\WireMock.Net-Logo.ico</ApplicationIcon>
|
<ApplicationIcon>..\..\resources\WireMock.Net-Logo.ico</ApplicationIcon>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<Reference Include="Handlebars, Version=2.0.4.0, Culture=neutral, PublicKeyToken=22225d0bf33cd661, processorArchitecture=MSIL">
|
<Reference Include="Handlebars, Version=2.0.4.0, Culture=neutral, PublicKeyToken=22225d0bf33cd661, processorArchitecture=MSIL">
|
||||||
|
|||||||
@@ -3,7 +3,7 @@
|
|||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<OutputType>Exe</OutputType>
|
<OutputType>Exe</OutputType>
|
||||||
<TargetFrameworks>netcoreapp2.1;netcoreapp3.1;net5.0</TargetFrameworks>
|
<TargetFrameworks>netcoreapp2.1;netcoreapp3.1;net5.0</TargetFrameworks>
|
||||||
<ApplicationIcon>../../WireMock.Net-Logo.ico</ApplicationIcon>
|
<ApplicationIcon>../../resources/WireMock.Net-Logo.ico</ApplicationIcon>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
|||||||
@@ -3,7 +3,7 @@
|
|||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<OutputType>Exe</OutputType>
|
<OutputType>Exe</OutputType>
|
||||||
<TargetFramework>net5.0</TargetFramework>
|
<TargetFramework>net5.0</TargetFramework>
|
||||||
<ApplicationIcon>../../WireMock.Net-Logo.ico</ApplicationIcon>
|
<ApplicationIcon>../../resources/WireMock.Net-Logo.ico</ApplicationIcon>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
|||||||
@@ -3,9 +3,11 @@ using System.Collections.Generic;
|
|||||||
using System.Linq;
|
using System.Linq;
|
||||||
using WireMock.Admin.Mappings;
|
using WireMock.Admin.Mappings;
|
||||||
using WireMock.Logging;
|
using WireMock.Logging;
|
||||||
|
using WireMock.Net.OpenApiParser.Extensions;
|
||||||
|
using WireMock.Net.OpenApiParser.Settings;
|
||||||
|
using WireMock.Net.OpenApiParser.Types;
|
||||||
using WireMock.Server;
|
using WireMock.Server;
|
||||||
using WireMock.Settings;
|
using WireMock.Settings;
|
||||||
using WireMock.Net.OpenApiParser.Extensions;
|
|
||||||
|
|
||||||
namespace WireMock.Net.OpenApiParser.ConsoleApp
|
namespace WireMock.Net.OpenApiParser.ConsoleApp
|
||||||
{
|
{
|
||||||
@@ -23,13 +25,18 @@ namespace WireMock.Net.OpenApiParser.ConsoleApp
|
|||||||
ReadStaticMappings = false,
|
ReadStaticMappings = false,
|
||||||
WatchStaticMappings = false,
|
WatchStaticMappings = false,
|
||||||
WatchStaticMappingsInSubdirectories = false,
|
WatchStaticMappingsInSubdirectories = false,
|
||||||
Logger = new WireMockConsoleLogger(),
|
Logger = new WireMockConsoleLogger()
|
||||||
});
|
});
|
||||||
Console.WriteLine("WireMockServer listening at {0}", string.Join(",", server.Urls));
|
Console.WriteLine("WireMockServer listening at {0}", string.Join(",", server.Urls));
|
||||||
|
|
||||||
server.SetBasicAuthentication("a", "b");
|
server.SetBasicAuthentication("a", "b");
|
||||||
|
|
||||||
server.WithMappingFromOpenApiFile(path, out var diag);
|
var settings = new WireMockOpenApiParserSettings
|
||||||
|
{
|
||||||
|
PathPatternToUse = ExampleValueType.Wildcard
|
||||||
|
};
|
||||||
|
|
||||||
|
server.WithMappingFromOpenApiFile(path, settings, out var diag);
|
||||||
|
|
||||||
Console.WriteLine("Press any key to stop the server");
|
Console.WriteLine("Press any key to stop the server");
|
||||||
System.Console.ReadKey();
|
System.Console.ReadKey();
|
||||||
|
|||||||
@@ -32,11 +32,8 @@
|
|||||||
<WarningLevel>4</WarningLevel>
|
<WarningLevel>4</WarningLevel>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<Reference Include="Handlebars, Version=1.9.5.0, Culture=neutral, PublicKeyToken=22225d0bf33cd661, processorArchitecture=MSIL">
|
<Reference Include="log4net, Version=2.0.12.0, Culture=neutral, PublicKeyToken=669e0ddf0bb1aa2a, processorArchitecture=MSIL">
|
||||||
<HintPath>..\..\packages\Handlebars.Net.1.9.5\lib\net452\Handlebars.dll</HintPath>
|
<HintPath>..\..\packages\log4net.2.0.12\lib\net45\log4net.dll</HintPath>
|
||||||
</Reference>
|
|
||||||
<Reference Include="log4net, Version=2.0.8.0, Culture=neutral, PublicKeyToken=669e0ddf0bb1aa2a, processorArchitecture=MSIL">
|
|
||||||
<HintPath>..\..\packages\log4net.2.0.8\lib\net45-full\log4net.dll</HintPath>
|
|
||||||
</Reference>
|
</Reference>
|
||||||
<Reference Include="Microsoft.Owin, Version=2.0.2.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
|
<Reference Include="Microsoft.Owin, Version=2.0.2.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
|
||||||
<HintPath>..\..\packages\Microsoft.Owin.2.0.2\lib\net45\Microsoft.Owin.dll</HintPath>
|
<HintPath>..\..\packages\Microsoft.Owin.2.0.2\lib\net45\Microsoft.Owin.dll</HintPath>
|
||||||
@@ -57,6 +54,7 @@
|
|||||||
<HintPath>..\..\packages\SimMetrics.Net.1.0.5\lib\net45\SimMetrics.Net.dll</HintPath>
|
<HintPath>..\..\packages\SimMetrics.Net.1.0.5\lib\net45\SimMetrics.Net.dll</HintPath>
|
||||||
</Reference>
|
</Reference>
|
||||||
<Reference Include="System" />
|
<Reference Include="System" />
|
||||||
|
<Reference Include="System.Configuration" />
|
||||||
<Reference Include="System.Configuration.Install" />
|
<Reference Include="System.Configuration.Install" />
|
||||||
<Reference Include="System.Core" />
|
<Reference Include="System.Core" />
|
||||||
<Reference Include="System.Management" />
|
<Reference Include="System.Management" />
|
||||||
|
|||||||
@@ -1,7 +1,6 @@
|
|||||||
<?xml version="1.0" encoding="utf-8"?>
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
<packages>
|
<packages>
|
||||||
<package id="Handlebars.Net" version="1.9.5" targetFramework="net452" />
|
<package id="log4net" version="2.0.12" targetFramework="net452" />
|
||||||
<package id="log4net" version="2.0.10" targetFramework="net452" />
|
|
||||||
<package id="Microsoft.AspNet.WebApi.Client" version="5.2.3" targetFramework="net452" />
|
<package id="Microsoft.AspNet.WebApi.Client" version="5.2.3" targetFramework="net452" />
|
||||||
<package id="Microsoft.AspNet.WebApi.Core" version="5.2.3" targetFramework="net452" />
|
<package id="Microsoft.AspNet.WebApi.Core" version="5.2.3" targetFramework="net452" />
|
||||||
<package id="Microsoft.AspNet.WebApi.Owin" version="5.2.3" targetFramework="net452" />
|
<package id="Microsoft.AspNet.WebApi.Owin" version="5.2.3" targetFramework="net452" />
|
||||||
@@ -12,6 +11,6 @@
|
|||||||
<package id="Newtonsoft.Json" version="11.0.2" targetFramework="net452" />
|
<package id="Newtonsoft.Json" version="11.0.2" targetFramework="net452" />
|
||||||
<package id="Owin" version="1.0" targetFramework="net452" />
|
<package id="Owin" version="1.0" targetFramework="net452" />
|
||||||
<package id="SimMetrics.Net" version="1.0.5" targetFramework="net452" />
|
<package id="SimMetrics.Net" version="1.0.5" targetFramework="net452" />
|
||||||
<package id="System.Net.Http" version="4.3.3" targetFramework="net452" />
|
<package id="System.Net.Http" version="4.3.4" targetFramework="net452" />
|
||||||
<package id="XPath2" version="1.1.0" targetFramework="net452" />
|
<package id="XPath2" version="1.1.0" targetFramework="net452" />
|
||||||
</packages>
|
</packages>
|
||||||
@@ -2,7 +2,7 @@
|
|||||||
"profiles": {
|
"profiles": {
|
||||||
"WireMock.Net.StandAlone.NETCoreApp": {
|
"WireMock.Net.StandAlone.NETCoreApp": {
|
||||||
"commandName": "Project",
|
"commandName": "Project",
|
||||||
"commandLineArgs": "--Urls https://localhost:10080 --WireMockLogger WireMockConsoleLogger"
|
"commandLineArgs": "--Urls http://localhost:9091 --WireMockLogger WireMockConsoleLogger"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1,9 +1,8 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk">
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<OutputType>Exe</OutputType>
|
<OutputType>Exe</OutputType>
|
||||||
<TargetFrameworks>netcoreapp3.1</TargetFrameworks>
|
<TargetFrameworks>netcoreapp3.1</TargetFrameworks>
|
||||||
<ApplicationIcon>../../WireMock.Net-Logo.ico</ApplicationIcon>
|
|
||||||
<StartupObject>WireMock.Net.StandAlone.NETCoreApp.Program</StartupObject>
|
<StartupObject>WireMock.Net.StandAlone.NETCoreApp.Program</StartupObject>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
|
|||||||
@@ -33,14 +33,14 @@
|
|||||||
<WarningLevel>4</WarningLevel>
|
<WarningLevel>4</WarningLevel>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<ApplicationIcon>..\..\WireMock.Net-Logo.ico</ApplicationIcon>
|
<ApplicationIcon>..\..\resources\WireMock.Net-Logo.ico</ApplicationIcon>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<StartupObject>WireMock.Net.StandAlone.Net452.Program</StartupObject>
|
<StartupObject>WireMock.Net.StandAlone.Net452.Program</StartupObject>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<Reference Include="log4net, Version=2.0.8.0, Culture=neutral, PublicKeyToken=669e0ddf0bb1aa2a, processorArchitecture=MSIL">
|
<Reference Include="log4net, Version=2.0.12.0, Culture=neutral, PublicKeyToken=669e0ddf0bb1aa2a, processorArchitecture=MSIL">
|
||||||
<HintPath>..\..\packages\log4net.2.0.8\lib\net45-full\log4net.dll</HintPath>
|
<HintPath>..\..\packages\log4net.2.0.12\lib\net45\log4net.dll</HintPath>
|
||||||
</Reference>
|
</Reference>
|
||||||
<Reference Include="Microsoft.Owin.Host.HttpListener, Version=4.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
|
<Reference Include="Microsoft.Owin.Host.HttpListener, Version=4.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
|
||||||
<HintPath>..\..\packages\Microsoft.Owin.Host.HttpListener.4.0.0\lib\net451\Microsoft.Owin.Host.HttpListener.dll</HintPath>
|
<HintPath>..\..\packages\Microsoft.Owin.Host.HttpListener.4.0.0\lib\net451\Microsoft.Owin.Host.HttpListener.dll</HintPath>
|
||||||
@@ -49,12 +49,14 @@
|
|||||||
<HintPath>..\..\packages\Newtonsoft.Json.11.0.2\lib\net45\Newtonsoft.Json.dll</HintPath>
|
<HintPath>..\..\packages\Newtonsoft.Json.11.0.2\lib\net45\Newtonsoft.Json.dll</HintPath>
|
||||||
</Reference>
|
</Reference>
|
||||||
<Reference Include="System" />
|
<Reference Include="System" />
|
||||||
|
<Reference Include="System.Configuration" />
|
||||||
<Reference Include="System.Core" />
|
<Reference Include="System.Core" />
|
||||||
<Reference Include="System.Net.Http" />
|
<Reference Include="System.Net.Http" />
|
||||||
<Reference Include="System.Net.Http.Formatting, Version=5.2.6.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
|
<Reference Include="System.Net.Http.Formatting, Version=5.2.6.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL">
|
||||||
<HintPath>..\..\packages\Microsoft.AspNet.WebApi.Client.5.2.6\lib\net45\System.Net.Http.Formatting.dll</HintPath>
|
<HintPath>..\..\packages\Microsoft.AspNet.WebApi.Client.5.2.6\lib\net45\System.Net.Http.Formatting.dll</HintPath>
|
||||||
</Reference>
|
</Reference>
|
||||||
<Reference Include="System.Numerics" />
|
<Reference Include="System.Numerics" />
|
||||||
|
<Reference Include="System.Web" />
|
||||||
<Reference Include="System.Xml" />
|
<Reference Include="System.Xml" />
|
||||||
<Reference Include="System.Xml.Linq" />
|
<Reference Include="System.Xml.Linq" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
<?xml version="1.0" encoding="utf-8"?>
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
<packages>
|
<packages>
|
||||||
<package id="log4net" version="2.0.10" targetFramework="net452" />
|
<package id="log4net" version="2.0.12" targetFramework="net452" />
|
||||||
<package id="Microsoft.AspNet.WebApi.Client" version="5.2.6" targetFramework="net452" />
|
<package id="Microsoft.AspNet.WebApi.Client" version="5.2.6" targetFramework="net452" />
|
||||||
<package id="Microsoft.Owin.Host.HttpListener" version="4.0.0" targetFramework="net452" />
|
<package id="Microsoft.Owin.Host.HttpListener" version="4.0.0" targetFramework="net452" />
|
||||||
<package id="Newtonsoft.Json" version="11.0.2" targetFramework="net452" />
|
<package id="Newtonsoft.Json" version="11.0.2" targetFramework="net452" />
|
||||||
|
|||||||
@@ -204,8 +204,8 @@
|
|||||||
<Reference Include="Owin, Version=1.0.0.0, Culture=neutral, PublicKeyToken=f0ebd12fd5e55cc5, processorArchitecture=MSIL">
|
<Reference Include="Owin, Version=1.0.0.0, Culture=neutral, PublicKeyToken=f0ebd12fd5e55cc5, processorArchitecture=MSIL">
|
||||||
<HintPath>..\..\packages\Owin.1.0\lib\net40\Owin.dll</HintPath>
|
<HintPath>..\..\packages\Owin.1.0\lib\net40\Owin.dll</HintPath>
|
||||||
</Reference>
|
</Reference>
|
||||||
<Reference Include="RestEase, Version=1.4.10.0, Culture=neutral, processorArchitecture=MSIL">
|
<Reference Include="RestEase, Version=1.5.5.0, Culture=neutral, processorArchitecture=MSIL">
|
||||||
<HintPath>..\..\packages\RestEase.1.4.10\lib\net45\RestEase.dll</HintPath>
|
<HintPath>..\..\packages\RestEase.1.5.5\lib\net45\RestEase.dll</HintPath>
|
||||||
</Reference>
|
</Reference>
|
||||||
<Reference Include="SimMetrics.Net, Version=1.0.5.0, Culture=neutral, PublicKeyToken=c58dc06d59f3391b, processorArchitecture=MSIL">
|
<Reference Include="SimMetrics.Net, Version=1.0.5.0, Culture=neutral, PublicKeyToken=c58dc06d59f3391b, processorArchitecture=MSIL">
|
||||||
<HintPath>..\..\packages\SimMetrics.Net.1.0.5\lib\net45\SimMetrics.Net.dll</HintPath>
|
<HintPath>..\..\packages\SimMetrics.Net.1.0.5\lib\net45\SimMetrics.Net.dll</HintPath>
|
||||||
|
|||||||
@@ -59,7 +59,7 @@
|
|||||||
<package id="MimeKitLite" version="2.0.7" targetFramework="net461" />
|
<package id="MimeKitLite" version="2.0.7" targetFramework="net461" />
|
||||||
<package id="Newtonsoft.Json" version="11.0.2" targetFramework="net461" />
|
<package id="Newtonsoft.Json" version="11.0.2" targetFramework="net461" />
|
||||||
<package id="Owin" version="1.0" targetFramework="net461" />
|
<package id="Owin" version="1.0" targetFramework="net461" />
|
||||||
<package id="RestEase" version="1.4.10" targetFramework="net461" />
|
<package id="RestEase" version="1.5.5" targetFramework="net461" />
|
||||||
<package id="SimMetrics.Net" version="1.0.5" targetFramework="net461" />
|
<package id="SimMetrics.Net" version="1.0.5" targetFramework="net461" />
|
||||||
<package id="System.Buffers" version="4.5.0" targetFramework="net461" />
|
<package id="System.Buffers" version="4.5.0" targetFramework="net461" />
|
||||||
<package id="System.Collections.Immutable" version="1.5.0" targetFramework="net461" />
|
<package id="System.Collections.Immutable" version="1.5.0" targetFramework="net461" />
|
||||||
@@ -76,7 +76,7 @@
|
|||||||
<package id="System.Security.Cryptography.Primitives" version="4.3.0" targetFramework="net461" />
|
<package id="System.Security.Cryptography.Primitives" version="4.3.0" targetFramework="net461" />
|
||||||
<package id="System.Security.Cryptography.X509Certificates" version="4.3.0" targetFramework="net461" />
|
<package id="System.Security.Cryptography.X509Certificates" version="4.3.0" targetFramework="net461" />
|
||||||
<package id="System.Security.Principal.Windows" version="4.5.1" targetFramework="net461" />
|
<package id="System.Security.Principal.Windows" version="4.5.1" targetFramework="net461" />
|
||||||
<package id="System.Text.Encodings.Web" version="4.5.0" targetFramework="net461" />
|
<package id="System.Text.Encodings.Web" version="4.5.1" targetFramework="net461" />
|
||||||
<package id="System.Threading.Tasks.Extensions" version="4.5.1" targetFramework="net461" />
|
<package id="System.Threading.Tasks.Extensions" version="4.5.1" targetFramework="net461" />
|
||||||
<package id="XPath2" version="1.1.0" targetFramework="net461" />
|
<package id="XPath2" version="1.1.0" targetFramework="net461" />
|
||||||
</packages>
|
</packages>
|
||||||
|
Before Width: | Height: | Size: 24 KiB After Width: | Height: | Size: 24 KiB |
|
Before Width: | Height: | Size: 13 KiB After Width: | Height: | Size: 13 KiB |
@@ -3,6 +3,7 @@
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Body Model
|
/// Body Model
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class BodyModel
|
public class BodyModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -3,6 +3,7 @@
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// ClientIPModel
|
/// ClientIPModel
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class ClientIPModel
|
public class ClientIPModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ namespace WireMock.Admin.Mappings
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Cookie Model
|
/// Cookie Model
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class CookieModel
|
public class CookieModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -3,6 +3,7 @@
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// EncodingModel
|
/// EncodingModel
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class EncodingModel
|
public class EncodingModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -3,6 +3,7 @@
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Fault Model
|
/// Fault Model
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class FaultModel
|
public class FaultModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ namespace WireMock.Admin.Mappings
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Header Model
|
/// Header Model
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class HeaderModel
|
public class HeaderModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ namespace WireMock.Admin.Mappings
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// MappingModel
|
/// MappingModel
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class MappingModel
|
public class MappingModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@@ -52,5 +53,15 @@ namespace WireMock.Admin.Mappings
|
|||||||
/// Saves this mapping as a static mapping file.
|
/// Saves this mapping as a static mapping file.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool? SaveToFile { get; set; }
|
public bool? SaveToFile { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The Webhook.
|
||||||
|
/// </summary>
|
||||||
|
public WebhookModel Webhook { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The Webhooks.
|
||||||
|
/// </summary>
|
||||||
|
public WebhookModel[] Webhooks { get; set; }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -3,6 +3,7 @@
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// MatcherModel
|
/// MatcherModel
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class MatcherModel
|
public class MatcherModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -3,6 +3,7 @@
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Param Model
|
/// Param Model
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class ParamModel
|
public class ParamModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -3,6 +3,7 @@
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// PathModel
|
/// PathModel
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class PathModel
|
public class PathModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ namespace WireMock.Admin.Mappings
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// RequestModel
|
/// RequestModel
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class RequestModel
|
public class RequestModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -1,11 +1,11 @@
|
|||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using WireMock.Types;
|
|
||||||
|
|
||||||
namespace WireMock.Admin.Mappings
|
namespace WireMock.Admin.Mappings
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// ResponseModel
|
/// ResponseModel
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class ResponseModel
|
public class ResponseModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ namespace WireMock.Admin.Mappings
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Status
|
/// Status
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class StatusModel
|
public class StatusModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -3,6 +3,7 @@
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// UrlModel
|
/// UrlModel
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class UrlModel
|
public class UrlModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -3,6 +3,7 @@
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// WebProxy settings
|
/// WebProxy settings
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class WebProxyModel
|
public class WebProxyModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
14
src/WireMock.Net.Abstractions/Admin/Mappings/WebhookModel.cs
Normal file
14
src/WireMock.Net.Abstractions/Admin/Mappings/WebhookModel.cs
Normal file
@@ -0,0 +1,14 @@
|
|||||||
|
namespace WireMock.Admin.Mappings
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// The Webhook
|
||||||
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
|
public class WebhookModel
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// The Webhook Request.
|
||||||
|
/// </summary>
|
||||||
|
public WebhookRequestModel Request { get; set; }
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,46 @@
|
|||||||
|
using System.Collections.Generic;
|
||||||
|
|
||||||
|
namespace WireMock.Admin.Mappings
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// RequestModel
|
||||||
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
|
public class WebhookRequestModel
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Gets or sets the Url.
|
||||||
|
/// </summary>
|
||||||
|
public string Url { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The methods
|
||||||
|
/// </summary>
|
||||||
|
public string Method { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets or sets the headers.
|
||||||
|
/// </summary>
|
||||||
|
public IDictionary<string, string> Headers { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets or sets the body.
|
||||||
|
/// </summary>
|
||||||
|
public string Body { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets or sets the body (as JSON object).
|
||||||
|
/// </summary>
|
||||||
|
public object BodyAsJson { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Use ResponseMessage Transformer.
|
||||||
|
/// </summary>
|
||||||
|
public bool? UseTransformer { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets the type of the transformer.
|
||||||
|
/// </summary>
|
||||||
|
public string TransformerType { get; set; }
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -5,6 +5,7 @@ namespace WireMock.Admin.Requests
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Request Log Model
|
/// Request Log Model
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class LogEntryModel
|
public class LogEntryModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ namespace WireMock.Admin.Requests
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// LogRequestMatchModel
|
/// LogRequestMatchModel
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class LogRequestMatchModel
|
public class LogRequestMatchModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -8,6 +8,7 @@ namespace WireMock.Admin.Requests
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// RequestMessage Model
|
/// RequestMessage Model
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class LogRequestModel
|
public class LogRequestModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -7,6 +7,7 @@ namespace WireMock.Admin.Requests
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Response MessageModel
|
/// Response MessageModel
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class LogResponseModel
|
public class LogResponseModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -3,6 +3,7 @@
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// ScenarioStateModel
|
/// ScenarioStateModel
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class ScenarioStateModel
|
public class ScenarioStateModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
@@ -3,6 +3,7 @@
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Settings
|
/// Settings
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[FluentBuilder.AutoGenerateBuilder]
|
||||||
public class SettingsModel
|
public class SettingsModel
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
|||||||
13
src/WireMock.Net.Abstractions/Models/IWebhook.cs
Normal file
13
src/WireMock.Net.Abstractions/Models/IWebhook.cs
Normal file
@@ -0,0 +1,13 @@
|
|||||||
|
namespace WireMock.Models
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// IWebhook
|
||||||
|
/// </summary>
|
||||||
|
public interface IWebhook
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Request
|
||||||
|
/// </summary>
|
||||||
|
IWebhookRequest Request { get; set; }
|
||||||
|
}
|
||||||
|
}
|
||||||
42
src/WireMock.Net.Abstractions/Models/IWebhookRequest.cs
Normal file
42
src/WireMock.Net.Abstractions/Models/IWebhookRequest.cs
Normal file
@@ -0,0 +1,42 @@
|
|||||||
|
using System.Collections.Generic;
|
||||||
|
using WireMock.Types;
|
||||||
|
using WireMock.Util;
|
||||||
|
|
||||||
|
namespace WireMock.Models
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// IWebhookRequest
|
||||||
|
/// </summary>
|
||||||
|
public interface IWebhookRequest
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// The Webhook Url.
|
||||||
|
/// </summary>
|
||||||
|
string Url { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The method to use.
|
||||||
|
/// </summary>
|
||||||
|
string Method { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The Headers to send.
|
||||||
|
/// </summary>
|
||||||
|
IDictionary<string, WireMockList<string>> Headers { get; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The body to send.
|
||||||
|
/// </summary>
|
||||||
|
IBodyData BodyData { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Use Transformer.
|
||||||
|
/// </summary>
|
||||||
|
bool? UseTransformer { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The transformer type.
|
||||||
|
/// </summary>
|
||||||
|
TransformerType TransformerType { get; set; }
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,37 +1,46 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk">
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<Description>Commonly used interfaces, models, enumerations and types.</Description>
|
<Description>Commonly used models, enumerations and types.</Description>
|
||||||
<AssemblyTitle>WireMock.Net.Abstractions</AssemblyTitle>
|
<AssemblyTitle>WireMock.Net.Abstractions</AssemblyTitle>
|
||||||
<Authors>Stef Heyenrath</Authors>
|
<Authors>Stef Heyenrath</Authors>
|
||||||
<TargetFrameworks>net45;netstandard1.0;netstandard2.0;netstandard2.1</TargetFrameworks>
|
<TargetFrameworks>net45;netstandard1.0;netstandard2.0;netstandard2.1</TargetFrameworks>
|
||||||
<GenerateDocumentationFile>true</GenerateDocumentationFile>
|
|
||||||
<AssemblyName>WireMock.Net.Abstractions</AssemblyName>
|
|
||||||
<PackageId>WireMock.Net.Abstractions</PackageId>
|
|
||||||
<PackageTags>wiremock;interfaces;models;classes;enumerations;types</PackageTags>
|
|
||||||
<RootNamespace>WireMock</RootNamespace>
|
|
||||||
<ProjectGuid>{B6269AAC-170A-4346-8B9A-579DED3D9A94}</ProjectGuid>
|
|
||||||
<PublishRepositoryUrl>true</PublishRepositoryUrl>
|
|
||||||
<AllowedOutputExtensionsInPackageBuildOutputFolder>$(AllowedOutputExtensionsInPackageBuildOutputFolder);.pdb</AllowedOutputExtensionsInPackageBuildOutputFolder>
|
|
||||||
<EmbedUntrackedSources>true</EmbedUntrackedSources>
|
|
||||||
<AutoGenerateBindingRedirects>true</AutoGenerateBindingRedirects>
|
|
||||||
<GenerateBindingRedirectsOutputType>true</GenerateBindingRedirectsOutputType>
|
|
||||||
<CodeAnalysisRuleSet>../WireMock.Net/WireMock.Net.ruleset</CodeAnalysisRuleSet>
|
|
||||||
<SignAssembly>true</SignAssembly>
|
|
||||||
<AssemblyOriginatorKeyFile>../WireMock.Net/WireMock.Net.snk</AssemblyOriginatorKeyFile>
|
|
||||||
<!--<DelaySign>true</DelaySign>-->
|
|
||||||
<PublicSign Condition=" '$(OS)' != 'Windows_NT' ">true</PublicSign>
|
|
||||||
<PackageLicenseExpression>MIT</PackageLicenseExpression>
|
|
||||||
</PropertyGroup>
|
|
||||||
|
|
||||||
<PropertyGroup Condition=" '$(Configuration)' == 'Release' ">
|
<GenerateDocumentationFile>true</GenerateDocumentationFile>
|
||||||
<!--<PathMap>$(MSBuildProjectDirectory)=/</PathMap>-->
|
<NoWarn>$(NoWarn);1591;8603</NoWarn>
|
||||||
<GeneratePackageOnBuild>true</GeneratePackageOnBuild>
|
|
||||||
</PropertyGroup>
|
|
||||||
|
|
||||||
<ItemGroup>
|
<AssemblyName>WireMock.Net.Abstractions</AssemblyName>
|
||||||
<PackageReference Include="JetBrains.Annotations" Version="2020.1.0" PrivateAssets="All" />
|
<PackageId>WireMock.Net.Abstractions</PackageId>
|
||||||
<PackageReference Include="Microsoft.SourceLink.GitHub" Version="1.0.0" PrivateAssets="All" />
|
<PackageTags>wiremock;wiremock.org;interfaces;models;classes;enumerations;types</PackageTags>
|
||||||
</ItemGroup>
|
<RootNamespace>WireMock</RootNamespace>
|
||||||
|
<ProjectGuid>{B6269AAC-170A-4346-8B9A-579DED3D9A94}</ProjectGuid>
|
||||||
|
<PublishRepositoryUrl>true</PublishRepositoryUrl>
|
||||||
|
<AllowedOutputExtensionsInPackageBuildOutputFolder>$(AllowedOutputExtensionsInPackageBuildOutputFolder);.pdb</AllowedOutputExtensionsInPackageBuildOutputFolder>
|
||||||
|
<EmbedUntrackedSources>true</EmbedUntrackedSources>
|
||||||
|
<AutoGenerateBindingRedirects>true</AutoGenerateBindingRedirects>
|
||||||
|
<GenerateBindingRedirectsOutputType>true</GenerateBindingRedirectsOutputType>
|
||||||
|
<CodeAnalysisRuleSet>../WireMock.Net/WireMock.Net.ruleset</CodeAnalysisRuleSet>
|
||||||
|
<SignAssembly>true</SignAssembly>
|
||||||
|
<AssemblyOriginatorKeyFile>../WireMock.Net/WireMock.Net.snk</AssemblyOriginatorKeyFile>
|
||||||
|
<!--<DelaySign>true</DelaySign>-->
|
||||||
|
<PublicSign Condition=" '$(OS)' != 'Windows_NT' ">true</PublicSign>
|
||||||
|
<PackageLicenseExpression>MIT</PackageLicenseExpression>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
<PropertyGroup Condition=" '$(Configuration)' == 'Release' ">
|
||||||
|
<!--<PathMap>$(MSBuildProjectDirectory)=/</PathMap>-->
|
||||||
|
<GeneratePackageOnBuild>true</GeneratePackageOnBuild>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<PackageReference Include="JetBrains.Annotations" Version="2021.2.0" PrivateAssets="All" />
|
||||||
|
<PackageReference Include="Microsoft.SourceLink.GitHub" Version="1.0.0" PrivateAssets="All" />
|
||||||
|
|
||||||
|
<!-- See also https://mstack.nl/blog/20210801-source-generators -->
|
||||||
|
<PackageReference Include="FluentBuilder" Version="0.0.11">
|
||||||
|
<PrivateAssets>all</PrivateAssets>
|
||||||
|
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
|
||||||
|
</PackageReference>
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
</Project>
|
</Project>
|
||||||
@@ -1,12 +1,19 @@
|
|||||||
using System;
|
using System.IO;
|
||||||
using System.IO;
|
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
using System.Runtime.InteropServices.ComTypes;
|
||||||
|
using JetBrains.Annotations;
|
||||||
using Microsoft.OpenApi.Models;
|
using Microsoft.OpenApi.Models;
|
||||||
using Microsoft.OpenApi.Readers;
|
using Microsoft.OpenApi.Readers;
|
||||||
|
using SharpYaml.Model;
|
||||||
|
using Stef.Validation;
|
||||||
|
using WireMock.Net.OpenApiParser.Settings;
|
||||||
using WireMock.Server;
|
using WireMock.Server;
|
||||||
|
|
||||||
namespace WireMock.Net.OpenApiParser.Extensions
|
namespace WireMock.Net.OpenApiParser.Extensions
|
||||||
{
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Some extension methods for <see cref="IWireMockServer"/>.
|
||||||
|
/// </summary>
|
||||||
public static class WireMockServerExtensions
|
public static class WireMockServerExtensions
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@@ -15,18 +22,26 @@ namespace WireMock.Net.OpenApiParser.Extensions
|
|||||||
/// <param name="server">The WireMockServer instance</param>
|
/// <param name="server">The WireMockServer instance</param>
|
||||||
/// <param name="path">Path containing OpenAPI file to parse and use the mappings.</param>
|
/// <param name="path">Path containing OpenAPI file to parse and use the mappings.</param>
|
||||||
/// <param name="diagnostic">Returns diagnostic object containing errors detected during parsing</param>
|
/// <param name="diagnostic">Returns diagnostic object containing errors detected during parsing</param>
|
||||||
|
[PublicAPI]
|
||||||
public static IWireMockServer WithMappingFromOpenApiFile(this IWireMockServer server, string path, out OpenApiDiagnostic diagnostic)
|
public static IWireMockServer WithMappingFromOpenApiFile(this IWireMockServer server, string path, out OpenApiDiagnostic diagnostic)
|
||||||
{
|
{
|
||||||
if (server == null)
|
return WithMappingFromOpenApiFile(server, path, null, out diagnostic);
|
||||||
{
|
}
|
||||||
throw new ArgumentNullException(nameof(server));
|
|
||||||
}
|
|
||||||
if (string.IsNullOrEmpty(path))
|
|
||||||
{
|
|
||||||
throw new ArgumentNullException(nameof(path));
|
|
||||||
}
|
|
||||||
|
|
||||||
var mappings = new WireMockOpenApiParser().FromFile(path, out diagnostic);
|
/// <summary>
|
||||||
|
/// Register the mappings via an OpenAPI (swagger) V2 or V3 file.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="server">The WireMockServer instance</param>
|
||||||
|
/// <param name="path">Path containing OpenAPI file to parse and use the mappings.</param>
|
||||||
|
/// <param name="diagnostic">Returns diagnostic object containing errors detected during parsing</param>
|
||||||
|
/// <param name="settings">Additional settings</param>
|
||||||
|
[PublicAPI]
|
||||||
|
public static IWireMockServer WithMappingFromOpenApiFile(this IWireMockServer server, string path, WireMockOpenApiParserSettings settings, out OpenApiDiagnostic diagnostic)
|
||||||
|
{
|
||||||
|
Guard.NotNull(server, nameof(server));
|
||||||
|
Guard.NotNullOrEmpty(path, nameof(path));
|
||||||
|
|
||||||
|
var mappings = new WireMockOpenApiParser().FromFile(path, settings, out diagnostic);
|
||||||
|
|
||||||
return server.WithMapping(mappings.ToArray());
|
return server.WithMapping(mappings.ToArray());
|
||||||
}
|
}
|
||||||
@@ -37,9 +52,27 @@ namespace WireMock.Net.OpenApiParser.Extensions
|
|||||||
/// <param name="server">The WireMockServer instance</param>
|
/// <param name="server">The WireMockServer instance</param>
|
||||||
/// <param name="stream">Stream containing OpenAPI description to parse and use the mappings.</param>
|
/// <param name="stream">Stream containing OpenAPI description to parse and use the mappings.</param>
|
||||||
/// <param name="diagnostic">Returns diagnostic object containing errors detected during parsing</param>
|
/// <param name="diagnostic">Returns diagnostic object containing errors detected during parsing</param>
|
||||||
|
[PublicAPI]
|
||||||
public static IWireMockServer WithMappingFromOpenApiStream(this IWireMockServer server, Stream stream, out OpenApiDiagnostic diagnostic)
|
public static IWireMockServer WithMappingFromOpenApiStream(this IWireMockServer server, Stream stream, out OpenApiDiagnostic diagnostic)
|
||||||
{
|
{
|
||||||
var mappings = new WireMockOpenApiParser().FromStream(stream, out diagnostic);
|
return WithMappingFromOpenApiStream(server, stream, null, out diagnostic);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Register the mappings via an OpenAPI (swagger) V2 or V3 stream.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="server">The WireMockServer instance</param>
|
||||||
|
/// <param name="stream">Stream containing OpenAPI description to parse and use the mappings.</param>
|
||||||
|
/// <param name="settings">Additional settings</param>
|
||||||
|
/// <param name="diagnostic">Returns diagnostic object containing errors detected during parsing</param>
|
||||||
|
[PublicAPI]
|
||||||
|
public static IWireMockServer WithMappingFromOpenApiStream(this IWireMockServer server, Stream stream, WireMockOpenApiParserSettings settings, out OpenApiDiagnostic diagnostic)
|
||||||
|
{
|
||||||
|
Guard.NotNull(server, nameof(server));
|
||||||
|
Guard.NotNull(stream, nameof(stream));
|
||||||
|
Guard.NotNull(settings, nameof(settings));
|
||||||
|
|
||||||
|
var mappings = new WireMockOpenApiParser().FromStream(stream, settings, out diagnostic);
|
||||||
|
|
||||||
return server.WithMapping(mappings.ToArray());
|
return server.WithMapping(mappings.ToArray());
|
||||||
}
|
}
|
||||||
@@ -49,9 +82,14 @@ namespace WireMock.Net.OpenApiParser.Extensions
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="server">The WireMockServer instance</param>
|
/// <param name="server">The WireMockServer instance</param>
|
||||||
/// <param name="document">The OpenAPI document to use as mappings.</param>
|
/// <param name="document">The OpenAPI document to use as mappings.</param>
|
||||||
public static IWireMockServer WithMappingFromOpenApiDocument(this IWireMockServer server, OpenApiDocument document)
|
/// <param name="settings">Additional settings [optional]</param>
|
||||||
|
[PublicAPI]
|
||||||
|
public static IWireMockServer WithMappingFromOpenApiDocument(this IWireMockServer server, OpenApiDocument document, WireMockOpenApiParserSettings settings = null)
|
||||||
{
|
{
|
||||||
var mappings = new WireMockOpenApiParser().FromDocument(document);
|
Guard.NotNull(server, nameof(server));
|
||||||
|
Guard.NotNull(document, nameof(document));
|
||||||
|
|
||||||
|
var mappings = new WireMockOpenApiParser().FromDocument(document, settings);
|
||||||
|
|
||||||
return server.WithMapping(mappings.ToArray());
|
return server.WithMapping(mappings.ToArray());
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -3,6 +3,7 @@ using System.IO;
|
|||||||
using Microsoft.OpenApi.Models;
|
using Microsoft.OpenApi.Models;
|
||||||
using Microsoft.OpenApi.Readers;
|
using Microsoft.OpenApi.Readers;
|
||||||
using WireMock.Admin.Mappings;
|
using WireMock.Admin.Mappings;
|
||||||
|
using WireMock.Net.OpenApiParser.Settings;
|
||||||
|
|
||||||
namespace WireMock.Net.OpenApiParser
|
namespace WireMock.Net.OpenApiParser
|
||||||
{
|
{
|
||||||
@@ -11,12 +12,30 @@ namespace WireMock.Net.OpenApiParser
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
public interface IWireMockOpenApiParser
|
public interface IWireMockOpenApiParser
|
||||||
{
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Generate <see cref="IEnumerable{MappingModel}"/> from a file-path.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="path">The path to read the OpenApi/Swagger/V2/V3 or Raml file.</param>
|
||||||
|
/// <param name="diagnostic">OpenApiDiagnostic output</param>
|
||||||
|
/// <returns>MappingModel</returns>
|
||||||
|
IEnumerable<MappingModel> FromFile(string path, out OpenApiDiagnostic diagnostic);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Generate <see cref="IEnumerable{MappingModel}"/> from a file-path.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="path">The path to read the OpenApi/Swagger/V2/V3 or Raml file.</param>
|
||||||
|
/// <param name="settings">Additional settings</param>
|
||||||
|
/// <param name="diagnostic">OpenApiDiagnostic output</param>
|
||||||
|
/// <returns>MappingModel</returns>
|
||||||
|
IEnumerable<MappingModel> FromFile(string path, WireMockOpenApiParserSettings settings, out OpenApiDiagnostic diagnostic);
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Generate <see cref="IEnumerable{MappingModel}"/> from an <seealso cref="OpenApiDocument"/>.
|
/// Generate <see cref="IEnumerable{MappingModel}"/> from an <seealso cref="OpenApiDocument"/>.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="document">The source OpenApiDocument</param>
|
/// <param name="document">The source OpenApiDocument</param>
|
||||||
|
/// <param name="settings">Additional settings [optional]</param>
|
||||||
/// <returns>MappingModel</returns>
|
/// <returns>MappingModel</returns>
|
||||||
IEnumerable<MappingModel> FromDocument(OpenApiDocument document);
|
IEnumerable<MappingModel> FromDocument(OpenApiDocument document, WireMockOpenApiParserSettings settings = null);
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Generate <see cref="IEnumerable{MappingModel}"/> from a <seealso cref="Stream"/>.
|
/// Generate <see cref="IEnumerable{MappingModel}"/> from a <seealso cref="Stream"/>.
|
||||||
@@ -27,11 +46,12 @@ namespace WireMock.Net.OpenApiParser
|
|||||||
IEnumerable<MappingModel> FromStream(Stream stream, out OpenApiDiagnostic diagnostic);
|
IEnumerable<MappingModel> FromStream(Stream stream, out OpenApiDiagnostic diagnostic);
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Generate <see cref="IEnumerable{MappingModel}"/> from a file-path.
|
/// Generate <see cref="IEnumerable{MappingModel}"/> from a <seealso cref="Stream"/>.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="path">The path to read the OpenApi/Swagger/V2/V3 or Raml file.</param>
|
/// <param name="stream">The source stream</param>
|
||||||
|
/// <param name="settings">Additional settings</param>
|
||||||
/// <param name="diagnostic">OpenApiDiagnostic output</param>
|
/// <param name="diagnostic">OpenApiDiagnostic output</param>
|
||||||
/// <returns>MappingModel</returns>
|
/// <returns>MappingModel</returns>
|
||||||
IEnumerable<MappingModel> FromFile(string path, out OpenApiDiagnostic diagnostic);
|
IEnumerable<MappingModel> FromStream(Stream stream, WireMockOpenApiParserSettings settings, out OpenApiDiagnostic diagnostic);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
276
src/WireMock.Net.OpenApiParser/Mappers/OpenApiPathsMapper.cs
Normal file
276
src/WireMock.Net.OpenApiParser/Mappers/OpenApiPathsMapper.cs
Normal file
@@ -0,0 +1,276 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.IO;
|
||||||
|
using System.Linq;
|
||||||
|
using Microsoft.OpenApi;
|
||||||
|
using Microsoft.OpenApi.Any;
|
||||||
|
using Microsoft.OpenApi.Models;
|
||||||
|
using Microsoft.OpenApi.Writers;
|
||||||
|
using Newtonsoft.Json.Linq;
|
||||||
|
using WireMock.Admin.Mappings;
|
||||||
|
using WireMock.Net.OpenApiParser.Extensions;
|
||||||
|
using WireMock.Net.OpenApiParser.Settings;
|
||||||
|
using WireMock.Net.OpenApiParser.Types;
|
||||||
|
using WireMock.Net.OpenApiParser.Utils;
|
||||||
|
|
||||||
|
namespace WireMock.Net.OpenApiParser.Mappers
|
||||||
|
{
|
||||||
|
internal class OpenApiPathsMapper
|
||||||
|
{
|
||||||
|
private readonly WireMockOpenApiParserSettings _settings;
|
||||||
|
private readonly ExampleValueGenerator _exampleValueGenerator;
|
||||||
|
|
||||||
|
public OpenApiPathsMapper(WireMockOpenApiParserSettings settings)
|
||||||
|
{
|
||||||
|
_settings = settings ?? throw new ArgumentNullException(nameof(settings));
|
||||||
|
_exampleValueGenerator = new ExampleValueGenerator(settings);
|
||||||
|
}
|
||||||
|
|
||||||
|
public IEnumerable<MappingModel> ToMappingModels(OpenApiPaths paths)
|
||||||
|
{
|
||||||
|
return paths.Select(p => MapPath(p.Key, p.Value)).SelectMany(x => x);
|
||||||
|
}
|
||||||
|
|
||||||
|
private IEnumerable<MappingModel> MapPaths(OpenApiPaths paths)
|
||||||
|
{
|
||||||
|
return paths.Select(p => MapPath(p.Key, p.Value)).SelectMany(x => x);
|
||||||
|
}
|
||||||
|
|
||||||
|
private IEnumerable<MappingModel> MapPath(string path, OpenApiPathItem pathItem)
|
||||||
|
{
|
||||||
|
return pathItem.Operations.Select(o => MapOperationToMappingModel(path, o.Key.ToString().ToUpperInvariant(), o.Value));
|
||||||
|
}
|
||||||
|
|
||||||
|
private MappingModel MapOperationToMappingModel(string path, string httpMethod, OpenApiOperation operation)
|
||||||
|
{
|
||||||
|
var queryParameters = operation.Parameters.Where(p => p.In == ParameterLocation.Query);
|
||||||
|
var pathParameters = operation.Parameters.Where(p => p.In == ParameterLocation.Path);
|
||||||
|
var response = operation.Responses.FirstOrDefault();
|
||||||
|
|
||||||
|
TryGetContent(response.Value?.Content, out OpenApiMediaType responseContent, out string responseContentType);
|
||||||
|
var responseSchema = response.Value?.Content?.FirstOrDefault().Value?.Schema;
|
||||||
|
var responseExample = responseContent?.Example;
|
||||||
|
|
||||||
|
var body = responseExample != null ? MapOpenApiAnyToJToken(responseExample) : MapSchemaToObject(responseSchema);
|
||||||
|
|
||||||
|
if (int.TryParse(response.Key, out var httpStatusCode))
|
||||||
|
{
|
||||||
|
httpStatusCode = 200;
|
||||||
|
}
|
||||||
|
|
||||||
|
return new MappingModel
|
||||||
|
{
|
||||||
|
Guid = Guid.NewGuid(),
|
||||||
|
Request = new RequestModel
|
||||||
|
{
|
||||||
|
Methods = new[] { httpMethod },
|
||||||
|
Path = MapPathWithParameters(path, pathParameters),
|
||||||
|
Params = MapQueryParameters(queryParameters)
|
||||||
|
},
|
||||||
|
Response = new ResponseModel
|
||||||
|
{
|
||||||
|
StatusCode = httpStatusCode,
|
||||||
|
Headers = MapHeaders(responseContentType, response.Value?.Headers),
|
||||||
|
BodyAsJson = body
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
private bool TryGetContent(IDictionary<string, OpenApiMediaType> contents, out OpenApiMediaType openApiMediaType, out string contentType)
|
||||||
|
{
|
||||||
|
openApiMediaType = null;
|
||||||
|
contentType = null;
|
||||||
|
|
||||||
|
if (contents == null || contents.Values.Count == 0)
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (contents.TryGetValue("application/json", out var content))
|
||||||
|
{
|
||||||
|
openApiMediaType = content;
|
||||||
|
contentType = "application/json";
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
var first = contents.FirstOrDefault();
|
||||||
|
openApiMediaType = first.Value;
|
||||||
|
contentType = first.Key;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
private object MapSchemaToObject(OpenApiSchema schema, string name = null)
|
||||||
|
{
|
||||||
|
if (schema == null)
|
||||||
|
{
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
switch (schema.GetSchemaType())
|
||||||
|
{
|
||||||
|
case SchemaType.Array:
|
||||||
|
var jArray = new JArray();
|
||||||
|
for (int i = 0; i < _settings.NumberOfArrayItems; i++)
|
||||||
|
{
|
||||||
|
if (schema.Items.Properties.Count > 0)
|
||||||
|
{
|
||||||
|
var arrayItem = new JObject();
|
||||||
|
foreach (var property in schema.Items.Properties)
|
||||||
|
{
|
||||||
|
var objectValue = MapSchemaToObject(property.Value, property.Key);
|
||||||
|
if (objectValue is JProperty jp)
|
||||||
|
{
|
||||||
|
arrayItem.Add(jp);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
arrayItem.Add(new JProperty(property.Key, objectValue));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
jArray.Add(arrayItem);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
jArray.Add(MapSchemaToObject(schema.Items, name));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return jArray;
|
||||||
|
|
||||||
|
case SchemaType.Boolean:
|
||||||
|
case SchemaType.Integer:
|
||||||
|
case SchemaType.Number:
|
||||||
|
case SchemaType.String:
|
||||||
|
return _exampleValueGenerator.GetExampleValue(schema);
|
||||||
|
|
||||||
|
case SchemaType.Object:
|
||||||
|
var propertyAsJObject = new JObject();
|
||||||
|
foreach (var schemaProperty in schema.Properties)
|
||||||
|
{
|
||||||
|
string propertyName = schemaProperty.Key;
|
||||||
|
var openApiSchema = schemaProperty.Value;
|
||||||
|
if (openApiSchema.GetSchemaType() == SchemaType.Object)
|
||||||
|
{
|
||||||
|
var mapped = MapSchemaToObject(schemaProperty.Value, schemaProperty.Key);
|
||||||
|
if (mapped is JProperty jp)
|
||||||
|
{
|
||||||
|
propertyAsJObject.Add(jp);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
bool propertyIsNullable = openApiSchema.Nullable || (openApiSchema.TryGetXNullable(out bool x) && x);
|
||||||
|
|
||||||
|
propertyAsJObject.Add(new JProperty(propertyName, _exampleValueGenerator.GetExampleValue(openApiSchema)));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return name != null ? new JProperty(name, propertyAsJObject) : (JToken)propertyAsJObject;
|
||||||
|
|
||||||
|
default:
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private string MapPathWithParameters(string path, IEnumerable<OpenApiParameter> parameters)
|
||||||
|
{
|
||||||
|
if (parameters == null)
|
||||||
|
{
|
||||||
|
return path;
|
||||||
|
}
|
||||||
|
|
||||||
|
string newPath = path;
|
||||||
|
foreach (var parameter in parameters)
|
||||||
|
{
|
||||||
|
newPath = newPath.Replace($"{{{parameter.Name}}}", GetExampleValue(parameter.Schema, _settings.PathPatternToUse));
|
||||||
|
}
|
||||||
|
|
||||||
|
return newPath;
|
||||||
|
}
|
||||||
|
|
||||||
|
private JToken MapOpenApiAnyToJToken(IOpenApiAny any)
|
||||||
|
{
|
||||||
|
if (any == null)
|
||||||
|
{
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
using var outputString = new StringWriter();
|
||||||
|
var writer = new OpenApiJsonWriter(outputString);
|
||||||
|
any.Write(writer, OpenApiSpecVersion.OpenApi3_0);
|
||||||
|
|
||||||
|
return JObject.Parse(outputString.ToString());
|
||||||
|
}
|
||||||
|
|
||||||
|
private IDictionary<string, object> MapHeaders(string responseContentType, IDictionary<string, OpenApiHeader> headers)
|
||||||
|
{
|
||||||
|
var mappedHeaders = headers.ToDictionary(
|
||||||
|
item => item.Key,
|
||||||
|
item => GetExampleValue(null, _settings.HeaderPatternToUse) as object
|
||||||
|
);
|
||||||
|
|
||||||
|
if (!string.IsNullOrEmpty(responseContentType))
|
||||||
|
{
|
||||||
|
if (!mappedHeaders.ContainsKey("Content-Type"))
|
||||||
|
{
|
||||||
|
mappedHeaders.Add("Content-Type", responseContentType);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mappedHeaders["Content-Type"] = responseContentType;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return mappedHeaders.Keys.Any() ? mappedHeaders : null;
|
||||||
|
}
|
||||||
|
|
||||||
|
private IList<ParamModel> MapQueryParameters(IEnumerable<OpenApiParameter> queryParameters)
|
||||||
|
{
|
||||||
|
var list = queryParameters
|
||||||
|
.Select(qp => new ParamModel
|
||||||
|
{
|
||||||
|
Name = qp.Name,
|
||||||
|
Matchers = new[]
|
||||||
|
{
|
||||||
|
new MatcherModel
|
||||||
|
{
|
||||||
|
Name = "ExactMatcher",
|
||||||
|
Pattern = GetDefaultValueAsStringForSchemaType(qp.Schema)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.ToList();
|
||||||
|
|
||||||
|
return list.Any() ? list : null;
|
||||||
|
}
|
||||||
|
|
||||||
|
private string GetDefaultValueAsStringForSchemaType(OpenApiSchema schema)
|
||||||
|
{
|
||||||
|
var value = _exampleValueGenerator.GetExampleValue(schema);
|
||||||
|
|
||||||
|
switch (value)
|
||||||
|
{
|
||||||
|
case string valueAsString:
|
||||||
|
return valueAsString;
|
||||||
|
|
||||||
|
default:
|
||||||
|
return value.ToString();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private string GetExampleValue(OpenApiSchema schema, ExampleValueType type)
|
||||||
|
{
|
||||||
|
switch (type)
|
||||||
|
{
|
||||||
|
case ExampleValueType.Value:
|
||||||
|
return GetDefaultValueAsStringForSchemaType(schema);
|
||||||
|
|
||||||
|
default:
|
||||||
|
return "*";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,30 @@
|
|||||||
|
using System;
|
||||||
|
|
||||||
|
namespace WireMock.Net.OpenApiParser.Settings
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// A class defining the example values to use for the different types.
|
||||||
|
/// </summary>
|
||||||
|
public class WireMockOpenApiParserExampleValues
|
||||||
|
{
|
||||||
|
#pragma warning disable 1591
|
||||||
|
public bool Boolean { get; set; } = true;
|
||||||
|
|
||||||
|
public int Integer { get; set; } = 42;
|
||||||
|
|
||||||
|
public float Float { get; set; } = 4.2f;
|
||||||
|
|
||||||
|
public double Double { get; set; } = 4.2d;
|
||||||
|
|
||||||
|
public Func<DateTime> Date { get; set; } = () => System.DateTime.UtcNow.Date;
|
||||||
|
|
||||||
|
public Func<DateTime> DateTime { get; set; } = () => System.DateTime.UtcNow;
|
||||||
|
|
||||||
|
public byte[] Bytes { get; set; } = { 48, 49, 50 };
|
||||||
|
|
||||||
|
public object Object { get; set; } = "example-object";
|
||||||
|
|
||||||
|
public string String { get; set; } = "example-string";
|
||||||
|
#pragma warning restore 1591
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,30 @@
|
|||||||
|
using WireMock.Net.OpenApiParser.Types;
|
||||||
|
|
||||||
|
namespace WireMock.Net.OpenApiParser.Settings
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// The WireMockOpenApiParser Settings
|
||||||
|
/// </summary>
|
||||||
|
public class WireMockOpenApiParserSettings
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// The number of array items to generate (default is 3).
|
||||||
|
/// </summary>
|
||||||
|
public int NumberOfArrayItems { get; set; } = 3;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The example value type to use when generating a Path
|
||||||
|
/// </summary>
|
||||||
|
public ExampleValueType PathPatternToUse { get; set; } = ExampleValueType.Value;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The example value type to use when generating a Header
|
||||||
|
/// </summary>
|
||||||
|
public ExampleValueType HeaderPatternToUse { get; set; } = ExampleValueType.Value;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The example values to use
|
||||||
|
/// </summary>
|
||||||
|
public WireMockOpenApiParserExampleValues ExampleValues { get; } = new WireMockOpenApiParserExampleValues();
|
||||||
|
}
|
||||||
|
}
|
||||||
18
src/WireMock.Net.OpenApiParser/Types/ExampleValueType.cs
Normal file
18
src/WireMock.Net.OpenApiParser/Types/ExampleValueType.cs
Normal file
@@ -0,0 +1,18 @@
|
|||||||
|
namespace WireMock.Net.OpenApiParser.Types
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// The example value to use
|
||||||
|
/// </summary>
|
||||||
|
public enum ExampleValueType
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Use a generated example value based on the SchemaType (default).
|
||||||
|
/// </summary>
|
||||||
|
Value,
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Just use a Wildcard (*) character.
|
||||||
|
/// </summary>
|
||||||
|
Wildcard
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,49 +1,57 @@
|
|||||||
using System;
|
using System;
|
||||||
using Microsoft.OpenApi.Models;
|
using Microsoft.OpenApi.Models;
|
||||||
using WireMock.Net.OpenApiParser.Extensions;
|
using WireMock.Net.OpenApiParser.Extensions;
|
||||||
|
using WireMock.Net.OpenApiParser.Settings;
|
||||||
using WireMock.Net.OpenApiParser.Types;
|
using WireMock.Net.OpenApiParser.Types;
|
||||||
|
|
||||||
namespace WireMock.Net.OpenApiParser.Utils
|
namespace WireMock.Net.OpenApiParser.Utils
|
||||||
{
|
{
|
||||||
internal static class ExampleValueGenerator
|
internal class ExampleValueGenerator
|
||||||
{
|
{
|
||||||
public static object GetExampleValue(OpenApiSchema schema)
|
private readonly WireMockOpenApiParserSettings _settings;
|
||||||
|
|
||||||
|
public ExampleValueGenerator(WireMockOpenApiParserSettings settings)
|
||||||
|
{
|
||||||
|
_settings = settings ?? throw new ArgumentNullException(nameof(settings));
|
||||||
|
}
|
||||||
|
|
||||||
|
public object GetExampleValue(OpenApiSchema schema)
|
||||||
{
|
{
|
||||||
switch (schema?.GetSchemaType())
|
switch (schema?.GetSchemaType())
|
||||||
{
|
{
|
||||||
case SchemaType.Boolean:
|
case SchemaType.Boolean:
|
||||||
return true;
|
return _settings.ExampleValues.Boolean;
|
||||||
|
|
||||||
case SchemaType.Integer:
|
case SchemaType.Integer:
|
||||||
return 42;
|
return _settings.ExampleValues.Integer;
|
||||||
|
|
||||||
case SchemaType.Number:
|
case SchemaType.Number:
|
||||||
switch (schema?.GetSchemaFormat())
|
switch (schema?.GetSchemaFormat())
|
||||||
{
|
{
|
||||||
case SchemaFormat.Float:
|
case SchemaFormat.Float:
|
||||||
return 4.2f;
|
return _settings.ExampleValues.Float;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
return 4.2d;
|
return _settings.ExampleValues.Double;
|
||||||
}
|
}
|
||||||
|
|
||||||
default:
|
default:
|
||||||
switch (schema?.GetSchemaFormat())
|
switch (schema?.GetSchemaFormat())
|
||||||
{
|
{
|
||||||
case SchemaFormat.Date:
|
case SchemaFormat.Date:
|
||||||
return DateTimeUtils.ToRfc3339Date(DateTime.UtcNow);
|
return DateTimeUtils.ToRfc3339Date(_settings.ExampleValues.Date());
|
||||||
|
|
||||||
case SchemaFormat.DateTime:
|
case SchemaFormat.DateTime:
|
||||||
return DateTimeUtils.ToRfc3339DateTime(DateTime.UtcNow);
|
return DateTimeUtils.ToRfc3339DateTime(_settings.ExampleValues.DateTime());
|
||||||
|
|
||||||
case SchemaFormat.Byte:
|
case SchemaFormat.Byte:
|
||||||
return new byte[] { 48, 49, 50 };
|
return _settings.ExampleValues.Bytes;
|
||||||
|
|
||||||
case SchemaFormat.Binary:
|
case SchemaFormat.Binary:
|
||||||
return "example-object";
|
return _settings.ExampleValues.Object;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
return "example-string";
|
return _settings.ExampleValues.String;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -12,6 +12,7 @@
|
|||||||
<AssemblyOriginatorKeyFile>../WireMock.Net/WireMock.Net.snk</AssemblyOriginatorKeyFile>
|
<AssemblyOriginatorKeyFile>../WireMock.Net/WireMock.Net.snk</AssemblyOriginatorKeyFile>
|
||||||
<PublicSign Condition=" '$(OS)' != 'Windows_NT' ">true</PublicSign>
|
<PublicSign Condition=" '$(OS)' != 'Windows_NT' ">true</PublicSign>
|
||||||
<PackageLicenseExpression>MIT</PackageLicenseExpression>
|
<PackageLicenseExpression>MIT</PackageLicenseExpression>
|
||||||
|
<LangVersion>8.0</LangVersion>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<PropertyGroup Condition="'$(Configuration)' == 'Release'">
|
<PropertyGroup Condition="'$(Configuration)' == 'Release'">
|
||||||
@@ -24,14 +25,11 @@
|
|||||||
<PackageReference Include="RamlToOpenApiConverter" Version="0.1.1" />
|
<PackageReference Include="RamlToOpenApiConverter" Version="0.1.1" />
|
||||||
<PackageReference Include="JetBrains.Annotations" Version="2020.1.0" PrivateAssets="All" />
|
<PackageReference Include="JetBrains.Annotations" Version="2020.1.0" PrivateAssets="All" />
|
||||||
<PackageReference Include="Microsoft.SourceLink.GitHub" Version="1.0.0" PrivateAssets="All" />
|
<PackageReference Include="Microsoft.SourceLink.GitHub" Version="1.0.0" PrivateAssets="All" />
|
||||||
|
<PackageReference Include="Stef.Validation" Version="0.0.3" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<ProjectReference Include="..\WireMock.Net.Abstractions\WireMock.Net.Abstractions.csproj" />
|
<ProjectReference Include="..\WireMock.Net.Abstractions\WireMock.Net.Abstractions.csproj" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
|
||||||
<Folder Include="Options\" />
|
|
||||||
</ItemGroup>
|
|
||||||
|
|
||||||
</Project>
|
</Project>
|
||||||
@@ -1,34 +1,33 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.Linq;
|
|
||||||
using JetBrains.Annotations;
|
using JetBrains.Annotations;
|
||||||
using Microsoft.OpenApi;
|
|
||||||
using Microsoft.OpenApi.Any;
|
|
||||||
using Microsoft.OpenApi.Models;
|
using Microsoft.OpenApi.Models;
|
||||||
using Microsoft.OpenApi.Readers;
|
using Microsoft.OpenApi.Readers;
|
||||||
using Microsoft.OpenApi.Writers;
|
|
||||||
using Newtonsoft.Json.Linq;
|
|
||||||
using RamlToOpenApiConverter;
|
using RamlToOpenApiConverter;
|
||||||
using WireMock.Admin.Mappings;
|
using WireMock.Admin.Mappings;
|
||||||
using WireMock.Net.OpenApiParser.Extensions;
|
using WireMock.Net.OpenApiParser.Mappers;
|
||||||
using WireMock.Net.OpenApiParser.Types;
|
using WireMock.Net.OpenApiParser.Settings;
|
||||||
using WireMock.Net.OpenApiParser.Utils;
|
|
||||||
|
|
||||||
namespace WireMock.Net.OpenApiParser
|
namespace WireMock.Net.OpenApiParser
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Parse a OpenApi/Swagger/V2/V3 or Raml to WireMock MappingModels.
|
/// Parse a OpenApi/Swagger/V2/V3 or Raml to WireMock.Net MappingModels.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public class WireMockOpenApiParser : IWireMockOpenApiParser
|
public class WireMockOpenApiParser : IWireMockOpenApiParser
|
||||||
{
|
{
|
||||||
private const int ArrayItems = 3;
|
|
||||||
|
|
||||||
private readonly OpenApiStreamReader _reader = new OpenApiStreamReader();
|
private readonly OpenApiStreamReader _reader = new OpenApiStreamReader();
|
||||||
|
|
||||||
/// <inheritdoc cref="IWireMockOpenApiParser.FromFile" />
|
/// <inheritdoc cref="IWireMockOpenApiParser.FromFile(string, out OpenApiDiagnostic)" />
|
||||||
[PublicAPI]
|
[PublicAPI]
|
||||||
public IEnumerable<MappingModel> FromFile(string path, out OpenApiDiagnostic diagnostic)
|
public IEnumerable<MappingModel> FromFile(string path, out OpenApiDiagnostic diagnostic)
|
||||||
|
{
|
||||||
|
return FromFile(path, new WireMockOpenApiParserSettings(), out diagnostic);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <inheritdoc cref="IWireMockOpenApiParser.FromFile(string, WireMockOpenApiParserSettings, out OpenApiDiagnostic)" />
|
||||||
|
[PublicAPI]
|
||||||
|
public IEnumerable<MappingModel> FromFile(string path, WireMockOpenApiParserSettings settings, out OpenApiDiagnostic diagnostic)
|
||||||
{
|
{
|
||||||
OpenApiDocument document;
|
OpenApiDocument document;
|
||||||
if (Path.GetExtension(path).EndsWith("raml", StringComparison.OrdinalIgnoreCase))
|
if (Path.GetExtension(path).EndsWith("raml", StringComparison.OrdinalIgnoreCase))
|
||||||
@@ -42,248 +41,28 @@ namespace WireMock.Net.OpenApiParser
|
|||||||
document = reader.Read(File.OpenRead(path), out diagnostic);
|
document = reader.Read(File.OpenRead(path), out diagnostic);
|
||||||
}
|
}
|
||||||
|
|
||||||
return FromDocument(document);
|
return FromDocument(document, settings);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc cref="IWireMockOpenApiParser.FromStream" />
|
/// <inheritdoc cref="IWireMockOpenApiParser.FromStream(Stream, out OpenApiDiagnostic)" />
|
||||||
[PublicAPI]
|
[PublicAPI]
|
||||||
public IEnumerable<MappingModel> FromStream(Stream stream, out OpenApiDiagnostic diagnostic)
|
public IEnumerable<MappingModel> FromStream(Stream stream, out OpenApiDiagnostic diagnostic)
|
||||||
{
|
{
|
||||||
return FromDocument(_reader.Read(stream, out diagnostic));
|
return FromDocument(_reader.Read(stream, out diagnostic));
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc cref="IWireMockOpenApiParser.FromDocument" />
|
/// <inheritdoc cref="IWireMockOpenApiParser.FromStream(Stream, WireMockOpenApiParserSettings, out OpenApiDiagnostic)" />
|
||||||
[PublicAPI]
|
[PublicAPI]
|
||||||
public IEnumerable<MappingModel> FromDocument(OpenApiDocument openApiDocument)
|
public IEnumerable<MappingModel> FromStream(Stream stream, WireMockOpenApiParserSettings settings, out OpenApiDiagnostic diagnostic)
|
||||||
{
|
{
|
||||||
return MapPaths(openApiDocument.Paths);
|
return FromDocument(_reader.Read(stream, out diagnostic), settings);
|
||||||
}
|
}
|
||||||
|
|
||||||
private static IEnumerable<MappingModel> MapPaths(OpenApiPaths paths)
|
/// <inheritdoc cref="IWireMockOpenApiParser.FromDocument(OpenApiDocument, WireMockOpenApiParserSettings)" />
|
||||||
|
[PublicAPI]
|
||||||
|
public IEnumerable<MappingModel> FromDocument(OpenApiDocument openApiDocument, WireMockOpenApiParserSettings settings = null)
|
||||||
{
|
{
|
||||||
return paths.Select(p => MapPath(p.Key, p.Value)).SelectMany(x => x);
|
return new OpenApiPathsMapper(settings).ToMappingModels(openApiDocument.Paths);
|
||||||
}
|
|
||||||
|
|
||||||
private static IEnumerable<MappingModel> MapPath(string path, OpenApiPathItem pathItem)
|
|
||||||
{
|
|
||||||
return pathItem.Operations.Select(o => MapOperationToMappingModel(path, o.Key.ToString().ToUpperInvariant(), o.Value));
|
|
||||||
}
|
|
||||||
|
|
||||||
private static MappingModel MapOperationToMappingModel(string path, string httpMethod, OpenApiOperation operation)
|
|
||||||
{
|
|
||||||
var queryParameters = operation.Parameters.Where(p => p.In == ParameterLocation.Query);
|
|
||||||
var pathParameters = operation.Parameters.Where(p => p.In == ParameterLocation.Path);
|
|
||||||
var response = operation.Responses.FirstOrDefault();
|
|
||||||
TryGetContent(response.Value?.Content, out OpenApiMediaType responseContent, out string responseContentType);
|
|
||||||
var responseSchema = response.Value?.Content?.FirstOrDefault().Value?.Schema;
|
|
||||||
var responseExample = responseContent?.Example;
|
|
||||||
|
|
||||||
var body = responseExample != null ? MapOpenApiAnyToJToken(responseExample) : MapSchemaToObject(responseSchema);
|
|
||||||
|
|
||||||
if (int.TryParse(response.Key, out var httpStatusCode))
|
|
||||||
{
|
|
||||||
httpStatusCode = 200;
|
|
||||||
}
|
|
||||||
|
|
||||||
return new MappingModel
|
|
||||||
{
|
|
||||||
Guid = Guid.NewGuid(),
|
|
||||||
Request = new RequestModel
|
|
||||||
{
|
|
||||||
Methods = new[] { httpMethod },
|
|
||||||
Path = MapPathWithParameters(path, pathParameters),
|
|
||||||
Params = MapQueryParameters(queryParameters)
|
|
||||||
},
|
|
||||||
Response = new ResponseModel
|
|
||||||
{
|
|
||||||
StatusCode = httpStatusCode,
|
|
||||||
Headers = MapHeaders(responseContentType, response.Value?.Headers),
|
|
||||||
BodyAsJson = body
|
|
||||||
}
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
private static bool TryGetContent(IDictionary<string, OpenApiMediaType> contents, out OpenApiMediaType openApiMediaType, out string contentType)
|
|
||||||
{
|
|
||||||
openApiMediaType = null;
|
|
||||||
contentType = null;
|
|
||||||
|
|
||||||
if (contents == null || contents.Values.Count == 0)
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (contents.TryGetValue("application/json", out var content))
|
|
||||||
{
|
|
||||||
openApiMediaType = content;
|
|
||||||
contentType = "application/json";
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
var first = contents.FirstOrDefault();
|
|
||||||
openApiMediaType = first.Value;
|
|
||||||
contentType = first.Key;
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
private static object MapSchemaToObject(OpenApiSchema schema, string name = null)
|
|
||||||
{
|
|
||||||
if (schema == null)
|
|
||||||
{
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
switch (schema.GetSchemaType())
|
|
||||||
{
|
|
||||||
case SchemaType.Array:
|
|
||||||
var jArray = new JArray();
|
|
||||||
for (int i = 0; i < ArrayItems; i++)
|
|
||||||
{
|
|
||||||
if (schema.Items.Properties.Count > 0)
|
|
||||||
{
|
|
||||||
var arrayItem = new JObject();
|
|
||||||
foreach (var property in schema.Items.Properties)
|
|
||||||
{
|
|
||||||
var objectValue = MapSchemaToObject(property.Value, property.Key);
|
|
||||||
if (objectValue is JProperty jp)
|
|
||||||
{
|
|
||||||
arrayItem.Add(jp);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
arrayItem.Add(new JProperty(property.Key, objectValue));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
jArray.Add(arrayItem);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
jArray.Add(MapSchemaToObject(schema.Items, name));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return jArray;
|
|
||||||
|
|
||||||
case SchemaType.Boolean:
|
|
||||||
case SchemaType.Integer:
|
|
||||||
case SchemaType.Number:
|
|
||||||
case SchemaType.String:
|
|
||||||
return ExampleValueGenerator.GetExampleValue(schema);
|
|
||||||
|
|
||||||
case SchemaType.Object:
|
|
||||||
var propertyAsJObject = new JObject();
|
|
||||||
foreach (var schemaProperty in schema.Properties)
|
|
||||||
{
|
|
||||||
string propertyName = schemaProperty.Key;
|
|
||||||
var openApiSchema = schemaProperty.Value;
|
|
||||||
if (openApiSchema.GetSchemaType() == SchemaType.Object)
|
|
||||||
{
|
|
||||||
var mapped = MapSchemaToObject(schemaProperty.Value, schemaProperty.Key);
|
|
||||||
if (mapped is JProperty jp)
|
|
||||||
{
|
|
||||||
propertyAsJObject.Add(jp);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
bool propertyIsNullable = openApiSchema.Nullable || (openApiSchema.TryGetXNullable(out bool x) && x);
|
|
||||||
|
|
||||||
propertyAsJObject.Add(new JProperty(propertyName, ExampleValueGenerator.GetExampleValue(openApiSchema)));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return name != null ? new JProperty(name, propertyAsJObject) : (JToken)propertyAsJObject;
|
|
||||||
|
|
||||||
default:
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private static string MapPathWithParameters(string path, IEnumerable<OpenApiParameter> parameters)
|
|
||||||
{
|
|
||||||
if (parameters == null)
|
|
||||||
{
|
|
||||||
return path;
|
|
||||||
}
|
|
||||||
|
|
||||||
string newPath = path;
|
|
||||||
foreach (var parameter in parameters)
|
|
||||||
{
|
|
||||||
newPath = newPath.Replace($"{{{parameter.Name}}}", ExampleValueGenerator.GetExampleValue(parameter.Schema).ToString());
|
|
||||||
}
|
|
||||||
|
|
||||||
return newPath;
|
|
||||||
}
|
|
||||||
|
|
||||||
private static JToken MapOpenApiAnyToJToken(IOpenApiAny any)
|
|
||||||
{
|
|
||||||
if (any == null)
|
|
||||||
{
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
using (var outputString = new StringWriter())
|
|
||||||
{
|
|
||||||
var writer = new OpenApiJsonWriter(outputString);
|
|
||||||
any.Write(writer, OpenApiSpecVersion.OpenApi3_0);
|
|
||||||
|
|
||||||
return JObject.Parse(outputString.ToString());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private static IDictionary<string, object> MapHeaders(string responseContentType, IDictionary<string, OpenApiHeader> headers)
|
|
||||||
{
|
|
||||||
var mappedHeaders = headers.ToDictionary(item => item.Key, item => ExampleValueGenerator.GetExampleValue(null));
|
|
||||||
if (!string.IsNullOrEmpty(responseContentType))
|
|
||||||
{
|
|
||||||
if (!mappedHeaders.ContainsKey("Content-Type"))
|
|
||||||
{
|
|
||||||
mappedHeaders.Add("Content-Type", responseContentType);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
mappedHeaders["Content-Type"] = responseContentType;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return mappedHeaders.Keys.Any() ? mappedHeaders : null;
|
|
||||||
}
|
|
||||||
|
|
||||||
private static IList<ParamModel> MapQueryParameters(IEnumerable<OpenApiParameter> queryParameters)
|
|
||||||
{
|
|
||||||
var list = queryParameters
|
|
||||||
.Select(qp => new ParamModel
|
|
||||||
{
|
|
||||||
Name = qp.Name,
|
|
||||||
Matchers = new[]
|
|
||||||
{
|
|
||||||
new MatcherModel
|
|
||||||
{
|
|
||||||
Name = "ExactMatcher",
|
|
||||||
Pattern = GetDefaultValueAsStringForSchemaType(qp.Schema)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
.ToList();
|
|
||||||
|
|
||||||
return list.Any() ? list : null;
|
|
||||||
}
|
|
||||||
|
|
||||||
private static string GetDefaultValueAsStringForSchemaType(OpenApiSchema schema)
|
|
||||||
{
|
|
||||||
var value = ExampleValueGenerator.GetExampleValue(schema);
|
|
||||||
|
|
||||||
switch (value)
|
|
||||||
{
|
|
||||||
case string valueAsString:
|
|
||||||
return valueAsString;
|
|
||||||
|
|
||||||
default:
|
|
||||||
return value.ToString();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk">
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<Description>A RestClient using RestEase to access the admin interface.</Description>
|
<Description>A RestClient using RestEase to access the admin interface.</Description>
|
||||||
@@ -31,7 +31,7 @@
|
|||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<PackageReference Include="Microsoft.SourceLink.GitHub" Version="1.0.0" PrivateAssets="All" />
|
<PackageReference Include="Microsoft.SourceLink.GitHub" Version="1.0.0" PrivateAssets="All" />
|
||||||
<PackageReference Include="RestEase" Version="1.4.10" />
|
<PackageReference Include="RestEase" Version="1.5.5" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
|||||||
@@ -7,7 +7,7 @@ namespace WireMock.Http
|
|||||||
{
|
{
|
||||||
internal static class HttpClientBuilder
|
internal static class HttpClientBuilder
|
||||||
{
|
{
|
||||||
public static HttpClient Build(IProxyAndRecordSettings settings)
|
public static HttpClient Build(IHttpClientSettings settings)
|
||||||
{
|
{
|
||||||
#if NETSTANDARD || NETCOREAPP3_1 || NET5_0
|
#if NETSTANDARD || NETCOREAPP3_1 || NET5_0
|
||||||
var handler = new HttpClientHandler
|
var handler = new HttpClientHandler
|
||||||
|
|||||||
85
src/WireMock.Net/Http/WebhookSender.cs
Normal file
85
src/WireMock.Net/Http/WebhookSender.cs
Normal file
@@ -0,0 +1,85 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Net.Http;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using JetBrains.Annotations;
|
||||||
|
using WireMock.Models;
|
||||||
|
using WireMock.Settings;
|
||||||
|
using WireMock.Transformers;
|
||||||
|
using WireMock.Transformers.Handlebars;
|
||||||
|
using WireMock.Transformers.Scriban;
|
||||||
|
using WireMock.Types;
|
||||||
|
using WireMock.Util;
|
||||||
|
using WireMock.Validation;
|
||||||
|
|
||||||
|
namespace WireMock.Http
|
||||||
|
{
|
||||||
|
internal class WebhookSender
|
||||||
|
{
|
||||||
|
private const string ClientIp = "::1";
|
||||||
|
|
||||||
|
private readonly IWireMockServerSettings _settings;
|
||||||
|
|
||||||
|
public WebhookSender(IWireMockServerSettings settings)
|
||||||
|
{
|
||||||
|
_settings = settings ?? throw new ArgumentNullException(nameof(settings));
|
||||||
|
}
|
||||||
|
|
||||||
|
public Task<HttpResponseMessage> SendAsync([NotNull] HttpClient client, [NotNull] IWebhookRequest request, [NotNull] RequestMessage originalRequestMessage, [NotNull] ResponseMessage originalResponseMessage)
|
||||||
|
{
|
||||||
|
Check.NotNull(client, nameof(client));
|
||||||
|
Check.NotNull(request, nameof(request));
|
||||||
|
Check.NotNull(originalRequestMessage, nameof(originalRequestMessage));
|
||||||
|
Check.NotNull(originalResponseMessage, nameof(originalResponseMessage));
|
||||||
|
|
||||||
|
IBodyData bodyData;
|
||||||
|
IDictionary<string, WireMockList<string>> headers;
|
||||||
|
if (request.UseTransformer == true)
|
||||||
|
{
|
||||||
|
ITransformer responseMessageTransformer;
|
||||||
|
switch (request.TransformerType)
|
||||||
|
{
|
||||||
|
case TransformerType.Handlebars:
|
||||||
|
var factoryHandlebars = new HandlebarsContextFactory(_settings.FileSystemHandler, _settings.HandlebarsRegistrationCallback);
|
||||||
|
responseMessageTransformer = new Transformer(factoryHandlebars);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case TransformerType.Scriban:
|
||||||
|
case TransformerType.ScribanDotLiquid:
|
||||||
|
var factoryDotLiquid = new ScribanContextFactory(_settings.FileSystemHandler, request.TransformerType);
|
||||||
|
responseMessageTransformer = new Transformer(factoryDotLiquid);
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
throw new NotImplementedException($"TransformerType '{request.TransformerType}' is not supported.");
|
||||||
|
}
|
||||||
|
|
||||||
|
(bodyData, headers) = responseMessageTransformer.Transform(originalRequestMessage, originalResponseMessage, request.BodyData, request.Headers);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
bodyData = request.BodyData;
|
||||||
|
headers = request.Headers;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Create RequestMessage
|
||||||
|
var requestMessage = new RequestMessage(
|
||||||
|
new UrlDetails(request.Url),
|
||||||
|
request.Method,
|
||||||
|
ClientIp,
|
||||||
|
bodyData,
|
||||||
|
headers?.ToDictionary(x => x.Key, x => x.Value.ToArray())
|
||||||
|
)
|
||||||
|
{
|
||||||
|
DateTime = DateTime.UtcNow
|
||||||
|
};
|
||||||
|
|
||||||
|
// Create HttpRequestMessage
|
||||||
|
var httpRequestMessage = HttpRequestMessageHelper.Create(requestMessage, request.Url);
|
||||||
|
|
||||||
|
// Call the URL
|
||||||
|
return client.SendAsync(httpRequestMessage);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -2,6 +2,7 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using WireMock.Matchers.Request;
|
using WireMock.Matchers.Request;
|
||||||
|
using WireMock.Models;
|
||||||
using WireMock.ResponseProviders;
|
using WireMock.ResponseProviders;
|
||||||
using WireMock.Settings;
|
using WireMock.Settings;
|
||||||
|
|
||||||
@@ -93,12 +94,17 @@ namespace WireMock
|
|||||||
/// </value>
|
/// </value>
|
||||||
bool LogMapping { get; }
|
bool LogMapping { get; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The Webhooks.
|
||||||
|
/// </summary>
|
||||||
|
IWebhook[] Webhooks { get; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// ProvideResponseAsync
|
/// ProvideResponseAsync
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="requestMessage">The request message.</param>
|
/// <param name="requestMessage">The request message.</param>
|
||||||
/// <returns>The <see cref="ResponseMessage"/>.</returns>
|
/// <returns>The <see cref="ResponseMessage"/> including a new (optional) <see cref="IMapping"/>.</returns>
|
||||||
Task<ResponseMessage> ProvideResponseAsync(RequestMessage requestMessage);
|
Task<(ResponseMessage Message, IMapping Mapping)> ProvideResponseAsync(RequestMessage requestMessage);
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Gets the RequestMatchResult based on the RequestMessage.
|
/// Gets the RequestMatchResult based on the RequestMessage.
|
||||||
|
|||||||
@@ -2,6 +2,7 @@
|
|||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using JetBrains.Annotations;
|
using JetBrains.Annotations;
|
||||||
using WireMock.Matchers.Request;
|
using WireMock.Matchers.Request;
|
||||||
|
using WireMock.Models;
|
||||||
using WireMock.ResponseProviders;
|
using WireMock.ResponseProviders;
|
||||||
using WireMock.Settings;
|
using WireMock.Settings;
|
||||||
|
|
||||||
@@ -54,6 +55,9 @@ namespace WireMock
|
|||||||
/// <inheritdoc cref="IMapping.LogMapping" />
|
/// <inheritdoc cref="IMapping.LogMapping" />
|
||||||
public bool LogMapping => !(Provider is DynamicResponseProvider || Provider is DynamicAsyncResponseProvider);
|
public bool LogMapping => !(Provider is DynamicResponseProvider || Provider is DynamicAsyncResponseProvider);
|
||||||
|
|
||||||
|
/// <inheritdoc cref="IMapping.Webhooks" />
|
||||||
|
public IWebhook[] Webhooks { get; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Initializes a new instance of the <see cref="Mapping"/> class.
|
/// Initializes a new instance of the <see cref="Mapping"/> class.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@@ -68,6 +72,7 @@ namespace WireMock
|
|||||||
/// <param name="executionConditionState">State in which the current mapping can occur. [Optional]</param>
|
/// <param name="executionConditionState">State in which the current mapping can occur. [Optional]</param>
|
||||||
/// <param name="nextState">The next state which will occur after the current mapping execution. [Optional]</param>
|
/// <param name="nextState">The next state which will occur after the current mapping execution. [Optional]</param>
|
||||||
/// <param name="stateTimes">Only when the current state is executed this number, the next state which will occur. [Optional]</param>
|
/// <param name="stateTimes">Only when the current state is executed this number, the next state which will occur. [Optional]</param>
|
||||||
|
/// <param name="webhooks">The Webhooks. [Optional]</param>
|
||||||
public Mapping(
|
public Mapping(
|
||||||
Guid guid,
|
Guid guid,
|
||||||
[CanBeNull] string title,
|
[CanBeNull] string title,
|
||||||
@@ -79,7 +84,8 @@ namespace WireMock
|
|||||||
[CanBeNull] string scenario,
|
[CanBeNull] string scenario,
|
||||||
[CanBeNull] string executionConditionState,
|
[CanBeNull] string executionConditionState,
|
||||||
[CanBeNull] string nextState,
|
[CanBeNull] string nextState,
|
||||||
[CanBeNull] int? stateTimes)
|
[CanBeNull] int? stateTimes,
|
||||||
|
[CanBeNull] IWebhook[] webhooks)
|
||||||
{
|
{
|
||||||
Guid = guid;
|
Guid = guid;
|
||||||
Title = title;
|
Title = title;
|
||||||
@@ -92,10 +98,11 @@ namespace WireMock
|
|||||||
ExecutionConditionState = executionConditionState;
|
ExecutionConditionState = executionConditionState;
|
||||||
NextState = nextState;
|
NextState = nextState;
|
||||||
StateTimes = stateTimes;
|
StateTimes = stateTimes;
|
||||||
|
Webhooks = webhooks;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc cref="IMapping.ProvideResponseAsync" />
|
/// <inheritdoc cref="IMapping.ProvideResponseAsync" />
|
||||||
public async Task<ResponseMessage> ProvideResponseAsync(RequestMessage requestMessage)
|
public async Task<(ResponseMessage Message, IMapping Mapping)> ProvideResponseAsync(RequestMessage requestMessage)
|
||||||
{
|
{
|
||||||
return await Provider.ProvideResponseAsync(requestMessage, Settings);
|
return await Provider.ProvideResponseAsync(requestMessage, Settings);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,10 +1,10 @@
|
|||||||
namespace WireMock.Matchers
|
namespace WireMock.Matchers
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// IValueMatcher
|
/// IValueMatcher
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <seealso cref="IObjectMatcher" />
|
/// <seealso cref="IObjectMatcher" />
|
||||||
public interface IValueMatcher: IObjectMatcher
|
public interface IValueMatcher : IObjectMatcher
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Gets the value (can be a string or an object).
|
/// Gets the value (can be a string or an object).
|
||||||
|
|||||||
52
src/WireMock.Net/Matchers/NotNullOrEmptyMatcher.cs
Normal file
52
src/WireMock.Net/Matchers/NotNullOrEmptyMatcher.cs
Normal file
@@ -0,0 +1,52 @@
|
|||||||
|
using System.Linq;
|
||||||
|
|
||||||
|
namespace WireMock.Matchers
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// NotNullOrEmptyMatcher
|
||||||
|
/// </summary>
|
||||||
|
/// <seealso cref="IObjectMatcher" />
|
||||||
|
public class NotNullOrEmptyMatcher : IObjectMatcher
|
||||||
|
{
|
||||||
|
/// <inheritdoc cref="IMatcher.Name"/>
|
||||||
|
public string Name => "NotNullOrEmptyMatcher";
|
||||||
|
|
||||||
|
/// <inheritdoc cref="IMatcher.MatchBehaviour"/>
|
||||||
|
public MatchBehaviour MatchBehaviour { get; }
|
||||||
|
|
||||||
|
/// <inheritdoc cref="IMatcher.ThrowException"/>
|
||||||
|
public bool ThrowException { get; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Initializes a new instance of the <see cref="NotNullOrEmptyMatcher"/> class.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="matchBehaviour">The match behaviour.</param>
|
||||||
|
public NotNullOrEmptyMatcher(MatchBehaviour matchBehaviour = MatchBehaviour.AcceptOnMatch)
|
||||||
|
{
|
||||||
|
MatchBehaviour = matchBehaviour;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <inheritdoc cref="IObjectMatcher.IsMatch"/>
|
||||||
|
public double IsMatch(object input)
|
||||||
|
{
|
||||||
|
bool match;
|
||||||
|
|
||||||
|
switch (input)
|
||||||
|
{
|
||||||
|
case string @string:
|
||||||
|
match = !string.IsNullOrEmpty(@string);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case byte[] bytes:
|
||||||
|
match = bytes != null && bytes.Any();
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
match = input != null;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return MatchBehaviourHelper.Convert(MatchBehaviour, MatchScores.ToScore(match));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -123,6 +123,32 @@ namespace WireMock.Matchers.Request
|
|||||||
|
|
||||||
private double CalculateMatchScore(IRequestMessage requestMessage, IMatcher matcher)
|
private double CalculateMatchScore(IRequestMessage requestMessage, IMatcher matcher)
|
||||||
{
|
{
|
||||||
|
if (matcher is NotNullOrEmptyMatcher notNullOrEmptyMatcher)
|
||||||
|
{
|
||||||
|
switch (requestMessage?.BodyData?.DetectedBodyType)
|
||||||
|
{
|
||||||
|
case BodyType.Json:
|
||||||
|
case BodyType.String:
|
||||||
|
return notNullOrEmptyMatcher.IsMatch(requestMessage.BodyData.BodyAsString);
|
||||||
|
|
||||||
|
case BodyType.Bytes:
|
||||||
|
return notNullOrEmptyMatcher.IsMatch(requestMessage.BodyData.BodyAsBytes);
|
||||||
|
|
||||||
|
default:
|
||||||
|
return MatchScores.Mismatch;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (matcher is ExactObjectMatcher exactObjectMatcher)
|
||||||
|
{
|
||||||
|
// If the body is a byte array, try to match.
|
||||||
|
var detectedBodyType = requestMessage?.BodyData?.DetectedBodyType;
|
||||||
|
if (detectedBodyType == BodyType.Bytes || detectedBodyType == BodyType.String)
|
||||||
|
{
|
||||||
|
return exactObjectMatcher.IsMatch(requestMessage.BodyData.BodyAsBytes);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Check if the matcher is a IObjectMatcher
|
// Check if the matcher is a IObjectMatcher
|
||||||
if (matcher is IObjectMatcher objectMatcher)
|
if (matcher is IObjectMatcher objectMatcher)
|
||||||
{
|
{
|
||||||
|
|||||||
11
src/WireMock.Net/Models/Webhook.cs
Normal file
11
src/WireMock.Net/Models/Webhook.cs
Normal file
@@ -0,0 +1,11 @@
|
|||||||
|
namespace WireMock.Models
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Webhook
|
||||||
|
/// </summary>
|
||||||
|
public class Webhook : IWebhook
|
||||||
|
{
|
||||||
|
/// <inheritdoc cref="IWebhook.Request"/>
|
||||||
|
public IWebhookRequest Request { get; set; }
|
||||||
|
}
|
||||||
|
}
|
||||||
30
src/WireMock.Net/Models/WebhookRequest.cs
Normal file
30
src/WireMock.Net/Models/WebhookRequest.cs
Normal file
@@ -0,0 +1,30 @@
|
|||||||
|
using System.Collections.Generic;
|
||||||
|
using WireMock.Types;
|
||||||
|
using WireMock.Util;
|
||||||
|
|
||||||
|
namespace WireMock.Models
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// WebhookRequest
|
||||||
|
/// </summary>
|
||||||
|
public class WebhookRequest : IWebhookRequest
|
||||||
|
{
|
||||||
|
/// <inheritdoc cref="IWebhookRequest.Url"/>
|
||||||
|
public string Url { get; set; }
|
||||||
|
|
||||||
|
/// <inheritdoc cref="IWebhookRequest.Method"/>
|
||||||
|
public string Method { get; set; }
|
||||||
|
|
||||||
|
/// <inheritdoc cref="IWebhookRequest.Headers"/>
|
||||||
|
public IDictionary<string, WireMockList<string>> Headers { get; set; }
|
||||||
|
|
||||||
|
/// <inheritdoc cref="IWebhookRequest.BodyData"/>
|
||||||
|
public IBodyData BodyData { get; set; }
|
||||||
|
|
||||||
|
/// <inheritdoc cref="IWebhookRequest.UseTransformer"/>
|
||||||
|
public bool? UseTransformer { get; set; }
|
||||||
|
|
||||||
|
/// <inheritdoc cref="IWebhookRequest.TransformerType"/>
|
||||||
|
public TransformerType TransformerType { get; set; }
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -66,6 +66,8 @@ namespace WireMock.Owin
|
|||||||
services.AddSingleton<IMappingMatcher, MappingMatcher>();
|
services.AddSingleton<IMappingMatcher, MappingMatcher>();
|
||||||
services.AddSingleton<IOwinRequestMapper, OwinRequestMapper>();
|
services.AddSingleton<IOwinRequestMapper, OwinRequestMapper>();
|
||||||
services.AddSingleton<IOwinResponseMapper, OwinResponseMapper>();
|
services.AddSingleton<IOwinResponseMapper, OwinResponseMapper>();
|
||||||
|
|
||||||
|
_wireMockMiddlewareOptions.AdditionalServiceRegistration?.Invoke(services);
|
||||||
})
|
})
|
||||||
.Configure(appBuilder =>
|
.Configure(appBuilder =>
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -8,6 +8,7 @@ using WireMock.Util;
|
|||||||
using Owin;
|
using Owin;
|
||||||
#else
|
#else
|
||||||
using IAppBuilder = Microsoft.AspNetCore.Builder.IApplicationBuilder;
|
using IAppBuilder = Microsoft.AspNetCore.Builder.IApplicationBuilder;
|
||||||
|
using Microsoft.Extensions.DependencyInjection;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
namespace WireMock.Owin
|
namespace WireMock.Owin
|
||||||
@@ -36,6 +37,10 @@ namespace WireMock.Owin
|
|||||||
|
|
||||||
Action<IAppBuilder> PostWireMockMiddlewareInit { get; set; }
|
Action<IAppBuilder> PostWireMockMiddlewareInit { get; set; }
|
||||||
|
|
||||||
|
#if USE_ASPNETCORE
|
||||||
|
Action<IServiceCollection> AdditionalServiceRegistration { get; set; }
|
||||||
|
#endif
|
||||||
|
|
||||||
IFileSystemHandler FileSystemHandler { get; set; }
|
IFileSystemHandler FileSystemHandler { get; set; }
|
||||||
|
|
||||||
bool? AllowBodyForAllHttpMethods { get; set; }
|
bool? AllowBodyForAllHttpMethods { get; set; }
|
||||||
|
|||||||
@@ -53,7 +53,7 @@ namespace WireMock.Owin.Mappers
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
BodyData body = null;
|
IBodyData body = null;
|
||||||
if (request.Body != null && BodyParser.ShouldParseBody(method, options.AllowBodyForAllHttpMethods == true))
|
if (request.Body != null && BodyParser.ShouldParseBody(method, options.AllowBodyForAllHttpMethods == true))
|
||||||
{
|
{
|
||||||
var bodyParserSettings = new BodyParserSettings
|
var bodyParserSettings = new BodyParserSettings
|
||||||
|
|||||||
@@ -9,6 +9,7 @@ using WireMock.Serialization;
|
|||||||
using WireMock.Types;
|
using WireMock.Types;
|
||||||
using WireMock.Validation;
|
using WireMock.Validation;
|
||||||
using WireMock.ResponseBuilders;
|
using WireMock.ResponseBuilders;
|
||||||
|
using WireMock.Settings;
|
||||||
#if !USE_ASPNETCORE
|
#if !USE_ASPNETCORE
|
||||||
using Microsoft.Owin;
|
using Microsoft.Owin;
|
||||||
using IContext = Microsoft.Owin.IOwinContext;
|
using IContext = Microsoft.Owin.IOwinContext;
|
||||||
@@ -128,15 +129,16 @@ namespace WireMock.Owin
|
|||||||
await Task.Delay(_options.RequestProcessingDelay.Value);
|
await Task.Delay(_options.RequestProcessingDelay.Value);
|
||||||
}
|
}
|
||||||
|
|
||||||
response = await targetMapping.ProvideResponseAsync(request);
|
var (theResponse, theOptionalNewMapping) = await targetMapping.ProvideResponseAsync(request);
|
||||||
|
response = theResponse;
|
||||||
|
|
||||||
var responseBuilder = targetMapping.Provider as Response;
|
var responseBuilder = targetMapping.Provider as Response;
|
||||||
|
|
||||||
if (!targetMapping.IsAdminInterface)
|
if (!targetMapping.IsAdminInterface && theOptionalNewMapping != null)
|
||||||
{
|
{
|
||||||
if (responseBuilder?.ProxyAndRecordSettings?.SaveMapping == true || targetMapping?.Settings?.ProxyAndRecordSettings?.SaveMapping == true)
|
if (responseBuilder?.ProxyAndRecordSettings?.SaveMapping == true || targetMapping?.Settings?.ProxyAndRecordSettings?.SaveMapping == true)
|
||||||
{
|
{
|
||||||
_options.Mappings.TryAdd(targetMapping.Guid, targetMapping);
|
_options.Mappings.TryAdd(theOptionalNewMapping.Guid, theOptionalNewMapping);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (responseBuilder?.ProxyAndRecordSettings?.SaveMappingToFile == true || targetMapping?.Settings?.ProxyAndRecordSettings?.SaveMappingToFile == true)
|
if (responseBuilder?.ProxyAndRecordSettings?.SaveMappingToFile == true || targetMapping?.Settings?.ProxyAndRecordSettings?.SaveMappingToFile == true)
|
||||||
@@ -145,7 +147,7 @@ namespace WireMock.Owin
|
|||||||
var mappingConverter = new MappingConverter(matcherMapper);
|
var mappingConverter = new MappingConverter(matcherMapper);
|
||||||
var mappingToFileSaver = new MappingToFileSaver(targetMapping.Settings, mappingConverter);
|
var mappingToFileSaver = new MappingToFileSaver(targetMapping.Settings, mappingConverter);
|
||||||
|
|
||||||
mappingToFileSaver.SaveMappingToFile(targetMapping);
|
mappingToFileSaver.SaveMappingToFile(theOptionalNewMapping);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -153,6 +155,11 @@ namespace WireMock.Owin
|
|||||||
{
|
{
|
||||||
UpdateScenarioState(targetMapping);
|
UpdateScenarioState(targetMapping);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!targetMapping.IsAdminInterface && targetMapping.Webhooks?.Length > 0)
|
||||||
|
{
|
||||||
|
await SendToWebhooksAsync(targetMapping, request, response).ConfigureAwait(false);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
catch (Exception ex)
|
catch (Exception ex)
|
||||||
{
|
{
|
||||||
@@ -184,6 +191,24 @@ namespace WireMock.Owin
|
|||||||
await CompletedTask;
|
await CompletedTask;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private async Task SendToWebhooksAsync(IMapping mapping, RequestMessage request, ResponseMessage response)
|
||||||
|
{
|
||||||
|
for (int index = 0; index < mapping.Webhooks.Length; index++)
|
||||||
|
{
|
||||||
|
var httpClientForWebhook = HttpClientBuilder.Build(mapping.Settings.WebhookSettings ?? new WebhookSettings());
|
||||||
|
var webhookSender = new WebhookSender(mapping.Settings);
|
||||||
|
|
||||||
|
try
|
||||||
|
{
|
||||||
|
await webhookSender.SendAsync(httpClientForWebhook, mapping.Webhooks[index].Request, request, response).ConfigureAwait(false);
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
_options.Logger.Error($"Sending message to Webhook [{index}] from Mapping '{mapping.Guid}' failed. Exception: {ex}");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private void UpdateScenarioState(IMapping mapping)
|
private void UpdateScenarioState(IMapping mapping)
|
||||||
{
|
{
|
||||||
var scenario = _options.Scenarios[mapping.Scenario];
|
var scenario = _options.Scenarios[mapping.Scenario];
|
||||||
|
|||||||
@@ -8,6 +8,7 @@ using WireMock.Util;
|
|||||||
using Owin;
|
using Owin;
|
||||||
#else
|
#else
|
||||||
using IAppBuilder = Microsoft.AspNetCore.Builder.IApplicationBuilder;
|
using IAppBuilder = Microsoft.AspNetCore.Builder.IApplicationBuilder;
|
||||||
|
using Microsoft.Extensions.DependencyInjection;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
namespace WireMock.Owin
|
namespace WireMock.Owin
|
||||||
@@ -36,6 +37,10 @@ namespace WireMock.Owin
|
|||||||
|
|
||||||
public Action<IAppBuilder> PostWireMockMiddlewareInit { get; set; }
|
public Action<IAppBuilder> PostWireMockMiddlewareInit { get; set; }
|
||||||
|
|
||||||
|
#if USE_ASPNETCORE
|
||||||
|
public Action<IServiceCollection> AdditionalServiceRegistration { get; set; }
|
||||||
|
#endif
|
||||||
|
|
||||||
/// <inheritdoc cref="IWireMockMiddlewareOptions.FileSystemHandler"/>
|
/// <inheritdoc cref="IWireMockMiddlewareOptions.FileSystemHandler"/>
|
||||||
public IFileSystemHandler FileSystemHandler { get; set; }
|
public IFileSystemHandler FileSystemHandler { get; set; }
|
||||||
|
|
||||||
|
|||||||
@@ -3,7 +3,6 @@ using System.Collections.Generic;
|
|||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Net.Http;
|
using System.Net.Http;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using HandlebarsDotNet.Helpers.Validation;
|
|
||||||
using JetBrains.Annotations;
|
using JetBrains.Annotations;
|
||||||
using WireMock.Http;
|
using WireMock.Http;
|
||||||
using WireMock.Matchers;
|
using WireMock.Matchers;
|
||||||
@@ -26,7 +25,7 @@ namespace WireMock.Proxy
|
|||||||
_settings = settings;
|
_settings = settings;
|
||||||
}
|
}
|
||||||
|
|
||||||
public async Task<(ResponseMessage ResponseMessage, IMapping Mapping)> SendAsync(
|
public async Task<(ResponseMessage Message, IMapping Mapping)> SendAsync(
|
||||||
[NotNull] IProxyAndRecordSettings proxyAndRecordSettings,
|
[NotNull] IProxyAndRecordSettings proxyAndRecordSettings,
|
||||||
[NotNull] HttpClient client,
|
[NotNull] HttpClient client,
|
||||||
[NotNull] RequestMessage requestMessage,
|
[NotNull] RequestMessage requestMessage,
|
||||||
@@ -106,7 +105,7 @@ namespace WireMock.Proxy
|
|||||||
|
|
||||||
var response = Response.Create(responseMessage);
|
var response = Response.Create(responseMessage);
|
||||||
|
|
||||||
return new Mapping(Guid.NewGuid(), string.Empty, null, _settings, request, response, 0, null, null, null, null);
|
return new Mapping(Guid.NewGuid(), string.Empty, null, _settings, request, response, 0, null, null, null, null, null);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -101,7 +101,7 @@ namespace WireMock
|
|||||||
/// <param name="bodyData">The BodyData.</param>
|
/// <param name="bodyData">The BodyData.</param>
|
||||||
/// <param name="headers">The headers.</param>
|
/// <param name="headers">The headers.</param>
|
||||||
/// <param name="cookies">The cookies.</param>
|
/// <param name="cookies">The cookies.</param>
|
||||||
public RequestMessage([NotNull] UrlDetails urlDetails, [NotNull] string method, [NotNull] string clientIP, [CanBeNull] BodyData bodyData = null, [CanBeNull] IDictionary<string, string[]> headers = null, [CanBeNull] IDictionary<string, string> cookies = null)
|
public RequestMessage([NotNull] UrlDetails urlDetails, [NotNull] string method, [NotNull] string clientIP, [CanBeNull] IBodyData bodyData = null, [CanBeNull] IDictionary<string, string[]> headers = null, [CanBeNull] IDictionary<string, string> cookies = null)
|
||||||
{
|
{
|
||||||
Check.NotNull(urlDetails, nameof(urlDetails));
|
Check.NotNull(urlDetails, nameof(urlDetails));
|
||||||
Check.NotNull(method, nameof(method));
|
Check.NotNull(method, nameof(method));
|
||||||
|
|||||||
@@ -335,7 +335,7 @@ namespace WireMock.ResponseBuilders
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc cref="IResponseProvider.ProvideResponseAsync(RequestMessage, IWireMockServerSettings)"/>
|
/// <inheritdoc cref="IResponseProvider.ProvideResponseAsync(RequestMessage, IWireMockServerSettings)"/>
|
||||||
public async Task<ResponseMessage> ProvideResponseAsync(RequestMessage requestMessage, IWireMockServerSettings settings)
|
public async Task<(ResponseMessage Message, IMapping Mapping)> ProvideResponseAsync(RequestMessage requestMessage, IWireMockServerSettings settings)
|
||||||
{
|
{
|
||||||
Check.NotNull(requestMessage, nameof(requestMessage));
|
Check.NotNull(requestMessage, nameof(requestMessage));
|
||||||
Check.NotNull(settings, nameof(settings));
|
Check.NotNull(settings, nameof(settings));
|
||||||
@@ -361,14 +361,12 @@ namespace WireMock.ResponseBuilders
|
|||||||
|
|
||||||
var proxyHelper = new ProxyHelper(settings);
|
var proxyHelper = new ProxyHelper(settings);
|
||||||
|
|
||||||
var (proxyResponseMessage, _) = await proxyHelper.SendAsync(
|
return await proxyHelper.SendAsync(
|
||||||
ProxyAndRecordSettings,
|
ProxyAndRecordSettings,
|
||||||
_httpClientForProxy,
|
_httpClientForProxy,
|
||||||
requestMessage,
|
requestMessage,
|
||||||
requestMessage.ProxyUrl
|
requestMessage.ProxyUrl
|
||||||
);
|
);
|
||||||
|
|
||||||
return proxyResponseMessage;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
ResponseMessage responseMessage;
|
ResponseMessage responseMessage;
|
||||||
@@ -394,7 +392,7 @@ namespace WireMock.ResponseBuilders
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Copy Headers from ResponseMessage (if defined)
|
// Copy Headers from ResponseMessage (if defined)
|
||||||
if (ResponseMessage.Headers != null)
|
if (ResponseMessage.Headers?.Count > 0)
|
||||||
{
|
{
|
||||||
responseMessage.Headers = ResponseMessage.Headers;
|
responseMessage.Headers = ResponseMessage.Headers;
|
||||||
}
|
}
|
||||||
@@ -420,7 +418,7 @@ namespace WireMock.ResponseBuilders
|
|||||||
throw new NotImplementedException($"TransformerType '{TransformerType}' is not supported.");
|
throw new NotImplementedException($"TransformerType '{TransformerType}' is not supported.");
|
||||||
}
|
}
|
||||||
|
|
||||||
return responseMessageTransformer.Transform(requestMessage, responseMessage, UseTransformerForBodyAsFile);
|
return (responseMessageTransformer.Transform(requestMessage, responseMessage, UseTransformerForBodyAsFile), null);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!UseTransformer && ResponseMessage.BodyData?.BodyAsFileIsCached == true)
|
if (!UseTransformer && ResponseMessage.BodyData?.BodyAsFileIsCached == true)
|
||||||
@@ -428,7 +426,7 @@ namespace WireMock.ResponseBuilders
|
|||||||
ResponseMessage.BodyData.BodyAsBytes = settings.FileSystemHandler.ReadResponseBodyAsFile(responseMessage.BodyData.BodyAsFile);
|
ResponseMessage.BodyData.BodyAsBytes = settings.FileSystemHandler.ReadResponseBodyAsFile(responseMessage.BodyData.BodyAsFile);
|
||||||
}
|
}
|
||||||
|
|
||||||
return responseMessage;
|
return (responseMessage, null);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -13,9 +13,9 @@ namespace WireMock.ResponseProviders
|
|||||||
_responseMessageFunc = responseMessageFunc;
|
_responseMessageFunc = responseMessageFunc;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Task<ResponseMessage> ProvideResponseAsync(RequestMessage requestMessage, IWireMockServerSettings settings)
|
public async Task<(ResponseMessage Message, IMapping Mapping)> ProvideResponseAsync(RequestMessage requestMessage, IWireMockServerSettings settings)
|
||||||
{
|
{
|
||||||
return _responseMessageFunc(requestMessage);
|
return (await _responseMessageFunc(requestMessage), null);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -13,9 +13,10 @@ namespace WireMock.ResponseProviders
|
|||||||
_responseMessageFunc = responseMessageFunc;
|
_responseMessageFunc = responseMessageFunc;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Task<ResponseMessage> ProvideResponseAsync(RequestMessage requestMessage, IWireMockServerSettings settings)
|
public Task<(ResponseMessage Message, IMapping Mapping)> ProvideResponseAsync(RequestMessage requestMessage, IWireMockServerSettings settings)
|
||||||
{
|
{
|
||||||
return Task.FromResult(_responseMessageFunc(requestMessage));
|
(ResponseMessage responseMessage, IMapping mapping) result = (_responseMessageFunc(requestMessage), null);
|
||||||
|
return Task.FromResult(result);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -16,7 +16,7 @@ namespace WireMock.ResponseProviders
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="requestMessage">The request.</param>
|
/// <param name="requestMessage">The request.</param>
|
||||||
/// <param name="settings">The WireMockServerSettings.</param>
|
/// <param name="settings">The WireMockServerSettings.</param>
|
||||||
/// <returns>The <see cref="ResponseMessage"/>.</returns>
|
/// <returns>The <see cref="ResponseMessage"/> including a new (optional) <see cref="IMapping"/>.</returns>
|
||||||
Task<ResponseMessage> ProvideResponseAsync([NotNull] RequestMessage requestMessage, [NotNull] IWireMockServerSettings settings);
|
Task<(ResponseMessage Message, IMapping Mapping)> ProvideResponseAsync([NotNull] RequestMessage requestMessage, [NotNull] IWireMockServerSettings settings);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -15,9 +15,9 @@ namespace WireMock.ResponseProviders
|
|||||||
_settings = settings;
|
_settings = settings;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Task<ResponseMessage> ProvideResponseAsync(RequestMessage requestMessage, IWireMockServerSettings settings)
|
public async Task<(ResponseMessage Message, IMapping Mapping)> ProvideResponseAsync(RequestMessage requestMessage, IWireMockServerSettings settings)
|
||||||
{
|
{
|
||||||
return _responseMessageFunc(requestMessage, _settings);
|
return (await _responseMessageFunc(requestMessage, _settings), null);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -87,6 +87,15 @@ namespace WireMock.Serialization
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
if (mapping.Webhooks?.Length == 1)
|
||||||
|
{
|
||||||
|
mappingModel.Webhook = WebhookMapper.Map(mapping.Webhooks[0]);
|
||||||
|
}
|
||||||
|
else if (mapping.Webhooks?.Length > 1)
|
||||||
|
{
|
||||||
|
mappingModel.Webhooks = mapping.Webhooks.Select(WebhookMapper.Map).ToArray();
|
||||||
|
}
|
||||||
|
|
||||||
if (bodyMatcher?.Matchers != null)
|
if (bodyMatcher?.Matchers != null)
|
||||||
{
|
{
|
||||||
mappingModel.Request.Body = new BodyModel();
|
mappingModel.Request.Body = new BodyModel();
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using JetBrains.Annotations;
|
using JetBrains.Annotations;
|
||||||
@@ -44,6 +44,9 @@ namespace WireMock.Serialization
|
|||||||
|
|
||||||
switch (matcherName)
|
switch (matcherName)
|
||||||
{
|
{
|
||||||
|
case "NotNullOrEmptyMatcher":
|
||||||
|
return new NotNullOrEmptyMatcher(matchBehaviour);
|
||||||
|
|
||||||
case "CSharpCodeMatcher":
|
case "CSharpCodeMatcher":
|
||||||
if (_settings.AllowCSharpCodeMatcher == true)
|
if (_settings.AllowCSharpCodeMatcher == true)
|
||||||
{
|
{
|
||||||
|
|||||||
103
src/WireMock.Net/Serialization/WebhookMapper.cs
Normal file
103
src/WireMock.Net/Serialization/WebhookMapper.cs
Normal file
@@ -0,0 +1,103 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using WireMock.Admin.Mappings;
|
||||||
|
using WireMock.Http;
|
||||||
|
using WireMock.Models;
|
||||||
|
using WireMock.Types;
|
||||||
|
using WireMock.Util;
|
||||||
|
|
||||||
|
namespace WireMock.Serialization
|
||||||
|
{
|
||||||
|
internal static class WebhookMapper
|
||||||
|
{
|
||||||
|
public static IWebhook Map(WebhookModel model)
|
||||||
|
{
|
||||||
|
var webhook = new Webhook
|
||||||
|
{
|
||||||
|
Request = new WebhookRequest
|
||||||
|
{
|
||||||
|
Url = model.Request.Url,
|
||||||
|
Method = model.Request.Method,
|
||||||
|
Headers = model.Request.Headers?.ToDictionary(x => x.Key, x => new WireMockList<string>(x.Value)) ?? new Dictionary<string, WireMockList<string>>()
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
if (model.Request.UseTransformer == true)
|
||||||
|
{
|
||||||
|
webhook.Request.UseTransformer = true;
|
||||||
|
if (!Enum.TryParse<TransformerType>(model.Request.TransformerType, out var transformerType))
|
||||||
|
{
|
||||||
|
transformerType = TransformerType.Handlebars;
|
||||||
|
}
|
||||||
|
webhook.Request.TransformerType = transformerType;
|
||||||
|
}
|
||||||
|
|
||||||
|
IEnumerable<string> contentTypeHeader = null;
|
||||||
|
if (webhook.Request.Headers.Any(header => string.Equals(header.Key, HttpKnownHeaderNames.ContentType, StringComparison.OrdinalIgnoreCase)))
|
||||||
|
{
|
||||||
|
contentTypeHeader = webhook.Request.Headers.First(header => string.Equals(header.Key, HttpKnownHeaderNames.ContentType, StringComparison.OrdinalIgnoreCase)).Value;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (model.Request.Body != null)
|
||||||
|
{
|
||||||
|
webhook.Request.BodyData = new BodyData
|
||||||
|
{
|
||||||
|
BodyAsString = model.Request.Body,
|
||||||
|
DetectedBodyType = BodyType.String,
|
||||||
|
DetectedBodyTypeFromContentType = BodyParser.DetectBodyTypeFromContentType(contentTypeHeader?.FirstOrDefault())
|
||||||
|
};
|
||||||
|
}
|
||||||
|
else if (model.Request.BodyAsJson != null)
|
||||||
|
{
|
||||||
|
webhook.Request.BodyData = new BodyData
|
||||||
|
{
|
||||||
|
BodyAsJson = model.Request.BodyAsJson,
|
||||||
|
DetectedBodyType = BodyType.Json,
|
||||||
|
DetectedBodyTypeFromContentType = BodyParser.DetectBodyTypeFromContentType(contentTypeHeader?.FirstOrDefault())
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
return webhook;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static WebhookModel Map(IWebhook webhook)
|
||||||
|
{
|
||||||
|
if (webhook?.Request == null)
|
||||||
|
{
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
var model = new WebhookModel
|
||||||
|
{
|
||||||
|
Request = new WebhookRequestModel
|
||||||
|
{
|
||||||
|
Url = webhook.Request.Url,
|
||||||
|
Method = webhook.Request.Method,
|
||||||
|
Headers = webhook.Request.Headers?.ToDictionary(x => x.Key, x => x.Value.ToString()),
|
||||||
|
UseTransformer = webhook.Request.UseTransformer,
|
||||||
|
TransformerType = webhook.Request.UseTransformer == true ? webhook.Request.TransformerType.ToString() : null
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
if (webhook.Request.BodyData != null)
|
||||||
|
{
|
||||||
|
switch (webhook.Request.BodyData.DetectedBodyType)
|
||||||
|
{
|
||||||
|
case BodyType.String:
|
||||||
|
model.Request.Body = webhook.Request.BodyData.BodyAsString;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case BodyType.Json:
|
||||||
|
model.Request.BodyAsJson = webhook.Request.BodyData.BodyAsJson;
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return model;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,5 +1,9 @@
|
|||||||
using System;
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using JetBrains.Annotations;
|
||||||
|
using WireMock.Models;
|
||||||
using WireMock.ResponseProviders;
|
using WireMock.ResponseProviders;
|
||||||
|
using WireMock.Types;
|
||||||
|
|
||||||
namespace WireMock.Server
|
namespace WireMock.Server
|
||||||
{
|
{
|
||||||
@@ -97,5 +101,50 @@ namespace WireMock.Server
|
|||||||
/// <param name="times">The number of times this match should be matched before the state will be changed to the specified one. Default value is 1.</param>
|
/// <param name="times">The number of times this match should be matched before the state will be changed to the specified one. Default value is 1.</param>
|
||||||
/// <returns>The <see cref="IRespondWithAProvider"/>.</returns>
|
/// <returns>The <see cref="IRespondWithAProvider"/>.</returns>
|
||||||
IRespondWithAProvider WillSetStateTo(int state, int? times = 1);
|
IRespondWithAProvider WillSetStateTo(int state, int? times = 1);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Add (multiple) Webhook(s) to call after the response has been generated.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="webhooks">The Webhooks</param>
|
||||||
|
/// <returns>The <see cref="IRespondWithAProvider"/>.</returns>
|
||||||
|
IRespondWithAProvider WithWebhook(params IWebhook[] webhooks);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Add a Webhook to call after the response has been generated.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="url">The Webhook Url</param>
|
||||||
|
/// <param name="method">The method to use. [optional]</param>
|
||||||
|
/// <param name="headers">The Headers to send. [optional]</param>
|
||||||
|
/// <param name="body">The body (as string) to send. [optional]</param>
|
||||||
|
/// <param name="useTransformer">Use Transformer. [optional]</param>
|
||||||
|
/// <param name="transformerType">The transformer type. [optional]</param>
|
||||||
|
/// <returns>The <see cref="IRespondWithAProvider"/>.</returns>
|
||||||
|
IRespondWithAProvider WithWebhook(
|
||||||
|
[NotNull] string url,
|
||||||
|
[CanBeNull] string method = "post",
|
||||||
|
[CanBeNull] IDictionary<string, WireMockList<string>> headers = null,
|
||||||
|
[CanBeNull] string body = null,
|
||||||
|
bool useTransformer = true,
|
||||||
|
TransformerType transformerType = TransformerType.Handlebars
|
||||||
|
);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Add a Webhook to call after the response has been generated.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="url">The Webhook Url</param>
|
||||||
|
/// <param name="method">The method to use. [optional]</param>
|
||||||
|
/// <param name="headers">The Headers to send. [optional]</param>
|
||||||
|
/// <param name="body">The body (as json) to send. [optional]</param>
|
||||||
|
/// <param name="useTransformer">Use Transformer. [optional]</param>
|
||||||
|
/// <param name="transformerType">The transformer type. [optional]</param>
|
||||||
|
/// <returns>The <see cref="IRespondWithAProvider"/>.</returns>
|
||||||
|
IRespondWithAProvider WithWebhook(
|
||||||
|
[NotNull] string url,
|
||||||
|
[CanBeNull] string method = "post",
|
||||||
|
[CanBeNull] IDictionary<string, WireMockList<string>> headers = null,
|
||||||
|
[CanBeNull] object body = null,
|
||||||
|
bool useTransformer = true,
|
||||||
|
TransformerType transformerType = TransformerType.Handlebars
|
||||||
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1,9 +1,15 @@
|
|||||||
// This source file is based on mock4net by Alexandre Victoor which is licensed under the Apache 2.0 License.
|
// This source file is based on mock4net by Alexandre Victoor which is licensed under the Apache 2.0 License.
|
||||||
// For more details see 'mock4net/LICENSE.txt' and 'mock4net/readme.md' in this project root.
|
// For more details see 'mock4net/LICENSE.txt' and 'mock4net/readme.md' in this project root.
|
||||||
using System;
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using JetBrains.Annotations;
|
||||||
using WireMock.Matchers.Request;
|
using WireMock.Matchers.Request;
|
||||||
|
using WireMock.Models;
|
||||||
using WireMock.ResponseProviders;
|
using WireMock.ResponseProviders;
|
||||||
using WireMock.Settings;
|
using WireMock.Settings;
|
||||||
|
using WireMock.Types;
|
||||||
|
using WireMock.Util;
|
||||||
|
using WireMock.Validation;
|
||||||
|
|
||||||
namespace WireMock.Server
|
namespace WireMock.Server
|
||||||
{
|
{
|
||||||
@@ -26,6 +32,8 @@ namespace WireMock.Server
|
|||||||
|
|
||||||
public Guid Guid { get; private set; } = Guid.NewGuid();
|
public Guid Guid { get; private set; } = Guid.NewGuid();
|
||||||
|
|
||||||
|
public IWebhook[] Webhooks { get; private set; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Initializes a new instance of the <see cref="RespondWithAProvider"/> class.
|
/// Initializes a new instance of the <see cref="RespondWithAProvider"/> class.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
@@ -47,7 +55,7 @@ namespace WireMock.Server
|
|||||||
/// <param name="provider">The provider.</param>
|
/// <param name="provider">The provider.</param>
|
||||||
public void RespondWith(IResponseProvider provider)
|
public void RespondWith(IResponseProvider provider)
|
||||||
{
|
{
|
||||||
_registrationCallback(new Mapping(Guid, _title, _path, _settings, _requestMatcher, provider, _priority, _scenario, _executionConditionState, _nextState, _timesInSameState), _saveToFile);
|
_registrationCallback(new Mapping(Guid, _title, _path, _settings, _requestMatcher, provider, _priority, _scenario, _executionConditionState, _nextState, _timesInSameState, Webhooks), _saveToFile);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <see cref="IRespondWithAProvider.WithGuid(string)"/>
|
/// <see cref="IRespondWithAProvider.WithGuid(string)"/>
|
||||||
@@ -140,5 +148,83 @@ namespace WireMock.Server
|
|||||||
{
|
{
|
||||||
return WillSetStateTo(state.ToString(), times);
|
return WillSetStateTo(state.ToString(), times);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <see cref="IRespondWithAProvider.WithWebhook(IWebhook[])"/>
|
||||||
|
public IRespondWithAProvider WithWebhook(params IWebhook[] webhooks)
|
||||||
|
{
|
||||||
|
Check.HasNoNulls(webhooks, nameof(webhooks));
|
||||||
|
|
||||||
|
Webhooks = webhooks;
|
||||||
|
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <see cref="IRespondWithAProvider.WithWebhook(string, string, IDictionary{string, WireMockList{string}}, string, bool, TransformerType)"/>
|
||||||
|
public IRespondWithAProvider WithWebhook(
|
||||||
|
[NotNull] string url,
|
||||||
|
[CanBeNull] string method = "post",
|
||||||
|
[CanBeNull] IDictionary<string, WireMockList<string>> headers = null,
|
||||||
|
[CanBeNull] string body = null,
|
||||||
|
bool useTransformer = true,
|
||||||
|
TransformerType transformerType = TransformerType.Handlebars)
|
||||||
|
{
|
||||||
|
Webhooks = new[] { InitWebhook(url, method, headers, useTransformer, transformerType) };
|
||||||
|
|
||||||
|
if (body != null)
|
||||||
|
{
|
||||||
|
Webhooks[0].Request.BodyData = new BodyData
|
||||||
|
{
|
||||||
|
BodyAsString = body,
|
||||||
|
DetectedBodyType = BodyType.String,
|
||||||
|
DetectedBodyTypeFromContentType = BodyType.String
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <see cref="IRespondWithAProvider.WithWebhook(string, string, IDictionary{string, WireMockList{string}}, object, bool, TransformerType)"/>
|
||||||
|
public IRespondWithAProvider WithWebhook(
|
||||||
|
[NotNull] string url,
|
||||||
|
[CanBeNull] string method = "post",
|
||||||
|
[CanBeNull] IDictionary<string, WireMockList<string>> headers = null,
|
||||||
|
[CanBeNull] object body = null,
|
||||||
|
bool useTransformer = true,
|
||||||
|
TransformerType transformerType = TransformerType.Handlebars)
|
||||||
|
{
|
||||||
|
Webhooks = new[] { InitWebhook(url, method, headers, useTransformer, transformerType) };
|
||||||
|
|
||||||
|
if (body != null)
|
||||||
|
{
|
||||||
|
Webhooks[0].Request.BodyData = new BodyData
|
||||||
|
{
|
||||||
|
BodyAsJson = body,
|
||||||
|
DetectedBodyType = BodyType.Json,
|
||||||
|
DetectedBodyTypeFromContentType = BodyType.Json
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
private IWebhook InitWebhook(
|
||||||
|
string url,
|
||||||
|
string method,
|
||||||
|
IDictionary<string, WireMockList<string>> headers,
|
||||||
|
bool useTransformer,
|
||||||
|
TransformerType transformerType)
|
||||||
|
{
|
||||||
|
return new Webhook
|
||||||
|
{
|
||||||
|
Request = new WebhookRequest
|
||||||
|
{
|
||||||
|
Url = url,
|
||||||
|
Method = method ?? "post",
|
||||||
|
Headers = headers,
|
||||||
|
UseTransformer = useTransformer,
|
||||||
|
TransformerType = transformerType
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -39,6 +39,7 @@ namespace WireMock.Server
|
|||||||
private const string ContentTypeJson = "application/json";
|
private const string ContentTypeJson = "application/json";
|
||||||
private const string AdminFiles = "/__admin/files";
|
private const string AdminFiles = "/__admin/files";
|
||||||
private const string AdminMappings = "/__admin/mappings";
|
private const string AdminMappings = "/__admin/mappings";
|
||||||
|
private const string AdminMappingsWireMockOrg = "/__admin/mappings/wiremock.org";
|
||||||
private const string AdminRequests = "/__admin/requests";
|
private const string AdminRequests = "/__admin/requests";
|
||||||
private const string AdminSettings = "/__admin/settings";
|
private const string AdminSettings = "/__admin/settings";
|
||||||
private const string AdminScenarios = "/__admin/scenarios";
|
private const string AdminScenarios = "/__admin/scenarios";
|
||||||
@@ -58,6 +59,7 @@ namespace WireMock.Server
|
|||||||
// __admin/mappings
|
// __admin/mappings
|
||||||
Given(Request.Create().WithPath(AdminMappings).UsingGet()).AtPriority(AdminPriority).RespondWith(new DynamicResponseProvider(MappingsGet));
|
Given(Request.Create().WithPath(AdminMappings).UsingGet()).AtPriority(AdminPriority).RespondWith(new DynamicResponseProvider(MappingsGet));
|
||||||
Given(Request.Create().WithPath(AdminMappings).UsingPost().WithHeader(HttpKnownHeaderNames.ContentType, _adminRequestContentTypeJson)).AtPriority(AdminPriority).RespondWith(new DynamicResponseProvider(MappingsPost));
|
Given(Request.Create().WithPath(AdminMappings).UsingPost().WithHeader(HttpKnownHeaderNames.ContentType, _adminRequestContentTypeJson)).AtPriority(AdminPriority).RespondWith(new DynamicResponseProvider(MappingsPost));
|
||||||
|
Given(Request.Create().WithPath(AdminMappingsWireMockOrg).UsingPost().WithHeader(HttpKnownHeaderNames.ContentType, _adminRequestContentTypeJson)).AtPriority(AdminPriority).RespondWith(new DynamicResponseProvider(MappingsPostWireMockOrg));
|
||||||
Given(Request.Create().WithPath(AdminMappings).UsingDelete()).AtPriority(AdminPriority).RespondWith(new DynamicResponseProvider(MappingsDelete));
|
Given(Request.Create().WithPath(AdminMappings).UsingDelete()).AtPriority(AdminPriority).RespondWith(new DynamicResponseProvider(MappingsDelete));
|
||||||
|
|
||||||
// __admin/mappings/reset
|
// __admin/mappings/reset
|
||||||
@@ -470,6 +472,16 @@ namespace WireMock.Server
|
|||||||
respondProvider = respondProvider.WillSetStateTo(mappingModel.SetStateTo);
|
respondProvider = respondProvider.WillSetStateTo(mappingModel.SetStateTo);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (mappingModel.Webhook != null)
|
||||||
|
{
|
||||||
|
respondProvider = respondProvider.WithWebhook(WebhookMapper.Map(mappingModel.Webhook));
|
||||||
|
}
|
||||||
|
else if (mappingModel.Webhooks?.Length > 1)
|
||||||
|
{
|
||||||
|
var webhooks = mappingModel.Webhooks.Select(WebhookMapper.Map).ToArray();
|
||||||
|
respondProvider = respondProvider.WithWebhook(webhooks);
|
||||||
|
}
|
||||||
|
|
||||||
respondProvider.RespondWith(responseBuilder);
|
respondProvider.RespondWith(responseBuilder);
|
||||||
|
|
||||||
return respondProvider.Guid;
|
return respondProvider.Guid;
|
||||||
|
|||||||
306
src/WireMock.Net/Server/WireMockServer.ImportWireMockOrg.cs
Normal file
306
src/WireMock.Net/Server/WireMockServer.ImportWireMockOrg.cs
Normal file
@@ -0,0 +1,306 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.IO;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Text;
|
||||||
|
using JetBrains.Annotations;
|
||||||
|
using Newtonsoft.Json.Linq;
|
||||||
|
using WireMock.Matchers;
|
||||||
|
using WireMock.RequestBuilders;
|
||||||
|
using WireMock.ResponseBuilders;
|
||||||
|
using WireMock.Util;
|
||||||
|
using WireMock.Validation;
|
||||||
|
using OrgMapping = WireMock.Org.Abstractions.Mapping;
|
||||||
|
|
||||||
|
namespace WireMock.Server
|
||||||
|
{
|
||||||
|
public partial class WireMockServer
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Read WireMock.org mapping json file.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="path">The path to the WireMock.org mapping json file.</param>
|
||||||
|
[PublicAPI]
|
||||||
|
public void ReadStaticWireMockOrgMappingAndAddOrUpdate([NotNull] string path)
|
||||||
|
{
|
||||||
|
Check.NotNull(path, nameof(path));
|
||||||
|
|
||||||
|
string filenameWithoutExtension = Path.GetFileNameWithoutExtension(path);
|
||||||
|
|
||||||
|
if (FileHelper.TryReadMappingFileWithRetryAndDelay(_settings.FileSystemHandler, path, out string value))
|
||||||
|
{
|
||||||
|
var mappings = DeserializeJsonToArray<OrgMapping>(value);
|
||||||
|
foreach (var mapping in mappings)
|
||||||
|
{
|
||||||
|
if (mappings.Length == 1 && Guid.TryParse(filenameWithoutExtension, out Guid guidFromFilename))
|
||||||
|
{
|
||||||
|
ConvertWireMockOrgMappingAndRegisterAsRespondProvider(mapping, guidFromFilename, path);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
ConvertWireMockOrgMappingAndRegisterAsRespondProvider(mapping, null, path);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private ResponseMessage MappingsPostWireMockOrg(RequestMessage requestMessage)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
var mappingModels = DeserializeRequestMessageToArray<OrgMapping>(requestMessage);
|
||||||
|
if (mappingModels.Length == 1)
|
||||||
|
{
|
||||||
|
Guid? guid = ConvertWireMockOrgMappingAndRegisterAsRespondProvider(mappingModels[0]);
|
||||||
|
return ResponseMessageBuilder.Create("Mapping added", 201, guid);
|
||||||
|
}
|
||||||
|
|
||||||
|
foreach (var mappingModel in mappingModels)
|
||||||
|
{
|
||||||
|
ConvertWireMockOrgMappingAndRegisterAsRespondProvider(mappingModel);
|
||||||
|
}
|
||||||
|
|
||||||
|
return ResponseMessageBuilder.Create("Mappings added", 201);
|
||||||
|
}
|
||||||
|
catch (ArgumentException a)
|
||||||
|
{
|
||||||
|
_settings.Logger.Error("HttpStatusCode set to 400 {0}", a);
|
||||||
|
return ResponseMessageBuilder.Create(a.Message, 400);
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
_settings.Logger.Error("HttpStatusCode set to 500 {0}", e);
|
||||||
|
return ResponseMessageBuilder.Create(e.ToString(), 500);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private Guid? ConvertWireMockOrgMappingAndRegisterAsRespondProvider(OrgMapping mapping, Guid? guid = null, string path = null)
|
||||||
|
{
|
||||||
|
var requestBuilder = Request.Create();
|
||||||
|
|
||||||
|
var request = mapping.Request;
|
||||||
|
if (request != null)
|
||||||
|
{
|
||||||
|
if (request.Url != null)
|
||||||
|
{
|
||||||
|
requestBuilder = requestBuilder.WithUrl(request.Url);
|
||||||
|
}
|
||||||
|
else if (request.UrlPattern != null)
|
||||||
|
{
|
||||||
|
requestBuilder = requestBuilder.WithUrl(new RegexMatcher(request.UrlPattern));
|
||||||
|
}
|
||||||
|
else if (request.UrlPath != null)
|
||||||
|
{
|
||||||
|
requestBuilder = requestBuilder.WithPath(request.Url);
|
||||||
|
}
|
||||||
|
else if (request.UrlPathPattern != null)
|
||||||
|
{
|
||||||
|
requestBuilder = requestBuilder.WithPath(new RegexMatcher(request.UrlPathPattern));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (request.Method != null)
|
||||||
|
{
|
||||||
|
requestBuilder = requestBuilder.UsingMethod(request.Method);
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
"headers" : {
|
||||||
|
"Accept" : {
|
||||||
|
"contains" : "xml"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
*/
|
||||||
|
if (request.Headers is JObject headers)
|
||||||
|
{
|
||||||
|
ProcessWireMockOrgJObjectAndUseStringMatcher(headers, (key, match) =>
|
||||||
|
{
|
||||||
|
requestBuilder = requestBuilder.WithHeader(key, match as IStringMatcher);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
if (request.Cookies is JObject cookies)
|
||||||
|
{
|
||||||
|
ProcessWireMockOrgJObjectAndUseStringMatcher(cookies, (key, match) =>
|
||||||
|
{
|
||||||
|
requestBuilder = requestBuilder.WithCookie(key, match as IStringMatcher);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
"queryParameters" : {
|
||||||
|
"search_term" : {
|
||||||
|
"equalTo" : "WireMock"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
*/
|
||||||
|
if (request.QueryParameters is JObject queryParameters)
|
||||||
|
{
|
||||||
|
ProcessWireMockOrgJObjectAndUseStringMatcher(queryParameters, (key, match) =>
|
||||||
|
{
|
||||||
|
requestBuilder = requestBuilder.WithParam(key, match);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
"bodyPatterns" : [ {
|
||||||
|
"equalToJson" : "{ "cityName": "São Paulo", "cityCode": 5001 },
|
||||||
|
"ignoreArrayOrder" : true,
|
||||||
|
"ignoreExtraElements" : true
|
||||||
|
} ]
|
||||||
|
*/
|
||||||
|
if (request.BodyPatterns?.Any() == true)
|
||||||
|
{
|
||||||
|
var jObjectArray = request.BodyPatterns.Cast<JObject>();
|
||||||
|
var bodyPattern = jObjectArray.First();
|
||||||
|
ProcessWireMockOrgJObjectAndUseIMatcher(bodyPattern, (match) =>
|
||||||
|
{
|
||||||
|
requestBuilder = requestBuilder.WithBody(match);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
IResponseBuilder responseBuilder = Response.Create();
|
||||||
|
|
||||||
|
var response = mapping.Response;
|
||||||
|
if (response != null)
|
||||||
|
{
|
||||||
|
responseBuilder = responseBuilder.WithStatusCode(response.Status);
|
||||||
|
|
||||||
|
if (response.Headers is JObject responseHeaders)
|
||||||
|
{
|
||||||
|
ProcessWireMockOrgJObjectAndConvertToIDictionary(responseHeaders, (headers) =>
|
||||||
|
{
|
||||||
|
responseBuilder = responseBuilder.WithHeaders(headers);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
if (response.Transformers != null)
|
||||||
|
{
|
||||||
|
responseBuilder = responseBuilder.WithTransformer();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (response.Body != null)
|
||||||
|
{
|
||||||
|
responseBuilder = responseBuilder.WithBody(response.Body);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (response.JsonBody != null)
|
||||||
|
{
|
||||||
|
responseBuilder = responseBuilder.WithBodyAsJson(response.JsonBody);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (response.Base64Body != null)
|
||||||
|
{
|
||||||
|
responseBuilder = responseBuilder.WithBody(Encoding.UTF8.GetString(Convert.FromBase64String(response.Base64Body)));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (response.BodyFileName != null)
|
||||||
|
{
|
||||||
|
responseBuilder = responseBuilder.WithBodyFromFile(response.BodyFileName);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
var respondProvider = Given(requestBuilder);
|
||||||
|
if (guid != null)
|
||||||
|
{
|
||||||
|
respondProvider = respondProvider.WithGuid(guid.Value);
|
||||||
|
}
|
||||||
|
else if (!string.IsNullOrEmpty(mapping.Uuid))
|
||||||
|
{
|
||||||
|
respondProvider = respondProvider.WithGuid(new Guid(mapping.Uuid));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (mapping.Name != null)
|
||||||
|
{
|
||||||
|
respondProvider = respondProvider.WithTitle(mapping.Name);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (path != null)
|
||||||
|
{
|
||||||
|
respondProvider = respondProvider.WithPath(path);
|
||||||
|
}
|
||||||
|
|
||||||
|
respondProvider.RespondWith(responseBuilder);
|
||||||
|
|
||||||
|
return respondProvider.Guid;
|
||||||
|
}
|
||||||
|
|
||||||
|
private void ProcessWireMockOrgJObjectAndConvertToIDictionary(JObject items, Action<IDictionary<string, string>> action)
|
||||||
|
{
|
||||||
|
var dict = new Dictionary<string, string>();
|
||||||
|
foreach (var item in items)
|
||||||
|
{
|
||||||
|
var key = item.Key;
|
||||||
|
var valueAsString = item.Value.Value<string>();
|
||||||
|
dict.Add(key, valueAsString);
|
||||||
|
}
|
||||||
|
|
||||||
|
action(dict);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void ProcessWireMockOrgJObjectAndUseStringMatcher(JObject items, Action<string, IStringMatcher> action)
|
||||||
|
{
|
||||||
|
foreach (var item in items)
|
||||||
|
{
|
||||||
|
var key = item.Key;
|
||||||
|
var match = item.Value.First as JProperty;
|
||||||
|
var valueAsString = match?.Value.Value<string>();
|
||||||
|
if (string.IsNullOrEmpty(valueAsString))
|
||||||
|
{
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
var matcher = ProcessAsStringMatcher(match, valueAsString);
|
||||||
|
if (matcher != null)
|
||||||
|
{
|
||||||
|
action(key, matcher);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void ProcessWireMockOrgJObjectAndUseIMatcher(JObject items, Action<IMatcher> action)
|
||||||
|
{
|
||||||
|
IMatcher matcher = null;
|
||||||
|
|
||||||
|
var firstItem = items.First as JProperty;
|
||||||
|
|
||||||
|
if (firstItem?.Name == "equalToJson")
|
||||||
|
{
|
||||||
|
matcher = new JsonMatcher(firstItem.Value);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
var valueAsString = (firstItem.Value as JValue)?.Value as string;
|
||||||
|
if (valueAsString == null)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
matcher = ProcessAsStringMatcher(firstItem, valueAsString);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (matcher != null)
|
||||||
|
{
|
||||||
|
action(matcher);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private static IStringMatcher ProcessAsStringMatcher(JProperty match, string valueAsString)
|
||||||
|
{
|
||||||
|
switch (match?.Name)
|
||||||
|
{
|
||||||
|
case "contains":
|
||||||
|
return new WildcardMatcher(valueAsString);
|
||||||
|
|
||||||
|
case "matches":
|
||||||
|
return new RegexMatcher(valueAsString);
|
||||||
|
|
||||||
|
case "equalTo":
|
||||||
|
return new ExactMatcher(valueAsString);
|
||||||
|
|
||||||
|
default:
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user