【Java实战项目】【超详细过程】—大饼的图片服务器2

本文主要讲述了maven项目创建后进行的一些基础配置及对数据库操作的前置准备工作(pom.xml、DBUtil类、Image类)。
maven项目创建可以看这里:Servlet-day01 这里面有详细介绍


pom.xml

pom.xml中放置了许多外部包

<?xml version="1.0" encoding="UTF-8"?>

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
  <modelVersion>4.0.0</modelVersion>

  <!--
  <groupId>org.example</groupId>
  <artifactId>untitled15</artifactId>
  <version>1.0-SNAPSHOT</version>
  <packaging>war</packaging>
  -->

  <groupId>com.bit</groupId>
  <artifactId>java_image_servlet</artifactId>
  <version>1.0-SNAPSHOT</version>
  <packaging>war</packaging>


  <name>untitled15 Maven Webapp</name>
  <!-- FIXME change it to the project's website -->
  <url>http://www.example.com</url>

  <properties>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    <maven.compiler.source>1.7</maven.compiler.source>
    <maven.compiler.target>1.7</maven.compiler.target>
  </properties>

  <dependencies>
    <dependency>
      <groupId>junit</groupId>
      <artifactId>junit</artifactId>
      <version>4.11</version>
      <scope>test</scope>
    </dependency>
    <!--json的依赖 gosn-->
    <dependency>
      <groupId>com.google.code.gson</groupId>
      <artifactId>gson</artifactId>
      <version>2.10.1</version>
    </dependency>
    <!--mysql依赖-->
    <dependency>
      <groupId>mysql</groupId>
      <artifactId>mysql-connector-java</artifactId>
      <version>8.0.13</version>
    </dependency>
    <!--上传文件的第三方仓库FileUpload-->
    <!-- https://mvnrepository.com/artifact/commons-fileupload/commons-fileupload -->
    <dependency>
      <groupId>commons-fileupload</groupId>
      <artifactId>commons-fileupload</artifactId>
      <version>1.4</version>
    </dependency>

    <!--servlet包-->
    <dependency>
      <groupId>javax.servlet</groupId>
      <artifactId>javax.servlet-api</artifactId>
      <version>3.1.0</version>
      <!--表示在开发阶段需要此依赖,部署到Tomcat后就不需要了-->
      <scope>provided</scope>

    </dependency>

  </dependencies>

  <build>
    <!--指定最终包的名称-->
    <finalName>java_image_servlet</finalName>
    <pluginManagement><!-- lock down plugins versions to avoid using Maven defaults (may be moved to parent pom) -->
      <plugins>
        <plugin>
          <artifactId>maven-clean-plugin</artifactId>
          <version>3.1.0</version>
        </plugin>
        <!-- see http://maven.apache.org/ref/current/maven-core/default-bindings.html#Plugin_bindings_for_war_packaging -->
        <plugin>
          <artifactId>maven-resources-plugin</artifactId>
          <version>3.0.2</version>
        </plugin>
        <plugin>
          <artifactId>maven-compiler-plugin</artifactId>
          <version>3.8.0</version>
        </plugin>
        <plugin>
          <artifactId>maven-surefire-plugin</artifactId>
          <version>2.22.1</version>
        </plugin>
        <plugin>
          <artifactId>maven-war-plugin</artifactId>
          <version>3.2.2</version>
        </plugin>
        <plugin>
          <artifactId>maven-install-plugin</artifactId>
          <version>2.5.2</version>
        </plugin>
        <plugin>
          <artifactId>maven-deploy-plugin</artifactId>
          <version>2.8.2</version>
        </plugin>
      </plugins>
    </pluginManagement>
  </build>
</project>

这些包中的具体内容以及如何加入的后续都会一一解释,首先我们这里解释一下这几个在这里插入图片描述

1.juit

   <dependency>
      <groupId>junit</groupId>
      <artifactId>junit</artifactId>
      <version>4.11</version>
      <scope>test</scope>
    </dependency>

用于在Java项目中添加JUnit测试框架。JUnit是一个用于编写和运行单元测试的框架,可以帮助开发者确保他们的代码能够按照预期工作。

