java项目中附件的上传下载

来源:互联网 发布:nginx源码 编辑:程序博客网 时间:2024/05/16 21:19
一、添加配置文件

    1)spring-mvc.xml文件   这个是注解包的扫描、视图解析、文件解析   内容如下:


<?xml version="1.0" encoding="UTF-8"?>
<beans default-lazy-init="true"
    xmlns="http://www.springframework.org/schema/beans"
    xmlns:p="http://www.springframework.org/schema/p"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:context="http://www.springframework.org/schema/context"
    xmlns:tx="http://www.springframework.org/schema/tx"
    xmlns:mvc="http://www.springframework.org/schema/mvc"
    xsi:schemaLocation="  
       http://www.springframework.org/schema/beans   
       http://www.springframework.org/schema/beans/spring-beans-4.3.xsd  
       http://www.springframework.org/schema/mvc   
       http://www.springframework.org/schema/mvc/spring-mvc-4.3.xsd   
       http://www.springframework.org/schema/tx   
       http://www.springframework.org/schema/tx/spring-tx-4.3.xsd   
       http://www.springframework.org/schema/context  
       http://www.springframework.org/schema/context/spring-context-4.3.xsd" >  

    <!-- spring 包的扫描
     1)dao
     2)service (@Service)
     3)controller(@Controller)
     4).....
     -->
    <context:component-scan base-package="cn.tedu.ttms" />
    <!-- spring mvc 注解及类型转换 -->
    <mvc:annotation-driven conversion-service="conversionService" />
    <bean id="conversionService" class="org.springframework.format.support.FormattingConversionServiceFactoryBean"></bean>
    <!-- spring mvc 视图解析器 -->    
    <!-- 定义跳转的文件的前后缀 ,视图模式配置 -->
    <bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver">
        <!-- 自动给后面action的方法return的字符串加上前缀和后缀,变成一个 可用的url地址 -->
        <property name="prefix" value="/WEB-INF/" />
        <property name="suffix" value=".jsp"></property>
    </bean>  
    <!-- 定义文件解释器 -->  
    <bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver">    
    <!-- 设置默认编码 -->  
    <property name="defaultEncoding" value="utf-8"></property>  
    <!-- 上传图片最大大小9M-->   
    <property name="maxUploadSize" value="9242440"></property>  
    <!-- 内存中的最大值 -->
    <property name="maxInMemorySize" value="40960" />
      
</bean>
     
</beans>

    2)spring-mybatis.xml文件  这个是自动扫描mapper.xml映射文件 内容如下:

<?xml version="1.0" encoding="UTF-8"?>
<beans default-lazy-init="true"
    xmlns="http://www.springframework.org/schema/beans"
    xmlns:p="http://www.springframework.org/schema/p"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:context="http://www.springframework.org/schema/context"
    xmlns:tx="http://www.springframework.org/schema/tx"
    xmlns:mvc="http://www.springframework.org/schema/mvc"
    xsi:schemaLocation="  
       http://www.springframework.org/schema/beans   
       http://www.springframework.org/schema/beans/spring-beans-4.3.xsd  
       http://www.springframework.org/schema/mvc   
       http://www.springframework.org/schema/mvc/spring-mvc-4.3.xsd   
       http://www.springframework.org/schema/tx   
       http://www.springframework.org/schema/tx/spring-tx-4.3.xsd   
       http://www.springframework.org/schema/context  
       http://www.springframework.org/schema/context/spring-context-4.3.xsd" >  

     <bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
       <property name="dataSource" ref="dataSource"></property>
       <property name="configLocation" value="classpath:mybatis-config.xml"></property>
       <!-- 自动扫描mapping.xml文件 -->
       <property name="mapperLocations" >
        <list><value>classpath:mapper/*.xml</value></list>
       </property>
    </bean>
    <!-- Mapper接口所在包,Spring会自动查找其下的Mapper -->
    <bean class="org.mybatis.spring.mapper.MapperScannerConfigurer">
        <property name="basePackage" value="cn.tedu.**.dao "/>
    </bean>
 
</beans>


    3)spring-pool.xml文件   这个是读取数据库的配置文件和建立连接池,连接池用的是durid 内容如下:

<?xml version="1.0" encoding="UTF-8"?>
<beans default-lazy-init="true"
    xmlns="http://www.springframework.org/schema/beans"
    xmlns:p="http://www.springframework.org/schema/p"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:context="http://www.springframework.org/schema/context"
    xmlns:tx="http://www.springframework.org/schema/tx"
    xmlns:mvc="http://www.springframework.org/schema/mvc"
    xsi:schemaLocation="  
       http://www.springframework.org/schema/beans   
       http://www.springframework.org/schema/beans/spring-beans-4.3.xsd  
       http://www.springframework.org/schema/mvc   
       http://www.springframework.org/schema/mvc/spring-mvc-4.3.xsd   
       http://www.springframework.org/schema/tx   
       http://www.springframework.org/schema/tx/spring-tx-4.3.xsd   
       http://www.springframework.org/schema/context  
       http://www.springframework.org/schema/context/spring-context-4.3.xsd" >  

   <!-- 加载jdbc.properties文件(一般加载多个文件时
        可考虑使用此方式) -->
   <bean id="propertyConfigurer" class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">
        <property name="locations">
            <list>
                <value>classpath:jdbc.properties</value>
            </list>
        </property>
   </bean>
   <!-- 配置DRUID连接池(这个连接池的说明:
   http://github.com 在搜索栏输入druid查找)
   -->
   <bean id="stat-filter" class="com.alibaba.druid.filter.stat.StatFilter"
    lazy-init="true">
        <description>状态过滤器</description>
         <!-- 通过slowSqlMillis用来配置SQL慢的标准 -->
        <property name="slowSqlMillis" value="3000" />
         <!-- 以日志形式输出执行效率慢的SQL -->
        <property name="logSlowSql" value="true" />
        <!-- 通过mergeSql属性,合并SQL -->
        <property name="mergeSql" value="true" />
   </bean>
 
   <!--配置DruidDataSource连接池 -->
   <bean id="dataSource" class="com.alibaba.druid.pool.DruidDataSource"
        destroy-method="close" init-method="init" lazy-init="true">
        <property name="driverClassName" value="${jdbc.driver}" />
        <property name="url" value="${jdbc.url}" />
        <property name="username" value="${jdbc.username}" />
        <property name="password" value="${jdbc.password}" />
        <!-- 初始化连接大小 -->
        <property name="initialSize" value="${jdbc.initialSize}" />
        <!-- 连接池最大数量 -->
        <property name="maxActive" value="${jdbc.maxActive}" />
        <!-- 连接池最小空闲 -->
        <property name="minIdle" value="${jdbc.minIdle}" />
        <!-- 获取连接最大等待时间 -->
        <property name="maxWait" value="${jdbc.maxWait}" />
        <!--配置了maxWait之后,缺省启用公平锁,并发效率会有所下降,如果需要可以通过配置useUnfairLock属性为true使用非公平锁。 -->
        <property name="useUnfairLock" value="true" />
        <property name="defaultReadOnly" value="false" />
        
        <!-- 通过配置StatFilter,打开监控台统计功能 -->
        <property name="proxyFilters">
            <list>
                <ref bean="stat-filter" />
            </list>
        </property>
        <property name="filters" value="${jdbc.druid.filters}" />
        <!--<property name="connectionProperties" value="password=${username}"/>-->
        <property name="testWhileIdle" value="true" />
        <property name="testOnBorrow" value="false" />
        <property name="testOnReturn" value="false" />
        <property name="validationQuery" value="SELECT 1 from DUAL" />
        <property name="timeBetweenLogStatsMillis" value="${jdbc.timeBetweenLogStatsMillis}" />
     </bean>
</beans>

二、实体类
    写一个数据库中关于文件的实体类 并添加get和set方法

    注意点:类的属性名称要和表的字段的名称一样

三、写dao层
    写一个接口,添加操作数据库的方法   内容如下:

package cn.tedu.ttms.dao;

import java.util.List;

import cn.tedu.ttms.entity.Attachement;

public interface AttachementDao {
    //查询表里面所有的上传过的文件
    List<Attachement> findObjects();
    //根据文件的摘要查询记录。用来判断要上传的文件是否已经存在
    int findObjectByDisgest(String fileDisgest);
    //根据id查询记录
    Attachement findAttachementById(Integer id);
    //上传文件,插入到表里面
    int insertObject(Attachement attachement);
}

四、根据dao里面的接口写mapper映射文件

    注意点:1)每条语句的id的值要和dao接口里面的方法想对应
        2)resultType返回值类型要写全名(即:包名.类名) parameterType参数类型也要写全名的

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<!--
 classpath:mapper/ProjectMapper.xml
 -->
<mapper namespace="cn.tedu.ttms.dao.AttachementDao">

    <select id="findObjects"
    resultType="cn.tedu.ttms.entity.Attachement">
       select *
       from tms_attachements
       order by createdTime desc
    </select>
    
    <select id="findObjectByDisgest"
      resultType="java.lang.Integer">
      select count(*)
      from tms_attachements
      where fileDisgest=#{fileDisgest}
    </select>
    
    <select id="findAttachementById"
     resultType="cn.tedu.ttms.entity.Attachement">
       select *
       from tms_attachements
       where id=#{id}
    </select>
    
    <insert id="insertObject"
    parameterType="cn.tedu.ttms.entity.Attachement">
    
       insert into tms_attachements
       (id,title,fileName,contentType,
        filePath,fileDisgest,athType,
        belongId,createdTime,modifiedTime,
        createdUser,modifiedUser)
        values(
        #{id},#{title},#{fileName},#{contentType},
        #{filePath},#{fileDisgest},#{athType},
        #{belongId},#{createdTime},#{modifiedTime},
        #{createdUser},#{modifiedUser})
    
    </insert>
    
</mapper>

五、service层
    写一个service接口,写上要进行业务逻辑处理的方法
package cn.tedu.ttms.service;

import java.io.File;
import java.util.List;

import org.springframework.web.multipart.MultipartFile;

import cn.tedu.ttms.entity.Attachement;

public interface AttachementAervice {
    //查询所有记录
    List<Attachement> findObjects();
    //上传,插入一条记录
    void saveObject(String title,Integer athType,Integer belongId,MultipartFile mFile,String serverPath);
    //根据id查询某条记录
    File findObjectById(Integer id);
}


六、service接口的实现类

    实现接口之后重写接口的所有方法,进行具体业务逻辑的处理
    将dao层接口依赖注入进来
package cn.tedu.ttms.service.Impl;

import java.io.File;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;
import java.util.UUID;

import javax.annotation.Resource;

import org.apache.commons.codec.digest.DigestUtils;
import org.apache.commons.io.FilenameUtils;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;

import cn.tedu.ttms.dao.AttachementDao;
import cn.tedu.ttms.entity.Attachement;
import cn.tedu.ttms.service.AttachementAervice;

@Service
public class AttachementServiceImpl implements AttachementAervice{
    @Resource
    private AttachementDao attachementDao;

    public List<Attachement> findObjects() {
        // TODO Auto-generated method stub
        return attachementDao.findObjects();
    }

    public void saveObject(String title, Integer athType, Integer belongId, MultipartFile mFile, String serverPath) {
        //上传文件,获得文件名
        String oFileName=mFile.getOriginalFilename();
        byte[] fileBytes;
        File dest = null;
        String fileDigest = null;
        try {
            fileBytes=mFile.getBytes();
            fileDigest=DigestUtils.md5Hex(fileBytes);
            
            //int count=attachementDao.findObjectByDisgest(fileDigest);
            
            SimpleDateFormat sdf=new SimpleDateFormat("yyyy/MM/dd");
            String dateStr=sdf.format(new Date());
            String newFileName=UUID.randomUUID().toString()+"."+FilenameUtils.getExtension(oFileName);
            String realPath=serverPath+"/uploads/"+dateStr+"/"+newFileName;
            dest=new File(realPath);
            File parent=dest.getParentFile();
            if(!parent.exists()){
                parent.mkdirs();
            }
            mFile.transferTo(dest);
            
            
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        Attachement t=new Attachement();
        t.setTitle(title);
        t.setFileName(oFileName);
        t.setFilePath(dest.getPath());
        t.setAthType(athType);//1
        t.setBelongId(belongId);//1
        t.setContentType(mFile.getContentType());
        t.setFileDisgest(fileDigest);
        t.setCreatedUser("admin");
        t.setModifiedUser("admin");
        attachementDao.insertObject(t);
        
    }

    public File findObjectById(Integer id) {
        
            //1.根据id查找记录     
            Attachement a=
            attachementDao.findAttachementById(id);
            
            //2.获得文件的真实路径,构建文件对象关联真实路径
            File file=new File(a.getFilePath());
            //3.检测文件是否存在,存在则下载 
            
            return file;
    }
    
    
}

七、写controller处理页面发过来的每个请求
    将service层的接口依赖注入进来
    其中有的返回的是JsonResult对象,那是我将结果都封装成一个对象

package cn.tedu.ttms.controller;

import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.List;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.multipart.MultipartFile;

import java.io.File;
import java.io.IOException;

import cn.tedu.ttms.entity.Attachement;
import cn.tedu.ttms.service.AttachementAervice;

@Controller

public class fileupdow {
    @Resource
    private AttachementAervice attachementService;
    
    //首页的跳转
    @RequestMapping("/indexUI.do")
    public String indexUI(){
        return "index";
    }

    
    //文件上传功能
    @RequestMapping("/attach/doSaveObject")
    @ResponseBody
    public JsonResult saveObject(String title,Integer athType,Integer belongId,MultipartFile mFile,HttpServletRequest request){
        String serverPath=request.getServletContext().getRealPath("/");
        attachementService.saveObject(title, athType, belongId, mFile, serverPath);
        System.out.println("11111111111111111111111");
        return new JsonResult();
    
    }
    //查询所有,将记录全部显示出来
    @RequestMapping("/attach/doFindObjects")
    @ResponseBody
    public JsonResult doFindObjects(){
        List<Attachement> list=attachementService.findObjects();
        System.out.println("2222222222222222222222222222");
        return new JsonResult(list);
    }
    //文件的下载
    @RequestMapping("/attach/doDownload")
    @ResponseBody
    public byte[] doDownload(Integer id,
        HttpServletResponse response)throws IOException{
        File file=
        attachementService.findObjectById(id);
        //设置响应消息头(下载时的固定写法)
        response.setContentType(
        "appliction/octet-stream");
        response.setHeader(
        "Content-disposition",
        "attachment;filename="+file.getName());
        //根据文件真实路径构建一个Path对象 
        Path path=Paths.get(file.getPath());
        //将文件的字节返回(spring mvc 会自动将这字节写入到文件)
        return Files.readAllBytes(path);
        //return file;
    }
    
}


八、jsp页面的设置

<div id="container">
      <form method="post" id="uploadFormId"
              enctype="multipart/form-data">
            <!-- 查询表单 -->
            <div class="row page-search">
             <div class="col-md-12">
                <ul class="list-unstyled list-inline">
                    <li><input type="text" name="title" class="form-control"placeholder="附件标题"></li>
                    <li><input type="file" name="mFile" class="form-control"></li>
                    <li class='O1'><button type="button" class="btn btn-primary btn-upload" >上传</button></li>
                </ul>
              </div>
            </div>
            <!-- 列表显示内容 -->
            <div class="row col-md-12">
                <table class="table table-bordered">
                    <thead>
                        <tr>
                           <th>选择</th>
                           <th>标题</th>
                            <th>文件名</th>
                            <th>文件类型</th>
                            <th>操作</th>
                        </tr>
                    </thead>
                    <tbody id="tbodyId"></tbody>
                </table>
            </div>
        </form>
 </div>

九、相应的页面的js代码处理的

$(document).ready(function(){
    $("#uploadFormId")
    .on("click",".btn-upload",doUpload)
    .on("click",".btn-down",doDownload)
    doGetObjects();
});

/*下载*/
function doDownload(){
    var id=$(this).parent().parent().data("id");
    console.log("id="+id);
    var url="attach/doDownload.do?id="+id;
    document.location.href=url;
}
/*查询所有记录*/
function doGetObjects(){
    var url="attach/doFindObjects.do";
    $.post(url,function(result){
        if(result.state==1){
         setTableRows(result.data);
        }else{
         alert(result.message);
        }
    });
};
/*以列表形式显示所有记录*/
function setTableRows(list){
    var tBody=$("#tbodyId");
    tBody.empty();
    var tds='<td><input type="checkbox" name="selectItem" value="[id]"></td>'
        +'<td>[title]</td>'
        +'<td>[name]</td>'
        +'<td>[contentType]</td>'
        +'<td><input type="button" class="btn btn-default btn-down" value="下载"></td>';
    for(var i in list){
        var tr=$("<tr></tr>");
        tr.data("id",list[i].id);
        tr.append(
        tds.replace("[id]",list[i].id)
           .replace("[title]",list[i].title)
           .replace("[name]",list[i].fileName)
           .replace("[contentType]",list[i].contentType));
        tBody.append(tr);
    }
}


/*上传*/
function doUpload(){
    var url="attach/doSaveObject.do";
    //异步提交表单(先确保jquery.form.js已经引入了)
    $("#uploadFormId").ajaxSubmit({
        type:'post',
        url:url,
        data:{"athType":1,"belongId":1},
        dataType:'json',
        success:function(result){
            if(result.state==1){
            alert("上传成功!");
            doGetObjects();
            }else{
            alert(result.message);
            }
        }
    });//url,type,dataType,success,...
}













原创粉丝点击