02尚硅谷书城案例-用户的注册

1、JavaEE 项目的三层架构

在这里插入图片描述

2、先创建书城需要的数据库和表

drop database if exists book;

create database book;

CREATE TABLE t_user(
id INT PRIMARY KEY auto_increment,
username VARCHAR(20) NOT NULL UNIQUE,
PASSWORD VARCHAR(32) NOT NULL,
email VARCHAR(200)
);

insert into t_user(username,password,email) values(‘admin’,‘admin’,‘admin@aiguigu.com’);
select * from t_user;

3、编写数据库表对应的 JavaBean 对象

public class User {
    private Integer id;
    private String username;
    private String password;
    private String email;
}

4、编写工具类 JdbcUtils

4.1、导入需要的 jar包(数据库和连接池需要)

在这里插入图片描述

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
导入完成之后:
在这里插入图片描述

4.2 在 src 源码目录编写 jdbc.properties 属性配置文件

在这里插入图片描述

4.3 编写 JdbcUtils 工具类

package com.utils;

import com.alibaba.druid.pool.DruidDataSource;
import com.alibaba.druid.pool.DruidDataSourceFactory;

import java.io.InputStream;
import java.sql.Connection;
import java.sql.SQLException;
import java.util.Properties;

public class JdbcUtils {

    private static DruidDataSource dataSource;

