1,在Web上修改指定文件位置的Web.config这里需要使用 WebConfigurationManager 类,但必须使用WebConfigurationFileMap类来指定文件位置,看代码:
longappId =123;//修改网站的配置文件varconfigFile =newFileInfo(configFilePath);varvdm =newVirtualDirectoryMapping(configFile.DirectoryName,true, configFile.Name);varwcfm =newWebConfigurationFileMap();
wcfm.VirtualDirectories.Add("/", vdm);varconfig = WebConfigurationManager.OpenMappedWebConfiguration(wcfm,"/", siteName);
AppSettingsSection appSection= (AppSettingsSection)config.GetSection("appSettings");
appSection.Settings["abc"].Value ="system tag";
appSection.Settings["appId"].Value =appId.ToString();
config.Save();
上面的代码参考自 stackoverflow ,但是OpenMappedWebConfiguration 必须指定第3个参数,否则会报错。不过,siteName 并不要求与IIS的站点名字对应,随意写一个也可以。
2,使用angularJS 绑定站点信息首先定义一个 webSiteListApp HTML代码片断:
<divng-app="webSiteListApp"class="container"><divng-controller="webSiteListController"><ul><ling-repeat="item in siteList">站点名:{{item.SiteName}} ------绑定信息:{{item.DomainPort}}</li></ul></div></div>
然后定义module和service:
<script type="text/javascript">//参考 http://www.infragistics.com/community/blogs/dhananjay_kumar/archive/2015/05/13/how-to-use-angularjs-in-asp.net-mvc-and-entity-framework-4.aspxvarwebSiteListApp = angular.module("webSiteListApp", []);
webSiteListApp.controller("webSiteListController",function($scope, webSiteService) {
getSiteList();functiongetSiteList() {varlist =webSiteService.getSiteList()
.success(function(sites) {
$scope.siteList=sites;
console.log($scope.siteList);
})
.error(function(error) {
$scope.status= 'Unable to load customer data: ' +error.message;
console.log($scope.status);
});
}
});
webSiteListApp.factory("webSiteService", ["$http",function($http) {varwebSiteService ={};
webSiteService.getSiteList=function() {return$http.get("/SiteManage/GetServerBindings");
}returnwebSiteService;
}]);</script>
这里定义了一个叫做 webSiteListApp 的module,然后注册一个 webSiteListController 的控制器,该控制器在前面的HTMl代码中定义,最后创建一个 webSiteService ,它监听后来MVC来的数据,该数据对应的ASP.NET MVC 方法如下:
publicJsonResult GetServerBindings()
{varsiteList =IISControlHelper.IISWorker.GetServerBindings();returnJson(siteList, JsonRequestBehavior.AllowGet);
}
3,IIS管理程序可以创建,删除网站,添加应用程序池,代码如下:
usingSystem;usingSystem.Collections;usingSystem.Collections.Generic;usingSystem.DirectoryServices;usingSystem.Linq;usingSystem.Net;usingSystem.Text;usingSystem.Threading.Tasks;namespaceIISControlHelper
{///<summary>///IIS 操作方法集合///http://blog.csdn.net/ts1030746080/article/details/8741399错误///</summary>publicclassIISWorker
{PRivatestaticstringHostName ="localhost";///<summary>///获取本地IIS版本///</summary>///<returns></returns>publicstaticstringGetIIsVersion()
{try{
DirectoryEntry entry=newDirectoryEntry("IIS://"+ HostName +"/W3SVC/INFO");stringversion = entry.Properties["MajorIISVersionNumber"].Value.ToString();returnversion;
}catch(Exception se)
{//说明一点:IIS5.0中没有(int)entry.Properties["MajorIISVersionNumber"].Value;属性,将抛出异常 证明版本为 5.0returnstring.Empty;
}
}///<summary>///创建虚拟目录网站///</summary>///<param name="webSiteName">网站名称</param>///<param name="physicalPath">物理路径</param>///<param name="domainPort">站点+端口,如192.168.1.23:90</param>///<param name="isCreateAppPool">是否创建新的应用程序池</param>///<returns></returns>publicstaticintCreateWebSite(stringwebSiteName,stringphysicalPath,stringdomainPort,boolisCreateAppPool)
{
DirectoryEntry root=newDirectoryEntry("IIS://"+ HostName +"/W3SVC");//为新WEB站点查找一个未使用的IDintsiteID =1;foreach(DirectoryEntry einroot.Children)
{if(e.SchemaClassName =="IIsWebServer")
{intID =Convert.ToInt32(e.Name);if(ID >= siteID) { siteID = ID +1; }
}
}//创建WEB站点DirectoryEntry site = (DirectoryEntry)root.Invoke("Create","IIsWebServer", siteID);
site.Invoke("Put","ServerComment", webSiteName);
site.Invoke("Put","KeyType","IIsWebServer");
site.Invoke("Put","ServerBindings", domainPort );
site.Invoke("Put","ServerState",2);
site.Invoke("Put","FrontPageWeb",1);
site.Invoke("Put","DefaultDoc","Default.html");//site.Invoke("Put", "SecureBindings", ":443:");site.Invoke("Put","ServerAutoStart",1);
site.Invoke("Put","ServerSize",1);
site.Invoke("SetInfo");//创建应用程序虚拟目录DirectoryEntry siteVDir= site.Children.Add("Root","IISWebVirtualDir");
siteVDir.Properties["AppIsolated"][0] =2;
siteVDir.Properties["Path"][0] =physicalPath;
siteVDir.Properties["accessFlags"][0] =513;
siteVDir.Properties["FrontPageWeb"][0] =1;
siteVDir.Properties["AppRoot"][0] ="LM/W3SVC/"+ siteID +"/Root";
siteVDir.Properties["AppFriendlyName"][0] ="Root";if(isCreateAppPool)
{
DirectoryEntry apppools=newDirectoryEntry("IIS://"+ HostName +"/W3SVC/AppPools");
DirectoryEntry newpool= apppools.Children.Add(webSiteName,"IIsapplicationPool");
newpool.Properties["AppPoolIdentityType"][0] ="4";//4newpool.Properties["ManagedPipelineMode"][0] ="0";//0:集成模式 1:经典模式newpool.Properties["ManagedRuntimeVersion"][0] ="v4.0";
newpool.CommitChanges();
siteVDir.Properties["AppPoolId"][0] =webSiteName;
}
siteVDir.CommitChanges();
site.CommitChanges();returnsiteID;
}///<summary>///得到网站的物理路径///</summary>///<param name="rootEntry">网站节点</param>///<returns></returns>publicstaticstringGetWebsitePhysicalPath(DirectoryEntry rootEntry)
{stringphysicalPath ="";foreach(DirectoryEntry childEntryinrootEntry.Children)
{if((childEntry.SchemaClassName =="IIsWebVirtualDir") && (childEntry.Name.ToLower() =="root"))
{if(childEntry.Properties["Path"].Value !=null)
{
physicalPath= childEntry.Properties["Path"].Value.ToString();
}else{
physicalPath="";
}
}
}returnphysicalPath;
}///<summary>///获取站点名///</summary>publicstaticList<IISInfo>GetServerBindings()
{
List<IISInfo> iisList =newList<IISInfo>();stringentPath = String.Format("IIS://{0}/w3svc", HostName);
DirectoryEntry ent=newDirectoryEntry(entPath);foreach(DirectoryEntry childinent.Children)
{if(child.SchemaClassName.Equals("IIsWebServer", StringComparison.OrdinalIgnoreCase))
{if(child.Properties["ServerBindings"].Value !=null)
{objectobjectArr = child.Properties["ServerBindings"].Value;stringserverBindingStr =string.Empty;if(IsArray(objectArr))//如果有多个绑定站点时{object[] objectToArr = (object[])objectArr;
serverBindingStr= objectToArr[0].ToString();
}else//只有一个绑定站点{
serverBindingStr= child.Properties["ServerBindings"].Value.ToString();
}
IISInfo iisInfo=newIISInfo();
iisInfo.DomainPort=serverBindingStr;
iisInfo.AppPool= child.Properties["AppPoolId"].Value.ToString();//应用程序池,有可能不准确objectobjComment=child.Properties["ServerComment"].Value;if(objComment !=null)
{
iisInfo.SiteName=objComment.ToString();
}
iisList.Add(iisInfo);
}
}
}returniisList;
}publicstaticboolCreateAppPool(stringappPoolName,stringUsername,stringPassWord)
{boolissucess =false;try{//创建一个新程序池DirectoryEntry newpool;
DirectoryEntry apppools=newDirectoryEntry("IIS://"+ HostName +"/W3SVC/AppPools");
newpool= apppools.Children.Add(appPoolName,"IIsApplicationPool");//设置属性 访问用户名和密码 一般采取默认方式newpool.Properties["WAMUserName"][0] =Username;
newpool.Properties["WAMUserPass"][0] =Password;
newpool.Properties["AppPoolIdentityType"][0] ="3";
newpool.CommitChanges();
issucess=true;returnissucess;
}catch//(Exception ex){returnfalse;
}
}///<summary>///建立程序池后关联相应应用程序及虚拟目录///</summary>publicstaticvoidSetAPPToPool(stringappname,stringpoolName)
{//获取目录DirectoryEntry getdir =newDirectoryEntry("IIS://localhost/W3SVC");foreach(DirectoryEntry getentityingetdir.Children)
{if(getentity.SchemaClassName.Equals("IIsWebServer"))
{//设置应用程序程序池 先获得应用程序 在设定应用程序程序池//第一次测试根目录foreach(DirectoryEntry getchildingetentity.Children)
{if(getchild.SchemaClassName.Equals("IIsWebVirtualDir"))
{//找到指定的虚拟目录.foreach(DirectoryEntry getsiteingetchild.Children)
{if(getsite.Name.Equals(appname))
{//【测试成功通过】getsite.Properties["AppPoolId"].Value =poolName;
getsite.CommitChanges();
}
}
}
}
}
}
}///<summary>///判断object对象是否为数组///</summary>publicstaticboolIsArray(objecto)
{returnoisArray;
}
}publicclassIISInfo
{publicstringSiteName {get;set; }publicstringDomainPort {get;set; }publicstringAppPool {get;set; }
}
}
View Code
然后,写一个页面来创建网站:
前端HTML:
<formaction="/SiteManage/CreateWebSite"><fieldset>网站名称(不能重复):————<inputtype="text"name="siteName"class="myInput"/></fieldset><fieldset>网站基准目录(服务器):———<inputtype="text"name="physicalPath"class="myInput"/></fieldset><fieldset>绑定域名(不能重复):————<inputtype="text"name="domain"class="myInput"/></fieldset><fieldset>网站压缩文件路径(服务器):—<inputtype="text"name="zipFile"class="myInput"value="@ViewBag.ZipFile"/>如果服务器没有网站压缩文件,请先上传。</fieldset><inputtype="submit"name="submit1"value="提交"/></form>
后端Controller:
publicActionResult CreateWebSite(stringsiteName,stringphysicalPath,stringdomain,stringzipFile)
{boolhasErr =false;stringmessage ="";stringwebSiteFolder ="";//检查参数,physicalPath 允许不存在,之后解压缩文件的时候将自动创建if(string.IsNullOrEmpty(siteName) ||string.IsNullOrEmpty(physicalPath) ||string.IsNullOrEmpty(domain) ||string.IsNullOrEmpty(zipFile))
{
hasErr=true;
message="参数不能为空!";
}//检查是否已经包含了要绑定的域名,如果是,则不允许创建if(!hasErr)
{varlist =IISControlHelper.IISWorker.GetServerBindings();foreach(variteminlist)
{if(string.Compare(item.DomainPort, domain, StringComparison.OrdinalIgnoreCase) >0)
{
hasErr=true;
message= domain +"域名已经绑定过,不能创建绑定此域名的新站点。";
break;
}
}
}//检查网站目录并解压缩文件到网站目录if(!hasErr)
{try{
webSiteFolder=CheckWebSiteFolder(physicalPath, zipFile);if(System.IO.File.Exists(zipFile))
{
UnZipFile(zipFile, physicalPath);
}else{
message= zipFile+"文件不存在!";
hasErr=true;
}
}catch(Exception ex1)
{
message=ex1.Message;
hasErr=true;
}
}if(!hasErr)
{try{//创建网站intsiteNumber;
siteNumber= IISControlHelper.IISWorker.CreateWebSite(siteName, webSiteFolder,"*:80:"+ domain,true);
message= siteNumber >0?"成功":"失败";
}catch(System.Runtime.InteropServices.COMException exCom)
{
hasErr=true;if(exCom.HResult == -2147024713)
{
message="网站名已经存在!";//(应用程序池IIS进程)文件已经存在,上面的方法默认会创建跟网站同名的应用程序池名称}else{
message=exCom.Message;
}
}catch(Exception ex2)
{
hasErr=true;
message=ex2.Message;
}
}
ViewBag.SiteName=siteName;
ViewBag.PhysicalPath=webSiteFolder;
ViewBag.Domain=domain;
ViewBag.ResultDesc=message;returnView("CreateResult");
}
注意这里会创建一个跟站点名字同名的应用程序池,默认是.NET 4.0,创建后即启动站点。
相关代码下载,点击这里。
4,ASP.NET MVC 上传文件前端HTML:
<formaction="/SiteManage/Upload"method="post"enctype="multipart/form-data">上传网站压缩文件:<inputtype="file"name="file1"value=""style="width:300px;"class="myInput"/><inputtype="submit"name="submit2"value="上传"/><span>@ViewBag.Message</span></form>
后端Controller:
publicActionResult Upload()
{stringmessage ="";
HttpPostedFileBase file= Request.Files["file1"];if(System.IO.Path.GetExtension(file.FileName).ToLower() !=".zip")
{
message="只能上传ZIP格式的压缩文件。";returnRedirectToAction("Index",new{ zipFile ="", message });
}else{stringfilePath = System.IO.Path.Combine(HttpContext.Server.MapPath("../Uploads"), System.IO.Path.GetFileName(file.FileName));
file.SaveAs(filePath);
message="上传成功";returnRedirectToAction("Index",new{ zipFile=filePath,message});
}
}
注意Request.Files["file1"] 表示获取前端HTML页面的文件双传控件名字 file1 对应的文件。
5,.NET解压缩文件.NET 4.5之后,集成了文件解压缩功能,下面是使用方法:
///<summary>///解压缩文件到指定目录,将在指定目录下解压出一个压缩文件名字的最终的目录///</summary>///<param name="ZipPath">ZIP文件路径</param>///<param name="ExtractPath">要解压缩的目录</param>privatevoidUnZipFile(stringZipPath,stringExtractPath)
{//string NewFile = @"c:\users\exampleuser\NewFile.txt";if(System.IO.File.Exists(ZipPath))
{using(ZipArchive Archive =ZipFile.Open(ZipPath, ZipArchiveMode.Update))
{//Archive.CreateEntryFromFile(NewFile, "NewEntry.txt");//如果目录下面有文件,将解压缩失败,所以之前先备份目录Archive.ExtractToDirectory(ExtractPath);
}
}
}
注意这里支持ZIP格式,不是RAR格式,同时需要使用 using System.IO.Compression;相关的程序集。
6,备份文件夹如果需要备份文件夹,可以使用Move 方法实现,看代码:
///<summary>///检查站点目录,如果原来的目录已经存在,将自动备份,如果该目录不存在,将自动创建///</summary>///<param name="physicalPath"></param>///<param name="zipFile"></param>///<returns></returns>privatestringCheckWebSiteFolder(stringphysicalPath,stringzipFile)
{stringwebSiteFolder =System.IO.Path.Combine(physicalPath, System.IO.Path.GetFileNameWithoutExtension(zipFile));if(System.IO.Directory.Exists(webSiteFolder))
{
System.IO.Directory.Move(webSiteFolder, webSiteFolder+"_back"+ DateTime.Now.ToString("yyyyMMddHHmmss"));
}//此目录returnwebSiteFolder;
7,给MVC页面传递数据可以使用ViewBag 方式,例如下面的方式:
publicActionResult Index(stringzipFile="",stringmessage="")
{stringiisVersion =IISControlHelper.IISWorker.GetIIsVersion();
ViewBag.IISVerion=iisVersion;
ViewBag.ZipFile=zipFile;
ViewBag.Message=message;returnView();
}
ViewBag 是动态类型,在前端页面直接使用它既可。
也可以通过Action传递一个对象给页面,方法如下:
publicActionResult Index(stringzipFile="",stringmessage="")
{varsiteList =IISControlHelper.IISWorker.GetServerBindings();returnView(siteList);
}
然后,在 index.cshtml 页面的头部,引入这个Model:
@model List<IISControlHelper.IISInfo>@{
ViewBag.Title = "ASP.NET在线创建网站Demo";
}
8,SQL语句创建Access数据库表可以使用SqlServer的基本建表语句,但是有几点不同,首先,不能使用User这样的关键词,然后,在创建自增字段上与SqlServer不同。
Access需要采用下面的方式:
[User ID] autoincrement PRIMARY KEY
不能使用下面的方式:
[User ID] Integer PRIMARY KEY autoincrement
PRIMARY KEY语句必须放在 autoincrement 之后,否则语法错。可见,Access功能的确很简单。
完整的一个建立表语句:
CREATETABLE[Users]([User ID]autoincrementPRIMARYKEY,[First Name]text,[Last Name]text,[Age]Integer)
PDF.NET SOD Ver5.3.3.0724 发布,增加了Access Code First 支持,可以生成上面的建表语句。
9,VS复制项目生成的文件到另外一个项目运行目录下这个问题常见于DLL需要动态加载的情况下,该DLL是在另外一个项目下生成,主体项目运行前需要拷贝到当前运行目录下。
如果DLL的源码经常修改,手工复制比较费事情,采用项目的
生成时间--〉后期生成命令行,输入下面类似的命令:
XCOPY"$(TargetPath)""$(ProjectDir)..\MainExeProj\bin\$(ConfigurationName)"/Y /D /R
这个命令会将当前项目生成的DLL复制到 跟当前项目文件夹同级的MainExeProj\bin文件夹下面去,$(ConfigurationName) 通常表示 Debug,Release.
10,使用XCopy备份指定日期之后的资料使用下面的命令:
xcopy C:\SourceDoc D:\CopyedDoc /i /s /y /EXCLUDE:D:\CopyedDoc\excludeFile.txt /d:7-1-2010
这将备份 SourceDoc 目录下面的 7月1日之后所有的文件和文件夹,exclued 文件包含了要排除的文件,比如:
obj
bin
.jpeg
.png
.gif