【Spring 篇】深入探索:Spring集成Web环境的奇妙世界

在这里插入图片描述

嗨,亲爱的小白们!欢迎来到这篇有关Spring集成Web环境的博客。如果你曾对如何在Spring中构建强大的Web应用程序感到好奇,那么这里将为你揭示Web开发的神秘面纱。我们将用情感丰富、语句通顺的文字,以小白友好的方式,一探Spring在Web环境中的强大功能。

前言:Web开发的新时代

在我们踏入Spring Web环境的奇妙世界之前,让我们简单了解一下什么是Web开发。Web开发是指构建和维护通过互联网或内联网访问的网页的过程。而Spring作为一个全能型的Java框架,提供了强大的支持来简化Web应用程序的开发。

现代Web应用不仅需要提供丰富的用户体验,还需要保证性能、可维护性和安全性。Spring就像是一位强大的导演,为我们打造了一个舞台,让我们在这个Web开发的新时代中轻松驾驭。

Spring框架简介

在探索Spring Web环境之前,让我们简单回顾一下Spring框架的基本概念。Spring是一个开源框架,它简化了Java应用程序的开发,提供了广泛的基础设施支持。

Spring的核心特性包括依赖注入(DI)、面向切面编程(AOP)、事务管理、以及我们即将深入讨论的Web模块。这些特性使得Spring成为一个理想的选择,不仅用于构建大型企业级应用,也可以轻松地用于小型项目的开发。

Spring集成Web环境:如何搭建舞台

1. 项目初始化

