Struts2文件上传的运行过程实现

1.1.  文件上传的实现步骤

1)在表单<form>标签设置属性enctype的值为"multipart/form-data", enctype属性用于指定表单数据的编码方式, “multipart/form-data"编码方式指定以二进制流的方处理表单数据,并把文件域指定文件的内容封装在请求参数中。

       <form name=""action="" method="post"enctype="multipart/form-data">

2)在jsp页面添加文件域标签<input type="file" name="xxx"/>, name属性用于指定文件域的名称。

3)在Action类中定义3个属性来封装该文件域的信息:

     a. 类型为File的xxx属性封装该文件域对应的文件内容。

     b. 类型为String的xxxFileName属性封装文件域对应的文件的文件名。

      c. 类型为String的xxxContentType属性封装文件域对应的文件的文件类型。

  Example:

        JSP页面:

              <formname="" action="" method="post"enctype="multipart/form-data">

               <input type="file"name="upload"/>

               <inputtype="submit"/>

               </form>

             Action类:

          private File upload; //上传文件的File对象

          private String uploadFileName; //上传文件的文件名

          private String uploadContentType; //上传文件的内容类型

          //getter & setter方法

4)在Action类的业务方法中将File对象复制到服务器端对应的目录下。

  
   

//工具方法,将文件source的内容复制到文件dest

publicstaticvoid copyFile(File source,File dest) throws Exception{

      //创建输入流和输出流

      FileInputStream fis=new FileInputStream(source);

      FileOutputStream fos=new FileOutputStream(dest);

      //fis--->fos

      byte[] b=newbyte[1024];

      int len;

      while((len=fis.read(b))!=-1){

            fos.write(b, 0, len);

      }

      //关闭流

      fis.close();

      fos.close();   

  }


1.2.    Struts2 文件上传的运行过程

  1)fileupload拦截器将浏览器端的文件复制到服务端的临时目录下(由struts.multipart.saveDir指定):

               客户端文件 ---> saveDir/临时文件

  2)fileupload拦截器创建临时文件的File对象,赋给Action类对应File类型的upload属性:

               saveDir/临时文件 ---> File upload

     同时设置uploadFileName属性和uploadContentType属性。

  3)在Action类将File upload复制到服务器端指定的目录下:

               File upload ---> images/uploadFileName

---------------------------------------------------------------------------------------------------------------------------------------------------------------------->

具体实现

1.测试页面,主要关注文件域开始以及相应form表单跳转的action链接

<%@ page language="java" contentType="text/html; charset=utf-8"
    pageEncoding="utf-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>用户注册</title>
<link type="text/css" rel="stylesheet" href="/dang/css/user.css"/>
<script charset="gbk" type="text/javascript"  src="/dang/js/jquery-1.4.1.js"></script>
<script charset="gbk" type="text/javascript"  src="/dang/js/jquery.validate.js"></script>
<script type="text/javascript">
	//跟换验证码
	function changVcode(){
		//获取图像对象的元素对象
		var idVcode = document.getElementById("idVcode");
		//改变其属性
		idVcode.src="/dang/vcode.action?d="
				+new Date().getTime();
	}
</script>
<script type="text/javascript">
 $(function(){
     //表单验证
     $('#registerForm').validate({
       rules:{
         'user.userName':{required:true},
         'user.nickname':{required:true,minlength:4,maxlength:20},
         'user.userPassword':{required:true,minlength:6,maxlength:20},
         passwordAgain:{required:true,equalTo:'#txtPassword'},
         'user.email':{required:true,email:true},
         vcode:{required:true}
       },
       messages:{
         'user.userName':{required:"<img src='/dang/images/wrong.gif'/>用户名不能为空"},
         'user.nickname':{required:"<img src='/dang/images/wrong.gif'/>昵称不能为空",
                          minlength:"<img src='/dang/images/wrong.gif'/>昵称的长度不能少于{0}位",
                          maxlength:"<img src='/dang/images/wrong.gif'/>昵称的长度不能大于{0}位"},
         'user.userPassword':{required:"<img src='/dang/images/wrong.gif'/>密码不能为空",
                              minlength:"<img src='/dang/images/wrong.gif'/>密码的长度不能少于{0}位",
                              maxlength:"<img src='/dang/images/wrong.gif'/>密码的长度不能大于{0}位"},
         passwordAgain:{required:"<img src='/dang/images/wrong.gif'/>确认密码不能为空",
                    equalTo:"<img src='/dang/images/wrong.gif'/>确认密码和密码不相等"},                          
         'user.email':{required:"<img src='/dang/images/wrong.gif'/>Email地址不能为空",
                       email:"<img src='/dang/images/wrong.gif'/>Email地址格式无效"},
         vcode:{required:"<img src='/dang/images/wrong.gif'/>验证码不能为空"}
       },
       errorPlacement:function(error,element){
         error.appendTo(
        element.parent().next().find("span").eq(0));        
       }
     });
   });
