Servlet 的初步学习

image-20231213183204440

前言

咱们最核心的目标是基于tomcat编程, 做出网站来 ~~ 基于tomcat进行网站后端的开发.
网站后端, http服务器,肯定是需要针对http 协议进行一系列操作的.
幸运的是, tomcat,已经把这些http相关的底层操作,封装好了只需要调用tomcat给咱们提供的api即可

Servlet 是什么

Servlet 就是Tomcat给java提供的原生的进行web开发的api

Servlet 是一种实现动态页面的技术. 是一组 Tomcat 提供给程序猿的 API, 帮助程序猿简单高效的开发一
个 web app.

未来咱们可能还要接触一些框架(Spring全家桶)Spring MVC也是进行web开发的api
(这组api也是基于servlet的,相当于对servlet的封装).企业中已经几乎不会使用servlet,学习它的原因是这个东西是未来学习的框架的基础

网页分成两类:
静态页面: 页面内容始终是固定不变的,比如百度主页
image-20231213174707298

动态页面: 页面内容随着输入参数的不同而改变,比如搜索结果页
image-20231213175104360
静态页面就只是单纯的html,动态页面,则是html+ 数据

第一个 Servlet 程序

先写个 hello world

预期写个 servlet 程序,部署到tomcat上,通过浏览器访问,得到hello world 字符串

让我们学习编程以来的最难的 hello world 编写
有以下步骤:
1.创建项目 2.引入依赖 3.创建目录结构
4.编写代码 5.打包程序 6.部署程序
7.验证

1.创建项目

此处要创建一个maven项目了.

maven是个"工程管理"工具,它的作用有

  • 规范目录结构
  • 管理依赖(处理好使用的第三方库)
  • 构建
  • 打包
  • 测试

注: 目前主要就是使用管理依赖和打包功能

开始创建项目

image-20231210204951844

如果你首次使用maven,项目创建好了之后,会在下面读条,从中央仓库加载一些maven的依赖.

  1. 需要联网

  2. maven 仓库在国外,网络不一定稳定,这里的读条可能会比较久.(长的可能要读1个小时)[(只是第一次使用会这样,读完之后,后面就好了,如果报错失败没事,过两天再试试~

怎么修改成国内镜像?

(不建议改成国内镜像,后面如果你要学spring还得改回来,国内镜像很多东西没有,比官方的源缺东西!!!)

将maven源改为国内阿里云镜像的超链接,点击即可跳转


maven不是个独立的程序吗, 为什么不需要单独下载安装嘛?

maven是独立的程序,但是不需要单独下载安装.IDEA已经自带了(天生的,不需要安装任何额外的插件)

maven项目的目录结构

image-20231211085055581

src: 存放源代码

  • main: 业务代码
    • java: 放java代码
    • resource:
    • 放程序依赖的文件(配置文件,数据文件,图片,图标,声音…)
  • test
    • java: 测试代码
  • pom.xml: maven项目总的配置文件,后面经常用到.

image-20231211085632046

2.引入依赖

引入servlet 对应的jar包

从中央仓库下载jar包

https://mvnrepository.com/

官网链接

如果页面一直显示在加载中,可以使用加速器Watt Toolkit(steam++),它在Windows自带的Microsoft Store就有.

image-20231211105218911

image-20231211105443022

正式开始下载

image-20231211123857525

image-20231211124223310

image-20231211193756434

上述复制粘贴的被称为该依赖在maven仓库的坐标.

image-20231211225309737

3.创建目录

虽然maven已经帮我们自动的创建了一些目录,但是还不够.此处是需要使用maven开发一个 web程序,还需要别的目录

1)在main目录下(和java, resources并列),创建一个webapp目录

image-20231212085520013

2)在webapp下创建WEB-INF目录

image-20231212092040192

3)再在WEB-INF目录下创建一个web.xml 文件

在这里插入图片描述

image-20231212093422397

注: 此处的目录名字和结构,都不能错.

4)给web.xml 写点东西进去

<!DOCTYPE web-app PUBLIC
		"-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"
		"http://java.sun.com/dtd/web-app_2_3.dtd" >
		
<web-app>
	<display-name>Archetype Created Web Application</display-name>
</web-app>

image-20231212104250463

web.xml的作用

当前写的servlet程序和以往写的别的代码相比,有一个非常大的区别:就是没有main方法.