首先,我们需要创建一个新的Spring项目。可以使用Spring Initializr(https://start.spring.io/)来初始化一个基本的Spring Boot项目。选择你需要的配置,点击"Generate"下载项目压缩包,解压后导入到你喜欢的集成开发环境中。

2. 添加Web依赖

pom.xml文件中,添加Spring Web的依赖:

<dependencies>
    <!-- ...其他依赖 ... -->
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
</dependencies>

这个依赖包含了构建基本的Spring Web应用所需的一切。

3. 创建一个简单的Controller

src/main/java/com/example/demo目录下,创建一个名为DemoController.java的类,用于处理Web请求:

import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;

@RestController
public class DemoController {

    @GetMapping("/hello")
    public String hello() {
        return "Hello, Spring Web!";
    }
}

这个简单的Controller定义了一个/hello的GET请求,返回一条简单的问候语。

4. 启动应用

在项目的根目录下执行以下命令启动应用:

./mvnw spring-boot:run

或者在集成开发环境中直接运行DemoApplication.java中的main方法。

打开浏览器访问:http://localhost:8080/hello,你将看到页面上显示着"Hello, Spring Web!"。

至此,我们已经成功搭建了一个简单的Spring Web应用。接下来,让我们更深入地探讨Spring Web环境中的一些核心概念。

MVC模式:将舞台分工明确

在Spring Web环境中,MVC(Model-View-Controller)是一个重要的设计模式。它将应用程序划分为三个主要的组件:

  • Model(模型):负责处理数据逻辑,与数据库交互,提供数据给View展示。
  • View(视图):负责用户界面的展示,将Model提供的数据呈现给用户。
  • Controller(控制器):负责处理用户请求,调用Model获取数据,并将数据传递给View展示。

1. 创建一个简单的Model

src/main/java/com/example/demo目录下,创建一个名为DemoModel.java的类,用于表示我们的数据:

public class DemoModel {

    private String message;

    public DemoModel(String message) {
        this.message = message;
    }

    public String getMessage() {
        return message;
    }
}

2. 修改Controller,引入Model

修改DemoController.java,将返回值从String改为DemoModel

@RestController
public class DemoController {

    @GetMapping("/hello")
    public DemoModel hello() {
        return new DemoModel("Hello, Spring Web!");
    }
}

3. 创建一个简单的View

src/main/resources/templates目录下,创建一个名为hello.html的HTML文件,用于展示我们的数据:

<!DOCTYPE html>
<html>
<body>

<h2 th:text="${message}"></h2>

</body>
</html>

4. 修改Controller,指定View

修改DemoController.java,指定要使用的View:

import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.GetMapping;

@Controller
public class DemoController {

    @GetMapping("/hello")
    public String hello(Model model) {
        model.addAttribute("message", "Hello, Spring Web!");
        return "hello";
    }
}

5. 启动应用

重新启动应用,访问http://localhost:8080/hello,你将看到页面上显示着"Hello, Spring Web!"。这一次,我们使用了MVC模式,将数据从Controller传递到了View,让整个Web应用更加结构清晰、分工明确。

数据绑定和表单处理:与用户互动的艺术

在真实的Web应用中,我们不仅仅是向用户展示静态的信息,还需要与用户进行交互。Spring提供了强大的数据绑定和表单处理功能,让我们能够轻松地处理用户提交的数据。

1. 创建一个简单的表单

src/main/resources/templates目录下,创建一个名为form.html的HTML文件,用于展示表单:

<!DOCTYPE html>
<html>
<body>

<form action="/submit" method="post">
    <label for="name">Name:</label>
    <input type="text" id="name" name="name" required><br><br>
    
    <label for="email">Email:</label>
    <input type="email" id="email" name="email" required><br><br>
    
    <input type="submit" value="Submit">
</form>

</body>
</html>

2. 创建一个Controller处理表单提交

src/main/java/com/example/demo目录下,创建一个名为FormController.java的类,用于处理表单提交:

import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;

@Controller
public class FormController {

    @GetMapping("/form")
    public String showForm() {
        return "form";
    }

    @PostMapping("/submit")
    public String submitForm(String name, String email, Model model) {
        // 处理表单提交逻辑
        model.addAttribute("name", name);
        model.addAttribute("email", email);
        return "result";
    }
}

3. 创建一个显示结果的View

src/main/resources/templates目录下,创建一个名为result.html的HTML文件,用于展示表单提交的结果:

<!DOCTYPE html>
<html>
<body>

<h2 th:text="'Hello, ' + ${name} + '! Thanks for submitting your email: ' + ${email}"></h2>

</body>
</html>

4. 启动应用

重新启动应用,访问http://localhost:8080/form,填写表单并提交,你将看到页面上显示着你提交的信息。通过这个简单的例子,我们演示了Spring如何处理表单提交,实现了用户与应用的互动。

拦截器和过滤器:定制Web应用的护卫

有时,我们需要在请求到达Controller之前或者之后执行一些额外的逻辑。这时,拦截器和过滤器就发挥了重要的作用。让我们看看如何在Spring中使用拦截器和过滤器。

拦截器

1. 创建一个拦截器

src/main/java/com/example/demo目录下,创建一个名为DemoInterceptor.java的类,用于定义我们的拦截器:

import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class DemoInterceptor implements HandlerInterceptor {

    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) {
        // 在请求到达Controller之前执行
        System.out.println("Pre Handle method is Calling");
        return true;
    }

    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) {
        // 在请求处理之后但视图未渲染前执行
        System.out.println("Post Handle method is Calling");
    }

    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) {
        // 在视图渲染之后执行
        System.out.println("Request and Response is completed");
    }
}
2. 注册拦截器

src/main/java/com/example/demo目录下,创建一个名为WebConfig.java的类,用于注册我们的拦截器:

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;

@Configuration
public class WebConfig implements WebMvcConfigurer {

    @Bean
    public DemoInterceptor demoInterceptor() {
        return new DemoInterceptor();
    }

    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(demoInterceptor());
    }
}

过滤器

1. 创建一个过滤器

src/main/java/com/example/demo目录下,创建一个名为DemoFilter.java的类,用于定义我们的过滤器:

import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import java.io.IOException;

public class DemoFilter implements Filter {

    @Override
    public void init(FilterConfig filterConfig) throws ServletException {
        // 初始化过滤器
        System.out.println("Filter initialized");
    }

    @Override
    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain)
            throws IOException, ServletException {
        // 在请求处理之前执行
        System.out.println("Filter is doing its job");
        chain.doFilter(request, response);
        // 在请求处理之后执行
        System.out.println("Filter is done");
    }

    @Override
    public void destroy() {
        // 销毁过滤器
        System.out.println("Filter destroyed");
    }
}
2. 注册过滤器

src/main/java/com/example/demo目录下,创建一个名为FilterConfig.java的类,用于注册我们的过滤器:

import org.springframework.boot.web.servlet.FilterRegistrationBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class FilterConfig {

    @Bean
    public FilterRegistrationBean<DemoFilter> demoFilter() {
        FilterRegistrationBean<DemoFilter> registrationBean = new FilterRegistrationBean<>();
        registrationBean.setFilter(new DemoFilter());
        registrationBean.addUrlPatterns("/hello"); // 过滤的URL
        return registrationBean;
    }
}

