using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
namespace Tesses.Http
{
///
/// mount multiple servers at different url paths
///
public sealed class MountableServer : IRequestHandler
{
Dictionary _servers = new Dictionary();
public MountableServer(IRequestHandler root)
{
_root = root;
}
IRequestHandler _root;
private (string Key,IRequestHandler Value) GetFromPath(ServerContext ctx)
{
string path = ctx.Request.GetQueryParameters(ctx.Request.CurrentUrl,new Dictionary>());
//bool j = false;
foreach(var item in _servers.Reverse())
{
if(path.StartsWith(item.Key,StringComparison.Ordinal))
{
return (item.Key,RequestHandler.Guaranteed(ctx,item.Value));
}
if (path == item.Key.TrimEnd('/'))
{
path += "/";
return (item.Key,RequestHandler.Guaranteed(ctx,item.Value));
}
}
//Console.WriteLine("HERE WE ARE");
return ("/",RequestHandler.Guaranteed(ctx,_root));
}
///
/// Mount the specified url and server.
/// Must mount like this
/// /somePath0
/// /somePath0/someSubPath0
/// /somePath0/someSubPath0/someSubSubPath0
/// /somePath0/someSubPath0/someSubSubPath1
/// /somePath0/someSubPath1
/// /somePath0/someSubPath1/someSubSubPath0
/// /somePath0/someSubPath1/someSubSubPath1
///
/// URL.
/// Server.
public void Mount(string url,IRequestHandler server)
{
_servers.Add(url, server);
}
///
/// Unmount a server
///
/// Url
public void Unmount(string url)
{
_servers.Remove(url);
}
///
/// Unmount all servers
///
public void UnmountAll()
{
_servers.Clear();
}
public async Task Handle(ServerContext ctx)
{
var v = GetFromPath(ctx);
string[] curUrl =ctx.Request.CurrentUrl.Split(new char[]{'?'},2,StringSplitOptions.RemoveEmptyEntries);
string url = '/' + curUrl[0].Substring(v.Key.Length).TrimStart('/');
if(curUrl.Length > 1)
{
url += $"?{curUrl[1]}";
}
ctx.Request.CurrentUrl = url;
await v.Value.Handle(ctx);
}
}
}