2.gson

   <dependency>
      <groupId>com.google.code.gson</groupId>
      <artifactId>gson</artifactId>
      <version>2.10.1</version>
    </dependency>

用于在Java项目中添加Google的Gson库。Gson是一个用于处理JSON数据的Java库,可以将Java对象转换为JSON字符串,也可以将JSON字符串转换为Java对象

3.mysql依赖

   <dependency>
      <groupId>mysql</groupId>
      <artifactId>mysql-connector-java</artifactId>
      <version>8.0.13</version>
    </dependency>

用于在Java项目中添加MySQL的JDBC驱动。这个驱动允许Java程序与MySQL数据库进行交互。

4.servlet

    <dependency>
      <groupId>javax.servlet</groupId>
      <artifactId>javax.servlet-api</artifactId>
      <version>3.1.0</version>
      <!--表示在开发阶段需要此依赖,部署到Tomcat后就不需要了-->
      <scope>provided</scope>
    </dependency>

用于在Java Web应用程序中添加Servlet API。Servlet API提供了一组接口和类,用于开发基于Java的Web应用程序。


DBUtil类

在Java目录下创建dao包(数据访问层,蔚然数据库展开操作),在dao包中创建DBUtil类
JDBC相关操作不清楚可以看这篇文章:0基础速成Java环境下JDBC编程(细节超全,保姆级教程)

package dao;

import com.mysql.cj.jdbc.MysqlDataSource;

import javax.sql.DataSource;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.concurrent.SynchronousQueue;

public class DBUtil {
    //获取数据库连接
    private static final String URL = "jdbc:mysql://127.0.0.1:3306/image_table?characterEncoding=utf8&useSSL=false&serverTimezone=UTC&allowPublicKeyRetrieval=true";
    private static final String USERNAME = "root";
    private static final String PASSWORD = "123456";
    private static volatile DataSource dataSource = null;
    //定义了一个私有的、静态的、易变的DataSource类型的变量,并且将其初始化为null

    public static DataSource getDataSource(){
        if(dataSource == null){
            Synchronized(DBUtil.class);{
                if(dataSource == null){
                    dataSource = new MysqlDataSource();
                    // MysqlDataSource 对象强制转换为 MysqlDataSource 类型,
                    // 并使用 setURL()、setUser() 和 setPassword() 方法设置数据库连接的相关信息,包括 URL、用户名和密码。
                    MysqlDataSource tmpDataSour = (MysqlDataSource) dataSource;
                    tmpDataSour.setURL(URL);
                    tmpDataSour.setUser(USERNAME);
                    tmpDataSour.setPassword(PASSWORD);
                }
            }

        }

        return dataSource;
    }
    //建立连接
    public static Connection getConnection() throws SQLException {
        return getDataSource().getConnection();
    }
    //关闭连接
    public static void close(Connection connection, PreparedStatement preparedStatement, ResultSet resultSet) throws RuntimeException {
        if(resultSet != null) {

            try {
                resultSet.close();
            } catch (SQLException e) {
                throw new RuntimeException(e);
            }
        }
        if(preparedStatement != null){
            try {
                preparedStatement.close();
            } catch (SQLException e) {
                throw new RuntimeException(e);
            }
        }
        if (connection != null){
            try {
                connection.close();
            } catch (SQLException e) {
                throw new RuntimeException(e);
            }
        }
        }
    private static void Synchronized(Class<DBUtil> dbUtilClass) {
    }
}

1.数据库基本信息

private static final String URL = "jdbc:mysql://127.0.0.1:3306/image_table?characterEncoding=utf8&useSSL=false&serverTimezone=UTC&allowPublicKeyRetrieval=true";
private static final String USERNAME = "root";
private static final String PASSWORD = "123456";

(1)jdbc:mysql://127.0.0.1:3306/image_table?characterEncoding=utf8&useSSL=false&serverTimezone=UTC&allowPublicKeyRetrieval=true";

