栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

图片服务器及测试报告

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

图片服务器及测试报告

图片服务器项目 1.项目需求 1.1项目描述:

主要分为三大模块,上传模块,删除模块,展示模块。其中展示模块又可分为展示多张图片与放大图片。进入页面之后就可进行上传操作、删除操作。

1.2核心功能:

本项目主要分为两部分,数据存储部分与服务器模块,使用MySQL数据库存储图片属性,将图片内容保存在本次磁盘,服务器提供上传图片,获取图片属性,根据图片URL获取图片内容和删除图片等接口。

1.3重要知识点
  1. 简单的Web服务器设计开发能力(Servlet 的使用)
  2. 使用数据库(MySQL)JDBC 操作 MySQL
  3. 数据库设计(根据实际场景设计数据库表结构)
  4. 前后端交互的 API 的设计(基于HTTP协议)
  5. 认识 JSON 数据格式,学习使用 Java 中的 Gson 这个库操作 JSON 数据
  6. 强化 HTTP 协议的理解,学习测试 HTTP 服务器,Postman 工具的使用
  7. 基于 md5 进行校验
  8. 使用 HTML CSS Javascript 技术构建一个简单的网页
2.项目实现



代码展示:

DBUtil.java

package dao;



import com.mysql.jdbc.jdbc2.optional.MysqlDataSource;

import javax.sql.DataSource;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;


public class DBUtil {
    private static final String URL="jdbc:mysql://127.0.0.1:3306/image_server";
    private static final String USERNAME="root";
    private static final String PASSWORD="1231";

    private static volatile DataSource dataSource=null;

    public static DataSource getDataSource(){
        //通过此方法创建DataSource的实例
        if(dataSource==null){
            synchronized (DBUtil.class){
                if(dataSource==null){
                    dataSource=new MysqlDataSource();
                    MysqlDataSource tmpDataSource=(MysqlDataSource)dataSource;
                    tmpDataSource.setURL(URL);
                    tmpDataSource.setUser(USERNAME);
                    tmpDataSource.setPassword(PASSWORD);
                }
            }
        }
        return dataSource;
    }

    public static Connection getConnection() {
        try {
            return getDataSource().getConnection();
        } catch (SQLException exc) {
            exc.printStackTrace();
        }
        return null;
    }

    public static void close(Connection connection, PreparedStatement preparedStatement, ResultSet resultSet){
        try {
            if(resultSet!=null){
                resultSet.close();
            }
            if(preparedStatement!=null){
                preparedStatement.close();
            }
            if(connection!=null){
                connection.close();
            }
        } catch (SQLException exc) {
            exc.printStackTrace();
        }
    }

}

Image.java

package dao;


public class Image {
    private int imageId;
    private String imageName;
    private int size;
    private String uploadTime;
    private String contentType;
    private String path;
    private String md5;

    public int getImageId() {
        return imageId;
    }

    public void setImageId(int imageId) {
        this.imageId = imageId;
    }

    public String getImageName() {
        return imageName;
    }

    public void setImageName(String imageName) {
        this.imageName = imageName;
    }

    public int getSize() {
        return size;
    }

    public void setSize(int size) {
        this.size = size;
    }

    public String getUploadTime() {
        return uploadTime;
    }

    public void setUploadTime(String uploadTime) {
        this.uploadTime = uploadTime;
    }

    public String getContentType() {
        return contentType;
    }

    public void setContentType(String contentType) {
        this.contentType = contentType;
    }

    public String getPath() {
        return path;
    }

    public void setPath(String path) {
        this.path = path;
    }

    public String getMd5() {
        return md5;
    }

    public void setMd5(String md5) {
        this.md5 = md5;
    }

