asp编写完整的一个ip所在地搜索类的修正文稿
修正了查询方法,查询的方法和追捕的一致;只是追捕会自动更正ip。
还有个函数的书写错误,也已经修正;
包括增加了一个ip地址正确性的验证函数。(只是从格式上判断)
<%
server.scripttimeout = &he10 &h3c
response.buffer = ("s.f." = "s.f.")
dim ipsearch
建立对象
set ipsearch = new clsipsearch
该句建立sql server的ip地址库的连接,可使用默认连接,但要保证存在wry.mdb
ipsearch.connectionstring = "driver={sql server};server=hostname:uid=sa;pwd=;database=ip"
设置要查询的ip,可用默认值,这里设置的是 127.0.0.1
ipsearch.ipaddress = &h7f & "." & &h00 & "." & &h00 & "." & &h01
if request.querystring("ip")<>"" then
if ipsearch.valid_ip(request.querystring("ip")) then
ipsearch.ipaddress = trim(request.querystring("ip"))
end if
end if
取得ip 所在地,反馈值有三个,以逗号分割
格式为:所在国家或地区,当地上网地区,提供正确ip地址信息的用户名
response.write ("所在地:" & ipsearch.getipaddrinfo() & "<br>")
取出ip地址
response.write ("ip:" & ipsearch.ipaddress & "<br>")
将ip地址转换为数值
response.write ("ip转换为数值:" & ipsearch.clongip(ipsearch.ipaddress) & "<br>")
将ip地址转换为数值后还原成ip字符串
response.write ("数值还原成ip:" & ipsearch.cstringip(ipsearch.clongip(ipsearch.ipaddress)) & "<br>")
response.write ("<hr>")
这里是测试代码
dim a,b,c,d
for a = 0 to 255
for b= 0 to 255 step 20
for c=0 to 255 step 20
for d = 0 to 255 step 20
ipsearch.ipaddress = a & "." & b & "." & c & "." & d
response.write ("所在地:" & ipsearch.getipaddrinfo() & "<br>")
response.write ("ip:" & ipsearch.ipaddress & "<br>")
response.write ("ip转换为数值:" & ipsearch.clongip(ipsearch.ipaddress) & "<br>")
response.write ("数值还原成ip:" & ipsearch.cstringip(ipsearch.clongip(ipsearch.ipaddress)) & "<br>")
response.write ("<hr>")
next
next
next
next
%>
<%
class clsipsearch
##################################################################
声明:本程序采用的数据为网络上著名的ip工具软件《追捕》作者“冯志宏”
先生所精心搜集整理。
《追捕》数据库的转换方法:
修改wry.dll 文件后缀名称为 wry.dbf
方法一:
启动access 数据,选择打开数据库,选择打开的文件类型为“dbase 5 (*.dbf)”
打开wry.dbf文件,选择《工具》菜单下的《数据库实用工具》中的《转换数据库》
选择《转换为 access 97 格式(版本可选)》功能,保存文件即可成为mdb格式。
方法二:
使用sql server提供的《导入和导出数据》向导。
方法简要说明:在odbc 控制面板中设置指向wry.dbf的dsn。
使用《导入和导出数据》向导,选择其正确的驱动程序和要导入的库即可。
或者直接导入由方法一生成的mdb文件入库。
方法三:
使用access 打开wry.dbf 文件后将自动通过mdb库引用原库数据。
未安装其他数据库平台,其他方法欠考虑。
###################### 类说明 ####################################
# ip 所在地搜索类
# connectionstring 为数据库连接声明,默认声明同级目录的wry.mdb
# ipaddress 请设置为进行搜索的ip 地址,默认取当前访问者ip
# 类建立方法
# dim objval 声明一个变量
# set objval = new clsipsearch 建立类对象
# response.write (objval.ipaddress) 显示当前访问者ip
# ip 搜索类方法列表:
# .valid_ip ip 地址正确性效验
# 参数:ip ip 数值或者字符串
# .clongip 将ip地址转换为长整型的数值
# 参数:asnewip 要转换的ip地址字符串
# .cstringip 将长整型的数值转换为ip
# 参数:annewip 要还原为ip地址的数值
# .getclientip 取访问者的ip
# .getipaddrinfo 得到设置过ipaddress属性的ip所在地
# 属性列表(自动初始化):
# connectionstring ado 访问数据库连接说明
# ipaddress 要操作的ip地址
# 内部错误处理:
# 欠缺,未做,请自行补充。
##################################################################
public connectionstring
public ipaddress
private dbconn 连接对象,模块级声明
────────────────────────────────
类初始化
private sub class_initialize()
这里建立的是通过“数据转换–方法一”生成的mdb 库文件
connectionstring="driver={microsoft access driver (*.mdb)};dbq=" & server.mappath("wry.mdb")
ipaddress = getclientip()
set dbconn = openconnection()
end sub
────────────────────────────────
类注销
private sub class_terminate()
connectionstring = null
ipaddress = null
dbconn.close
set dbconn = nothing
end sub
────────────────────────────────
建立一个连接
private function openconnection()
dim tmpconn
set tmpconn=server.createobject("adodb.connection")
tmpconn.open connectionstring
set openconnection=tmpconn
set tmpconn=nothing
end function
────────────────────────────────
执行一个sql命令,并返回一个数据集对象
private function sqlexecute(strsql)
dim rs
set rs=dbconn.execute(strsql)
set sqlexecute = rs
set rs=nothing
end function
────────────────────────────────
ip 效验
public function valid_ip(byval ip)
dim i
dim dot_count
dim test_octet
dim byte_check
ip = trim(ip)
确认ip长度
if len(ip) < &h08 then
valid_ip = false
显示错误提示
exit function
end if
i = &h01
dot_count = &h00
for i = 1 to len(ip)
if mid(ip, i, &h01) = "." then
增加点的记数值
并且设置text_octet 值为空
dot_count = dot_count + &h01
test_octet = ""
if i = len(ip) then
如果点在结尾则ip效验失败
valid_ip = false
显示错误提示
exit function
end if
else
test_octet = test_octet & mid(ip, i, &h01)
使用错误屏蔽来检查数据段值的正确性
on error resume next
进行强制类型转换
如果转换失败就可通过检查err是否为真来确认
byte_check = cbyte(test_octet)
if (err) then
强制类型转换产生错误
所取段值的数据不为数值
或所取段值的数据长度大于&hff
则类型不为byte类型
ip 地址的正确性为假
valid_ip = false
exit function
end if
end if
next
通过上一步的验证,现在应该要检查小点是否有3个
if dot_count <> &h03 then
valid_ip = false
exit function
end if
一切正常,那么该ip为正确的ip地址
valid_ip = true
end function
────────────────────────────────
转换一个数值为ip
public function cstringip(byval annewip)
dim lsresults
dim lntemp
dim lnindex
for lnindex = &h03 to &h00 step -&h01
lntemp = int(annewip / (&h100 ^ lnindex))
lsresults = lsresults & lntemp & "."
annewip = annewip – (lntemp * (&h100 ^ lnindex))
next
lsresults = left(lsresults, len(lsresults) – &h01)
cstringip = lsresults
end function
────────────────────────────────
转换一个ip到数值
public function clongip(byval asnewip)
dim lnresults
dim lnindex
dim lnipary
lnipary = split(asnewip, ".", &h04)
for lnindex = &h00 to &h03
if not lnindex = &h03 then
lnipary(lnindex) = lnipary(lnindex) * (&h100 ^ (&h03 – lnindex))
end if
lnresults = lnresults + lnipary(lnindex)
next
clongip = lnresults
end function
────────────────────────────────
取client ip
public function getclientip()
dim uipaddr
本函数参考webcn.net/asphouse 文献<取真实的客户ip>
uipaddr = request.servervariables("http_x_forwarded_for")
if uipaddr = "" then uipaddr = request.servervariables("remote_addr")
getclientip = uipaddr
uipaddr = ""
end function
────────────────────────────────
读取ip所在地的信息
public function getipaddrinfo()
dim tmpipaddr
dim ipaddrval
dim ic,charspace
dim tmpsql
charspace = ""
ipaddrval = ipaddress
if not valid_ip(ipaddrval) then
getipaddrinfo =null
exit function
end if
将ip字符串劈开成数组好进行处理
tmpipaddr = split(ipaddrval,".",-1,1)
for ic = &h00 to ubound(tmpipaddr)
补位操作,保证每间隔满足3个字符
select case len(tmpipaddr(ic))
case &h01 :charspace = "00"
case &h02 :charspace = "0"
case else :charspace = ""
end select
tmpipaddr(ic) = charspace & tmpipaddr(ic)
next
ipaddrval = tmpipaddr(&h00) & "." & tmpipaddr(&h01) & "." & tmpipaddr(&h02) & "." & tmpipaddr(&h03)
以下为查询,ip地址库基于《追捕》的ip数据库,感谢"冯志宏"先生的贡献
库结构如下:
create table [dbo].[wry] (
[startip] [nvarchar] (17) collate chinese_prc_ci_as null , –起始ip段
[endip] [nvarchar] (17) collate chinese_prc_ci_as null , –终止ip段
[country] [nvarchar] (16) collate chinese_prc_ci_as null , –国家或者地区
[local] [nvarchar] (54) collate chinese_prc_ci_as null , –本地地址
[thank] [nvarchar] (23) collate chinese_prc_ci_as null –感谢修正ip地址用户姓名
) on [primary]
经过分析库的数据存放结构,总结出准确的查询方法,具体看下面的查询过程
tmpsql = "select * from wry where (startip<=" & ipaddrval & ") and (endip>=" & ipaddrval & ") " & _
" and left(startip," & len(tmpipaddr(&h00)) & ") = " & tmpipaddr(&h00) & "" & _
" and left(endip," & len(tmpipaddr(&h00)) & ")=" & tmpipaddr(&h00) & ""
charspace = getdbipinfo(tmpsql)
if len(charspace)=&h00 then
getipaddrinfo = null
else
getipaddrinfo = charspace
end if
charspace = null
tmpsql = null
end function
────────────────────────────────
返回数据查询的字符串
private function getdbipinfo(byval sql)
dim openipsearchrs
dim result
set openipsearchrs = sqlexecute(sql)
if not openipsearchrs.eof then
result = nulltospace(openipsearchrs("country")) & "," & nulltospace(openipsearchrs("local")) & "," & nulltospace(openipsearchrs("thank"))
else
result = null
end if
openipsearchrs.close
set openipsearchrs=nothing
getdbipinfo = result
end function
────────────────────────────────
将数据库空记录转换为空字符
private function nulltospace(byval rsstr)
if isnull(rsstr) then
nulltospace = ""
else
nulltospace = trim(rsstr)
end if
end function
end class
%>