Files
WireMock.Net/src/WireMock.Net/Handlers/LocalFileSystemHandler.cs
Noah Lerner 5e76a82a21 Improved relative path checking based on file existence (#411)
* Improved relative path checking based on file existence

If the file exists at the relative path, then use it. If not, then use the path as is.

* Apply File.Exists logic to ReadResponseBodyAsString as well

* Make path handling more robust since path is user defined

* Unit tests for relative path feature

* Replace all back and forward slashes with system dependent DirectorySeparatorChar

* Attempt fix broken directory separator chars for Unix platforms

* Revert wrapping GetMappingFolder with CleanPath

* Move CleanPath logic to its own class

* Remove whitespace

* Remove more whitespace

* Improve CleanPath method

* Move PathUtils tests to separate class

Add another test to ResponseWithBodyFromFileTests

* Fix Response_ProvideResponse_WithBodyFromFile_InAdminMappingFolder

* Debug Linux CI build

* Debug Linux CI

* print all files from admin mappings folder

* Debug CleanPath

* Fix removed leading directory separator char in Linux breaks file path

Remove debugging statements

* Move combine to PathUtils

* PathUtils + PathUtilsTests

* Remove replicated (3x) tests throughout ResponseWithBodyFromFileTests

Co-authored-by: Stef Heyenrath <Stef.Heyenrath@gmail.com>
2020-02-02 13:49:34 +01:00

144 lines
5.0 KiB
C#

using System.Collections.Generic;
using System.IO;
using WireMock.Util;
using WireMock.Validation;
namespace WireMock.Handlers
{
/// <summary>
/// Default implementation for a handler to interact with the local file system to read and write static mapping files.
/// </summary>
public class LocalFileSystemHandler : IFileSystemHandler
{
private static readonly string AdminMappingsFolder = Path.Combine("__admin", "mappings");
private readonly string _rootFolder;
/// <summary>
/// Initializes a new instance of the <see cref="LocalFileSystemHandler"/> class.
/// </summary>
public LocalFileSystemHandler() : this(Directory.GetCurrentDirectory())
{
}
/// <summary>
/// Initializes a new instance of the <see cref="LocalFileSystemHandler"/> class.
/// </summary>
/// <param name="rootFolder">The root folder.</param>
public LocalFileSystemHandler(string rootFolder)
{
_rootFolder = rootFolder;
}
/// <inheritdoc cref="IFileSystemHandler.FolderExists"/>
public bool FolderExists(string path)
{
Check.NotNullOrEmpty(path, nameof(path));
return Directory.Exists(path);
}
/// <inheritdoc cref="IFileSystemHandler.CreateFolder"/>
public void CreateFolder(string path)
{
Check.NotNullOrEmpty(path, nameof(path));
Directory.CreateDirectory(path);
}
/// <inheritdoc cref="IFileSystemHandler.EnumerateFiles"/>
public IEnumerable<string> EnumerateFiles(string path, bool includeSubdirectories)
{
Check.NotNullOrEmpty(path, nameof(path));
return includeSubdirectories ? Directory.EnumerateFiles(path, "*", SearchOption.AllDirectories) : Directory.EnumerateFiles(path);
}
/// <inheritdoc cref="IFileSystemHandler.GetMappingFolder"/>
public string GetMappingFolder()
{
return Path.Combine(_rootFolder, AdminMappingsFolder);
}
/// <inheritdoc cref="IFileSystemHandler.ReadMappingFile"/>
public string ReadMappingFile(string path)
{
Check.NotNullOrEmpty(path, nameof(path));
return File.ReadAllText(path);
}
/// <inheritdoc cref="IFileSystemHandler.WriteMappingFile(string, string)"/>
public void WriteMappingFile(string path, string text)
{
Check.NotNullOrEmpty(path, nameof(path));
Check.NotNull(text, nameof(text));
File.WriteAllText(path, text);
}
/// <inheritdoc cref="IFileSystemHandler.ReadResponseBodyAsFile"/>
public byte[] ReadResponseBodyAsFile(string path)
{
Check.NotNullOrEmpty(path, nameof(path));
path = PathUtils.CleanPath(path);
// If the file exists at the given path relative to the MappingsFolder, then return that.
// Else the path will just be as-is.
return File.ReadAllBytes(File.Exists(PathUtils.Combine(GetMappingFolder(), path)) ? PathUtils.Combine(GetMappingFolder(), path) : path);
}
/// <inheritdoc cref="IFileSystemHandler.ReadResponseBodyAsString"/>
public string ReadResponseBodyAsString(string path)
{
Check.NotNullOrEmpty(path, nameof(path));
path = PathUtils.CleanPath(path);
// In case the path is a filename, the path will be adjusted to the MappingFolder.
// Else the path will just be as-is.
return File.ReadAllText(File.Exists(PathUtils.Combine(GetMappingFolder(), path)) ? PathUtils.Combine(GetMappingFolder(), path) : path);
}
/// <inheritdoc cref="IFileSystemHandler.FileExists"/>
public bool FileExists(string filename)
{
Check.NotNullOrEmpty(filename, nameof(filename));
return File.Exists(AdjustPath(filename));
}
/// <inheritdoc cref="IFileSystemHandler.WriteFile(string, byte[])"/>
public void WriteFile(string filename, byte[] bytes)
{
Check.NotNullOrEmpty(filename, nameof(filename));
Check.NotNull(bytes, nameof(bytes));
File.WriteAllBytes(AdjustPath(filename), bytes);
}
/// <inheritdoc cref="IFileSystemHandler.DeleteFile"/>
public void DeleteFile(string filename)
{
Check.NotNullOrEmpty(filename, nameof(filename));
File.Delete(AdjustPath(filename));
}
/// <inheritdoc cref="IFileSystemHandler.ReadFile"/>
public byte[] ReadFile(string filename)
{
Check.NotNullOrEmpty(filename, nameof(filename));
return File.ReadAllBytes(AdjustPath(filename));
}
/// <summary>
/// Adjusts the path to the MappingFolder.
/// </summary>
/// <param name="filename">The path.</param>
/// <returns>Adjusted path</returns>
private string AdjustPath(string filename)
{
return Path.Combine(GetMappingFolder(), filename);
}
}
}