ln.http/ln.http/FileSystemRouter.cs

105 lines
3.2 KiB
C#

// /**
// * File: FileSystemRouter.cs
// * Author: haraldwolff
// *
// * This file and it's content is copyrighted by the Author and / or copyright holder.
// * Any use wihtout proper permission is illegal and may lead to legal actions.
// *
// *
// **/
using System;
using System.IO;
using System.Collections.Generic;
using ln.http.mime;
namespace ln.http
{
public class FileSystemRouter : IDisposable
{
private string _rootPath;
public String RootPath
{
get => _rootPath;
private set
{
_rootPath = Path.GetFullPath(value);
}
}
List<string> indexNames = new List<string>();
public String[] IndexNames => indexNames.ToArray();
private HttpServer _httpServer;
private HttpRouter _parentRouter;
private HttpRouter.HttpMapping _parentMapping;
public FileSystemRouter(HttpServer httpServer, string path)
{
_httpServer = httpServer;
httpServer?.AddRouter(this.Route);
if (!Directory.Exists(path))
throw new FileNotFoundException();
RootPath = path;
Console.Error.WriteLine("FileSystemRouter created ({0})", RootPath);
AddIndex("index.html");
AddIndex("index.htm");
}
public FileSystemRouter(string path)
:this(null, path)
{
}
public FileSystemRouter(HttpRouter parentRouter, string mappingPath, string path)
:this(null, path)
{
_parentRouter = parentRouter;
_parentMapping = _parentRouter.Map(HttpMethod.ANY, mappingPath, this.Route);
}
public void AddIndex(string indexName) => indexNames.Add(indexName);
public void RemoveIndex(string indexName) => indexNames.Remove(indexName);
public bool Route(HttpContext httpContext)
{
string finalPath = httpContext.RoutableUri.Length > 0 ? Path.Combine(RootPath, httpContext.RoutableUri.Substring(1)) : ".";
if (Directory.Exists(finalPath))
{
foreach (string indexName in indexNames)
{
string indexFileName = Path.Combine(finalPath, indexName);
if (File.Exists(indexFileName))
{
finalPath = indexFileName;
break;
}
}
}
if (File.Exists(finalPath))
{
lock (this)
{
httpContext.Response = new HttpResponse(httpContext.Request, new FileStream(finalPath, FileMode.Open, FileAccess.Read));
httpContext.Response.SetHeader("content-type", MimeTypeMap.GetMimeType(Path.GetExtension(finalPath)));
return true;
}
}
return false;
}
public void Dispose()
{
_httpServer?.RemoveRouter(this.Route);
_httpServer = null;
_parentRouter?.RemoveHttpMapping(_parentMapping);
_parentMapping = null;
_parentRouter = null;
}
}
}