127.0.0.1:3306/ 数据库服务器的地址
image_table 数据库名,写自己需要对数据库中操作的那个数据库的名字
characterEncoding=utf8:客户端和服务器之间的通信字符编码为UTF-8
useSSL=false:表示不使用SSL进行安全连接
serverTimezone=UTC:设置服务器的时区为UTC
allowPublicKeyRetrieval=true:允许从服务器获取公钥。执行需要公钥认证的操作(如SSL/TLS连接)是必要的

(2)private static final String USERNAME = "root";:表示该数据库的名字为root
(3)private static final String PASSWORD = "123456";:表示该数据库的密码为123456

2.获取数据库连接

这是一个单例模式且线程安全的获取数据库连接的代码
单例模式详解:我给面试官讲解了单例模式后,他对我竖起了大拇指!
线程安全详解:多线程中synchronized和volatile-解决线程安全问题

    private static DataSource dataSource = null;
    public static DataSource getDataSource(){
    if(dataSource == null){
        dataSource = new MysqlDataSource();
        //类型加强,将dataSource 对象强制转换为 MysqlDataSource 类型
        MysqlDataSource tmpDataSour = (MysqlDataSource) dataSource;
        //使用 setURL()、setUser() 和 setPassword() 方法设置数据库连接的相关信息,包括 URL、用户名和密码
        tmpDataSour.setURL(URL); 
        tmpDataSour.setUser(USERNAME);
        tmpDataSour.setPassword(PASSWORD);
    }
    public static Connection getConnection() throws SQLException {
        //从一个数据源(DataSource)对象中获取数据库连接,以便执行SQL语句和操作数据库。
        // 数据源可以是配置文件中定义的数据源,也可以是通过编程方式创建的数据源
        return getDataSource().getConnection();

    }

(1)dataSource这个对象在一个程序中只用存在一份,且在使用前线判断是否创建了,若没有则创建,若已经创建则将URL,USERNAME,PASSWORD等信息设置进去
(2)if(dataSource == null){ dataSource = new MysqlDataSource(); } return dataSource;

判断dataSource是否为空,为空说明还未创建,此时应该创建dataSource对象并调用相关方法设置数据库 URL、数据库名和密码,若不为空则直接返回dataSource
这个判断很明显可以看出来这段代码为单例模式中的懒汉模式

(3)上述代码很明显不是一个线程安全的代码,解决方法:

首先:用volatiledataSource变量每次读取都会去主存中获取最新值,每次写入都会立即写主存(volatile不能保证原子性,即它不能替代synchronized关键字实现同步操作) 其次:Synchronized(DBUtil.class):同步块,确保在多线程环境下,只有一个线程可以执行这个代码块。锁对象为DBUtil.class 最后:在Synchronized(DBUtil.class)`同步块外加入一个if判断,判断dataSource变量是否为空

(4)return getDataSource().getConnection();

调用了getDataSource()方法获取数据源对象,然后调用该对象的getConnection()方法获取数据库连接,并将连接返回。


Image类

在java目录下的dao包中创建Image类

package dao;

public class Image {
    private int imageId;//图片ID
    private String imageName;//图片名字
    private int size;//图片大小
    private String uploadTime;//图片上传时间
    private String contentType;//图片类型
    private String path;//图片存储路径
    private String md5;//图片md5校验和
}

然后进行自动生成get方法、set方法和toString方法方便在后期直接调用这些方法

(1)自动生成get和set方法:alt+ins 选择Getter and Setter 全选,按下OK
(2)自动生成toString方法:alt+ins 选择toString… 全选,按下OK

最后结果:

package dao;

public class Image {
    private int imageId;//图片ID
    private String imageName;//图片名字
    private int size;//图片大小
    private String uploadTime;//图片上传时间
    private String contentType;//图片类型
    private String path;//图片存储路径
    private String md5;//图片md5校验和

    public int getImageId() {
        return imageId;
    }

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

    public String getMd5() {
        return md5;
    }

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

    public String getPath() {
        return path;
    }

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

    public String getContentType() {
        return contentType;
    }

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

    public String getUploadTime() {
        return uploadTime;
    }

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

    public int getSize() {
        return size;
    }

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

    public String getImageName() {
        return imageName;
    }

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

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


感谢您对大饼的支持
今天的你也很辛苦,晚安,明天见!

在这里插入图片描述

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

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值