mirror of
https://github.com/wiremock/WireMock.Net.git
synced 2026-04-23 01:08:49 +02:00
SaveUnmatchedRequests (#703)
This commit is contained in:
@@ -1,4 +1,5 @@
|
|||||||
<wpf:ResourceDictionary xml:space="preserve" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:s="clr-namespace:System;assembly=mscorlib" xmlns:ss="urn:shemas-jetbrains-com:settings-storage-xaml" xmlns:wpf="http://schemas.microsoft.com/winfx/2006/xaml/presentation">
|
<wpf:ResourceDictionary xml:space="preserve" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:s="clr-namespace:System;assembly=mscorlib" xmlns:ss="urn:shemas-jetbrains-com:settings-storage-xaml" xmlns:wpf="http://schemas.microsoft.com/winfx/2006/xaml/presentation">
|
||||||
|
<s:String x:Key="/Default/CodeStyle/Naming/CSharpNaming/Abbreviations/=AD/@EntryIndexedValue">AD</s:String>
|
||||||
<s:String x:Key="/Default/CodeStyle/Naming/CSharpNaming/Abbreviations/=CS/@EntryIndexedValue">CS</s:String>
|
<s:String x:Key="/Default/CodeStyle/Naming/CSharpNaming/Abbreviations/=CS/@EntryIndexedValue">CS</s:String>
|
||||||
<s:String x:Key="/Default/CodeStyle/Naming/CSharpNaming/Abbreviations/=ID/@EntryIndexedValue">ID</s:String>
|
<s:String x:Key="/Default/CodeStyle/Naming/CSharpNaming/Abbreviations/=ID/@EntryIndexedValue">ID</s:String>
|
||||||
<s:String x:Key="/Default/CodeStyle/Naming/CSharpNaming/Abbreviations/=IP/@EntryIndexedValue">IP</s:String>
|
<s:String x:Key="/Default/CodeStyle/Naming/CSharpNaming/Abbreviations/=IP/@EntryIndexedValue">IP</s:String>
|
||||||
|
|||||||
@@ -7,6 +7,7 @@ namespace WireMock.Net.ConsoleApplication
|
|||||||
internal class CustomFileSystemFileHandler : IFileSystemHandler
|
internal class CustomFileSystemFileHandler : IFileSystemHandler
|
||||||
{
|
{
|
||||||
private static readonly string AdminMappingsFolder = Path.Combine("__admin", "mappings");
|
private static readonly string AdminMappingsFolder = Path.Combine("__admin", "mappings");
|
||||||
|
private static readonly string UnmatchedRequestsFolder = Path.Combine("requests", "unmatched");
|
||||||
|
|
||||||
/// <inheritdoc cref="IFileSystemHandler.FolderExists"/>
|
/// <inheritdoc cref="IFileSystemHandler.FolderExists"/>
|
||||||
public bool FolderExists(string path)
|
public bool FolderExists(string path)
|
||||||
@@ -86,6 +87,21 @@ namespace WireMock.Net.ConsoleApplication
|
|||||||
return File.ReadAllText(path);
|
return File.ReadAllText(path);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <inheritdoc cref="IFileSystemHandler.GetUnmatchedRequestsFolder"/>
|
||||||
|
public string GetUnmatchedRequestsFolder()
|
||||||
|
{
|
||||||
|
return Path.Combine(@"c:\temp-wiremock", UnmatchedRequestsFolder);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <inheritdoc cref="IFileSystemHandler.WriteUnmatchedRequest"/>
|
||||||
|
public void WriteUnmatchedRequest(string filename, string text)
|
||||||
|
{
|
||||||
|
var folder = GetUnmatchedRequestsFolder();
|
||||||
|
Directory.CreateDirectory(folder);
|
||||||
|
|
||||||
|
File.WriteAllText(Path.Combine(folder, filename), text);
|
||||||
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Adjusts the path to the MappingFolder.
|
/// Adjusts the path to the MappingFolder.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
|||||||
@@ -23,7 +23,8 @@ namespace WireMock.Net.OpenApiParser.ConsoleApp
|
|||||||
ReadStaticMappings = false,
|
ReadStaticMappings = false,
|
||||||
WatchStaticMappings = false,
|
WatchStaticMappings = false,
|
||||||
WatchStaticMappingsInSubdirectories = false,
|
WatchStaticMappingsInSubdirectories = false,
|
||||||
Logger = new WireMockConsoleLogger()
|
Logger = new WireMockConsoleLogger(),
|
||||||
|
SaveUnmatchedRequests = true
|
||||||
});
|
});
|
||||||
Console.WriteLine("WireMockServer listening at {0}", string.Join(",", server.Urls));
|
Console.WriteLine("WireMockServer listening at {0}", string.Join(",", server.Urls));
|
||||||
|
|
||||||
|
|||||||
@@ -1,4 +1,7 @@
|
|||||||
namespace WireMock.Admin.Settings
|
using System.Text.RegularExpressions;
|
||||||
|
using WireMock.Handlers;
|
||||||
|
|
||||||
|
namespace WireMock.Admin.Settings
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Settings
|
/// Settings
|
||||||
@@ -40,5 +43,15 @@
|
|||||||
/// Throw an exception when the Matcher fails because of invalid input. (default set to false).
|
/// Throw an exception when the Matcher fails because of invalid input. (default set to false).
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public bool? ThrowExceptionWhenMatcherFails { get; set; }
|
public bool? ThrowExceptionWhenMatcherFails { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Use the RegexExtended instead of the default <see cref="Regex"/>. (default set to true).
|
||||||
|
/// </summary>
|
||||||
|
public bool? UseRegexExtended { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Save unmatched requests to a file using the <see cref="IFileSystemHandler"/>. (default set to false).
|
||||||
|
/// </summary>
|
||||||
|
public bool? SaveUnmatchedRequests { get; set; }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -96,5 +96,18 @@ namespace WireMock.Handlers
|
|||||||
/// <param name="filename">The filename.</param>
|
/// <param name="filename">The filename.</param>
|
||||||
/// <returns>The file content as a string.</returns>
|
/// <returns>The file content as a string.</returns>
|
||||||
string ReadFileAsString([NotNull] string filename);
|
string ReadFileAsString([NotNull] string filename);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gets the folder where the unmatched requests should be stored. For local file system, this would be `{CurrentFolder}/requests/unmatched`.
|
||||||
|
/// </summary>
|
||||||
|
/// <returns>The folder name.</returns>
|
||||||
|
string GetUnmatchedRequestsFolder();
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Write a unmatched request to the Unmatched RequestsFolder.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="filename">The filename.</param>
|
||||||
|
/// <param name="text">The text.</param>
|
||||||
|
void WriteUnmatchedRequest([NotNull] string filename, [NotNull] string text);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -11,6 +11,7 @@ namespace WireMock.Handlers
|
|||||||
public class LocalFileSystemHandler : IFileSystemHandler
|
public class LocalFileSystemHandler : IFileSystemHandler
|
||||||
{
|
{
|
||||||
private static readonly string AdminMappingsFolder = Path.Combine("__admin", "mappings");
|
private static readonly string AdminMappingsFolder = Path.Combine("__admin", "mappings");
|
||||||
|
private static readonly string UnmatchedRequestsFolder = Path.Combine("requests", "unmatched");
|
||||||
|
|
||||||
private readonly string _rootFolder;
|
private readonly string _rootFolder;
|
||||||
|
|
||||||
@@ -31,7 +32,7 @@ namespace WireMock.Handlers
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc cref="IFileSystemHandler.FolderExists"/>
|
/// <inheritdoc cref="IFileSystemHandler.FolderExists"/>
|
||||||
public bool FolderExists(string path)
|
public virtual bool FolderExists(string path)
|
||||||
{
|
{
|
||||||
Check.NotNullOrEmpty(path, nameof(path));
|
Check.NotNullOrEmpty(path, nameof(path));
|
||||||
|
|
||||||
@@ -39,7 +40,7 @@ namespace WireMock.Handlers
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc cref="IFileSystemHandler.CreateFolder"/>
|
/// <inheritdoc cref="IFileSystemHandler.CreateFolder"/>
|
||||||
public void CreateFolder(string path)
|
public virtual void CreateFolder(string path)
|
||||||
{
|
{
|
||||||
Check.NotNullOrEmpty(path, nameof(path));
|
Check.NotNullOrEmpty(path, nameof(path));
|
||||||
|
|
||||||
@@ -47,7 +48,7 @@ namespace WireMock.Handlers
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc cref="IFileSystemHandler.EnumerateFiles"/>
|
/// <inheritdoc cref="IFileSystemHandler.EnumerateFiles"/>
|
||||||
public IEnumerable<string> EnumerateFiles(string path, bool includeSubdirectories)
|
public virtual IEnumerable<string> EnumerateFiles(string path, bool includeSubdirectories)
|
||||||
{
|
{
|
||||||
Check.NotNullOrEmpty(path, nameof(path));
|
Check.NotNullOrEmpty(path, nameof(path));
|
||||||
|
|
||||||
@@ -55,13 +56,13 @@ namespace WireMock.Handlers
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc cref="IFileSystemHandler.GetMappingFolder"/>
|
/// <inheritdoc cref="IFileSystemHandler.GetMappingFolder"/>
|
||||||
public string GetMappingFolder()
|
public virtual string GetMappingFolder()
|
||||||
{
|
{
|
||||||
return Path.Combine(_rootFolder, AdminMappingsFolder);
|
return Path.Combine(_rootFolder, AdminMappingsFolder);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc cref="IFileSystemHandler.ReadMappingFile"/>
|
/// <inheritdoc cref="IFileSystemHandler.ReadMappingFile"/>
|
||||||
public string ReadMappingFile(string path)
|
public virtual string ReadMappingFile(string path)
|
||||||
{
|
{
|
||||||
Check.NotNullOrEmpty(path, nameof(path));
|
Check.NotNullOrEmpty(path, nameof(path));
|
||||||
|
|
||||||
@@ -69,7 +70,7 @@ namespace WireMock.Handlers
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc cref="IFileSystemHandler.WriteMappingFile(string, string)"/>
|
/// <inheritdoc cref="IFileSystemHandler.WriteMappingFile(string, string)"/>
|
||||||
public void WriteMappingFile(string path, string text)
|
public virtual void WriteMappingFile(string path, string text)
|
||||||
{
|
{
|
||||||
Check.NotNullOrEmpty(path, nameof(path));
|
Check.NotNullOrEmpty(path, nameof(path));
|
||||||
Check.NotNull(text, nameof(text));
|
Check.NotNull(text, nameof(text));
|
||||||
@@ -78,7 +79,7 @@ namespace WireMock.Handlers
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc cref="IFileSystemHandler.ReadResponseBodyAsFile"/>
|
/// <inheritdoc cref="IFileSystemHandler.ReadResponseBodyAsFile"/>
|
||||||
public byte[] ReadResponseBodyAsFile(string path)
|
public virtual byte[] ReadResponseBodyAsFile(string path)
|
||||||
{
|
{
|
||||||
Check.NotNullOrEmpty(path, nameof(path));
|
Check.NotNullOrEmpty(path, nameof(path));
|
||||||
path = PathUtils.CleanPath(path);
|
path = PathUtils.CleanPath(path);
|
||||||
@@ -88,7 +89,7 @@ namespace WireMock.Handlers
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc cref="IFileSystemHandler.ReadResponseBodyAsString"/>
|
/// <inheritdoc cref="IFileSystemHandler.ReadResponseBodyAsString"/>
|
||||||
public string ReadResponseBodyAsString(string path)
|
public virtual string ReadResponseBodyAsString(string path)
|
||||||
{
|
{
|
||||||
Check.NotNullOrEmpty(path, nameof(path));
|
Check.NotNullOrEmpty(path, nameof(path));
|
||||||
path = PathUtils.CleanPath(path);
|
path = PathUtils.CleanPath(path);
|
||||||
@@ -98,42 +99,63 @@ namespace WireMock.Handlers
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc cref="IFileSystemHandler.FileExists"/>
|
/// <inheritdoc cref="IFileSystemHandler.FileExists"/>
|
||||||
public bool FileExists(string filename)
|
public virtual bool FileExists(string filename)
|
||||||
{
|
{
|
||||||
Check.NotNullOrEmpty(filename, nameof(filename));
|
Check.NotNullOrEmpty(filename, nameof(filename));
|
||||||
|
|
||||||
return File.Exists(AdjustPath(filename));
|
return File.Exists(AdjustPathForMappingFolder(filename));
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc cref="IFileSystemHandler.WriteFile(string, byte[])"/>
|
/// <inheritdoc cref="IFileSystemHandler.WriteFile(string, byte[])"/>
|
||||||
public void WriteFile(string filename, byte[] bytes)
|
public virtual void WriteFile(string filename, byte[] bytes)
|
||||||
{
|
{
|
||||||
Check.NotNullOrEmpty(filename, nameof(filename));
|
Check.NotNullOrEmpty(filename, nameof(filename));
|
||||||
Check.NotNull(bytes, nameof(bytes));
|
Check.NotNull(bytes, nameof(bytes));
|
||||||
|
|
||||||
File.WriteAllBytes(AdjustPath(filename), bytes);
|
File.WriteAllBytes(AdjustPathForMappingFolder(filename), bytes);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc cref="IFileSystemHandler.DeleteFile"/>
|
/// <inheritdoc cref="IFileSystemHandler.DeleteFile"/>
|
||||||
public void DeleteFile(string filename)
|
public virtual void DeleteFile(string filename)
|
||||||
{
|
{
|
||||||
Check.NotNullOrEmpty(filename, nameof(filename));
|
Check.NotNullOrEmpty(filename, nameof(filename));
|
||||||
|
|
||||||
File.Delete(AdjustPath(filename));
|
File.Delete(AdjustPathForMappingFolder(filename));
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc cref="IFileSystemHandler.ReadFile"/>
|
/// <inheritdoc cref="IFileSystemHandler.ReadFile"/>
|
||||||
public byte[] ReadFile(string filename)
|
public virtual byte[] ReadFile(string filename)
|
||||||
{
|
{
|
||||||
Check.NotNullOrEmpty(filename, nameof(filename));
|
Check.NotNullOrEmpty(filename, nameof(filename));
|
||||||
|
|
||||||
return File.ReadAllBytes(AdjustPath(filename));
|
return File.ReadAllBytes(AdjustPathForMappingFolder(filename));
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <inheritdoc cref="IFileSystemHandler.ReadFileAsString"/>
|
/// <inheritdoc cref="IFileSystemHandler.ReadFileAsString"/>
|
||||||
public string ReadFileAsString(string filename)
|
public virtual string ReadFileAsString(string filename)
|
||||||
{
|
{
|
||||||
return File.ReadAllText(AdjustPath(Check.NotNullOrEmpty(filename, nameof(filename))));
|
return File.ReadAllText(AdjustPathForMappingFolder(Check.NotNullOrEmpty(filename, nameof(filename))));
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <inheritdoc cref="IFileSystemHandler.GetUnmatchedRequestsFolder"/>
|
||||||
|
public virtual string GetUnmatchedRequestsFolder()
|
||||||
|
{
|
||||||
|
return Path.Combine(_rootFolder, UnmatchedRequestsFolder);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <inheritdoc cref="IFileSystemHandler.WriteUnmatchedRequest"/>
|
||||||
|
public virtual void WriteUnmatchedRequest(string filename, string text)
|
||||||
|
{
|
||||||
|
Check.NotNullOrEmpty(filename, nameof(filename));
|
||||||
|
Check.NotNull(text, nameof(text));
|
||||||
|
|
||||||
|
var folder = GetUnmatchedRequestsFolder();
|
||||||
|
if (!FolderExists(folder))
|
||||||
|
{
|
||||||
|
CreateFolder(folder);
|
||||||
|
}
|
||||||
|
|
||||||
|
File.WriteAllText(Path.Combine(folder, filename), text);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@@ -141,7 +163,7 @@ namespace WireMock.Handlers
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="filename">The path.</param>
|
/// <param name="filename">The path.</param>
|
||||||
/// <returns>Adjusted path</returns>
|
/// <returns>Adjusted path</returns>
|
||||||
private string AdjustPath(string filename)
|
private string AdjustPathForMappingFolder(string filename)
|
||||||
{
|
{
|
||||||
return Path.Combine(GetMappingFolder(), filename);
|
return Path.Combine(GetMappingFolder(), filename);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ using WireMock.Handlers;
|
|||||||
using WireMock.Logging;
|
using WireMock.Logging;
|
||||||
using WireMock.Matchers;
|
using WireMock.Matchers;
|
||||||
using WireMock.Util;
|
using WireMock.Util;
|
||||||
|
using JetBrains.Annotations;
|
||||||
#if !USE_ASPNETCORE
|
#if !USE_ASPNETCORE
|
||||||
using Owin;
|
using Owin;
|
||||||
#else
|
#else
|
||||||
@@ -64,5 +65,7 @@ namespace WireMock.Owin
|
|||||||
string X509CertificatePassword { get; set; }
|
string X509CertificatePassword { get; set; }
|
||||||
|
|
||||||
bool CustomCertificateDefined { get; }
|
bool CustomCertificateDefined { get; }
|
||||||
|
|
||||||
|
bool? SaveUnmatchedRequests { get; set; }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
@@ -23,7 +23,7 @@ namespace WireMock.Owin.Mappers
|
|||||||
/// <inheritdoc cref="IOwinRequestMapper.MapAsync"/>
|
/// <inheritdoc cref="IOwinRequestMapper.MapAsync"/>
|
||||||
public async Task<RequestMessage> MapAsync(IRequest request, IWireMockMiddlewareOptions options)
|
public async Task<RequestMessage> MapAsync(IRequest request, IWireMockMiddlewareOptions options)
|
||||||
{
|
{
|
||||||
(UrlDetails urldetails, string clientIP) = ParseRequest(request);
|
var (urlDetails, clientIP) = ParseRequest(request);
|
||||||
|
|
||||||
string method = request.Method;
|
string method = request.Method;
|
||||||
|
|
||||||
@@ -68,7 +68,7 @@ namespace WireMock.Owin.Mappers
|
|||||||
body = await BodyParser.Parse(bodyParserSettings);
|
body = await BodyParser.Parse(bodyParserSettings);
|
||||||
}
|
}
|
||||||
|
|
||||||
return new RequestMessage(urldetails, method, clientIP, body, headers, cookies) { DateTime = DateTime.UtcNow };
|
return new RequestMessage(urlDetails, method, clientIP, body, headers, cookies) { DateTime = DateTime.UtcNow };
|
||||||
}
|
}
|
||||||
|
|
||||||
private (UrlDetails UrlDetails, string ClientIP) ParseRequest(IRequest request)
|
private (UrlDetails UrlDetails, string ClientIP) ParseRequest(IRequest request)
|
||||||
|
|||||||
@@ -2,6 +2,7 @@ using System;
|
|||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using WireMock.Logging;
|
using WireMock.Logging;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
using HandlebarsDotNet.Helpers.Utils;
|
||||||
using WireMock.Matchers;
|
using WireMock.Matchers;
|
||||||
using WireMock.Http;
|
using WireMock.Http;
|
||||||
using WireMock.Owin.Mappers;
|
using WireMock.Owin.Mappers;
|
||||||
@@ -35,28 +36,18 @@ namespace WireMock.Owin
|
|||||||
#if !USE_ASPNETCORE
|
#if !USE_ASPNETCORE
|
||||||
public WireMockMiddleware(Next next, IWireMockMiddlewareOptions options, IOwinRequestMapper requestMapper, IOwinResponseMapper responseMapper, IMappingMatcher mappingMatcher) : base(next)
|
public WireMockMiddleware(Next next, IWireMockMiddlewareOptions options, IOwinRequestMapper requestMapper, IOwinResponseMapper responseMapper, IMappingMatcher mappingMatcher) : base(next)
|
||||||
{
|
{
|
||||||
Check.NotNull(options, nameof(options));
|
_options = Check.NotNull(options, nameof(options));
|
||||||
Check.NotNull(requestMapper, nameof(requestMapper));
|
_requestMapper = Check.NotNull(requestMapper, nameof(requestMapper));
|
||||||
Check.NotNull(responseMapper, nameof(responseMapper));
|
_responseMapper = Check.NotNull(responseMapper, nameof(responseMapper));
|
||||||
Check.NotNull(mappingMatcher, nameof(mappingMatcher));
|
_mappingMatcher = Check.NotNull(mappingMatcher, nameof(mappingMatcher));
|
||||||
|
|
||||||
_options = options;
|
|
||||||
_requestMapper = requestMapper;
|
|
||||||
_responseMapper = responseMapper;
|
|
||||||
_mappingMatcher = mappingMatcher;
|
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
public WireMockMiddleware(Next next, IWireMockMiddlewareOptions options, IOwinRequestMapper requestMapper, IOwinResponseMapper responseMapper, IMappingMatcher mappingMatcher)
|
public WireMockMiddleware(Next next, IWireMockMiddlewareOptions options, IOwinRequestMapper requestMapper, IOwinResponseMapper responseMapper, IMappingMatcher mappingMatcher)
|
||||||
{
|
{
|
||||||
Check.NotNull(options, nameof(options));
|
_options = Check.NotNull(options, nameof(options));
|
||||||
Check.NotNull(requestMapper, nameof(requestMapper));
|
_requestMapper = Check.NotNull(requestMapper, nameof(requestMapper));
|
||||||
Check.NotNull(responseMapper, nameof(responseMapper));
|
_responseMapper = Check.NotNull(responseMapper, nameof(responseMapper));
|
||||||
Check.NotNull(mappingMatcher, nameof(mappingMatcher));
|
_mappingMatcher = Check.NotNull(mappingMatcher, nameof(mappingMatcher));
|
||||||
|
|
||||||
_options = options;
|
|
||||||
_requestMapper = requestMapper;
|
|
||||||
_responseMapper = responseMapper;
|
|
||||||
_mappingMatcher = mappingMatcher;
|
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
@@ -70,20 +61,18 @@ namespace WireMock.Owin
|
|||||||
{
|
{
|
||||||
lock (_lock)
|
lock (_lock)
|
||||||
{
|
{
|
||||||
return InvokeInternal(ctx);
|
return InvokeInternalAsync(ctx);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
|
||||||
{
|
return InvokeInternalAsync(ctx);
|
||||||
return InvokeInternal(ctx);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private async Task InvokeInternal(IContext ctx)
|
private async Task InvokeInternalAsync(IContext ctx)
|
||||||
{
|
{
|
||||||
var request = await _requestMapper.MapAsync(ctx.Request, _options);
|
var request = await _requestMapper.MapAsync(ctx.Request, _options);
|
||||||
|
|
||||||
bool logRequest = false;
|
var logRequest = false;
|
||||||
ResponseMessage response = null;
|
ResponseMessage response = null;
|
||||||
(MappingMatcherResult Match, MappingMatcherResult Partial) result = (null, null);
|
(MappingMatcherResult Match, MappingMatcherResult Partial) result = (null, null);
|
||||||
try
|
try
|
||||||
@@ -185,6 +174,19 @@ namespace WireMock.Owin
|
|||||||
|
|
||||||
LogRequest(log, logRequest);
|
LogRequest(log, logRequest);
|
||||||
|
|
||||||
|
try
|
||||||
|
{
|
||||||
|
if (_options.SaveUnmatchedRequests == true && result.Match?.RequestMatchResult.IsPerfectMatch != true)
|
||||||
|
{
|
||||||
|
var filename = $"{log.Guid}.LogEntry.json";
|
||||||
|
_options.FileSystemHandler?.WriteUnmatchedRequest(filename, Util.JsonUtils.Serialize(log));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch
|
||||||
|
{
|
||||||
|
// Empty catch
|
||||||
|
}
|
||||||
|
|
||||||
await _responseMapper.MapAsync(response, ctx.Response);
|
await _responseMapper.MapAsync(response, ctx.Response);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Concurrent;
|
using System.Collections.Concurrent;
|
||||||
using WireMock.Handlers;
|
using WireMock.Handlers;
|
||||||
using WireMock.Logging;
|
using WireMock.Logging;
|
||||||
@@ -78,5 +78,8 @@ namespace WireMock.Owin
|
|||||||
public bool CustomCertificateDefined =>
|
public bool CustomCertificateDefined =>
|
||||||
!string.IsNullOrEmpty(X509StoreName) && !string.IsNullOrEmpty(X509StoreLocation) ||
|
!string.IsNullOrEmpty(X509StoreName) && !string.IsNullOrEmpty(X509StoreLocation) ||
|
||||||
!string.IsNullOrEmpty(X509CertificateFilePath) && !string.IsNullOrEmpty(X509CertificatePassword);
|
!string.IsNullOrEmpty(X509CertificateFilePath) && !string.IsNullOrEmpty(X509CertificatePassword);
|
||||||
|
|
||||||
|
/// <inheritdoc cref="IWireMockMiddlewareOptions.SaveUnmatchedRequests"/>
|
||||||
|
public bool? SaveUnmatchedRequests { get; set; }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
using Newtonsoft.Json;
|
using Newtonsoft.Json;
|
||||||
|
|
||||||
namespace WireMock.Serialization
|
namespace WireMock.Serialization
|
||||||
{
|
{
|
||||||
@@ -15,5 +15,10 @@ namespace WireMock.Serialization
|
|||||||
Formatting = Formatting.Indented,
|
Formatting = Formatting.Indented,
|
||||||
NullValueHandling = NullValueHandling.Include
|
NullValueHandling = NullValueHandling.Include
|
||||||
};
|
};
|
||||||
|
|
||||||
|
public static readonly JsonSerializerSettings JsonDeserializerSettingsWithDateParsingNone = new JsonSerializerSettings
|
||||||
|
{
|
||||||
|
DateParseHandling = DateParseHandling.None
|
||||||
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -291,7 +291,9 @@ namespace WireMock.Server
|
|||||||
GlobalProcessingDelay = (int?)_options.RequestProcessingDelay?.TotalMilliseconds,
|
GlobalProcessingDelay = (int?)_options.RequestProcessingDelay?.TotalMilliseconds,
|
||||||
AllowBodyForAllHttpMethods = _settings.AllowBodyForAllHttpMethods,
|
AllowBodyForAllHttpMethods = _settings.AllowBodyForAllHttpMethods,
|
||||||
HandleRequestsSynchronously = _settings.HandleRequestsSynchronously,
|
HandleRequestsSynchronously = _settings.HandleRequestsSynchronously,
|
||||||
ThrowExceptionWhenMatcherFails = _settings.ThrowExceptionWhenMatcherFails
|
ThrowExceptionWhenMatcherFails = _settings.ThrowExceptionWhenMatcherFails,
|
||||||
|
UseRegexExtended = _settings.UseRegexExtended,
|
||||||
|
SaveUnmatchedRequests = _settings.SaveUnmatchedRequests
|
||||||
};
|
};
|
||||||
|
|
||||||
return ToJson(model);
|
return ToJson(model);
|
||||||
@@ -302,31 +304,16 @@ namespace WireMock.Server
|
|||||||
var settings = DeserializeObject<SettingsModel>(requestMessage);
|
var settings = DeserializeObject<SettingsModel>(requestMessage);
|
||||||
_options.MaxRequestLogCount = settings.MaxRequestLogCount;
|
_options.MaxRequestLogCount = settings.MaxRequestLogCount;
|
||||||
_options.RequestLogExpirationDuration = settings.RequestLogExpirationDuration;
|
_options.RequestLogExpirationDuration = settings.RequestLogExpirationDuration;
|
||||||
|
_options.AllowPartialMapping = settings.AllowPartialMapping;
|
||||||
if (settings.AllowPartialMapping != null)
|
|
||||||
{
|
|
||||||
_options.AllowPartialMapping = settings.AllowPartialMapping.Value;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (settings.GlobalProcessingDelay != null)
|
if (settings.GlobalProcessingDelay != null)
|
||||||
{
|
{
|
||||||
_options.RequestProcessingDelay = TimeSpan.FromMilliseconds(settings.GlobalProcessingDelay.Value);
|
_options.RequestProcessingDelay = TimeSpan.FromMilliseconds(settings.GlobalProcessingDelay.Value);
|
||||||
}
|
}
|
||||||
|
_options.AllowBodyForAllHttpMethods = settings.AllowBodyForAllHttpMethods;
|
||||||
if (settings.AllowBodyForAllHttpMethods != null)
|
_options.HandleRequestsSynchronously = settings.HandleRequestsSynchronously;
|
||||||
{
|
_settings.ThrowExceptionWhenMatcherFails = settings.ThrowExceptionWhenMatcherFails;
|
||||||
_options.AllowBodyForAllHttpMethods = settings.AllowBodyForAllHttpMethods.Value;
|
_settings.UseRegexExtended = settings.UseRegexExtended;
|
||||||
}
|
_settings.SaveUnmatchedRequests = settings.SaveUnmatchedRequests;
|
||||||
|
|
||||||
if (settings.HandleRequestsSynchronously != null)
|
|
||||||
{
|
|
||||||
_options.HandleRequestsSynchronously = settings.HandleRequestsSynchronously.Value;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (settings.ThrowExceptionWhenMatcherFails != null)
|
|
||||||
{
|
|
||||||
_settings.ThrowExceptionWhenMatcherFails = settings.ThrowExceptionWhenMatcherFails.Value;
|
|
||||||
}
|
|
||||||
|
|
||||||
return ResponseMessageBuilder.Create("Settings updated");
|
return ResponseMessageBuilder.Create("Settings updated");
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -226,6 +226,7 @@ namespace WireMock.Server
|
|||||||
_options.Logger = _settings.Logger;
|
_options.Logger = _settings.Logger;
|
||||||
_options.DisableJsonBodyParsing = _settings.DisableJsonBodyParsing;
|
_options.DisableJsonBodyParsing = _settings.DisableJsonBodyParsing;
|
||||||
_options.HandleRequestsSynchronously = settings.HandleRequestsSynchronously;
|
_options.HandleRequestsSynchronously = settings.HandleRequestsSynchronously;
|
||||||
|
_options.SaveUnmatchedRequests = settings.SaveUnmatchedRequests;
|
||||||
|
|
||||||
if (settings.CustomCertificateDefined)
|
if (settings.CustomCertificateDefined)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -213,15 +213,21 @@ namespace WireMock.Settings
|
|||||||
bool CustomCertificateDefined { get; }
|
bool CustomCertificateDefined { get; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Defines the global IWebhookSettingsto use
|
/// Defines the global IWebhookSettings to use.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[PublicAPI]
|
[PublicAPI]
|
||||||
IWebhookSettings WebhookSettings { get; set; }
|
IWebhookSettings WebhookSettings { get; set; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Use the <see cref="RegexExtended"/> instead of the default <see cref="Regex"/>.
|
/// Use the <see cref="RegexExtended"/> instead of the default <see cref="Regex"/> (default set to true).
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[PublicAPI]
|
[PublicAPI]
|
||||||
bool? UseRegexExtended { get; }
|
bool? UseRegexExtended { get; set; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Save unmatched requests to a file using the <see cref="IFileSystemHandler"/> (default set to false).
|
||||||
|
/// </summary>
|
||||||
|
[PublicAPI]
|
||||||
|
bool? SaveUnmatchedRequests { get; set; }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -20,7 +20,6 @@ namespace WireMock.Settings
|
|||||||
public int? Port { get; set; }
|
public int? Port { get; set; }
|
||||||
|
|
||||||
/// <inheritdoc cref="IWireMockServerSettings.UseSSL"/>
|
/// <inheritdoc cref="IWireMockServerSettings.UseSSL"/>
|
||||||
// ReSharper disable once InconsistentNaming
|
|
||||||
[PublicAPI]
|
[PublicAPI]
|
||||||
public bool? UseSSL { get; set; }
|
public bool? UseSSL { get; set; }
|
||||||
|
|
||||||
@@ -155,5 +154,9 @@ namespace WireMock.Settings
|
|||||||
/// <inheritdoc cref="IWireMockServerSettings.UseRegexExtended"/>
|
/// <inheritdoc cref="IWireMockServerSettings.UseRegexExtended"/>
|
||||||
[PublicAPI]
|
[PublicAPI]
|
||||||
public bool? UseRegexExtended { get; set; } = true;
|
public bool? UseRegexExtended { get; set; } = true;
|
||||||
|
|
||||||
|
/// <inheritdoc cref="IWireMockServerSettings.SaveUnmatchedRequests"/>
|
||||||
|
[PublicAPI]
|
||||||
|
public bool? SaveUnmatchedRequests { get; set; }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -49,7 +49,8 @@ namespace WireMock.Settings
|
|||||||
DisableJsonBodyParsing = parser.GetBoolValue("DisableJsonBodyParsing"),
|
DisableJsonBodyParsing = parser.GetBoolValue("DisableJsonBodyParsing"),
|
||||||
HandleRequestsSynchronously = parser.GetBoolValue("HandleRequestsSynchronously"),
|
HandleRequestsSynchronously = parser.GetBoolValue("HandleRequestsSynchronously"),
|
||||||
ThrowExceptionWhenMatcherFails = parser.GetBoolValue("ThrowExceptionWhenMatcherFails"),
|
ThrowExceptionWhenMatcherFails = parser.GetBoolValue("ThrowExceptionWhenMatcherFails"),
|
||||||
UseRegexExtended = parser.GetBoolValue(nameof(IWireMockServerSettings.UseRegexExtended), true)
|
UseRegexExtended = parser.GetBoolValue(nameof(IWireMockServerSettings.UseRegexExtended), true),
|
||||||
|
SaveUnmatchedRequests = parser.GetBoolValue(nameof(IWireMockServerSettings.SaveUnmatchedRequests))
|
||||||
};
|
};
|
||||||
|
|
||||||
if (logger != null)
|
if (logger != null)
|
||||||
|
|||||||
@@ -1,18 +1,19 @@
|
|||||||
using Newtonsoft.Json;
|
using Newtonsoft.Json;
|
||||||
using Newtonsoft.Json.Linq;
|
using Newtonsoft.Json.Linq;
|
||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Text;
|
using System.Text;
|
||||||
|
using WireMock.Serialization;
|
||||||
|
|
||||||
namespace WireMock.Util
|
namespace WireMock.Util
|
||||||
{
|
{
|
||||||
internal static class JsonUtils
|
internal static class JsonUtils
|
||||||
{
|
{
|
||||||
private static readonly JsonSerializerSettings JsonSerializerSettings = new JsonSerializerSettings
|
public static string Serialize<T>(T value)
|
||||||
{
|
{
|
||||||
DateParseHandling = DateParseHandling.None
|
return JsonConvert.SerializeObject(value, JsonSerializationConstants.JsonSerializerSettingsIncludeNullValues);
|
||||||
};
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Load a Newtonsoft.Json.Linq.JObject from a string that contains JSON.
|
/// Load a Newtonsoft.Json.Linq.JObject from a string that contains JSON.
|
||||||
@@ -22,7 +23,7 @@ namespace WireMock.Util
|
|||||||
/// <returns>A Newtonsoft.Json.Linq.JToken populated from the string that contains JSON.</returns>
|
/// <returns>A Newtonsoft.Json.Linq.JToken populated from the string that contains JSON.</returns>
|
||||||
public static JToken Parse(string json)
|
public static JToken Parse(string json)
|
||||||
{
|
{
|
||||||
return JsonConvert.DeserializeObject<JToken>(json, JsonSerializerSettings);
|
return JsonConvert.DeserializeObject<JToken>(json, JsonSerializationConstants.JsonDeserializerSettingsWithDateParsingNone);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@@ -33,7 +34,7 @@ namespace WireMock.Util
|
|||||||
/// <returns>The deserialized object from the JSON string.</returns>
|
/// <returns>The deserialized object from the JSON string.</returns>
|
||||||
public static object DeserializeObject(string json)
|
public static object DeserializeObject(string json)
|
||||||
{
|
{
|
||||||
return JsonConvert.DeserializeObject(json, JsonSerializerSettings);
|
return JsonConvert.DeserializeObject(json, JsonSerializationConstants.JsonDeserializerSettingsWithDateParsingNone);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@@ -44,7 +45,7 @@ namespace WireMock.Util
|
|||||||
/// <returns>The deserialized object from the JSON string.</returns>
|
/// <returns>The deserialized object from the JSON string.</returns>
|
||||||
public static T DeserializeObject<T>(string json)
|
public static T DeserializeObject<T>(string json)
|
||||||
{
|
{
|
||||||
return JsonConvert.DeserializeObject<T>(json, JsonSerializerSettings);
|
return JsonConvert.DeserializeObject<T>(json, JsonSerializationConstants.JsonDeserializerSettingsWithDateParsingNone);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static T ParseJTokenToObject<T>(object value)
|
public static T ParseJTokenToObject<T>(object value)
|
||||||
|
|||||||
@@ -85,5 +85,22 @@ namespace WireMock.Net.Tests.Handlers
|
|||||||
// Act
|
// Act
|
||||||
Check.ThatCode(() => _sut.DeleteFile(null)).Throws<ArgumentNullException>();
|
Check.ThatCode(() => _sut.DeleteFile(null)).Throws<ArgumentNullException>();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public void LocalFileSystemHandler_GetUnmatchedRequestsFolder()
|
||||||
|
{
|
||||||
|
// Act
|
||||||
|
string result = _sut.GetUnmatchedRequestsFolder();
|
||||||
|
|
||||||
|
// Assert
|
||||||
|
Check.That(result).EndsWith(Path.Combine("requests", "unmatched"));
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public void LocalFileSystemHandler_WriteUnmatchedRequest()
|
||||||
|
{
|
||||||
|
// Act
|
||||||
|
Check.ThatCode(() => _sut.WriteUnmatchedRequest(null, null)).Throws<ArgumentNullException>();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Reference in New Issue
Block a user