测试拦截器和过滤器

重新启动应用,通过访问http://localhost:8080/hello,你将在控制台上看到拦截器和过滤器的输出信息。这证明了拦截器在请求到达Controller之前和之后,过滤器在请求处理前后都能够执行相应的逻辑。

异常处理:妙用ControllerAdvice

在真实的Web应用中,异常处理是一个必不可少的部分。Spring提供了@ControllerAdvice注解,允许我们集中处理全局的异常情况。

1. 创建一个自定义异常

src/main/java/com/example/demo目录下,创建一个名为CustomException.java的类,用于表示我们的自定义异常:

public class CustomException extends RuntimeException {

    public CustomException(String message) {
        super(message);
    }
}

2. 创建一个异常处理器

src/main/java/com/example/demo目录下,创建一个名为CustomExceptionHandler.java的类,用于处理自定义异常:

import org.springframework.http.HttpStatus;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import javax.servlet.http.HttpServletResponse;

@ControllerAdvice
public class CustomExceptionHandler {

    @ExceptionHandler(CustomException.class)
    public String handleCustomException(CustomException ex, Model model, HttpServletResponse response) {
        model.addAttribute("error", ex.getMessage());
        response.setStatus(HttpStatus.BAD_REQUEST.value());
        return "error";
    }
}

3. 创建一个显示错误信息的View

src/main/resources/templates目录下,创建一个名为error.html的HTML文件,用于展示错误信息:

<!DOCTYPE html>
<html>
<body>

<h2 th:text="${error}"></h2>

</body>
</html>

4. 测试异常处理

DemoController.java中,添加一个新的请求处理方法,用于抛出自定义异常:

@GetMapping("/error-demo")
public String errorDemo() {
    throw new CustomException("This is a custom exception");
}

重新启动应用,访问http://localhost:8080/error-demo,你将看到页面上显示着自定义异常的错误信息。

通过这个简单的例子,我们演示了如何使用@ControllerAdvice注解来集中处理全局的异常情况,使得异常处理更加统一和可维护。

安全性:保护Web应用的护盾

Web应用的安全性是非常重要的,Spring提供了一套强大的安全性机制,使我们能够轻松地保护我们的Web应用。

1. 添加Spring Security依赖

pom.xml文件中,添加Spring Security的依赖:

<dependencies>
    <!-- ...其他依赖 ... -->
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-security</artifactId>
    </dependency>
</dependencies>

2. 创建一个简单的Security配置

src/main/java/com/example/demo目录下,创建一个名为SecurityConfig.java的类,用于配置Spring Security:

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;

@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http
            .authorizeRequests()
                .antMatchers("/", "/home").permitAll()
                .anyRequest().authenticated()
                .and()
            .formLogin()
                .loginPage("/login")
                .permitAll()
                .and()
            .logout()
                .permitAll();
    }

    @Bean
    public PasswordEncoder passwordEncoder() {
        return new BCryptPasswordEncoder();
    }
}

3. 创建一个登录页面

src/main/resources/templates目录下,创建一个名为login.html的HTML文件,用于展示登录页面:

<!DOCTYPE html>
<html>
<body>

<form th:action="@{/login}" method="post">
    <label for="username">Username:</label>
    <input type="text" id="username" name="username" required><br><br>
    
    <label for="password">Password:</label>
    <input type="password" id="password" name="password" required><br><br>
    
    <input type="submit" value="Login">
</form>

</body>
</html>

4. 测试Spring Security

重新启动应用,访问http://localhost:8080/login,你将看到登录页面。输入任意用户名和密码,点击登录按钮,你将被重定向到首页。

通过这个简单的例子,我们演示了如何使用Spring Security来保护我们的Web应用,限制访问权限,以及提供登录认证功能。

结语:在Spring的指导下舞动Web的旋律

通过这篇博客,我们深入浅出地探讨了Spring集成Web环境的世界。从项目初始化、MVC模式、数据绑定和表单处理,到拦截器和过滤器、异常处理、以及安全性,我们一步步地领略了Spring框架在Web开发中的强大功能。

