对WebApi进行单元测试时,一般需要一个IIS站点,一般的做法,是通过写一个批处理的bat脚本来实现,其实通过编码,也能实现该功能。
主要有关注三点:应用程序池、Web站点、绑定(协议类型:http、https,IP地址,端口,主机名)
1.总体代码
var webSite = app.WebSite;
using (var sm = new ServerManager())
{
//创建应用程序池
var appPool = sm.ApplicationPools.FirstOrDefault(ap => ap.Name.Equals(webSite.PoolName));
if (appPool == null)
{
CreateAppPool(sm.ApplicationPools, webSite.PoolName);
}
//创建Web站点
var site = sm.Sites.FirstOrDefault(s => s.Name.Equals(webSite.SiteName));
if (site == null)
{
CreateWebSite(sm.Sites, webSite, app.InstallPath);
}
sm.CommitChanges();
}
2.创建应用程序池:
/// <summary>
/// 创建应用程序池
/// </summary>
/// <param name="appPools"></param>
/// <param name="appPoolName"></param>
private void CreateAppPool(ApplicationPoolCollection appPools, string appPoolName)
{
var appPool = appPools.Add(appPoolName);
//是否自启动
appPool.AutoStart = true;
//队列长度
appPool.QueueLength = 10000;
//启动模式
appPool.StartMode = StartMode.AlwaysRunning;
//回收时间间隔
appPool.Recycling.PeriodicRestart.Time = new TimeSpan();
//闲置超时
appPool.ProcessModel.IdleTimeout = new TimeSpan();
//最大工作进程数
appPool.ProcessModel.MaxProcesses = 1;
}
3.创建站点
/// <summary>
/// 创建Web站点
/// </summary>
/// <param name="sites"></param>
/// <param name="webSite"></param>
/// <param name="physicalPath"></param>
private void CreateWebSite(SiteCollection sites, WebSite webSite, string physicalPath)
{
Site site = null;
bool isSiteCreated = false;
foreach (var binding in webSite.Bindings)
{
var bingdingInfo = ConstructBindingInfo(binding);
if (!isSiteCreated)
{
site = sites.Add(webSite.SiteName, binding.BindingType, bingdingInfo, physicalPath);
//是否自启动
site.ServerAutoStart = true;
isSiteCreated = true;
}
else
{
site.Bindings.Add(bingdingInfo, binding.BindingType);
}
}
var root = site.Applications["/"];
//设置应用程序池
root.ApplicationPoolName = webSite.PoolName;
//设置虚拟目录
// root.VirtualDirectories["/"].PhysicalPath = pathToRoot;
//预加载
root.SetAttributeValue("preloadEnabled", true);
}
4.创建绑定
/// <summary>
/// 构建绑定信息
/// </summary>
/// <param name="binding"></param>
/// <returns></returns>
private string ConstructBindingInfo(WebSiteBinding binding)
{
var sb = new StringBuilder();
if (!string.IsNullOrEmpty(binding.IP))
{
sb.Append(binding.IP);
}
else
{
sb.Append("*");
}
sb.Append(":");
sb.Append(binding.Port);
sb.Append(":");
if (!string.IsNullOrEmpty(binding.HostName))
{
sb.Append(binding.HostName);
}
else
{
sb.Append(string.Empty);
}
return sb.ToString();
}