lovegigi 发表于 2015-8-14 11:41:50

asp.net URL 重写 附IIS配置+源码

这里给大家ISAPI重写URL的其中一个方法。
这是以前C# + Oracle 开发B/S的时候用到的。

  相关下载
  
还是那句。@2008 ATGO 版权所有. 保留所有权利,仅供学习使用。

ATGO_IRewrite.cpp的代码如下:
配置文件只有在运行的时候才会读取,这里提供了正则来用于不用重启IIS来重读配置文件

读取配置文件:

1//初始化配置
2bool ListInit()
3{
4    list<string> listRule;
5    string strBuffer;
6    int i = 0;
7    int len = 0;
8    fstream fsRead;
9   
10    //打开文件
11    fsRead.open("C:\\ATGO_IRewrite.ini", ios::in | ios::binary);
12    fsRead.seekg(0, ios::end);
13    len = fsRead.tellg();
14    fsRead.seekg(0, ios::beg);
15    char *buf = new char;
16    buf = '\0';
17    fsRead.read(buf, len);
18
19    //读取文件内容
20    for (i=0; i< len; i++)
21    {
22      if (buf != '\n' && buf != '\r')
23      {
24            strBuffer += buf;
25      }
26      else
27      {
28            if (!strBuffer.empty())
29            {
30                listRule.push_back(strBuffer);
31            }
32            strBuffer = "";
33      }
34    }
35
36    if (!strBuffer.empty())
37    {
38      listRule.push_back(strBuffer);
39    }
40    strBuffer = "";
41    fsRead.close();
42
43    listItem.clear();
44    cmatch match;
45
46    //如果RewriteEngine On则继续
47    if (regex_match((*listRule.begin()).c_str(), match, regexIsOn))
48    {
49      i = 0;
50
51      list<string>::iterator it = listRule.begin();
52      it ++;
53
54      //如果RewriteLogger On则启动日志功能
55      if (regex_match((*it).c_str(), match, regexIsLogger))
56      {
57            isLogger = true;
58      }
59      it ++;
60      
61      //从第三行开始读取规则
62      for (; it != listRule.end(); it++)
63      {
64            string strItem = (*it);
65
66            string strItems;
67            int findBlank = strItem.find_first_of(' ');
68            strItems = strItem.substr(0, findBlank);
69            strItems = strItem.substr(findBlank + 1, strItem.length());
70
71            findBlank = strItems.find_first_of(' ');
72            strItems = strItems.substr(findBlank + 1, strItems.length());
73            strItems = strItems.substr(0, findBlank);
74            
75            CItem i;
76            i.regex = strItems;
77            i.target = strItems;
78            listItem.push_back(i);
79      }
80    }
81    return 0;
82}
83
84//释放配置
85bool ListRelease()
86{
87    listItem.clear();
88    return true;
89}   URL重写部分:


代码