main方法可以视为是汽车的发动机,有发动机,汽车才能跑,如果现在有辆车,没有发动机,能不能有办法跑???
答案是有办法的!挂个车头,让车头拽着它跑就行了.比如地铁,一节一节的,每一节车厢,自己没有发动机,车头才有.

咱们写的servlet程序就是车厢,tomcat就是车头!
把咱们写好的servlet程序扔到webapps目录下就相当于把车厢给挂到车头后面了.

tomcat 如何识别 webapps目录下,哪些是需要拉着跑的车厢?哪些是普通的不需要拉着跑的目录呢?
就是靠目录下有个WEB-INF/web.xml.此时tomcat就把我们写的代码加载并运行起来了.

4.编写代码

image-20231213111027790

public class HelloServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        // 父类里的这个方法只是返回了一个错误页面,需要注释掉
        // super.doGet(req, resp);
        //这个是在服务器的控制台里打印.
        System.out.println("hello world");
        //要想把 hello world返回到客户端,需要使用下面的代码.
        //getWriter会得到一个 Writer 对象.
        resp.getWriter().write("hello world");
        // 此处的writer对象是从属于resp对象的,此时进行的write操作其实是往resp的 body部分进行写入
        // 等resp对象整个构造好了,tomcat 会统一的转成HTTP响应的格式,再写socket.
    }
}

HttpServlet: servlet api里提供的现成的类写servlet 代码一般都是继承这个HttpServlet的.
HttpServletRequest req: 这个参数表示一个HTTP请求.
HttpServletResponse resp: 这个参数表示一个HTTP响应,一个空的对象.

doGet: 写的这个doGet方法,不需要我们自己手动调用,而是交给Tomcat来调用.
Tomcat收到 get请求,就会触发doGet方法,此时Tomcat会构造好两个参数reqresp.
req: 从TCP socket中读出来的字符串,按照HTTP协议解析得到的一个对象,这个对象里的属性和HTTP请求报文格式相对应的!
resp: 就需要我们在doGet根据请求req,结合我们自己的业务逻辑构造出一个resp对象来.

字符流: ReaderWriter,Writer
字节流: lnputStream,OutputStream

resp.getWriter().write("hello world");

此处的writer对象是从属于resp对象的,此时进行的write操作其实是往resp的 body部分进行写入,等resp对象整个构造好了, tomcat会统一的转成HTTP响应的格式,再写socket.
流对象,不一定非得是写入网卡,也不一定非得是写入硬盘,也可以写到内存缓冲区里(关键是看你代码实现的细节).

@WebServlet("/hello")

注解是 Java 中的特殊的类, Java专门定义了一种"语法糖"来实现注解.
注解的作用,针对一个类/方法,进行额外的“解释说明",赋予这个类/方法额外的功能/含义.

此处这个@WebServlet注解的作用是把当前的类,和一个HTTP请求的路径送联起来.

