【JAVAWEB】复习系列 第一部分

这篇博客详细介绍了JavaWeb开发中的关键知识点,包括JDBC的基本概念、原理及API使用,数据库连接池的原理与Druid的实践,Maven的标准化构建流程和依赖管理,以及Mybatis的使用与动态SQL操作。通过实例讲解了如何避免SQL注入,以及Mybatis中的事务处理和主键返回。此外,还涵盖了HTML基础和JavaScript的基本语法及引入方式。
摘要由CSDN通过智能技术生成

导语

本系列的导语与java复习系列相同

1.JDBC

1.1 JDBC概述

全称:( Java DataBase Connectivity ) 即Java 数据库连接

定义:是使用Java语言操作关系型数据库的一套API

功能:java代码通过jdbc这个接口与不同的数据库进行连接,数据库驱动即为jdbc这个接口的实现类,因此JDBC中定义了所有操作关系型数据库的规则

本质:是接口【sun公司定义的一套操作所有关系型数据库的规则】

  不同数据库厂商实现接口,提供了jar包

  故:使用JDBC 让驱动jar包执行操作

优点:

  1. 使用jdbc可以用相同的java语言操作不同数据库
  2. 替换数据库不影响java代码

  在具体使用时,操作哪个关系型数据库就需要导入该数据库的驱动包即可

1.2 JDBC原理

想使用java操作数据库,基本的思路是:

第一步:编写Java代码

第二步:Java代码将SQL发送到MySQL服务端

第三步:MySQL服务端接收到SQL语句并执行该SQL语句

第四步:将SQL语句执行的结果返回给Java代码

1.2.1 基本JDBC代码

实现jdbc的流程是:

1.创建工程,导入驱动jar包

2.编写代码

public static void main(String[] args) throws Exception {
//        1.注册驱动
        Class.forName("com.mysql.jdbc.Driver");
//        2.获取连接
        String username = "root";
        String password = "123456";
        String url = "jdbc:mysql://127.0.0.1:3306/test";
        Connection conn = DriverManager.getConnection(url, username, password);
//        3.定义sql
        String sql = "UPDATE yuangong SET id = 123";
//        4.获取执行sql的对象
        Statement statement = conn.createStatement();
//			5,执行sql
        int count = statement.executeUpdate(sql);//受影响的行数
//		6.处理结果
        System.out.println(count);
//        7.释放资源
        statement.close();//后执行的先关闭
        conn.close();
    }

记忆:

最基本的JDBC编写共有七步

1.注册驱动

确定用那个数据库
2.获取连接 连接数据库
3.定义SQL语句 执行什么操作
4.获取执行SQL对象 让获取到的连接来找人干活(执行sql)
5.执行SQL 让找来的人执行sql
6.处理返回结果 执行完了得有个交代
7.释放资源 让人回去,连接和找来的人都干活了(一个找人了,一个干活了),让他俩回去
后执行的资源

变化:MySQL 5之后的驱动包,可以省略注册驱动的步骤,因为它会自动加载jar包中META-INF/services/java.sql.Driver文件中的驱动类

1.3 JDBC API详解

1.3.1 DriverManager(驱动管理类)

该类在当前使用的方法有

方法 功能
static void registerDriver​(Driver driver) 使用 DriverManager注册给定的驱动程序
static Connection getConnection​(String url, String user, String password) 与url指向的数据库建立连接

1.3.1.1 registerDriver

在之前,我们使用:Class.forName("com.mysql.jdbc.Driver");这种反射的形式来注册驱动

按住ctrl点进Driver里,我们会看到

static {
        try {
            DriverManager.registerDriver(new Driver());
        } catch (SQLException var1) {
            throw new RuntimeException("Can't register driver!");
        }
    }

在静态代码块中,正是使用了registerDriver方法注册驱动

静态代码块会随着类的加载一起加载,因此只要使用反射加载Driver类即可

1.3.1.2 getConnection

参数说明:

参数 含义 语法 备注
url  连接路径 jdbc:mysql://ip地址(域名):端口号/数据库名称?参数键值对1&参数键值对2… 1.jdbc:mysql:是“协议”。
2.如果连接的是本机mysql服务器,并且mysql服务默认端口是3306,则url可以简写为:jdbc:mysql:///数
据库名称?参数键值对
3.配置 useSSL=false 参数,禁用安全连接方式,解决
警告提示
user 用户名 \ 填写数据库用户的用户名
password 密码 \ 填写数据库用户的密码