在这个Web的舞台上,Spring为我们打造了一个灵活而强大的舞台,让我们能够自如地表演、与用户互动,同时又有着强大的安全性保障。希望这篇博客对于初学者来说是一次愉快的学习之旅,让你能够在Web的世界里舞动自如。

如果你有任何疑问或者想要分享自己的经验,不妨在评论区留下你的足迹。让我们一起共同探索Spring集成Web环境的奇

妙之处,愉快地编写出安全、高效、可维护的Web应用。感谢你的阅读,希望你在Web的旋律中找到属于自己的节奏!🚀🌐

作者信息

作者 : 繁依Fanyi
CSDN: https://techfanyi.blog.csdn.net
掘金:https://juejin.cn/user/4154386571867191

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/316293.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

survey和surveyCV:如何用R语言进行复杂抽样设计、权重计算和10折交叉验证?

一、引言 在实际调查和研究中&#xff0c;我们往往面临着样本选择的复杂性。复杂抽样设计能够更好地反映真实情况&#xff0c;提高数据的代表性和可靠性。例如&#xff0c;多阶段抽样可以有效地解决大规模调查的问题&#xff0c;整群抽样能够在保证样本的随机性的同时减少资源消…

D25XB100-ASEMI家用电器整流桥D25XB100

编辑&#xff1a;ll D25XB100-ASEMI家用电器整流桥D25XB100 型号&#xff1a;D25XB100 品牌&#xff1a;ASEMI 封装&#xff1a;GBJ-5&#xff08;带康铜丝&#xff09; 平均正向整流电流&#xff08;Id&#xff09;&#xff1a;25A 最大反向击穿电压&#xff08;VRM&…

thinkphp递归实现无限级子分类合并上级children

//设别分类列表public function getCategoryList(){$list = Db::name(categorys)->select(

玩转Mysql 七 (索引的创建与设计原则)

一、索引的创建与使用 1、索引的分类 MySQL的索引包括普通索引、唯一性索引、全文索引、单列索引、多列索引和空间索引等。 &#xff08;1&#xff09;从 功能逻辑 上说&#xff0c;索引主要有 4 种&#xff0c;分别是普通索引、唯一索引、主键索引、全文索引。 &#xff08;…

20_GC垃圾回收机制

文章目录 GC如何确定垃圾如何回收垃圾回收垃圾的时机 GC 如何确定垃圾 引用计数算法 给对象添加一个引用计数器&#xff0c;每当一个地方引用它时&#xff0c;计数器加1&#xff0c;每当引用失效时&#xff0c;计数器减少1&#xff0c;当计数器的数值为0时&#xff0c;也就是对…

Django教程|数据统计图表(echarts、highchart)

前言 highchart&#xff0c;国外。 echarts&#xff0c;国内。 本项目集成 hightchart和echarts图表库实现数据统计功能。 包括&#xff1a;折线图&#xff0c;柱状图&#xff0c;饼图和数据集图。 效果图 echats Highcharts 源代码 编写模板&#xff08;Template&#x…

Docker安装Atlassian全家桶

文章目录 省流&#xff1a;1.docker-compose文件2.其他服务都正常启动&#xff0c;唯独Bitbucket不行。日志错误刚启动时候重启后查询分析原因再针对第一点排查看样子是安装的bitbucket和系统环境有冲突问题&#xff1f; 结论&#xff1a; 省流&#xff1a; bitbucket 只能安装…

idea使用ssh连接docker,并通过Dockerfile文件,直接在idea中启动docker应用,并进行远程debug

idea使用ssh连接docker&#xff0c;并通过Dockerfile文件&#xff0c;直接在idea中启动docker应用&#xff0c;并进行远程debug 第一步: idea通过ssh连接docker第二步&#xff1a;使用Dockerfile文件在远程启动应用第三步: 远程debug 容器运行的好处是减轻本地运行的负担(本地电…

数据结构初探:揭开数据结构奥秘

&#x1f308;个人主页&#xff1a;聆风吟 &#x1f525;系列专栏&#xff1a;数据结构、算法模板、汇编语言 &#x1f516;少年有梦不应止于心动&#xff0c;更要付诸行动。 文章目录 &#x1f4cb;前言一. 数组结构起源二. 基本概念和术语2.1 数据2.2 数据元素2.3 数据项2.4 …

Rust-语句和表达式