</script>
</head>
<body>
<div class="container">
   <!-- header begin -->
   <div class="header">
     <a href="http://localhost:8080/dang">
       <img border="0" alt="我的当当网" src="/dang/images/logo_20110808.png"/>
     </a>
   </div>
   <!-- header end -->
   <!-- middle begin -->
   <div class="middle register">
      <h1>欢迎注册我的当当网!</h1>
      <div>
      <span class="error"></span>
       <form id="registerForm" name="registerForm" 
			 enctype="multipart/form-data"  
			 action="/dang/user/register.action"
			 method="post">  
         <table>
           <tr><td class="c1">请输入您的用户名:</td>
               <td class="c2">             
                <input id="userName" name="user.userName"/>
               </td>
               <td class="c3">
                <span id="userNameInfo" class="info"></span>
               </td></tr>
           <!-- 文件域开始 -->
           <tr><td class="c1">上传头像</td>
           		<td class="c2"><input type="file" name="upload"></td>
           </tr>
           <tr><td class="c3"></td></tr>
           <!-- 文件域开始 -->
           <tr><td class="c1">设置您的昵称:</td>
               <td class="c2"><input name="user.nickname"/></td>
               <td class="c3">
               <span class="tip">您的昵称由英文字母、数字、中文组成,长度为4-20个字符<br/></span>
               </td></tr>
           <tr><td class="c1">设置密码:</td>
               <td class="c2"><input id="txtPassword" type="password" name="user.userPassword"/></td>
               <td class="c3"><span class="tip">你的密码由英文字母、数字组成,长度6-20位<br/></span></td></tr>
           <tr><td class="c1">再次输入您设置的密码:</td>
               <td class="c2"><input type="password" name="passwordAgain"/></td>
               <td class="c3">
               <span class="tip"></span>
               </td></tr>
           <tr><td class="c1">请填写您的Email地址:</td>
               <td class="c2"><input name="user.email"/></td>
               <td class="c3"><span class="tip"></span></td></tr>
           <tr><td class="c1">验证码:</td>
               <td class="c2">
                 <input name="vcode" style="width:96px;"/>
                 <img id="idVcode" alt="验证码" src="/dang/vcode.action" align="bottom" style="height:20px;"/>
               </td>
               <td class="c3">
                  <span class="tip">请输入图片中文字  
                  <a id="idRefresh" href="#" οnclick="changVcode()">看不清,再换一张</a>
                  <br/>
                  <font color="red">${vcode_info}</font>
                  </span>
               </td></tr>
         </table>
         <div>
         <input id="btn_register" type="image" class="btn_register" alt="" 
                src="/dang/images/register.jpg"/>               
               
        </div>
       </form>
      </div>
   </div>
   <!-- middle end -->
   <!-- footer begin -->
   <div class="footer">
       Copyright © dangdang v2.0, 2011-2012, All Rights Reserved
           |     京ICP证08000853号  北京达内科技有限公司
        <br/>
        <img alt="" src="/dang/images/validate.gif"/>    
        <img alt="" src="/dang/images/knetSealLogo.png"/>
   </div>
   <!-- footer end -->
</div>
</body>
</html>

 