1.3.2 Connection(数据库连接对象)

方法 功能
Statement createStatement() 获取执行sql的对象
void setAutoCommit​(boolean autoCommit) 设置是否自动提交事务 true 自动提交 false 手动提交
⁠⁠void commit()⁠⁠ 提交事务
⁠⁠void rollback()⁠⁠ 回滚事务

事务

回顾:在java中,我们做过关于转账的内容,假设a转账给b,中途发生异常,a掏钱了b却没有得到钱,为了防止这件事的发生,我们需要将这整个转账过程作为一个事务,倘若中途出现异常,则会回滚到最初。

以上方法使用案例:

public static void main(String[] args) throws Exception {
//        2.获取连接
        String username = "root";
        String password = "123456";
        String url = "jdbc:mysql:///test?useSSL=false";
        Connection conn = DriverManager.getConnection(url, username, password);
//        3.定义sql
        String sql = "UPDATE yuangong SET id = 12333";
        String sql1 = "UPDATE yuangong SET yuangongid = 145544";
//        4.获取执行sql的对象
        Statement statement = conn.createStatement();
        try {
//        开启事务 手动提交事务
            conn.setAutoCommit(false);
//			5.执行sql
            int count = statement.executeUpdate(sql);//受影响的行数
            int i = 3/0;
			//6.处理结果
            System.out.println(count);
//        提交事务
            conn.commit();
        } catch (Exception e) {
//            回滚事务
            conn.rollback();
            e.printStackTrace();
        }
//        7.释放资源
        statement.close();//后执行的先关闭
        conn.close();
    }

1.3.3 Statement

方法 功能
int executeUpdate() 执行DDL、DML语句,返回执行语句后影响的行数
ResultSet executeQuery() 执行DQL语句,返回ResultSet对象,可以理解为查询出的结果集

使用Statement对象调用方法,也就是在JDBC书写中的第5步,执行sql中使用,之前已经有executeUpdate()方法的案例,之后我们会和ResultSet对象一起展示executeQuery()的使用。

1.3.4 ResultSet(结果集对象)

作用:封装了SQL查询语句的结果

方法 功能
boolean next()

将光标从当前位置向前移动一行并且判断当前行是否为有效行,

返回值true : 有效行,当前行有数据
false : 无效行,当前行没有数据

xxx getXxx(参数) xxx : 数据类型;如: int getInt(参数) ;String getString(参数)
参数
int类型的参数:列的编号,从1开始
String类型的参数: 列的名称

案例:

假设有这样一个表格

姓名  年龄
桂小太郎 27
让基尔希斯坦 19

想要得到参数姓名可以写getString("姓名"),也可写getString(1);

参数类型一定是存放的数据的类型,“姓名”是表头,“1”是姓名的顺序排第一个

使用案例:

//创建一个集合
        List<Account> list = new ArrayList<>();
//        1.光标向下移动一行,并判断当前行是否有数据
        while (resultSet.next()){
            int id = resultSet.getInt("id");
            String name = resultSet.getString("name");
            double money = resultSet.getDouble("money");
          //不论写数字还是表头名,结果都是一样的
            //        1.新建一个account对象
            Account account = new Account();
            //将结果存放进account对象里
            account.setId(id);
            account.setName(name);
            account.setMoney(money);
            list.add(account);
        }

1.3.5 PreparedStatement

功能:预编译SQL语句并执行,预防SQL注入问题

1.3.5.1 SQL注入

定义:SQL注入是通过操作输入来修改事先定义好的SQL语句,用以达到执行代码对服务器进行攻击的方法。

案例:

假设在登录场景中,我不知道某个人的密码是多少,通过sql注入强行登录

判断用户能否登录的sql语句为:

 String sql = "select * from tb_user where username = '"+name+"' and password = '"+pwd+"'";

也就是在用户表中查询全部信息,当用户名等于name,密码等于pwd的时候,这里的name和pwd都是变量名,相当于是接收用户传来的信息

在这种情况下,我如果将pwd写成:

 String pwd = "' or '1' = '1";

那么sql语句就会变为

select * from tb_user where username = 'sjdljfld'and password = ''or '1' = '1';