doGet在``Tomcat收到GET请求的时候就会调用,这个说法其实并不准确!!!具体要不要调用doGet`,还得看当前GET请求的路径是什么.
不同的路径可以触发不同的代码(关联到不同的类上).

例子: 我去餐馆吃饭

早上我发起请求:老板,来份油泼面.
http://ip:port/油泼面?辣椒=少放
老板收到请求之后,就需要按照"制作油泼面"的流程来做饭(根据请求计算响应)

中午我来发起请求:老板,来个蛋炒饭.
http://ip:port/蛋炒饭?葱=多放
老板收到请求之后,就需要按照"制作蛋炒饭”的流程来做这份饭

晚上我来发起请求:老板,来份抄手.
http://ip:port/抄手?辣椒=微辣
老板收到请求之后,就需要按照"制作抄手”的流程来做这份饭

上述三个不同的流程,相当于是三个不同的类/方法

一个Servlet程序中,可以有很多的Servlet类.每个Servlet类都可以关联到不同的路径(对应到不同的资源)
因此此处的多个Servlet就实现了不同的功能.

5.打包程序

把程序编译好(得到一些.class文件),再把这些.class打成压缩包.
jar就是一种.class 构成的压缩包,不过此处要打的是war包.
jar只是一个普通的java程序, war则是tomcat专属的用来描述webapp的程序,可以认为-个war就是一个webapp.

借助maven直接一点击即可

image-20231213121341958

微调 pom.xml

image-20231213123942412

再次打包

image-20231213124618253

打包的作用; 开发环境(自己写代码的电脑)和运行环境(另外一个服务器)很可能不是一个环境!!
直接使用IDEA的三角号运行是本地运行,而不是在另一个服务器上运行.

6.部署

把刚才打包好的war拷贝到tomcat的 webapps目录中即可!
注: 无论tomcat是在你同一个电脑上还是不同电脑上,都是这样拷贝.

image-20231213161559034

启动tomcat

image-20231213161839922

image-20231213162204877

7.验证

打开浏览器,输入url,访问写好的这个代码.
URL: http://127.0.0.1:8080/hello_servlet/hello

这个url的路径的写法
image-20231213163639609

image-20231213164803853

务必保证这两级路径都是正确的!!!稍微错一点,就很容易出现404.

小结:

刚才在浏览器地址栏中输入url之后,浏览器就构造了一个对应的HTTP GET请求,发给了tomcat.
tomcat就根据第一级路径,确定了具体的 webapp.根据第二级路径,确定了是调用哪个类.
再然后通过GET/POST方法确定调用HelloServlet的哪个方法(doGet, doPost…)
此时Tomcat 就执行对应的代码,完成对应工作.

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

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

相关文章

做数据分析为何要学统计学(6)——什么问题适合使用卡方检验?

卡方检验作为一种非常著名的非参数检验方法&#xff08;不受总体分布因素的限制&#xff09;&#xff0c;在工程试验、临床试验、社会调查等领域被广泛应用。但是也正是因为使用的便捷性&#xff0c;造成时常被误用。本文参阅相关的文献&#xff0c;对卡方检验的适用性进行粗浅…

基于Java8构建Docke镜像

基于Java8构建Docke镜像 搜索java8安装包 docker search java8 --no-trunc &#xff0c; --no-trunc展开描述信息 选择拉取 docker pull docker.io/mykro/java8-jre&#xff0c;为了减少磁盘占用&#xff0c;选择jre版本基础镜像 在宿主机创建文件夹iot&#xff0c;并把所需…

opencv 十五 红外图像中虹膜的提取

一、算法需求 在医疗检测中&#xff0c;需要使用红外相机拍摄眼睛照片&#xff0c;然后提取出虹膜的区域。在拍摄过程瞳孔需要进行运动&#xff0c;其通常不在正前方&#xff0c;无法形成圆形&#xff0c;不能使用常规的霍夫圆检测进行提取定位。且在在红外图像中&#xff0c;…

Java 语言关键字

Java关键字是电脑语言里事先定义的&#xff0c;有特别意义的标识符&#xff0c;有时又叫保留字&#xff0c;还有特别意义的变量。Java的关键字对Java的编译器有特殊的意义&#xff0c;他们用来表示一种数据类型&#xff0c;或者表示程序的结构等&#xff0c;关键字不能用作变量…

鸿蒙OS应用开发者高级认证题库

一、判断题 云函数打包完成后&#xff0c;需要到AppGallery Connect创建对应函数的触发器才可以在端侧中调用&#xff08;错&#xff09; 在column和Row容器组件中&#xff0c;aligntems用于设置子组件在主轴方向上的对齐格式&#xff0c;justifycontent用于设置子组件在交叉轴…

IO零拷贝

在介绍零拷贝之前我们先看看传统的 Java 网络 IO 编程是怎样的。 下面代码展示了一个典型的 Java 网络程序。 File file new File("index.jsp");RandomAccessFile rdf new RandomAccessFile(file, "rw");byte[] arr new byte[(int) file.length()];rdf…

差分进化算法DE

此算法是一种基于贪心的并行直接搜索算法。 1.过程 &#xff08;1&#xff09;初始化种群 NP个D维的参数向量(i1,2,...,NP)作为每一代G种群&#xff0c;种群规模必须>4 &#xff08;2&#xff09;变异 使用种群中两个不同向量来干扰一个现有向量&#xff0c;进行差分操…

穿梭时光的Java魔法:轻松掌握Date类,揭示当前时间的神秘面纱!

一、实现目标 获取当前时间&#xff01; 二、上代码 import java.text.SimpleDateFormat; import java.util.Date; public class Date_ { // 输出当前的时间 public static void main(String[] arg…

集群监控Zabbix和Prometheus

文章目录 一、Zabbix入门概述1、Zabbix概述2、Zabbix 基础架构3、Zabbix部署3.1 前提环境准备3.2 安装Zabbix3.3 配置Zabbix3.4 启动停止Zabbix 二、Zabbix的使用与集成1、Zabbix常用术语2、Zabbix实战2.1 创建Host2.2 创建监控项&#xff08;Items&#xff09;2.3 创建触发器&…

Dueling DQN 跑 Pendulum-v1

gym-0.26.1 Pendulum-v1 Dueling DQN 因为还是DQN,所以我们沿用double DQN,然后把 Qnet 换成 VAnet。 其他的不变&#xff0c;详情参考前一篇文章。 class VA(nn.Module):"""只有一层隐藏层的A网络和V网络"""def __init__(self, state_dim, hidd…

二百一十五、Flume——Flume拓扑结构之复制和多路复用的开发案例(亲测,附截图)

一、目的 对于Flume的复制和多路复用拓扑结构&#xff0c;进行一个小的开发测试 二、复制和多路复用拓扑结构 &#xff08;一&#xff09;结构含义 Flume 支持将事件流向一个或者多个目的地。 &#xff08;二&#xff09;结构特征 这种模式可以将相同数据复制到多个channe…

【UML】组件图中的供接口和需接口与面向对象中的接口

UML&#xff08;统一建模语言&#xff09;组件图中的“供接口”&#xff08;Provided Interface&#xff09;和“需接口”&#xff08;Required Interface&#xff09;与面向对象编程中的接口概念有关联&#xff0c;但它们在应用上有所区别。 下面解释两者的关系&#xff1a; …

使用kubeadm部署一套Kubernetes v1.23.0集群

使用kubeadm部署一套Kubernetes v1.23.0集群 1、前置知识点 1.1 生产环境可部署Kubernetes集群的两种方式 目前生产部署Kubernetes集群主要有两种方式&#xff1a; • kubeadm Kubeadm是一个K8s部署工具&#xff0c;提供kubeadm init和kubeadm join&#xff0c;用于快速部…

14光线追踪(加速结构)

1.Uniform Spatial Partitions(Grids)—均匀空间划分 1.1场景预处理 Find bounding boxCreate gridStore each object in overlapping cells判断哪些网格可能有物体&#xff0c;有物体的格子做上特殊标记 1.2开始光线追踪 开始做光追→ 光线到有物体的格子 → 判断是否有交点…

day03、关系模型之基本概念

关系模型之基本概念 1.关系模型概述1.1 关系模型三要素基本结构&#xff1a;relation/Table基本操作:relation operator 2.什么是关系3.关系模型中的完整性约束 本视频来源于B站&#xff0c;战德臣老师 1.关系模型概述 1.1 关系模型三要素 基本结构&#xff1a;relation/Table…

【Kubernetes】四层代理Service

Service四层代理 一、Service概念原理1.1、为什么要有Service1.2、Service概述1.3、工作原理1.4、三类IP地址【1】Node Network&#xff08;节点网络&#xff09;【2】Pod network&#xff08;pod 网络&#xff09;【3】Cluster Network&#xff08;服务网络&#xff09; 二、S…

Leetcode 139.单词拆分

OJ链接 &#xff1a;139.单词拆分 代码&#xff1a; class Solution {public boolean wordBreak(String s, List<String> wordDict) {Set<String> set new HashSet<String>(wordDict);int n s.length();boolean[] dp new boolean[n1];dp[0] true;//初始…

现代雷达车载应用——第2章 汽车雷达系统原理 2.5节 检测基础

经典著作&#xff0c;值得一读&#xff0c;英文原版下载链接【免费】ModernRadarforAutomotiveApplications资源-CSDN文库。 2.5 检测基础 对于要测试目标是否存在的雷达测量&#xff0c;可以假定下列两个假设之一为真&#xff1a; •H0:—测量结果仅为噪声。 •H1:—测量是噪…

leaflet使用热力图报L找不到的问题ReferenceError: L is not defined at leaflet-heat.js:11:3

1.在main.js中直接引入会显示找不到L 2.解决办法 直接在组件中单独引入使用 可以直接显示出来。 至于为什么main中不能引入为全局&#xff0c;我是没找到&#xff0c;我的另外一个项目可以&#xff0c;新项目不行&#xff0c;不知哪里设置的问题

LangChain 25: SQL Agent通过自然语言查询数据库sqlite

LangChain系列文章 LangChain 实现给动物取名字&#xff0c;LangChain 2模块化prompt template并用streamlit生成网站 实现给动物取名字LangChain 3使用Agent访问Wikipedia和llm-math计算狗的平均年龄LangChain 4用向量数据库Faiss存储&#xff0c;读取YouTube的视频文本搜索I…