    static {

        try {
            Properties  properties = new Properties();
            //读取 jdbc.properties 属性配置文件
            InputStream inputStream = JdbcUtils.class.getClassLoader().getResourceAsStream("jdbc.properties");
            //从流中加载数据
            properties.load(inputStream);
            //创建 数据库 连接池
            dataSource = (DruidDataSource) DruidDataSourceFactory.createDataSource(properties);

        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    /*
    * 获取数据库连接池中的连接
    *@return 如果返回null,说明获取连接失败<br/>有值就是获取连接成功 */
    public static Connection getConnection(){
        Connection conn = null;
        try {
            conn = dataSource.getConnection();
        } catch (SQLException e) {
            e.printStackTrace();
        }
        return conn;
    }
    

    /*
    * 关闭连接,放回数据库连接池
    * */
    public static void close(Connection conn){
        if (conn != null){
            try {
                conn.close();
            } catch (SQLException e) {
                e.printStackTrace();
            }
        }
    }
}

4.4、Jdbc测试

package com.aiguigu.test;

import com.utils.JdbcUtils;
import org.junit.Test;

import java.sql.Connection;

public class JdbcUtilsTest {

    @Test
    public void testJdbcUtils(){
        for (int i = 0; i < 100; i++) {
            Connection connection = JdbcUtils.getConnection();
            System.out.println(connection);
            JdbcUtils.close(connection);
        }


    }
}

5、编写BaseDao(这一块不懂,得补)

package com.aiguigu.dao;

import com.utils.JdbcUtils;
import org.apache.commons.dbutils.QueryRunner;
import org.apache.commons.dbutils.handlers.BeanHandler;
import org.apache.commons.dbutils.handlers.BeanListHandler;
import org.apache.commons.dbutils.handlers.ScalarHandler;

import java.awt.*;
import java.sql.Connection;
import java.sql.SQLException;
import java.util.List;

public abstract class BaseDao {

    //使用DbUtils 操作数据库
    private QueryRunner queryRunner = new QueryRunner();

    /**
    * update() 方法用来执行:Insert\Update\Delete
    * @return 如果返回 -1 ,说明执行失败<br/>返回其他表示影响的行数
    */
    public int update(String sql,Object ... args){
        Connection connection = JdbcUtils.getConnection();

        try {
            queryRunner.update(connection,sql,args);
        } catch (SQLException e) {
            e.printStackTrace();
        }finally {
           JdbcUtils.close(connection);
        }
        return -1;
    }

    /**
    * 查询返回一个 javaBean 的 sql 语句
    * @param type 返回的对象类型
    * @param sql  执行的sql语句
    * @param args sql对应的参数值
    * @param <T>  返回的类型的泛型*/
    public <T> T queryForOne(Class<T> type,String sql,Object ... args){
        Connection con = JdbcUtils.getConnection();
        try {
            return queryRunner.query(con,sql,new BeanHandler<T>(type),args);
        } catch (SQLException e) {
            e.printStackTrace();
        }finally {
            JdbcUtils.close(con);
        }
        return null;
    }

    /**
     * 查询返回多个 javaBean 的 sql 语句
     * @param type 返回的对象类型
     * @param sql  执行的sql语句
     * @param args sql对应的参数值
     * @param <T>  返回的类型的泛型*/
    public <T> List<T>  queryForList(Class<T> type, String sql, Object ... args){
        Connection con = JdbcUtils.getConnection();
        try {
            return queryRunner.query(con,sql,new BeanListHandler<T>(type),args);
        } catch (SQLException e) {
            e.printStackTrace();
        }finally {
            JdbcUtils.close(con);
        }
        return null;
    }

    /**
    * 执行返回一行一列的sql语句
    * @param sql 执行的sql语句
    * @param args sql对应的参数值*/
    public Object queryForSingleValue(String sql,Object ... args){
        Connection conn = JdbcUtils.getConnection();

        try {
            return queryRunner.query(conn,sql,new ScalarHandler(),args);
        } catch (SQLException e) {
            e.printStackTrace();
        } finally {
            JdbcUtils.close(conn);
        }
        return null;
    }

}

6、编写UserDao 和测试

package com.aiguigu.dao;

import com.aiguigu.pojo.User;

public interface UserDao {

    /**
     * 根据用户名查询用户信息
     * @param username 用户名
     * @return 如果返回null,说明没有这个用户,反之亦然*/
    public User queryUserByUsername(String username);
    /**
     * 根据用户名和密码查询用户信息
     * @param username 用户名
     * @param password 密码
     * @return 如果返回null,说明没用户名或密码错误,反之亦然*/
    public User queryUserByUsernameAndPassword(String username,String password);

/**
 * 保存用户信息
 * @param user
 * @return 返回-1表示操作失败,其他sql语句影响的行数*/
    public int saveUser(User user);


}

package com.aiguigu.dao.impl;

import com.aiguigu.dao.BaseDao;
import com.aiguigu.dao.UserDao;
import com.aiguigu.pojo.User;

public class UserDaoImpl extends BaseDao implements UserDao {
    @Override
    public User queryUserByUsername(String username) {
        String sql = "select `id`,`username`,`password`,`email` from t_user where username=?";
        return queryForOne(User.class,sql,username);
    }

    @Override
    public User queryUserByUsernameAndPassword(String username, String password) {
        String sql = "select `id`,`username`,`password`,`email` from t_user where username=? and password=?";
        return queryForOne(User.class,sql,username,password);
    }

    @Override
    public int saveUser(User user) {
        String sql = "insert into t_user(`username`,`password`,`email`) values(?,?,?)";
        return update(sql,user.getUsername(),user.getPassword(),user.getEmail());

    }
}

package com.aiguigu.dao.impl;

import com.aiguigu.pojo.User;
import org.junit.Test;

import static org.junit.Assert.*;

public class UserDaoImplTest {

    @Test
    public void queryUserByUsername() {
        UserDaoImpl userDao = new UserDaoImpl();
        if (userDao.queryUserByUsername("admin") == null){
            System.out.println("用户名可用");
        }else {
            System.out.println("用户名已存在");
        }

    }

    @Test
    public void queryUserByUsernameAndPassword() {
        UserDaoImpl userDao = new UserDaoImpl();
        if (userDao.queryUserByUsernameAndPassword("admin","admin") == null){
            System.out.println("用户名或密码错误,登录失败");
        }else {
            System.out.println("查询成功");
        }
    }


    @Test
    public void saveUser() {
        UserDaoImpl userDao = new UserDaoImpl();
        System.out.println( userDao.saveUser(new User(null,"qweg168", "12qw6", "qwe168@qq.com")) );
    }
}

编写UserService 和测试

UserService接口:

package com.aiguigu.service;

import com.aiguigu.pojo.User;

public interface UserService {
    /**
     * 注册用户
     * @param  user
     * */
    public void registUser(User user);

    /**
     * 登录
     * @param user
     * @return 如果返回 null,说明登录失败,返回有值,是登录 成功*/
    public User login(User user);

    /**
     * 检查 用户名是否可用
     * @param username
     * @return 返回true表示用户名已存在,返回false表示用户名可用*/
    public boolean existUsername(String username);
}

UserServiceImpl:

package com.aiguigu.service.impl;

import com.aiguigu.dao.UserDao;
import com.aiguigu.dao.impl.UserDaoImpl;
import com.aiguigu.pojo.User;
import com.aiguigu.service.UserService;
import com.aiguigu.test.UserDaoImplTest;

public class UserServiceImpl implements UserService {
    private UserDao useDao = new UserDaoImpl();

    @Override
    public void registUser(User user) {
        useDao.saveUser(user);
    }

    @Override
    public User login(User user) {
       return useDao.queryUserByUsernameAndPassword(user.getUsername(),user.getPassword());
    }

    @Override
    public boolean existUsername(String username) {
        if (useDao.queryUserByUsername(username) == null){
            // 等于null,说明没查到,没查到表示可用
            return false;
        }
        return true;
    }
}

UserServiceImplTest:

package com.aiguigu.test;

import com.aiguigu.dao.impl.UserDaoImpl;
import com.aiguigu.pojo.User;
import com.aiguigu.service.UserService;
import com.aiguigu.service.impl.UserServiceImpl;
import org.junit.Test;

import static org.junit.Assert.*;

public class UserServiceImplTest {
    UserService userService = new UserServiceImpl();
    @Test
    public void registUser() {
        userService.registUser(new User(null,"qwe1234","qwe123",null));
    }

    @Test
    public void login() {
        System.out.println(userService.login(new  User(null,"qwe1234","qwe1235",null)));
    }

    @Test
    public void existUsername() {
        if (userService.existUsername("qwe1234")){
            System.out.println("用户名已存在!");
        }else {
            System.out.println("用户名可用!");
        }
    }


}

7、编写 web 层

7.1、实现用户注册的功能

分析:
在这里插入图片描述
编写 RegistServlet:
在这里插入图片描述

package com.aiguigu.web;

import com.aiguigu.dao.UserDao;
import com.aiguigu.pojo.User;
import com.aiguigu.service.UserService;
import com.aiguigu.service.impl.UserServiceImpl;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;

public class RegistServlet extends HttpServlet {
    UserService userService = new UserServiceImpl();
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
       //1.获取请求参数
        String username = req.getParameter("username");
        String password = req.getParameter("password");
        String email = req.getParameter("email");
        String code = req.getParameter("code");

        //2.检查 验证码是否正确   写死,要求验证码为:abcde
        if ("abcde".equalsIgnoreCase(code)){//equalsIgnoreCase:比较时忽略大小写

            //正确
            //3.检查 用户名是否可用
            if (userService.existUsername(username)){
                //不可用
                System.out.println("用户名[" + username + "]已存在");
                //跳回注册页面
                req.getRequestDispatcher("/pages/user/regist.html").forward(req,resp);

            }else {

                //可用
                //调用Service 保存到数据库
                userService.registUser(new User(null,username,password,email));

                //跳到注册成功页面 regist_success.html
                req.getRequestDispatcher("/pages/user/regist_success.html").forward(req,resp);
            }
        }else {
            System.out.println("验证码["+ code + "]错误");
            req.getRequestDispatcher("/pages/user/regist.html").forward(req,resp);
        }

    }
}

在 前端的 regist.html 页面加上 base相对路径