1DWORD CATGO_IRewriteFilter::OnPreprocHeaders(CHttpFilterContext* pCtxt,
2    PHTTP_FILTER_PREPROC_HEADERS pHeaderInfo)
3{
4    // TODO: React to this notification accordingly and
5    // return the appropriate status code
6
7    //获取hostname
8    char server_name;
9    DWORD buffSize_server_name = sizeof(server_name);
10    BOOL bHeader_server_name = pCtxt->GetServerVariable("SERVER_NAME", server_name, &buffSize_server_name);
11
12    //获取url
13    char buffer;
14    DWORD buffSize = sizeof(buffer);
15    BOOL bHeader = pHeaderInfo->GetHeader(pCtxt->m_pFC, "url",
16      buffer, &buffSize);
17
18    cmatch match;
19    fstream fs;
20
21    //特别码
22    if (boost::regex_match(buffer, match, regexAtgo))
23    {
24      for (int i=1; i<match.size(); i++)
25      {
26            string strMatch = match;
27
28            if (strMatch == "Release")
29            {
30                ListRelease();
31                if (isLogger)
32                {
33                  fs.open("C:\\Log\\ATGO_IRewrite_Error.log", ios::in | ios::app | ios::binary | ios::out | ios::ate);   
34                  string error = "错误代码1004-1!请与kx.ATGO@hotmail.com联系!";
35                  fs.write(error.c_str(), error.length());
36                  fs.write("\r\n", ::strlen("\r\n"));
37                  fs.close();
38                }
39            }
40            else if (strMatch == "Init")
41            {
42                ListInit();
43
44                if (isLogger)
45                {
46                  fs.open("C:\\Log\\ATGO_IRewrite_Error.log", ios::in | ios::app | ios::binary | ios::out | ios::ate);   
47                  string error = "错误代码1004-2!请与kx.ATGO@hotmail.com联系!";
48                  fs.write(error.c_str(), error.length());
49                  fs.write("\r\n", ::strlen("\r\n"));
50                  fs.close();
51                }
52            }
53            else if (strMatch == "Cmd")
54            {
55                ;
56            }
57            if (isLogger)
58            {
59                fs.open("C:\\Log\\ATGO_IRewrite_Error.log", ios::in | ios::app | ios::binary | ios::out | ios::ate);   
60                string error = "警告代码1004-3!" + strMatch + "请与kx.ATGO@hotmail.com联系!";
61                fs.write(error.c_str(), error.length());
62                fs.write("\r\n", ::strlen("\r\n"));
63                fs.close();
64            }
65      }
66    }
67
68
69    if (listItem.size() > 0)
70    {
71      string str = "";
72
73      string allUrl = "http://";
74      allUrl = allUrl + server_name;
75      allUrl = allUrl + buffer;
76      
77      if (isLogger)
78      {
79            fs.open("C:\\Log\\ATGO_IRewrite_log.log", ios::in | ios::app | ios::binary | ios::out | ios::ate);
80            str = "原始进来的URL:" + allUrl;
81            fs.write(str.c_str(), str.length());
82            fs.write("\r\n", ::strlen("\r\n"));
83            fs.close();
84      }
85
86      //从配置文件中的配置,找相关匹配
87      for (list<CItem>::iterator it = listItem.begin(); it != listItem.end(); it++)
88      {
89            CItem ci = (*it);
90            boost::regex regex(ci.regex, boost::regex::icase);
91
92            if (boost::regex_match(allUrl, match, regex))
93            {
94                string temp = ci.target;
95                for (int i=1; i<match.size(); i++)
96                {
97                  char buffer;
98                  ::sprintf(buffer, "$%d", i);
99                  string str = buffer;
100                  int index = temp.find(str, 0);
101                  if (index != -1)
102                  {
103                        temp = temp.replace(index, str.length(), match);
104                  }
105                }
106                allUrl = temp;
107                if (isLogger)
108                {
109                  fs.open("C:\\Log\\ATGO_IRewrite_log.log", ios::in | ios::app | ios::binary | ios::out | ios::ate);
110                  str = "按正则生成URL为:" + allUrl;
111                  fs.write(str.c_str(), str.length());
112                  fs.write("\r\n", ::strlen("\r\n"));
113                  fs.close();
114                }
115                break;
116            }
117      }
118      
119      if (allUrl != "")
120      {
121            int itemp = 0;
122            itemp =allUrl.find_first_of("//");
123
124            if (itemp > 0)
125            {
126                allUrl = allUrl.substr(itemp + 2, allUrl.length());
127               
128                itemp = allUrl.find_first_of("/");
129                allUrl = allUrl.substr(itemp, allUrl.length());
130            }
131            if (isLogger)
132            {
133                fs.open("C:\\Log\\ATGO_IRewrite_log.log", ios::in | ios::app | ios::binary | ios::out | ios::ate);
134                str = "重定向URL为" + allUrl;
135                fs.write(str.c_str(), str.length());
136                fs.write("\r\n", ::strlen("\r\n"));
137                fs.write("\r\n", ::strlen("\r\n"));
138                fs.close();
139            }
140
141            pHeaderInfo->SetHeader(pCtxt->m_pFC, "url", (char *)allUrl.c_str());
142      }
143    }
144   
145    return SF_STATUS_REQ_NEXT_NOTIFICATION;
146}  

  配置文件说明:
RewriteEngine on
RewriteLogger on
RewriteRule .*/(.*)\.atgo /$1.htm
第一行是开启URL重写
第二行是开启日志
第三行是对URL进行正则匹配,Pattern为.*/(.*)\.atgo,如果匹配成功,则转换成/$1.htm
其中$1是前面正则中()的值。

安装说明:
1.把ATGO_IRewrite.ini放到C盘根目录下;
2.把ATGO_IRewrite.dll添加到IIS的ISAPI里;


注:如果是NTFS格式的要设置一下配置文件的权限


3.重启IIS服务。
效果图:
页: [1]
查看完整版本: asp.net URL 重写 附IIS配置+源码