由于and比or先执行,所以  username = 'sjdljfld'and password = '' 用户名随便乱写and密码为空字符串判断为false,or '1' = '1'恒成立,结果为true,将强行登录

这就是sql注入

1.3.5.2 PreparedStatement使用

方法 功能
PreparedStatement prepareStatement​(String sql) connection的方法,获取 PreparedStatement 对象来操控sql语句
void setXxx(参数1,参数2) 给 ? 赋值
Xxx:数据类型 ; 如 setInt (参数1,参数2)
参数:
参数1: ?的位置编号,从1 开始
参数2: ?的值
int executeUpdate() 执行DDL、DML语句,返回执行语句后影响的行数
无需传递sql语句,因为获取SQL语句执行对象时已经对SQL语句进行预编译了。
ResultSet executeQuery() 执行DQL语句,返回ResultSet对象,可以理解为查询出的结果集
无需传递sql语句,因为获取SQL语句执行对象时已经对SQL语句进行预编译了。

想要使用PreparedStatement方法对sql语句的书写格式有要求

案例:

String sql = "select * from user where username =? and password = ?";

也就是说,sql语句中参数必须使用 ? 进行占位

因此想要赋值则需要:

 pstmt.setString(1,name);    代表第一个问号传入变量name

 pstmt.setString(2,pwd);       代表第二个问号传入变量pwd

案例:

@Test
    public void testLogin1() throws Exception {
//        1.加载驱动
        Class.forName("com.mysql.jdbc.Driver");
//        2.连接数据库
        Connection conn = DriverManager.getConnection("jdbc:mysql:///test2?useSSL=false&useServerPrepStmts=true", "root", "123456");
//        用户输入的用户名与密码
        String name = "zhangsan";
        String password = "123";
        //    3.编写sql语句
        String sql = "select * from tb_user where username = ? and password = ?";
//        4.创建statement
        PreparedStatement ps = conn.prepareStatement(sql);
        ps.setString(2,password);
        ps.setString(1,name);
//        5.执行sql语句
        ResultSet rs = ps.executeQuery();
//        6.处理结果
        if(rs.next()){//有无数据
            System.out.println("登陆成功");
        }else{
            System.out.println("登录失败");
        }
//        7.回收资源
        rs.close();
       ps.close();
        conn.close();
    }

为何PreparedStatement能够防止sql注入?

它是将特殊字符进行了转义,转义的SQL如下:

select * from tb_user where username = 'sjdljfld' and password = '\'or \'1\' = \'1'

1.3.5.3 PreparedStatement预编译原理

当Java代码操作数据库时,sql语句发送到MySQL服务器端,MySQL服务端会对sql语句进行如下操作:

1. 检查SQL语句  检查SQL语句的语法是否正确。

2. 编译SQL语句。将SQL语句编译成可执行的函数。

3. 执行SQL语句

检查SQL和编译SQL花费的时间比执行SQL的时间还要长。如果我们只是重新设置参数,那么检查SQL语句和编译SQL语句将不需要重复执行。这样就提高了性能。

开启预编译功能

1.在代码中编写url时需要加上以下参数

useServerPrepStmts=true

2.配置MySQL执行日志(重启mysql服务后生效)

在mysql配置文件(my.ini)中添加如下配置

log-output=FILE

general-log=1

general_log_file="D:\mysql.log"

slow-query-log=1

slow_query_log_file="D:\mysql_slow.log"

long_query_time=2

1.4 数据库连接池

1.4.1 数据库连接池概述

定义:数据库连接池是个容器,负责分配、管理数据库连接(Connection)

和java的线程池非常类似

它允许应用程序重复使用一个现有的数据库连接,而不是再重新建立一个;

释放空闲时间超过最大空闲时间的数据库连接来避免因为没有释放数据库连接而引起的数据库连接遗漏

优点:

  1. 资源重用
  2. 提升系统响应速度
  3. 避免数据库连接遗漏

常见的数据库连接池:DBCP,C3P0,Druid

我们会学习Druid连接池 Druid连接池是阿里巴巴开源的数据库连接池项目

1.4.2 Driud使用

使用步骤:

1.导入jar包 druid-1.1.12.jar

2.定义配置文件

driverClassName=com.mysql.jdbc.Driver

url=jdbc:mysql:///db1?

useSSL=false&useServerPrepStmts=true

username=root

password=1234