	<!--写 base 标签,永远固定相对路径跳转	的结果-->
	<base href="http://localhost:8080/book/">

在这里插入图片描述
修改 regist.html 里面的资源路径:

在页面运行按 F12 通过 网络来测试,有 报红的 都要修改路径
在这里插入图片描述
修改注册表单的提交 路径 并添加 post 方法 将表单信息发送给 servlet服务器:
在这里插入图片描述
验证码输入框 添加一个 name属性 便于服务器获取(这个以后优化):
在这里插入图片描述
后端接收参数:
在这里插入图片描述
对接收到的参数进行以下操作:
在这里插入图片描述

 //2.检查 验证码是否正确   写死,要求验证码为:abcde
        if ("abcde".equalsIgnoreCase(code)){//equalsIgnoreCase:比较时忽略大小写

            //正确
            //3.检查 用户名是否可用
            if (userService.existUsername(username)){
                //不可用
                System.out.println("用户名[" + username + "]已存在");
                //跳回注册页面
                req.getRequestDispatcher("/pages/user/regist.html").forward(req,resp);

            }else {

                //可用
                //调用Service 保存到数据库
                userService.registUser(new User(null,username,password,email));

                //跳到注册成功页面 regist_success.html
                req.getRequestDispatcher("/pages/user/regist_success.html").forward(req,resp);
            }
        }else {
            System.out.println("验证码["+ code + "]错误");
            req.getRequestDispatcher("/pages/user/regist.html").forward(req,resp);
        }

到 regist,html 进行测试

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值