SpringBoot之Web应用(未使用数据库)

Web应用(未使用数据库)

编写Web前准备

静态资源导入问题
  1. 在springboot中,我们可以使用以下方式处理静态资源

    https://www.webjars.org/

    • webjars localhost:8080/webjars/

      示例(导入依赖):

      <dependency>
          <groupId>org.webjars.npm</groupId>
          <artifactId>jquery</artifactId>
          <version>3.6.0</version>
      </dependency>
      
    • 在resources目录下的resources、static、public包 localhost:8080/

  2. 优先级:resources>static(默认)>public

  3. 在templates目录下的所有页面,只能通过controller来跳转(需要模板引擎的支持)

模板引擎

与springmvc中的视图解析器相识,可以让controller访问template下的html页面

thymeleaf

官方使用文档:https://www.thymeleaf.org/doc/tutorials/3.0/usingthymeleaf.html#attribute-precedence

public static final String DEFAULT_PREFIX = "classpath:/templates/";

public static final String DEFAULT_SUFFIX = ".html";
  1. 导入依赖

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-thymeleaf</artifactId>
    </dependency>
    
  2. 在需要使用的html页的标签后加上约束

    <html lang="en" xmlns:th="http://www.thymeleaf.org">
    
  3. 更多语法可以查看官方文档

修改mvc的默认配置

比如默认的时间格式等等

首页配置和国际化

首页配置

页面的所有静态资源都需要使用thymeleaf接管

使用thymeleaf需要先在头部导入约束

访问url需要使用 @{}

# 关闭模板引擎的缓存
spring.thymeleaf.cache=false
# 我们的配置文件的真实位置
spring.messages.basename=i18n.login
#时间日期格式化
spring.mvc.format.date=yyyy-MM-dd
国际化