# 初始化连接数量

initialSize=5

# 最大连接数

maxActive=10

# 最大等待时间

maxWait=3000

3.加载配置文件

4.获取数据库连接池对象

5.获取连接

案例:

Druid数据库连接池演示
public class DruidDemo {
    public static void main(String[] args) throwsException {
        //1.导入jar包
        //2.定义配置文件
        //3. 加载配置文件
        Properties prop = new Properties();
        prop.load(new FileInputStream("jdbc-demo/src/druid.properties"));
        //4. 获取连接池对象
        DataSource dataSource =DruidDataSourceFactory.createDataSource(prop);
        //5. 获取数据库连接 Connection
        Connection connection =dataSource.getConnection();
        System.out.println(connection); //获取到了连接后就可以继续做其他操作了
      //System.out.println(System.getProperty("user.dir"));
   }
}

2 Maven

2.1 概述

定义:
Apache Maven 是一个项目管理和构建 工具 ,它基于项目对象模型 (POM) 的概念,通过一小段描述信息来管理项目的构 建、报告和文档。

官网http://maven.apache.org/

主要功能:
  • 提供了一套标准化的项目结构
  • 提供了一套标准化的构建流程(编译,测试,打包,发布……
  • 提供了一套依赖管理机制

记忆:

1.标准化的项目结构:
每一个开发工具( IDE)都有自己不同的项目结构,它们互相之间不通用。Maven 提供了一套标准化的项目结构,所有的 IDE 使用 Maven 构建的项目完全一样,所以 IDE 创建的 Maven 项目可以通用。
2. 标准化的构建流程:

开发过程中,代码需要进行编译、测试、打包、发布的过程,自己做很麻烦,使用Maven可以快捷的完成【之后就会展示,点击几下就可以,不用我们管】

3.依赖管理:

管理项目所依赖的 jar 包、插件。通过坐标导入,也提供了快捷键“alt+ins”直接搜索名称就可以导入。
总体来说:Maven是一个项目【标准化的项目结构】管理【依赖管理】和构建【标准化的构建流程】工具
从功能上来看,Maven把一些通用且琐碎的环节都承包了,这些琐碎的环节可以看做:怎么样在不同地方都能用,怎么样找第三方资源,怎么样直接测试/打包等。

2.2 Maven模型

  • 项目对象模型 (Project Object Model)
  • 依赖管理模型(Dependency)
  • 插件(Plugin)
图片来源:黑马
图片来源:黑马

我们将Maven模型与功能放在一起来理解记忆

2.2.1 标准化的构建流程 与 插件

代码需要进行编译、测试、打包、发布,这些过程在Maven中使用插件来辅助完成。

2.2.2 依赖管理 与 项目对象模型、依赖管理模型

Maven的依赖管理采用坐标管理的形式,而项目对象模型就是将项目抽象成一个对象模型,有自己专属的坐标

案例:

MYsql的坐标案例
<dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
            <version>5.1.32</version>
            <scope>provided</scope>
</dependency>
项目的坐标案例
<groupId>com.xuexi</groupId>
<artifactId>maven-project</artifactId>
<version>1.0-SNAPSHOT</version>

2.2.3 仓库

 Maven使用坐标来快速导入jar包,jar包的来源就是仓库

仓库分类:
  • 本地仓库:自己计算机上的一个目录
  • 中央仓库:由Maven团队维护的全球唯一的仓库   地址: https://repo1.maven.org/maven2/
  • 远程仓库(私服):一般由公司团队搭建的私有仓库
Maven寻找jar包的过程:
当项目中使用坐标引入对应依赖 jar 包后,首先会查找本地仓库中是否有对应的 jar包, 如果有,则在项目直接引用;如果没有,则去远程仓库寻找,还没有则去中央仓库中下载对应的jar 包到本地仓库。

2.3 Maven安装与配置简述

1.下载apache-maven-x.x.rar,并解压

2.配置环境变量MAVEN_HOME 为安装路径的bin目录

3.配置本地仓库:修改 conf/settings.xml 中的<localRespository>为一个指定目录作为本地仓库,用来存储jar包。

4.配置阿里云私服:修改 conf/settings.xml 中的<mirror> 标签

2.3.1 在IDEA中配置,使用Maven概述

1.配置Maven环境:

选择 IDEA 中 File --> Settings,搜索
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值