    @Override
    public String toString() {
        return "Image{" +
                "imageId=" + imageId +
                ", imageName='" + imageName + ''' +
                ", size=" + size +
                ", uploadTime='" + uploadTime + ''' +
                ", contentType='" + contentType + ''' +
                ", path='" + path + ''' +
                ", md5='" + md5 + ''' +
                '}';
    }
}

ImageDao.java

package dao;

import common.JavaImageServerException;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;


public class ImageDao {

    public void insert(Image image) {
        //1.获取数据库连接
        Connection connection = DBUtil.getConnection();
        //2.创建并拼装sql语句
        String sql = "insert into image_table values(null,?,?,?,?,?,?)";
        PreparedStatement statement = null;
        try {
            statement = connection.prepareStatement(sql);
            statement.setString(1, image.getImageName());
            statement.setInt(2, image.getSize());
            statement.setString(3, image.getUploadTime());
            statement.setString(4, image.getContentType());
            statement.setString(5, image.getPath());
            statement.setString(6, image.getMd5());

            //3.执行sql语句
            int ret = statement.executeUpdate();

            if(ret!=1){
                //程序出现问题,抛出一个异常
                throw new JavaImageServerException("插入数据库错误!");
            }

        } catch (SQLException exc) {
            exc.printStackTrace();
        } catch (JavaImageServerException e) {
            e.printStackTrace();
        }finally {
            //4.关闭连接和statement对象
            DBUtil.close(connection,statement,null);
        }
    }


    public List selectAll(){
        List images=new ArrayList();
        //1.获取数据库连接
        Connection connection=DBUtil.getConnection();
        //2.构造sql语句
        String sql="select * from image_table";
        PreparedStatement statement=null;
        ResultSet resultSet=null;
        try {
            //3.执行sql语句
            statement=connection.prepareStatement(sql);
            resultSet=statement.executeQuery();
            //4.处理结果集
            while(resultSet.next()){
                Image image=new Image();
                image.setImageId(resultSet.getInt("imageId"));
                image.setImageName(resultSet.getString("imageName"));
                image.setSize(resultSet.getInt("size"));
                image.setUploadTime(resultSet.getString("uploadTime"));
                image.setContentType(resultSet.getString("contentType"));
                image.setPath(resultSet.getString("path"));
                image.setMd5(resultSet.getString("md5"));
                images.add(image);
            }
            return images;

        } catch (SQLException exc) {
            exc.printStackTrace();
        }finally {
            //5.关闭连接
            DBUtil.close(connection,statement,resultSet);
        }
        return null;
    }


    public Image selectOne(int imageId){
        //1.获取数据库连接
        Connection connection=DBUtil.getConnection();
        //2.构造sql语句
        String sql="select * from image_table where imageId = ? ";
        //3.执行sql语句
        PreparedStatement statement=null;
        ResultSet resultSet=null;
        try {
            statement=connection.prepareStatement(sql);
            statement.setInt(1,imageId);
            resultSet=statement.executeQuery();
            //4.处理结果集
            if(resultSet.next()){
                Image image=new Image();
                image.setImageId(resultSet.getInt("imageId"));
                image.setImageName(resultSet.getString("imageName"));
                image.setSize(resultSet.getInt("size"));
                image.setUploadTime(resultSet.getString("uploadTime"));
                image.setContentType(resultSet.getString("contentType"));
                image.setPath(resultSet.getString("path"));
                image.setMd5(resultSet.getString("md5"));

                return image;
            }

        } catch (SQLException exc) {
            exc.printStackTrace();
        }finally {
            //5.关闭连接
            DBUtil.close(connection,statement,resultSet);
        }
        return null;
    }


    public void delete(int imageId){
        //1.获取数据库连接
        Connection connection=DBUtil.getConnection();
        //2.拼装sql语句
        String sql="delete from image_table where imageId=?";
        //3.执行sql语句
        PreparedStatement statement=null;
        ResultSet resultSet=null;
        try {
            statement=connection.prepareStatement(sql);
            statement.setInt(1,imageId);
            int ret=statement.executeUpdate();
            if(ret!=1){
                throw new JavaImageServerException("删除图片失败!");
            }

        } catch (SQLException exc) {
            exc.printStackTrace();
        } catch (JavaImageServerException e) {
            e.printStackTrace();
        } finally {
            //4.关闭连接
            DBUtil.close(connection,statement,resultSet);

        }
    }


    public Image selectByMd5(String md5){
        //1.获取数据库连接
        Connection connection=DBUtil.getConnection();
        //2.构造sql语句
        String sql="select * from image_table where md5 = ? ";
        //3.执行sql语句
        PreparedStatement statement=null;
        ResultSet resultSet=null;
        try {
            statement=connection.prepareStatement(sql);
            statement.setString(1,md5);
            resultSet=statement.executeQuery();
            //4.处理结果集
            if(resultSet.next()){
                Image image=new Image();
                image.setImageId(resultSet.getInt("imageId"));
                image.setImageName(resultSet.getString("imageName"));
                image.setSize(resultSet.getInt("size"));
                image.setUploadTime(resultSet.getString("uploadTime"));
                image.setContentType(resultSet.getString("contentType"));
                image.setPath(resultSet.getString("path"));
                image.setMd5(resultSet.getString("md5"));

                return image;
            }

        } catch (SQLException exc) {
            exc.printStackTrace();
        }finally {
            //5.关闭连接
            DBUtil.close(connection,statement,resultSet);
        }
        return null;
    }

}

ImageServlet.java

package api;

import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import dao.Image;
import dao.ImageDao;
import org.apache.commons.codec.digest.DigestUtils;
import org.apache.commons.fileupload.FileItem;
import org.apache.commons.fileupload.FileItemFactory;
import org.apache.commons.fileupload.FileUploadException;
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
import org.apache.commons.fileupload.servlet.ServletFileUpload;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.File;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;
import java.util.SimpleTimeZone;


@WebServlet("/image")
public class ImageServlet extends HttpServlet{
    

    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        String imageId=req.getParameter("imageId");
        if(imageId==null||imageId.equals("")){
            selectAll(req,resp);
        }else{
            selectOne(imageId,resp);
        }
    }

    private void selectOne(String imageId, HttpServletResponse resp) throws IOException {

        resp.setContentType("application/json; charset=utf-8");
        ImageDao imageDao=new ImageDao();
        Image image=imageDao.selectOne(Integer.parseInt(imageId));

        Gson gson=new GsonBuilder().create();
        String jsonData=gson.toJson(image);
        resp.getWriter().write(jsonData);

    }

    private void selectAll(HttpServletRequest req, HttpServletResponse resp) throws IOException {
        resp.setContentType("application/json; charset=utf-8");
        ImageDao imageDao=new ImageDao();
        List images=imageDao.selectAll();

        Gson gson=new GsonBuilder().create();

        String jsonData=gson.toJson(images);
        resp.getWriter().write(jsonData);

    }

    
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        //1.获取图片的属性信息,并且存入数据库
            //a.固定格式
        FileItemFactory factory=new DiskFileItemFactory();
        ServletFileUpload upload=new ServletFileUpload(factory);
            //b.通过upload对象进一步解析请求(解析HTTP请求中奇怪的body中的内容)
                //FileItem代表一个上传文件的对象
        List items=null;
        try {
            //理论上来说,http支持一个请求同时上传多个文件
            items=upload.parseRequest(req);
        } catch (FileUploadException e) {
            //解析出错
            e.printStackTrace();
            //告诉客户端出现的具体错误
            resp.setContentType("application/json; charset:utf-8");
            resp.getWriter().write("{"ok":false,"reason":"请求解析失败"}");
            return;
        }
            //c.把FileItem中的属性提取出来,转换成Image对象,才能存储到数据库中
            //当前只考虑一张图片的情况
        FileItem fileItem=items.get(0);
        Image image=new Image();
        image.setImageName(fileItem.getName());
        image.setSize((int)fileItem.getSize());

        //手动获取当前时间,并格式化日期,yyyyMMdd
        SimpleDateFormat simpleDateFormat=new SimpleDateFormat("yyyyMMdd");
        image.setUploadTime(simpleDateFormat.format(new Date()));
        image.setContentType(fileItem.getContentType());

        image.setMd5(DigestUtils.md5Hex(fileItem.get()));
        //自己构造一个路径来保存
        image.setPath("./image/"+image.getMd5());

        ImageDao imageDao=new ImageDao();

        Image existImage=imageDao.selectByMd5(image.getMd5());

        imageDao.insert(image);

        //2.获取图片内容信息,并且写入磁盘
        if(existImage==null) {
            File file = new File(image.getPath());
            try {
                fileItem.write(file);
            } catch (Exception e) {
                e.printStackTrace();

                resp.setContentType("application/json; charset:utf-8");
                resp.getWriter().write("{"ok":false,"reason":"写入磁盘失败"}");
                return;
            }
        }

        //3.给客户端返回一个结果数据
       
        resp.sendRedirect("index.html");
    }


    
    @Override
    protected void doDelete(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        resp.setContentType("application/json;charset:utf-8");
        //1.先获取到请求中的imageId
        String imageId=req.getParameter("imageId");
        if(imageId==null||imageId.equals("")){
            resp.setStatus(200);
            resp.getWriter().write("{"ok":false,"reason":"解析请求失败"}");
            return;
        }

        //2.创建ImageDao对象,查到该图片的属性,文件路径
        ImageDao imageDao=new ImageDao();
        Image image=imageDao.selectOne(Integer.parseInt(imageId));
        if(image==null){
            resp.setStatus(200);
            resp.getWriter().write("{"ok":false,"reason":"imageId在数据库中不存在"}");
            return;
        }

        //3.删除数据库中的记录
        imageDao.delete(Integer.parseInt(imageId));
        //4.删除本地磁盘文件
        File file=new File(image.getPath());
        file.delete();
        resp.setStatus(200);
        resp.getWriter().write("{"ok":true}");

    }
}

ImageShow.java

package api;

import dao.Image;
import dao.ImageDao;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.OutputStream;



@WebServlet("/imageShow")
public class ImageShowServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        //1.解析出imageId
        String imageId=req.getParameter("imageId");
        if(imageId==null||imageId.equals("")){
            resp.setContentType("application/json;charset:utf-8");
            resp.getWriter().write("{"ok":false,"reason":"imageId解析失败"}");
            return;
        }
        //2.根据imageId查找数据库
        ImageDao imageDao=new ImageDao();
        Image image=imageDao.selectOne(Integer.parseInt(imageId));
        //3.根据路径打开文件,读取其中内容,写入到响应对象中
        resp.setContentType(image.getContentType());
        File file=new File(image.getPath());

        //由于图片为二进制文件,应该使用字节流方式读取文件
        OutputStream outputStream=resp.getOutputStream();
        FileInputStream fileInputStream=new FileInputStream(file);
        byte[] buffer=new byte[1024];
        while(true){
            int len=fileInputStream.read(buffer);
            if(len==-1){
                break;
            }
            //此时已经读到一部分数据,放入buffer中
            outputStream.write(buffer);
        }
        fileInputStream.close();
        outputStream.close();
    }
}

index.html




  
  
  
  
  
  CY 图片列表
  
  
  
  
  
  
  
  
  
  
  
  
  
    




CY 图片列表



{{image.imageName}}

© 2015 AllMobilize, Inc. Licensed under MIT license. Made with love By LWXYFER

pom.xml






  4.0.0
  war

  picture_Server
  org.example
  picture_Server
  1.0-SNAPSHOT

  
    
      
        org.mortbay.jetty
        maven-jetty-plugin
        6.1.7
        
          
            
              8888
              30000
            
          
          ${project.build.directory}/${pom.artifactId}-${pom.version}
          /
        
      
    
  

  
    
    
      mysql
      mysql-connector-java
      5.1.49
    

    
      javax.servlet
      javax.servlet-api
      3.1.0
      provided
    

    
      commons-fileupload
      commons-fileupload
      1.4
    

    
      com.google.code.gson
      gson
      2.8.5
    

    
      commons-codec
      commons-codec
      1.10
    

    
      commons-io
      commons-io
      2.4
    

    
      junit
      junit
      4.11
      test
    

  


3.界面展示



项目测试 1.单元测试

框架:junit框架

测试方法:白盒测试,主要对代码的路径覆盖、错误处理等进行测试。

步骤:

1.添加junit依赖

2.创建测试类

package dao;

import java.util.List;

import static org.junit.Assert.*;

public class ImageDaoTest {

    @org.junit.Test
    public void insert() {
        ImageDao imageDao=new ImageDao();
        Image image=new Image();

        image.setSize(195083);
        image.setUploadTime("20211014");
        image.setContentType("image/jpeg");
        image.setMd5("8a5a0eb24dd33c14f12e58fcae53d7f5");
        image.setImageName("test.jpg");
        image.setImageId(37);
        image.setPath("./image/8a5a0eb24dd33c14f12e58fcae53d7f5");

        imageDao.insert(image);
    }

    @org.junit.Test
    public void selectAll() {
        ImageDao imageDao = new ImageDao();
        List lists = imageDao.selectAll();
        System.out.println(lists.size());
        System.out.println();
        for (Image image:lists) {
            System.out.println("imageId = " + image.getImageId()+" "+"imageName = "+image.getImageName());
        }
    }

    @org.junit.Test
    public void selectOne() {
        ImageDao imageDao = new ImageDao();
        try {
            Image image = imageDao.selectOne(2);

            System.out.println(image.getImageName());
            System.out.println(image.getImageId());
            System.out.println(image.getSize());
            System.out.println(image.getMd5());
        }catch (Exception e){
            System.out.println("查询失败,imageId 不存在!!!");
        }
    }

    @org.junit.Test
    public void delete() {
        ImageDao imageDao = new ImageDao();
        List lists1 = imageDao.selectAll();
        System.out.println("删除前图片容量" + lists1.size());
        imageDao.delete(54);
        List lists2 = imageDao.selectAll();
        System.out.println("删除后图片容量" + lists2.size());
        if(lists1.size()>lists2.size()) {
            System.out.println("删除成功");
        }else {
            System.out.println("删除失败,imageId 不存在!!!");
        }
    }

    @org.junit.Test
    public void selectByMd5() {
        ImageDao imageDao = new ImageDao();
        try {
            Image image = imageDao.selectByMd5("fbab242a577efdf0c530a27a92e0c255");
            System.out.println(image.getImageId());
            System.out.println(image.getImageName());
            System.out.println(image.getPath());
        } catch (Exception e) {
            System.out.println("查询失败,Md5 不存在!!!");
        }
    }
}
2.系统功能测试

编写测试用例

黑盒测试

3.自动化测试

编写自动化测试脚本,测试上传,删除功能

unit框架

from selenium import webdriver
import unittest
import time

class imageTest(unittest.TestCase):
    def setUp(self):
        self.driver=webdriver.Chrome(executable_path=r"C:UsersAdministratorAppDataLocalGoogleChromeApplicationchromedriver.exe")
        self.driver.get("http://localhost:8080/picture_Server/index.html")
        self.driver.maximize_window()

    def tearDown(self):
        self.driver.quit()

    def test_upload(self):
        driver=self.driver
        driver.find_element_by_name("upload").send_keys("C:/Users/Administrator/Pictures/背景/yy.jpg")
        driver.find_element_by_xpath("/html/body/nav/div/form/div[2]/input").click()
        time.sleep(6)

    @unittest.skip("skipping")
    def test_delete(self):
        driver=self.driver
        driver.find_element_by_xpath("/html/body/div[1]/figure/div/div[6]/button").click()
        time.sleep(6)
        alert=driver.switch_to.alert
        alert.accept()
        time.sleep(6)

    if __name__ == '__main__':
        unittest.main()
4.性能测试

使用loadRunner进行性能测试

录制脚本(上传图片功能)



进行测试(设置3个用户并发,每5s退出一个)

生成测试报告

我们以测试场景“上传图片”为例,对测试报告进行说明

1.测试说明

功能上传图片
测试目的进行上传图片操作,评估服务器承受能力
场景说明打开首页,点击登录,选择照片,点击上传
事务说明上传图片
参数设置通过HP LoadRunner11.00压力测试工具,导入录制脚本,设置测试1台控制主机,1台压力测试机被控制机,设置参数如下: Start vusers:3,100Vusers every 00:00:05 Duration:Run 3 minute Stop vusers:3Vusers every 00:00:05 All user:3

2.结果分析

指标最大平均
并发用户数3
TPS149
响应时间上传0.5000.014
关闭上传0.2500.014
点击率210108

1.统计信息摘要

下图说明本次测试运行的最大并发数为3,总吞吐量为2,481,485,491字节,平均每秒吞吐量为11,650,167字节,总的请求数为23,016,平均每秒的请求为108.056。对于吞吐量,单位时间内吞吐量越大,说明服务器的处理能越好,而请求数仅表示客户端向服务器发出的请求数,与吞吐量一般是成正比关系。

2.事务摘要

这部分给出了场景执行结束后相关Action的平均响应时间、通过率等情况,如下图所示,从该图中我们可以得到每个Action的平均响应时间与业务成功率。

3.HTTP响应摘要

该部分显示在场景执行中,每次发送HTTP请求所得到的状态。本次测试其中“HTTP200”有23,016,000次,基本所有的请求都能成功。

4.每秒点击数

“Hits per Second(每秒点击数)”反映了每秒向服务器提交的请求数量。下图显示的是“Hits per Second”与“Throughput”的复合图。如果两种图像的曲线都正常且基本一致,说明服务器能及时接受客户端的请求,并能返回结果。从图中可以看出,整体表现一般。

5.业务成功率

业务成功率就是事务成功率,用户一般把一个Action当做一笔业务,在“Transaction Summary”中我们可以很明确地看到每个事务的执行状态

5.项目bug

1.删除图片后刷新页面图片依旧存在
原因:删除图片未删除干净(上传时本地还有一份图片数据,删除时未删除)

2.上传已删除过的图片显示写失败,再次刷新页面才会显图片
原因:删除图片未删除干净(上传时本地还有一份图片数据,删除时未删除)

3.上传非图片的文件上传成功
建议:上传时进行判断

4.上传空文件上传成功
建议:上传时进行判断

5.全部图片在同一个页面,图片过多时,对服务器压力过大
原因:未分页

6.图片名称过长时未折行展示,影响美观
建议:折行展示

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/424993.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号