if-else Rust中if-else表达式的作用是实现条件分支。if-else表达式的构成方式为&#xff1a;以if关键字开头&#xff0c;后面跟上条件表达式&#xff0c;后续是结果语句块&#xff0c;最后是可选的else块。条件表达式的类型必须是bool。 if-else结构还可以当表达式使用 loop …

苹果手机怎么恢复备份?详细攻略为你整理好了!

随着智能手机和互联网的普及&#xff0c;手机中存储的个人信息、照片、视频、聊天记录等数据会变得越来越多。一旦手机丢失、损坏或系统出现问题&#xff0c;我们很可能会面临数据丢失的风险。因此&#xff0c;越来越多的人开始意识到保护手机数据的重要性。 当苹果手机数据丢…

Mnajora 使用deb包安装软件

说明 Mnajora 安装deb软件包主要有两种方式 可以使用dpkg 直接安装也可是使用debtap将deb软件包转换成 使用dpkg sudo pacman -S dpkg #安装dpkgsudo dpkg -i ###.deb #使用dpkg安装deb软件包和在ubuntu上是一样的 安装成功 使用debtap debtap是一个用于将.deb包转换为A…

C++力扣题目617--合并二叉树

给你两棵二叉树&#xff1a; root1 和 root2 。 想象一下&#xff0c;当你将其中一棵覆盖到另一棵之上时&#xff0c;两棵树上的一些节点将会重叠&#xff08;而另一些不会&#xff09;。你需要将这两棵树合并成一棵新二叉树。合并的规则是&#xff1a;如果两个节点重叠&#…

“+”连接符用法(Java)

""可以作为连接符使用&#xff0c;如果与字符串一起运算&#xff0c;结果依旧是一个字符串 比如"aaa"6 --> "aaa6" 在打印中&#xff0c;能算就算&#xff0c;不能计算的时候就会连接在一起 注意先后顺序 ascii编码&#xff1a; 字符串&…

VASP结合vaspkit+ShengBTE计算热电优值(一)

电导率σ&#xff0c;塞贝克系数S的计算&#xff1a; 使用vaspkit计算处对应的物理量&#xff0c;具体流程为&#xff1a; 准备好计算的材料对应的POSCAR。如果是二维材料可以使用vaspkit 的921或923功能对二维材料POSCAR进行标准化。进行结构优化。使用 vaspkit-681命令生成高…

卡尔曼滤波:理论与代码

卡尔曼滤波&#xff1a;理论与代码 引言 卡尔曼滤波是一种用于估计系统状态的优化技术&#xff0c;特别适用于含有噪声的测量数据和系统动态变化的情况。本文将简单探讨卡尔曼滤波的理论基础、数学公式的推导&#xff0c;并通过Python代码示例演示其在实际应用中的效果。 一…

python,序列的切片

序列的切片就是指从一个序列中取出子序列 语法&#xff1a; 序列[起始下标&#xff1a;结束下标&#xff1a;步长] 步长为1表示一个一个的取元素&#xff0c;步长为2表示每次跳过一个元素的取元素&#xff0c;步长为负数表示反向切片&#xff0c;取元素时取到结束下标&#…

养老数据监控大屏:护航金色晚年,打造智慧养老新标杆

随着老龄化社会的加速到来&#xff0c;养老服务的质量和效率成为了社会关注的焦点。如何运用现代科技手段提升养老服务水平&#xff0c;让老年人享受更加舒适、便捷的晚年生活&#xff0c;成为了我们面临的重要课题。在这一背景下&#xff0c;养老数据监控大屏应运而生&#xf…

2-《Java并发编程实战》(Java Concurrency in Practice) 代码示例

说明 这是针对《Java并发编程实战》(Java Concurrency in Practice)一书中的示例代码进行扩展&#xff0c;并且进行验证的完整代码&#xff0c;具体背景可看这篇文章&#xff1a;1-《Java并发编程实战》(Java Concurrency in Practice) 代码示例 下面的示例代码都是针对书中的&…

API对象上千个,有啥关联性,kubectl-tree一键搞定

关注【云原生百宝箱】公众号&#xff0c;获取更多云原生消息 "kubectl-tree 是一款强大的 kubectl 插件&#xff0c;通过 ownerReferences 实现 Kubernetes 对象之间的所有权关系探索。相较于 kubectl lineage&#xff0c;它不仅更全面理解 API 对象的逻辑关系&#xff0c…