2.struts.xml配置信息

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE struts PUBLIC "-//Apache Software Foundation//DTD Struts Configuration 2.1//EN" "http://struts.apache.org/dtds/struts-2.1.dtd">
<struts>
     <!-- 定义用户模块对应的package -->
     <!-- package的属性:
              name - 指定package的名称,不能重复
               namespace - 指定访问package中的Action使用的路径,要求以/开头
               extends - 指定所继承的基包,一般继承自Struts2框架提供的基包struts-default
      -->
     <package name="user"
                       namespace="/user"
                       extends="struts-default">
       <!-- package用于管理Action的配置,
              在一个package中可以配置多个Action
           -->
           <!-- 配置LoginAction
                  package的namespace="/user"
                  actionName="login"
                  访问http://localhost:8080/dang/user/login.action
            -->
           <action name="login"
                          class="com.tarena.dang.user.action.LoginAction">
              <!-- 配置result ,jsp页面以/开头-->
               <result name="fail">/jsp/user/fail.jsp</result>
               <!-- 重定向到/dang/book/tolist.action -->
               <result name="success" type="redirectAction">
               		<param name="actionName">tolist</param>
               		<param name="namespace">/book</param>
               </result>
           </action>
           <!-- 配置RegisterAction -->
           <action name="register"
                         class="com.tarena.dang.user.action.RegisterAction">
                   <result name="ok">/jsp/user/registerOK.jsp</result>
                   <result name="input">/jsp/user/registerForm.jsp</result>
            </action>
            <!-- 配置LogoutAction -->
            <action name="logout"
                           class="com.tarena.dang.user.action.LogoutAction">
               <result name="login" 
                             type="redirect">
                             /jsp/user/loginForm.jsp
                </result>              
             </action>
     </package>
</struts>    


3.逻辑实现

package com.tarena.dang.user.action;

import java.io.*;

import org.apache.struts2.ServletActionContext;
import com.opensymphony.xwork2.ActionContext;
import com.tarena.dang.domain.User;
import com.tarena.dang.user.service.UserService;
import com.tarena.dang.user.service.UserServiceImpl;
/**
 * 注册页面的Action控制器业务实现
 * @author JimmyZhang
 *
 */
public class RegisterAction {
 private UserService userService;
 //使用实体对象简化与表单元素对应关系
 private User user;
 private String vcode;
 //定义与文件域upload赌赢的属性
 private File upload;//上传文件
 private String uploadFileName;//上传文件的文件名
 private String uploadContentType;//上传文件类型
 public String getVcode() {
  return vcode;
 }
 public void setVcode(String vcode) {
  this.vcode = vcode;
 }
 public User getUser() {
  return user;
 }
 public void setUser(User user) {
  this.user = user;
 }
 public RegisterAction(){
  userService = new UserServiceImpl();
  System.out.println("【RegisterAction】调用默认无参构造方法");
 }
 
 
 public String execute() throws Exception{
  //判断用户输入的验证与session中是否一直一致
  ActionContext ac = ActionContext.getContext();
  String session_vocode = (String)ac.getSession().get("vcode");
  if(!vcode.equals(session_vocode)){
   ac.put("vcode_info", "<img src='/dang/images/wrong.gif'/>验证码不匹配");
   return "input";
  }
  boolean isSuccess = userService.register(user);
  if(isSuccess){
   //上传头像,File upload-->/images/user/userName.jpg
   //得到服务器端的物理路径
   String path = ServletActionContext
     .getServletContext().getRealPath("/images/user/"+user.getUserName()+".jpg");
   //创建服务器端文件的File对象
   File dest = new File(path);
   //upload-->dest
   InputStream fis = new FileInputStream(upload);
   OutputStream fos = new FileOutputStream(dest);
   byte[] b = new byte[1024];
   int n;
   while((n=fis.read(b,0,b.length))!=-1){
    fos.write(b,0,n);    
   }
   fos.close();
   fis.close();
   //注册成功
   ac.put("user", user);
   return "ok";
  }else{
   return "input";
  }
  
 }
 public File getUpload() {
  return upload;
 }
 public void setUpload(File upload) {
  this.upload = upload;
 }
 public String getUploadFileName() {
  return uploadFileName;
 }
 public void setUploadFileName(String uploadFileName) {
  this.uploadFileName = uploadFileName;
 }
 public String getUploadContentType() {
  return uploadContentType;
 }
 public void setUploadContentType(String uploadContentType) {
  this.uploadContentType = uploadContentType;
 }

 
 
}


 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值