mirror of
https://github.com/wiremock/WireMock.Net.git
synced 2026-05-02 13:14:12 +02:00
Fix WithBody when using Pact and added more nullable annotations (#783)
* More nullable annotations * . * . * FIX * pact * . * p * xxx * ... * auth * array * ...
This commit is contained in:
@@ -1,30 +1,28 @@
|
||||
using System.Net.Http;
|
||||
using System.Net.Http;
|
||||
using System.Net.Http.Headers;
|
||||
using JetBrains.Annotations;
|
||||
using Stef.Validation;
|
||||
|
||||
namespace WireMock.Http
|
||||
namespace WireMock.Http;
|
||||
|
||||
internal static class ByteArrayContentHelper
|
||||
{
|
||||
internal static class ByteArrayContentHelper
|
||||
/// <summary>
|
||||
/// Creates a ByteArrayContent object.
|
||||
/// </summary>
|
||||
/// <param name="content">The byte[] content (cannot be null)</param>
|
||||
/// <param name="contentType">The ContentType (can be null)</param>
|
||||
/// <returns>ByteArrayContent</returns>
|
||||
internal static ByteArrayContent Create(byte[] content, MediaTypeHeaderValue? contentType)
|
||||
{
|
||||
/// <summary>
|
||||
/// Creates a ByteArrayContent object.
|
||||
/// </summary>
|
||||
/// <param name="content">The byte[] content (cannot be null)</param>
|
||||
/// <param name="contentType">The ContentType (can be null)</param>
|
||||
/// <returns>ByteArrayContent</returns>
|
||||
internal static ByteArrayContent Create([NotNull] byte[] content, [CanBeNull] MediaTypeHeaderValue contentType)
|
||||
Guard.NotNull(content);
|
||||
|
||||
var byteContent = new ByteArrayContent(content);
|
||||
if (contentType != null)
|
||||
{
|
||||
Guard.NotNull(content, nameof(content));
|
||||
|
||||
var byteContent = new ByteArrayContent(content);
|
||||
if (contentType != null)
|
||||
{
|
||||
byteContent.Headers.Remove(HttpKnownHeaderNames.ContentType);
|
||||
byteContent.Headers.ContentType = contentType;
|
||||
}
|
||||
|
||||
return byteContent;
|
||||
byteContent.Headers.Remove(HttpKnownHeaderNames.ContentType);
|
||||
byteContent.Headers.ContentType = contentType;
|
||||
}
|
||||
|
||||
return byteContent;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,122 +1,121 @@
|
||||
// Licensed to the .NET Foundation under one or more agreements.
|
||||
// Licensed to the .NET Foundation under one or more agreements.
|
||||
// The .NET Foundation licenses this file to you under the MIT license.
|
||||
// See the LICENSE file in the project root for more information.
|
||||
|
||||
using System;
|
||||
using System.Linq;
|
||||
|
||||
namespace WireMock.Http
|
||||
namespace WireMock.Http;
|
||||
|
||||
/// <summary>
|
||||
/// Copied from https://raw.githubusercontent.com/dotnet/corefx/master/src/Common/src/System/Net/HttpKnownHeaderNames.cs
|
||||
/// </summary>
|
||||
internal static class HttpKnownHeaderNames
|
||||
{
|
||||
/// <summary>
|
||||
/// Copied from https://raw.githubusercontent.com/dotnet/corefx/master/src/Common/src/System/Net/HttpKnownHeaderNames.cs
|
||||
/// </summary>
|
||||
internal static class HttpKnownHeaderNames
|
||||
// https://docs.microsoft.com/en-us/dotnet/api/system.net.webheadercollection.isrestricted
|
||||
private static readonly string[] RestrictedResponseHeaders =
|
||||
{
|
||||
// https://docs.microsoft.com/en-us/dotnet/api/system.net.webheadercollection.isrestricted
|
||||
private static readonly string[] RestrictedResponseHeaders =
|
||||
{
|
||||
Accept,
|
||||
Connection,
|
||||
ContentLength,
|
||||
ContentType,
|
||||
Date, // RFC1123Pattern
|
||||
Expect,
|
||||
Host,
|
||||
IfModifiedSince,
|
||||
Range,
|
||||
Referer,
|
||||
TransferEncoding,
|
||||
UserAgent,
|
||||
ProxyConnection
|
||||
};
|
||||
Accept,
|
||||
Connection,
|
||||
ContentLength,
|
||||
ContentType,
|
||||
Date, // RFC1123Pattern
|
||||
Expect,
|
||||
Host,
|
||||
IfModifiedSince,
|
||||
Range,
|
||||
Referer,
|
||||
TransferEncoding,
|
||||
UserAgent,
|
||||
ProxyConnection
|
||||
};
|
||||
|
||||
/// <summary>Tests whether the specified HTTP header can be set for the response.</summary>
|
||||
/// <param name="headerName">The header to test.</param>
|
||||
/// <returns>true if the header is restricted; otherwise, false.</returns>
|
||||
public static bool IsRestrictedResponseHeader(string headerName) => RestrictedResponseHeaders.Contains(headerName, StringComparer.OrdinalIgnoreCase);
|
||||
/// <summary>Tests whether the specified HTTP header can be set for the response.</summary>
|
||||
/// <param name="headerName">The header to test.</param>
|
||||
/// <returns>true if the header is restricted; otherwise, false.</returns>
|
||||
public static bool IsRestrictedResponseHeader(string headerName) => RestrictedResponseHeaders.Contains(headerName, StringComparer.OrdinalIgnoreCase);
|
||||
|
||||
public const string Accept = "Accept";
|
||||
public const string AcceptCharset = "Accept-Charset";
|
||||
public const string AcceptEncoding = "Accept-Encoding";
|
||||
public const string AcceptLanguage = "Accept-Language";
|
||||
public const string AcceptPatch = "Accept-Patch";
|
||||
public const string AcceptRanges = "Accept-Ranges";
|
||||
public const string AccessControlAllowCredentials = "Access-Control-Allow-Credentials";
|
||||
public const string AccessControlAllowHeaders = "Access-Control-Allow-Headers";
|
||||
public const string AccessControlAllowMethods = "Access-Control-Allow-Methods";
|
||||
public const string AccessControlAllowOrigin = "Access-Control-Allow-Origin";
|
||||
public const string AccessControlExposeHeaders = "Access-Control-Expose-Headers";
|
||||
public const string AccessControlMaxAge = "Access-Control-Max-Age";
|
||||
public const string Age = "Age";
|
||||
public const string Allow = "Allow";
|
||||
public const string AltSvc = "Alt-Svc";
|
||||
public const string Authorization = "Authorization";
|
||||
public const string CacheControl = "Cache-Control";
|
||||
public const string Connection = "Connection";
|
||||
public const string ContentDisposition = "Content-Disposition";
|
||||
public const string ContentEncoding = "Content-Encoding";
|
||||
public const string ContentLanguage = "Content-Language";
|
||||
public const string ContentLength = "Content-Length";
|
||||
public const string ContentLocation = "Content-Location";
|
||||
public const string ContentMD5 = "Content-MD5";
|
||||
public const string ContentRange = "Content-Range";
|
||||
public const string ContentSecurityPolicy = "Content-Security-Policy";
|
||||
public const string ContentType = "Content-Type";
|
||||
public const string Cookie = "Cookie";
|
||||
public const string Cookie2 = "Cookie2";
|
||||
public const string Date = "Date";
|
||||
public const string ETag = "ETag";
|
||||
public const string Expect = "Expect";
|
||||
public const string Expires = "Expires";
|
||||
public const string From = "From";
|
||||
public const string Host = "Host";
|
||||
public const string IfMatch = "If-Match";
|
||||
public const string IfModifiedSince = "If-Modified-Since";
|
||||
public const string IfNoneMatch = "If-None-Match";
|
||||
public const string IfRange = "If-Range";
|
||||
public const string IfUnmodifiedSince = "If-Unmodified-Since";
|
||||
public const string KeepAlive = "Keep-Alive";
|
||||
public const string LastModified = "Last-Modified";
|
||||
public const string Link = "Link";
|
||||
public const string Location = "Location";
|
||||
public const string MaxForwards = "Max-Forwards";
|
||||
public const string Origin = "Origin";
|
||||
public const string P3P = "P3P";
|
||||
public const string Pragma = "Pragma";
|
||||
public const string ProxyAuthenticate = "Proxy-Authenticate";
|
||||
public const string ProxyAuthorization = "Proxy-Authorization";
|
||||
public const string ProxyConnection = "Proxy-Connection";
|
||||
public const string PublicKeyPins = "Public-Key-Pins";
|
||||
public const string Range = "Range";
|
||||
public const string Referer = "Referer"; // NB: The spelling-mistake "Referer" for "Referrer" must be matched.
|
||||
public const string RetryAfter = "Retry-After";
|
||||
public const string SecWebSocketAccept = "Sec-WebSocket-Accept";
|
||||
public const string SecWebSocketExtensions = "Sec-WebSocket-Extensions";
|
||||
public const string SecWebSocketKey = "Sec-WebSocket-Key";
|
||||
public const string SecWebSocketProtocol = "Sec-WebSocket-Protocol";
|
||||
public const string SecWebSocketVersion = "Sec-WebSocket-Version";
|
||||
public const string Server = "Server";
|
||||
public const string SetCookie = "Set-Cookie";
|
||||
public const string SetCookie2 = "Set-Cookie2";
|
||||
public const string StrictTransportSecurity = "Strict-Transport-Security";
|
||||
public const string TE = "TE";
|
||||
public const string TSV = "TSV";
|
||||
public const string Trailer = "Trailer";
|
||||
public const string TransferEncoding = "Transfer-Encoding";
|
||||
public const string Upgrade = "Upgrade";
|
||||
public const string UpgradeInsecureRequests = "Upgrade-Insecure-Requests";
|
||||
public const string UserAgent = "User-Agent";
|
||||
public const string Vary = "Vary";
|
||||
public const string Via = "Via";
|
||||
public const string WWWAuthenticate = "WWW-Authenticate";
|
||||
public const string Warning = "Warning";
|
||||
public const string XAspNetVersion = "X-AspNet-Version";
|
||||
public const string XContentDuration = "X-Content-Duration";
|
||||
public const string XContentTypeOptions = "X-Content-Type-Options";
|
||||
public const string XFrameOptions = "X-Frame-Options";
|
||||
public const string XMSEdgeRef = "X-MSEdge-Ref";
|
||||
public const string XPoweredBy = "X-Powered-By";
|
||||
public const string XRequestID = "X-Request-ID";
|
||||
public const string XUACompatible = "X-UA-Compatible";
|
||||
}
|
||||
public const string Accept = "Accept";
|
||||
public const string AcceptCharset = "Accept-Charset";
|
||||
public const string AcceptEncoding = "Accept-Encoding";
|
||||
public const string AcceptLanguage = "Accept-Language";
|
||||
public const string AcceptPatch = "Accept-Patch";
|
||||
public const string AcceptRanges = "Accept-Ranges";
|
||||
public const string AccessControlAllowCredentials = "Access-Control-Allow-Credentials";
|
||||
public const string AccessControlAllowHeaders = "Access-Control-Allow-Headers";
|
||||
public const string AccessControlAllowMethods = "Access-Control-Allow-Methods";
|
||||
public const string AccessControlAllowOrigin = "Access-Control-Allow-Origin";
|
||||
public const string AccessControlExposeHeaders = "Access-Control-Expose-Headers";
|
||||
public const string AccessControlMaxAge = "Access-Control-Max-Age";
|
||||
public const string Age = "Age";
|
||||
public const string Allow = "Allow";
|
||||
public const string AltSvc = "Alt-Svc";
|
||||
public const string Authorization = "Authorization";
|
||||
public const string CacheControl = "Cache-Control";
|
||||
public const string Connection = "Connection";
|
||||
public const string ContentDisposition = "Content-Disposition";
|
||||
public const string ContentEncoding = "Content-Encoding";
|
||||
public const string ContentLanguage = "Content-Language";
|
||||
public const string ContentLength = "Content-Length";
|
||||
public const string ContentLocation = "Content-Location";
|
||||
public const string ContentMD5 = "Content-MD5";
|
||||
public const string ContentRange = "Content-Range";
|
||||
public const string ContentSecurityPolicy = "Content-Security-Policy";
|
||||
public const string ContentType = "Content-Type";
|
||||
public const string Cookie = "Cookie";
|
||||
public const string Cookie2 = "Cookie2";
|
||||
public const string Date = "Date";
|
||||
public const string ETag = "ETag";
|
||||
public const string Expect = "Expect";
|
||||
public const string Expires = "Expires";
|
||||
public const string From = "From";
|
||||
public const string Host = "Host";
|
||||
public const string IfMatch = "If-Match";
|
||||
public const string IfModifiedSince = "If-Modified-Since";
|
||||
public const string IfNoneMatch = "If-None-Match";
|
||||
public const string IfRange = "If-Range";
|
||||
public const string IfUnmodifiedSince = "If-Unmodified-Since";
|
||||
public const string KeepAlive = "Keep-Alive";
|
||||
public const string LastModified = "Last-Modified";
|
||||
public const string Link = "Link";
|
||||
public const string Location = "Location";
|
||||
public const string MaxForwards = "Max-Forwards";
|
||||
public const string Origin = "Origin";
|
||||
public const string P3P = "P3P";
|
||||
public const string Pragma = "Pragma";
|
||||
public const string ProxyAuthenticate = "Proxy-Authenticate";
|
||||
public const string ProxyAuthorization = "Proxy-Authorization";
|
||||
public const string ProxyConnection = "Proxy-Connection";
|
||||
public const string PublicKeyPins = "Public-Key-Pins";
|
||||
public const string Range = "Range";
|
||||
public const string Referer = "Referer"; // NB: The spelling-mistake "Referer" for "Referrer" must be matched.
|
||||
public const string RetryAfter = "Retry-After";
|
||||
public const string SecWebSocketAccept = "Sec-WebSocket-Accept";
|
||||
public const string SecWebSocketExtensions = "Sec-WebSocket-Extensions";
|
||||
public const string SecWebSocketKey = "Sec-WebSocket-Key";
|
||||
public const string SecWebSocketProtocol = "Sec-WebSocket-Protocol";
|
||||
public const string SecWebSocketVersion = "Sec-WebSocket-Version";
|
||||
public const string Server = "Server";
|
||||
public const string SetCookie = "Set-Cookie";
|
||||
public const string SetCookie2 = "Set-Cookie2";
|
||||
public const string StrictTransportSecurity = "Strict-Transport-Security";
|
||||
public const string TE = "TE";
|
||||
public const string TSV = "TSV";
|
||||
public const string Trailer = "Trailer";
|
||||
public const string TransferEncoding = "Transfer-Encoding";
|
||||
public const string Upgrade = "Upgrade";
|
||||
public const string UpgradeInsecureRequests = "Upgrade-Insecure-Requests";
|
||||
public const string UserAgent = "User-Agent";
|
||||
public const string Vary = "Vary";
|
||||
public const string Via = "Via";
|
||||
public const string WWWAuthenticate = "WWW-Authenticate";
|
||||
public const string Warning = "Warning";
|
||||
public const string XAspNetVersion = "X-AspNet-Version";
|
||||
public const string XContentDuration = "X-Content-Duration";
|
||||
public const string XContentTypeOptions = "X-Content-Type-Options";
|
||||
public const string XFrameOptions = "X-Frame-Options";
|
||||
public const string XMSEdgeRef = "X-MSEdge-Ref";
|
||||
public const string XPoweredBy = "X-Powered-By";
|
||||
public const string XRequestID = "X-Request-ID";
|
||||
public const string XUACompatible = "X-UA-Compatible";
|
||||
}
|
||||
@@ -3,89 +3,87 @@ using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Net.Http;
|
||||
using System.Net.Http.Headers;
|
||||
using JetBrains.Annotations;
|
||||
using Newtonsoft.Json;
|
||||
using WireMock.Types;
|
||||
using Stef.Validation;
|
||||
using WireMock.Types;
|
||||
|
||||
namespace WireMock.Http
|
||||
namespace WireMock.Http;
|
||||
|
||||
internal static class HttpRequestMessageHelper
|
||||
{
|
||||
internal static class HttpRequestMessageHelper
|
||||
internal static HttpRequestMessage Create(IRequestMessage requestMessage, string url)
|
||||
{
|
||||
internal static HttpRequestMessage Create([NotNull] IRequestMessage requestMessage, [NotNull] string url)
|
||||
Guard.NotNull(requestMessage);
|
||||
Guard.NotNullOrEmpty(url);
|
||||
|
||||
var httpRequestMessage = new HttpRequestMessage(new HttpMethod(requestMessage.Method), url);
|
||||
|
||||
MediaTypeHeaderValue? contentType = null;
|
||||
if (requestMessage.Headers != null && requestMessage.Headers.ContainsKey(HttpKnownHeaderNames.ContentType))
|
||||
{
|
||||
Guard.NotNull(requestMessage, nameof(requestMessage));
|
||||
Guard.NotNullOrEmpty(url, nameof(url));
|
||||
var value = requestMessage.Headers[HttpKnownHeaderNames.ContentType].FirstOrDefault();
|
||||
MediaTypeHeaderValue.TryParse(value, out contentType);
|
||||
}
|
||||
|
||||
var httpRequestMessage = new HttpRequestMessage(new HttpMethod(requestMessage.Method), url);
|
||||
switch (requestMessage.BodyData?.DetectedBodyType)
|
||||
{
|
||||
case BodyType.Bytes:
|
||||
httpRequestMessage.Content = ByteArrayContentHelper.Create(requestMessage.BodyData.BodyAsBytes, contentType);
|
||||
break;
|
||||
|
||||
MediaTypeHeaderValue contentType = null;
|
||||
if (requestMessage.Headers != null && requestMessage.Headers.ContainsKey(HttpKnownHeaderNames.ContentType))
|
||||
{
|
||||
var value = requestMessage.Headers[HttpKnownHeaderNames.ContentType].FirstOrDefault();
|
||||
MediaTypeHeaderValue.TryParse(value, out contentType);
|
||||
}
|
||||
case BodyType.Json:
|
||||
httpRequestMessage.Content = StringContentHelper.Create(JsonConvert.SerializeObject(requestMessage.BodyData.BodyAsJson), contentType);
|
||||
break;
|
||||
|
||||
switch (requestMessage.BodyData?.DetectedBodyType)
|
||||
{
|
||||
case BodyType.Bytes:
|
||||
httpRequestMessage.Content = ByteArrayContentHelper.Create(requestMessage.BodyData.BodyAsBytes, contentType);
|
||||
break;
|
||||
case BodyType.String:
|
||||
httpRequestMessage.Content = StringContentHelper.Create(requestMessage.BodyData.BodyAsString, contentType);
|
||||
break;
|
||||
}
|
||||
|
||||
case BodyType.Json:
|
||||
httpRequestMessage.Content = StringContentHelper.Create(JsonConvert.SerializeObject(requestMessage.BodyData.BodyAsJson), contentType);
|
||||
break;
|
||||
|
||||
case BodyType.String:
|
||||
httpRequestMessage.Content = StringContentHelper.Create(requestMessage.BodyData.BodyAsString, contentType);
|
||||
break;
|
||||
}
|
||||
|
||||
// Overwrite the host header
|
||||
httpRequestMessage.Headers.Host = new Uri(url).Authority;
|
||||
|
||||
// Set other headers if present
|
||||
if (requestMessage.Headers == null || requestMessage.Headers.Count == 0)
|
||||
{
|
||||
return httpRequestMessage;
|
||||
}
|
||||
|
||||
var excludeHeaders = new List<string> { HttpKnownHeaderNames.Host, HttpKnownHeaderNames.ContentLength };
|
||||
if (contentType != null)
|
||||
{
|
||||
// Content-Type should be set on the content
|
||||
excludeHeaders.Add(HttpKnownHeaderNames.ContentType);
|
||||
}
|
||||
|
||||
foreach (var header in requestMessage.Headers.Where(h => !excludeHeaders.Contains(h.Key, StringComparer.OrdinalIgnoreCase)))
|
||||
{
|
||||
// Skip if already added. We need to ToList() else calling httpRequestMessage.Headers.Contains() with a header starting with a ":" throws an exception.
|
||||
if (httpRequestMessage.Headers.ToList().Any(h => string.Equals(h.Key, header.Key, StringComparison.OrdinalIgnoreCase)))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
// Skip if already added. We need to ToList() else calling httpRequestMessage.Content.Headers.Contains(...) with a header starting with a ":" throws an exception.
|
||||
if (httpRequestMessage.Content != null && httpRequestMessage.Content.Headers.ToList().Any(h => string.Equals(h.Key, header.Key, StringComparison.OrdinalIgnoreCase)))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
// Try to add to request headers. If failed - try to add to content headers. If still fails, just ignore this header.
|
||||
try
|
||||
{
|
||||
if (!httpRequestMessage.Headers.TryAddWithoutValidation(header.Key, header.Value))
|
||||
{
|
||||
httpRequestMessage.Content?.Headers.TryAddWithoutValidation(header.Key, header.Value);
|
||||
}
|
||||
}
|
||||
catch
|
||||
{
|
||||
// Just continue
|
||||
}
|
||||
}
|
||||
// Overwrite the host header
|
||||
httpRequestMessage.Headers.Host = new Uri(url).Authority;
|
||||
|
||||
// Set other headers if present
|
||||
if (requestMessage.Headers == null || requestMessage.Headers.Count == 0)
|
||||
{
|
||||
return httpRequestMessage;
|
||||
}
|
||||
|
||||
var excludeHeaders = new List<string> { HttpKnownHeaderNames.Host, HttpKnownHeaderNames.ContentLength };
|
||||
if (contentType != null)
|
||||
{
|
||||
// Content-Type should be set on the content
|
||||
excludeHeaders.Add(HttpKnownHeaderNames.ContentType);
|
||||
}
|
||||
|
||||
foreach (var header in requestMessage.Headers.Where(h => !excludeHeaders.Contains(h.Key, StringComparer.OrdinalIgnoreCase)))
|
||||
{
|
||||
// Skip if already added. We need to ToList() else calling httpRequestMessage.Headers.Contains() with a header starting with a ":" throws an exception.
|
||||
if (httpRequestMessage.Headers.ToList().Any(h => string.Equals(h.Key, header.Key, StringComparison.OrdinalIgnoreCase)))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
// Skip if already added. We need to ToList() else calling httpRequestMessage.Content.Headers.Contains(...) with a header starting with a ":" throws an exception.
|
||||
if (httpRequestMessage.Content != null && httpRequestMessage.Content.Headers.ToList().Any(h => string.Equals(h.Key, header.Key, StringComparison.OrdinalIgnoreCase)))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
// Try to add to request headers. If failed - try to add to content headers. If still fails, just ignore this header.
|
||||
try
|
||||
{
|
||||
if (!httpRequestMessage.Headers.TryAddWithoutValidation(header.Key, header.Value))
|
||||
{
|
||||
httpRequestMessage.Content?.Headers.TryAddWithoutValidation(header.Key, header.Value);
|
||||
}
|
||||
}
|
||||
catch
|
||||
{
|
||||
// Just continue
|
||||
}
|
||||
}
|
||||
|
||||
return httpRequestMessage;
|
||||
}
|
||||
}
|
||||
@@ -1,18 +1,17 @@
|
||||
namespace WireMock.Http
|
||||
namespace WireMock.Http;
|
||||
|
||||
/// <summary>
|
||||
/// https://developer.mozilla.org/en-US/docs/Web/HTTP/Methods
|
||||
/// </summary>
|
||||
internal static class HttpRequestMethods
|
||||
{
|
||||
/// <summary>
|
||||
/// https://developer.mozilla.org/en-US/docs/Web/HTTP/Methods
|
||||
/// </summary>
|
||||
internal static class HttpRequestMethods
|
||||
{
|
||||
public const string CONNECT = "CONNECT";
|
||||
public const string DELETE = "DELETE";
|
||||
public const string GET = "GET";
|
||||
public const string HEAD = "HEAD";
|
||||
public const string OPTIONS = "OPTIONS";
|
||||
public const string PATCH = "PATCH";
|
||||
public const string POST = "POST";
|
||||
public const string PUT = "PUT";
|
||||
public const string TRACE = "TRACE";
|
||||
}
|
||||
public const string CONNECT = "CONNECT";
|
||||
public const string DELETE = "DELETE";
|
||||
public const string GET = "GET";
|
||||
public const string HEAD = "HEAD";
|
||||
public const string OPTIONS = "OPTIONS";
|
||||
public const string PATCH = "PATCH";
|
||||
public const string POST = "POST";
|
||||
public const string PUT = "PUT";
|
||||
public const string TRACE = "TRACE";
|
||||
}
|
||||
@@ -1,25 +1,23 @@
|
||||
using System.Net.Http;
|
||||
using System.Net.Http;
|
||||
using System.Net.Http.Headers;
|
||||
using JetBrains.Annotations;
|
||||
using Stef.Validation;
|
||||
|
||||
namespace WireMock.Http
|
||||
{
|
||||
internal static class StringContentHelper
|
||||
{
|
||||
/// <summary>
|
||||
/// Creates a StringContent object.
|
||||
/// </summary>
|
||||
/// <param name="content">The string content (cannot be null)</param>
|
||||
/// <param name="contentType">The ContentType (can be null)</param>
|
||||
/// <returns>StringContent</returns>
|
||||
internal static StringContent Create([NotNull] string content, [CanBeNull] MediaTypeHeaderValue contentType)
|
||||
{
|
||||
Guard.NotNull(content, nameof(content));
|
||||
namespace WireMock.Http;
|
||||
|
||||
var stringContent = new StringContent(content);
|
||||
stringContent.Headers.ContentType = contentType;
|
||||
return stringContent;
|
||||
}
|
||||
internal static class StringContentHelper
|
||||
{
|
||||
/// <summary>
|
||||
/// Creates a StringContent object.
|
||||
/// </summary>
|
||||
/// <param name="content">The string content (cannot be null)</param>
|
||||
/// <param name="contentType">The ContentType (can be null)</param>
|
||||
/// <returns>StringContent</returns>
|
||||
internal static StringContent Create(string content, MediaTypeHeaderValue? contentType)
|
||||
{
|
||||
Guard.NotNull(content);
|
||||
|
||||
var stringContent = new StringContent(content);
|
||||
stringContent.Headers.ContentType = contentType;
|
||||
return stringContent;
|
||||
}
|
||||
}
|
||||
@@ -3,7 +3,7 @@ using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Net.Http;
|
||||
using System.Threading.Tasks;
|
||||
using JetBrains.Annotations;
|
||||
using Stef.Validation;
|
||||
using WireMock.Models;
|
||||
using WireMock.Settings;
|
||||
using WireMock.Transformers;
|
||||
@@ -11,75 +11,73 @@ using WireMock.Transformers.Handlebars;
|
||||
using WireMock.Transformers.Scriban;
|
||||
using WireMock.Types;
|
||||
using WireMock.Util;
|
||||
using Stef.Validation;
|
||||
|
||||
namespace WireMock.Http
|
||||
namespace WireMock.Http;
|
||||
|
||||
internal class WebhookSender
|
||||
{
|
||||
internal class WebhookSender
|
||||
private const string ClientIp = "::1";
|
||||
|
||||
private readonly WireMockServerSettings _settings;
|
||||
|
||||
public WebhookSender(WireMockServerSettings settings)
|
||||
{
|
||||
private const string ClientIp = "::1";
|
||||
_settings = Guard.NotNull(settings);
|
||||
}
|
||||
|
||||
private readonly WireMockServerSettings _settings;
|
||||
public Task<HttpResponseMessage> SendAsync(HttpClient client, IWebhookRequest request, IRequestMessage originalRequestMessage, IResponseMessage originalResponseMessage)
|
||||
{
|
||||
Guard.NotNull(client);
|
||||
Guard.NotNull(request);
|
||||
Guard.NotNull(originalRequestMessage);
|
||||
Guard.NotNull(originalResponseMessage);
|
||||
|
||||
public WebhookSender(WireMockServerSettings settings)
|
||||
IBodyData? bodyData;
|
||||
IDictionary<string, WireMockList<string>>? headers;
|
||||
if (request.UseTransformer == true)
|
||||
{
|
||||
_settings = settings ?? throw new ArgumentNullException(nameof(settings));
|
||||
}
|
||||
|
||||
public Task<HttpResponseMessage> SendAsync(HttpClient client, IWebhookRequest request, IRequestMessage originalRequestMessage, IResponseMessage originalResponseMessage)
|
||||
{
|
||||
Guard.NotNull(client);
|
||||
Guard.NotNull(request);
|
||||
Guard.NotNull(originalRequestMessage);
|
||||
Guard.NotNull(originalResponseMessage);
|
||||
|
||||
IBodyData? bodyData;
|
||||
IDictionary<string, WireMockList<string>>? headers;
|
||||
if (request.UseTransformer == true)
|
||||
ITransformer responseMessageTransformer;
|
||||
switch (request.TransformerType)
|
||||
{
|
||||
ITransformer responseMessageTransformer;
|
||||
switch (request.TransformerType)
|
||||
{
|
||||
case TransformerType.Handlebars:
|
||||
var factoryHandlebars = new HandlebarsContextFactory(_settings.FileSystemHandler, _settings.HandlebarsRegistrationCallback);
|
||||
responseMessageTransformer = new Transformer(factoryHandlebars);
|
||||
break;
|
||||
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;
|
||||
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, request.TransformerReplaceNodeOptions);
|
||||
}
|
||||
else
|
||||
{
|
||||
bodyData = request.BodyData;
|
||||
headers = request.Headers;
|
||||
default:
|
||||
throw new NotImplementedException($"TransformerType '{request.TransformerType}' is not supported.");
|
||||
}
|
||||
|
||||
// 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);
|
||||
(bodyData, headers) = responseMessageTransformer.Transform(originalRequestMessage, originalResponseMessage, request.BodyData, request.Headers, request.TransformerReplaceNodeOptions);
|
||||
}
|
||||
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);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user