ASP无组件上传文件到服务器

        最近参与了一个网站开发的项目,在做后台管理时用到了文件上传,因为客户要求数据库保存的是文件路径,文件就得直接上传到服务器,而且麻烦的是需要把其他表单信息和上传的图片一起进行数据处理,这样就不能用Request.Form来得到表单信息,只能以二进制的方式进行处理。现就以我开发的项目为例来说明如何以二进制方式来处理表单数据。

< form  action ="?action=Addnew"  method ="post"  name ="Center2"  enctype ="multipart/form-data" >     
   
< table  width ="590" >
     
< tr >
       
< td  align ="center" > 新增教学点(带 < font  color =red > * </ font > 的为必填字段) </ td >
     
</ tr >
   
</ table >        
   
< table  width ="590"  border ="1" >
     
< tr >
       
< td  align ="right" > 教学点ID: </ td >
       
< td >< input  name ="CenterID2"  type ="text"  maxlength ="3"   /> &nbsp; < font  color =red > * </ font ></ td >
       
< td > 唯一性3位代码,如“LJD”=临时西南交大 </ td >
     
</ tr >
     
< tr >
       
< td  align ="right" > 教学点名称: </ td >
       
< td >< input  name ="CenterName2"  type ="text"   /> &nbsp; < font  color =red > * </ font ></ td >
       
< td > &nbsp; </ td >
     
</ tr >
     
< tr >
       
< td  align ="right" > 教学点地址: </ td >
       
< td >< input  name ="CenterAddress2"  type ="text"  size ="40"   /></ td >
       
< td > &nbsp; </ td >
     
</ tr >
     
< tr >
       
< td  align ="right" > 教学点电话: </ td >
       
< td >< input  name ="CenterPhone2"  type ="text" size ="40"   /></ td >
       
< td > &nbsp; </ td >
     
</ tr >
     
< tr >
       
< td  align ="right" > 教学点交通指南信息: </ td >
       
< td >< textarea  name ="CenterTraffic2"  cols ="40"  rows ="6" ></ textarea ></ td >
       
< td > 多条线路之间用“;”分隔,如“乘坐16和99路在人民南路四段北站下; 乘坐303、78、61、45、12、19、27和34路在跳伞塔路口下”
     
</ tr >
     
< tr >
       
< td  align ="right"  width ="120" > 教学点示意图: </ td >
       
< td  width ="290"  align ="center" >< input  name ="image"  type ="file" >
       
< td > 教学点的图片表示,长宽比xx:xx的jpg文件,文件名格式:DDmaps+教学点ID.jpg,如“DDmapsLJD.jpg” </ td >
     
</ tr >
     
< tr >
       
< td  colspan ="3"  align ="center" >< input  name ="submit"  type ="submit"  value ="增加"   /> &nbsp;&nbsp;
                                      
< input  type ="reset"  name ="reset"  value ="重置"   /></ td >
     
</ tr >
   
</ table >
   
</ form >

        需要注意的是Form里一定要包含enctype="multipart/form-data"这句话。下面我们来看看以二进制方式读取表单的代码:

filesize  =  Request.TotalBytes  ' filesize是表单数据大小
filedata  =  Request.BinaryRead(filesize)  ' filedata是表单的二进制数据

        以上面的方式读取表单后,我们再用下面的语句在浏览器中查看表单中输入的数据是怎么表示的:

 Response.BinaryWrite(filedata)

       现在让我们看看表单的二进制表示方式吧:

-----------------------------7d733c3240e98 Content-Disposition: form-data; name="CenterID2" TEP -----------------------------7d733c3240e98 Content-Disposition: form-data; name="CenterName2" tempCenter -----------------------------7d733c3240e98 Content-Disposition: form-data; name="CenterAddress2" RenMinRoad -----------------------------7d733c3240e98 Content-Disposition: form-data; name="CenterPhone2" 88888888 -----------------------------7d733c3240e98 Content-Disposition: form-data; name="CenterTraffic2" -----------------------------7d733c3240e98 Content-Disposition: form-data; name="image"; filename="C:/Documents and Settings/milanello/My Documents/My Pictures/AC Milan.jpg" Content-Type: image/pjpeg ?JFIFddDucky&Adobed &&))&&87778>>>>>>>>>> ''#% %#++''++55355>>>>>>>>>>22"!1Aa"Qq?4?BsDb偄#1Aa!Qq?? ?樵?Y儆b?ead桺 eF踨鏏斢斷觠鋭餲絴=G烩c榩/,鵵0恆猝? 交lΒl垲躾y銦n|? Yku憯泍sA缛謎G啐1攆棥F拞?缺%凂y]=岴)J襐)JP 徃fG亙憶/饲崵n?鲽詩??h?榃鮵j}谠熉幠臯Isiqr3r檞,?k 霊簬惴?"E鶲;蜥S2鍙q8K氹封g?T剎?V堩s{/p?厷i塮i?菈$€I5?龜磍傻?J?猛V!An<m獰祄N迖?敠咎安p蕯诒H鑎栜g馅攅齨#?_頓t擇5qX這淞6V跻腴L裆悅?穭胤-6鏪*???3i琟珪t?NQz?昌1?峀?鲐;?{^:+?€世哠葍缞2b栌潢p萸k死)4藎l梻/l?霊 ??h飙:1?颐丈z鋳#x?酮f^)儇m朌樆r楙^幛?IY]牃軝t貽}<睾灈訖彎窵?hF渪a攊?,;盱獢謻嵊辈_з$紃n蚆I6﨓竣遛3?z湶奡俍!o魝?旱5h踑诙? 鈵-?l菋1鲹z橵?漘 YtV?@?@G销I~W/鋦瞑?臃瑶o鄚繌})@X覕??? -----------------------------7d733c3240e98 Content-Disposition: form-data; name="submit" 增加 -----------------------------7d733c3240e98--

    分析浏览器上显示的二进制代码,发现每一段代码包括四个部分,每一部分的内容是用回车换行符号来进行分隔的:

    1 )第一部分(起始标志)
   -----------------------------7d733c3240e98 

    2 )第二部分(文件说明)
    如:Content-Disposition: form-data; name="CenterID2"

        3 )第三部分(文件内容)
    如果是其他表单内容,如文本框,则是你输入的内容,如TEP,而文件框则是你上传文件的二进制代码,就像上面那段代码中显示的乱码一样。

        4 )第四部分(结束标志)

    -----------------------------7d733c3240e98 

下面是完整的处理表单的代码:

if  request( " action " =   " Addnew "   then
     newline 
=  chrB( 13 &  chrB( 10 ' newline表示二进制的回车符
     filesize  =  Request.TotalBytes  ' filesize是表单数据大小
     filedata  =  Request.BinaryRead(filesize)  ' filedata是表单的二进制数据
     divider  =  leftB(filedata, clng (instrb(filedata,newline)) - 1 ' divider是分割符
      set  rst  =  Server.CreateObject( " ADODB.Recordset " )
     rst.open 
" Center " ,bb, 1 , 3
     rst.Addnew     
     k 
=   1      
     
While  instrb(k,filedata,divider)  <  instrb((instrb(k,filedata,divider) + lenb(divider)),filedata,divider)
        start 
=  instrb(k,filedata,divider)  +  lenb(divider)  + 2
        endsize 
=  instrb((instrb(k,filedata,divider)  +  lenb(divider)),filedata,divider)  -  start  -   2
        content 
=  midb(filedata,start,endsize)  ' 取文件说明部分
        start_name  =  instrb(content,toByte( " name="" " ))
        end_name 
=  instrb(start_name  +   6 ,content,toByte( " "" " ))
        nametag 
=  midb(content,start_name + 6 ,end_name - start_name - 6 ' 取文件说明部分中name=""中的内容,即表单元素的名称
        pos1_filename  =  instrb(end_name,content,toByte( " filename="" " ))  ' 如果是文件框,则文件说明部分应有filename="",那么pos1_filename不等于0
         If  pos1_filename  =   0   Then    ' 表单中不属于文件上传的数据处理
            namevalue  =  toStr(midb(content,end_name + 5 ,lenb(content) - end_name - 4 ))   ' 取文件内容
            '  将文件说明部分的name=""中的内容与表单元素的名称进行比较,把相应的内容加入数据库
             If ( InStr (toStr(nametag), " CenterID2 " >   0 ) Then
                rst(
" CenterID " =  namevalue
                session(
" CenterID " =  namevalue    ' 用于上传文件保存时的文件名中
               
            
End   If
            
If ( InStr (toStr(nametag), " CenterName2 " >   0 ) Then
                rst(
" CenterName " =  namevalue
            
End   If
            
If ( InStr (toStr(nametag), " CenterAddress2 " >   0 ) Then
                rst(
" CenterAddress " =  namevalue
            
End   If
            
If ( InStr (toStr(nametag), " CenterPhone2 " >   0 ) Then
                rst(
" CenterTel " =  namevalue
            
End   If

            
If ( InStr (toStr(nametag), " CenterTraffic2 " >   0 ) Then
                rst(
" CenterTraffic " =  namevalue
            
End   If
            
' Response.Write (namevalue)
             ' Response.Write("<br>")
         else     ' 处理文件上传部分的数据
            pos2_filename  =  instrb(pos1_filename + 10 ,content,toByte( " "" " ))
            fullpath 
=  midb(content,pos1_filename + 10 ,pos2_filename - pos1_filename - 10 ' 从文件说明部分中取出文件路径
             If (fullpath  <>   "" ) Then   ' 如果有上传的文件,执行以下代码
                 dim  bStart   '  取二进制流文件部分开始位置 
                bStart  =  instrb(start,filedata,newline & newline) + 3
            
                
dim  bEnd  '  取二进制流文件部分结束位置 
                bEnd = inStrB(bStart + 6 ,filedata,divider) - bStart - 3  
            
                
dim  stm  '  定义一个 adodb.stream 源对象 stm, 用以拷贝二进制流文件部分至另一 adodb.stream fromStm 
                 set  stm = createObject ( " adodb.stream "
                stm.type
= 1   '  二进制模式 
                stm.mode = 3   '  指定打开模式为读写 
                stm.open 
                stm.write filedata 
' 写入二进制流内容 
         
                
dim  fromStm  ' 定义 adodb.stream 对象 fromStm, 以保存文件 
                 set  fromStm = createOBject ( " adodb.stream "
                
with  fromStm 
                    .type
= 1  
                    .mode
= 3  
                    .open 
                    stm.position 
=  bStart  '  指定 stm 对象的起始位置, 以变量 bStart 的值为起始位置 
                    stm.copyTo fromStm, bEnd  '  拷贝 stm 二进制流至 fromStm 对象, 长度为 bEnd 变量的长度 
                    .saveTofile server.MapPath( " ./ " ) & " imageDDmap " & session( " CenterID " ) & " .jpg " , 2 '  保存文件, 如果存在相同名称, 则覆盖 
                    .close 
                
end   with  
                
set  fromStm  =   nothing  
      
                stm.close 
                
set  stm  =   nothing  
                rst(
" CenterMap " =   " Image/DDmap " & session( " CenterID " ) & " .jpg "    ' 将文件的相对路径写入数据库中
             end   if   
        
end   if
        k 
=  instrb((instrb(k,filedata,divider) + lenb(divider)),filedata,divider) 
     
Wend
     rst.update
     rst.close
     
set  rst  =   nothing
     session.abandon
  
end   if   
  
function  toStr(Byt)   ' 将二进制转换为字符串
     toStr = ""
     
for  i = 1   to  lenb(byt)
    blow 
=  midb(byt,i, 1 )
    
if   ascb(blow) > 127   then     
    toStr 
=  toStr & chr (ascw(midb(byt,i + 1 , 1 ) & blow))   '
    i  =  i + 1
    
else
    toStr 
=  toStr & chr (ascb(blow))
    
end   if
    
Next
 
End function

Function  toByte(Str)   ' 将字符串转换为二进制
    dim  i,iCode,c,iLow,iHigh
   toByte
= ""
   
For  i = 1   To   Len (Str)
   c
= mid (Str,i, 1 )
   iCode 
= Asc (c)
   
If  iCode < 0   Then  iCode  =  iCode  +   65535
   
If  iCode > 255   Then
     iLow 
=   Left ( Hex ( Asc (c)), 2 )
     iHigh 
= Right ( Hex ( Asc (c)), 2 )
     toByte 
=  toByte  &  chrB( " &H " & iLow)  &  chrB( " &H " & iHigh)
   
Else
     toByte 
=  toByte  &  chrB(AscB(c))
   
End   If
   
Next
 
End function

    总结,以上例子只是上传文件的一种方法,当应用不同时,处理的方法应随机应变,希望这篇文章能起到抛砖引玉的作用。

展开阅读全文

没有更多推荐了,返回首页