示例为将首页国际化

  1. 配置i18n文件(在resources目录下创建i18n目录,然后再创建如下文件)

    login.properties

    login.btn=登录
    login.password=密码
    login.remember=记住我
    login.tip=请登录
    login.username=用户名
    

    login_en_US.properties

    login.btn=Sign in
    login.password=password
    login.remember=Remember me
    login.tip=Please sign in
    login.username=Username
    

    login_zh_CN.properties

    login.btn=登录
    login.password=密码
    login.remember=记住我
    login.tip=请登录
    login.username=用户名
    
  2. 编写application.properties文件,进行配置

    # 我们的配置文件的真实位置
    spring.messages.basename=i18n.login
    
  3. 修改html页面中的显示,和点击中英文切换

    这里通过 #{} 来获取值

    <!DOCTYPE html>
    <html lang="en" xmlns:th="http://www.thymeleaf.org">
       <head>
          <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
          <meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
          <meta name="description" content="">
          <meta name="author" content="">
          <title>Signin Template for Bootstrap</title>
          <!-- Bootstrap core CSS -->
          <link th:href="@{/css/bootstrap.min.css}" rel="stylesheet">
          <!-- Custom styles for this template -->
          <link th:href="@{/css/signin.css}" rel="stylesheet">
       </head>
    
       <body class="text-center">
          <form class="form-signin" action="dashboard.html">
             <img class="mb-4" th:src="@{/img/bootstrap-solid.svg}" alt="" width="72" height="72">
             <h1 class="h3 mb-3 font-weight-normal" th:text="#{login.tip}">Please sign in</h1>
             <label class="sr-only">Username</label>
             <input type="text" class="form-control" th:placeholder="#{login.username}" required="" autofocus="">
             <label class="sr-only">Password</label>
             <input type="password" class="form-control" th:placeholder="#{login.password}" required="">
             <div class="checkbox mb-3">
                <label>
              <input type="checkbox" value="remember-me">[[#{login.remember}]]
            </label>
             </div>
             <button class="btn btn-lg btn-primary btn-block" type="submit">[[#{login.btn}]]</button>
             <p class="mt-5 mb-3 text-muted">© 2017-2018</p>
             <a class="btn btn-sm" th:href="@{/index(l='zh_CN')}">中文</a>
             <a class="btn btn-sm" th:href="@{/index(l='en_US')}">English</a>
          </form>
    
       </body>
    
    </html>
    
  4. 在config包下创建MyLocaleResolver

    public class MyLocaleResolver implements LocaleResolver {
        //解析请求
        @Override
        public Locale resolveLocale(HttpServletRequest request) {
            //获取请求中的语言参数
            String language = request.getParameter("l");
            Locale locale = Locale.getDefault();//如果没有就使用默认的
            //如果请求的连接携带了国际化的参数
            if(!StringUtils.isEmpty(language)){
                //zh_CN
                String[] split = language.split("_");
                //国家,地区
                locale=new Locale(split[0],split[1]);
    
            }
            return locale;
        }
    
        @Override
        public void setLocale(HttpServletRequest request, HttpServletResponse response, Locale locale) {
    
        }
    }
    
  5. 在config包下创建MyMvcConfig,将MyLocaleResolver载入spring容器中

    @Configuration
    public class MyMvcConfig implements WebMvcConfigurer {
        //自定义的国际化组件就生效了
        @Bean
        public LocaleResolver localeResolver(){
            return new MyLocaleResolver();
        }
    }
    
  6. 检查Controller(检查是否能够访问index)

    @Controller
    public class IndexController {
        //地址栏访问这两个路径都可以访问首页
        @RequestMapping({"/","/index"})
        public String index(){
            return "index";
        }
    }
    
  7. 测试

    image-20220310203455174

登录功能的实现

  1. 编写controller

    @Controller
    public class LoginController {
        @RequestMapping("/user/login")
        public String login(@RequestParam("username") String username, @RequestParam("password") String password, Model model, HttpSession session){
            if(!StringUtils.isEmpty(username)&&"123456".equals(password)){
                session.setAttribute("loginUser",username);
                System.out.println("成功");
                return "redirect:/main";
            }else {
                model.addAttribute("msg","用户名或者密码错误");
                System.out.println("错误");
                return "index";
            }
        }
    
        @RequestMapping("/main")
        public String dashboard(){
            return "dashboard";
        }
    }
    
  2. 修改html页面中的表单action,判断msg返回值是否未空

    <form class="form-signin" th:action="@{/user/login}" method="post">
    			<img class="mb-4" th:src="@{/img/bootstrap-solid.svg}" alt="" width="72" height="72">
    			<h1 class="h3 mb-3 font-weight-normal" th:text="#{login.tip}">Please sign in</h1>
        
    <!--			如果msg的值为空,则不显示消息-->
    			<p style="color: red" th:text="${msg}" th:if="${not #strings.isEmpty(msg)}"></p>
    
    			<label class="sr-only">Username</label>
    			<input type="text" name="username" class="form-control" th:placeholder="#{login.username}" required="" autofocus="">
    			<label class="sr-only">Password</label>
    			<input type="password" name="password" class="form-control" th:placeholder="#{login.password}" required="">
    			<div class="checkbox mb-3">
    				<label>
              <input type="checkbox" value="remember-me">[[#{login.remember}]]
            </label>
    			</div>
    			<button class="btn btn-lg btn-primary btn-block" type="submit">[[#{login.btn}]]</button>
    			<p class="mt-5 mb-3 text-muted">© 2017-2018</p>
    			<a class="btn btn-sm" th:href="@{/index(l='zh_CN')}">中文</a>
    			<a class="btn btn-sm" th:href="@{/index(l='en_US')}">English</a>
    		</form>
    

编写拦截器

  1. 在config目录下创建LoginHandlerInterceptor类

    public class LoginHandlerInterceptor implements HandlerInterceptor {
        @Override
        public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
    
            Object loginUser = request.getSession().getAttribute("loginUser");
            if(loginUser==null){
                request.setAttribute("msg","没有权限,请先登录");
                request.getRequestDispatcher("/").forward(request,response);;
                return false;
            }else {
                return true;
            }
        }
    }
    
  2. 在MyMvcConfig类中配置拦截器到spring容器中

    @Configuration
    public class MyMvcConfig implements WebMvcConfigurer {
    
        public void addInterceptors(InterceptorRegistry registry){
            registry.addInterceptor(new LoginHandlerInterceptor()).addPathPatterns("/**").excludePathPatterns("/","/index","/user/login","/css/**","/img/**","/js/**");
        }
    }
    
  3. 测试

展示员工列表

实体类

Department

@Data
@AllArgsConstructor
@NoArgsConstructor
//部门表
public class Department {
    private Integer id;
    private String departmentName;
}

Employee

@Data
@NoArgsConstructor
//员工表
public class Employee {
    private Integer id;
    private String lastName;
    private String email;
    private Integer gender;//0:女 1:男
    private Department department;
    private Date birth;

    public Employee(Integer id, String lastName, String email, Integer gender, Department department) {
        this.id = id;
        this.lastName = lastName;
        this.email = email;
        this.gender = gender;
        this.department = department;
        //默认的创建日期
        this.birth=new Date();
    }
}
dao层模仿数据库

DepartmentDao

@Repository
public class DepartmentDao {
    //模拟数据库中的数据
    private static Map<Integer, Department> departments=null;

    static {
        departments=new HashMap<Integer, Department>();//创建一个部门表
        departments.put(101,new Department(101,"教学部"));
        departments.put(102,new Department(102,"市场部"));
        departments.put(103,new Department(103,"教研部"));
        departments.put(104,new Department(104,"运营部"));
        departments.put(105,new Department(105,"后勤部"));
    }

    //获得所有部门信息
    public Collection<Department> getDepartments(){
        return departments.values();
    }

    //通过id得到部门
    public Department getDepartmentById(Integer id){
        return departments.get(id);
    }
}

EmployeeDao

@Repository
public class EmployeeDao {
    //模拟数据库中的数据
    private static Map<Integer, Employee> employees=null;
    //员工有所属的部门
    @Autowired
    private DepartmentDao departmentDao;
    static {
        employees=new HashMap<Integer, Employee>();//创建一个部门表
        employees.put(1001,new Employee(1001,"AA","A123456789@qq.com",0,new Department(101,"教学部")));
        employees.put(1002,new Employee(1002,"BB","B123456789@qq.com",1,new Department(102,"市场部")));
        employees.put(1003,new Employee(1003,"CC","C123456789@qq.com",0,new Department(103,"教研部")));
        employees.put(1004,new Employee(1004,"DD","D123456789@qq.com",1,new Department(104,"运营部")));
        employees.put(1005,new Employee(1005,"EE","E123456789@qq.com",0,new Department(105,"后勤部")));
    }
    //主键自增
    private static Integer initId=1006;
    //增加一个员工
    public void save(Employee employee){
        if(employee.getId()==null){
            employee.setId(initId++);
        }
        employee.setDepartment(departmentDao.getDepartmentById((employee.getDepartment().getId())));
        employees.put(employee.getId(),employee);
    }

    //查询全部员工信息
    public Collection<Employee> getAll(){
        return employees.values();
    }

    //通过id查询员工
    public Employee getEmployeeById(Integer id){
        return employees.get(id);
    }

    //删除员工通过id
    public void delete(Integer id){
        employees.remove(id);
    }
}
提取公共页面
  1. 在需要提取出来的标签中加入如下语句

    th:fragment="sidebar"
    
  2. 在需要引用的位置加入如下语句

    commons/commons为commons路径下的comoms.html文件

    sidebar为自定义的名字

    后面括号内的为需要传参的值

    <div th:insert="~{commons/commons::sidebar(active='main.html')}"></div>
    
  3. 另一页面接收判断值

    使用${}取值判断,使用三元运算符进行判断

    "${active=='main.html'?'nav-link active':'nav-link'}"
    
列表循环展示
  • 使用三元判断输出男女

  • 使用thymeleaf将时间进行格式化输出

<tbody>
   <tr th:each="emp:${emps}">
      <td th:text="${emp.getId()}"></td>
      <td th:text="${emp.getLastName()}"></td>
      <td th:text="${emp.getEmail()}"></td>
      <td th:text="${emp.getGender()==0?'':''}"></td>
      <td th:text="${emp.getDepartment().getDepartmentName()}"></td>
      <td th:text="${#dates.format(emp.getBirth(),'yyyy-MM-dd HH:mm:ss')}"></td>
      <td>
         <button class="btn btn-sm btn-primary">编辑</button>
         <button class="btn btn-sm btn-danger">删除</button>
      </td>
   </tr>
</tbody>

添加员工

  1. 编写controller

    @GetMapping("/emp")
    public String toAddpage(Model model){
        //查出所有部门的信息
        Collection<Department> departments = departmentDao.getDepartments();
        model.addAttribute("departments",departments);
        return "/emp/add";
    }
    @PostMapping("/emp")
    public String addEmp(Employee employee){
        System.out.println("save=>"+employee);
        employeeDao.save(employee);
        //查出所有部门的信息
        return "redirect:/emps";
    }
    
  2. 编写前端from表单

    <form th:action="@{/emp}" method="post">
                      <div class="form-group">
                         <label>LastName</label>
                         <input name="lastName" type="text" class="form-control" placeholder="lzj">
                      </div>
                      <div class="form-group">
                         <label>Email</label>
                         <input name="email" type="email" class="form-control" placeholder="1481315703@qq.com">
                      </div>
                      <div class="form-group">
                         <label>Gender</label><br>
                         <div class="form-check form-check-inline">
                            <input class="form-check-input" type="radio" name="gender" value="1">
                            <label class="form-check-label"></label>
                         </div>
                         <div class="form-check form-check-inline">
                            <input class="form-check-input" type="radio" name="gender" value="0">
                            <label class="form-check-label"></label>
                         </div>
                      </div>
                      <div class="form-group">
                         <label>department</label>
                         <select class="form-control" name="department.id">
    <!--                        我们在controller接收的是一个Employee,所以我们需要提交的是其中的一个属性-->
                            <option th:each="dept:${departments}" th:text="${dept.getDepartmentName()}" th:value="${dept.getId()}"></option>
                         </select>
                      </div>
                      <div class="form-group">
                         <label>Birth</label>
                         <input name="birth" type="text" class="form-control" placeholder="嘤嘤嘤">
                      </div>
                      <button type="submit" class="btn btn-primary">添加</button>
                   </form>
    
  3. 修改时间格式

    #时间日期格式化
    spring.mvc.format.date=yyyy-MM-dd
    

修改员工信息

  1. 编写controller

    //全部员工页面传递id值过来
    @GetMapping("/emp/{id}")
    public String toUpdateEmp(@PathVariable("id") Integer id,Model model){
        Employee employee = employeeDao.getEmployeeById(id);
        model.addAttribute("emp",employee);
        Collection<Department> departments = departmentDao.getDepartments();
        model.addAttribute("departments",departments);
        System.out.println(employee);
        return "emp/update";
    
    }
    
    @PostMapping("/updateEmp")
    public String updateEmp(Employee employee){
        employeeDao.save(employee);
        return "redirect:/emps";
    }
    
  2. 编写前端from表单

                    <form th:action="@{/updateEmp}" method="post">
                      <input type="hidden" name="id" th:value="${emp.getId()}">
                      <div class="form-group">
                         <label>LastName</label>
                         <input th:value="${emp.getLastName()}" name="lastName" type="text" class="form-control" placeholder="lzj">
                      </div>
                      <div class="form-group">
                         <label>Email</label>
                         <input th:value="${emp.getEmail()}" name="email" type="email" class="form-control" placeholder="1481315703@qq.com">
                      </div>
                      <div class="form-group">
                         <label>Gender</label><br>
                         <div class="form-check form-check-inline">
                            <input th:checked="${emp.getGender()==1}" class="form-check-input" type="radio" name="gender" value="1">
                            <label class="form-check-label"></label>
                         </div>
                         <div class="form-check form-check-inline">
                            <input th:checked="${emp.getGender()==0}" class="form-check-input" type="radio" name="gender" value="0">
                            <label class="form-check-label"></label>
                         </div>
                      </div>
                      <div class="form-group">
                         <label>department</label>
                         <select class="form-control" name="department.id">
    <!--                        我们在controller接收的是一个Employee,所以我们需要提交的是其中的一个属性-->
                            <option th:selected="${dept.getId()}==${emp.getDepartment().getId()}" th:each="dept:${departments}" th:text="${dept.getDepartmentName()}" th:value="${dept.getId()}"></option>
                         </select>
                      </div>
                      <div class="form-group">
                         <label>Birth</label>
                         <input th:value="${#dates.format(emp.getBirth(),'yyyy-MM-dd HH:mm:ss')}" name="birth" type="text" class="form-control" placeholder="嘤嘤嘤">
                      </div>
                      <button type="submit" class="btn btn-primary">修改</button>
                   </form>
    

    删除员工、404页面和注销

    1. 删除员工

      • 编写controller

        @GetMapping("/delemp/{id}")
        public String deleteEmp(@PathVariable("id") Integer id){
            employeeDao.delete(id);
            return "redirect:/emps";
        }
        
    2. 404页面

      在templates目录下创建error文件夹,将404.html页面放进去即可

    3. 注销

      • 编写controller

        @RequestMapping("/user/logout")
        public String logout(HttpSession session){
            session.removeAttribute("loginUser");
            return "redirect:/";
        
        }
        
    ```

    删除员工、404页面和注销

    1. 删除员工

      • 编写controller

        @GetMapping("/delemp/{id}")
        public String deleteEmp(@PathVariable("id") Integer id){
            employeeDao.delete(id);
            return "redirect:/emps";
        }
        
    2. 404页面

      在templates目录下创建error文件夹,将404.html页面放进去即可

    3. 注销

      • 编写controller

        @RequestMapping("/user/logout")
        public String logout(HttpSession session){
            session.removeAttribute("loginUser");
            return "redirect:/";
        
        }
        
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

爱学习的大雄

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值