单机时代
联机时代(Client-Server模式) [微信+支付宝+QQ] [需安装APP]
- Client/Server结构(C/S结构)是指客户端和服务器结构
互联网时代(Browser-Server模式) [百度+淘宝+火车票系统]
- Browser-Server模式(B/S模式)即浏览器和服务器架构模式
请求与响应 [成对出现]
- 从浏览器发出送给服务器的数据包成为”请求(Request)“
- 从服务器返回给浏览器的结果称为”响应(Response)“
J2EE
- J2EE(Java 2 Platform Enterprise Edition)是指”Java 2企业版”
- **开发BS(Web)**应用程序就是J2EE最核心的功能
- J2EE由13个功能模块组成
Apache Tomcat
- Tomcat是Apache旗下免费的开放源代码的Web应用服务器程序
J2EE与Tomcat的关系
- J2EE是一组技术规范与指南
- Tomcat是J2EE Web (Servlet与JSP) 标准的实现者
- J2SE是J2EE运行的基石,运行Tomcat离不开J2SE
Servlet
Servlet (Server Applet) 服务器小程序,主要功能用于生成动态Web内容
Servlet是J2EE最重要的组成部分
Web与 Servlet的关系:
获取请求参数(来自HTML的数据输入)
(1) request.getParameter() 取得是通过容器的实现来取得通过类似post,get等方式传入的数据
request.setAttribute()[往域中保存数据] 和 getAttribute()[从域中获取数据]只是在web容器内部流转,仅仅是请求处理阶段。
(2) request.getParameter () 方法传递的数据,会从Web客户端传到Web服务器端,代表HTTP请求数据。
原文链接:https://blog.csdn.net/qq_54000767/article/details/128003181ContentType
(3) String getParameter(String name) 根据请求参数名获取请求参数值
(4) String[] getParameterValues(String name) 根据请求参数名获取请求参数多个值
(5) Enumeration getParameterNames() 获取所有的请求参数名
(6) Map<String, String[]> getParameterMap() 获取所有请求擦桉树 把请求参数保存到map集合
(7) req.getServletContext() 实质上可以看做一个对象,其可以使用ServletContext接口中的方法1.在javax.servlet.Filter中直接获取 ServletContext context = config.getServletContext();
2.在HttpServlet中直接获取 this.getServletContext()
3.在其他方法中,通过HttpRequest获得 request.getSession().getServletContext();(8) getRequestDispatcher() getRequestDispatcher()包含两个重要方法
分别是请求转发和请求包含。一个请求跨多个Servlet时,需要使用请求转发和请求包含。
首先需要获得一个RequestDispatcher 对象:RequestDispatcher rd = request.getRequestDispatcher(“/MyServlet”);
- request.getRequestDispatcher().forward() - 请求转发[请求自发器]
请求转发是服务器跳转,指挥产生一次请求- response.sendRedirect() - 响应重定向
响应重定向是浏览器端跳转,会产生两次请求- request.setAttribute(属性名,属性值) - 设置请求属性
Object attr = request.getAttribute(属性名) - 获取请求属性
请求允许创建自定义属性决定浏览器采用何种方式对响应体进行处理
response.setContentType(“text/html; charset=utf-8”);
========FirstServlet.java========
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;
public class FirstServlet extends HttpServlet {
@Override
protected void service(HttpServletRequest request, HttpServletResponse response) throws IOException {
String name = request.getParameter("name"); //接收请求发来的参数
String html = "<h1 style = 'color : red'>hi," + name + "!</h1><hr/>";
System.out.println("返回給浏览器的响应数据为:" + html);
PrintWriter out = response.getWriter();
out.println(html);//将html发送回浏览器
}
}
======================web.xml===============================
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"
version="4.0">
<display-name>FirstServlet</display-name>
<servlet> //servlet的别名
<servlet-name>first</servlet-name>
<servlet-class>FirstServlet</servlet-class>
</servlet>
<servlet-mapping> //映射 web应用程序都是网址来运用 把servlet和网址(url)绑定在一起
<servlet-name>first</servlet-name>//输入地址.../hi 再通过别名来访问FirstServlet
<url-pattern>/hi</url-pattern>//若是直接写会暴露系统类名完整信息的隐私
<!--http://localhost:8080/Test_Tomcat_war_exploded/hi?name=jackson-->
</servlet-mapping>
</web-app>
HttpServlet 是所有小程序的父类,需要继承 (Eclipse 快速导包 Ctrl + Shift + O)
启动项目:Servers右键Tomcat - Add and Remove
Servlet开发步骤
- 创建Servlet类,继承HTTPServlet
- 重写service方法,编写程序代码
- 配置web.xml,绑定URL
Servlet访问方法
- http:// IP地址:端口 / context-path / url-mapping
- 远程访问使用IP地址,本地访问localhost(127.0.0.1)
- context-path成为”上下文路径”,默认为工程名
☆ web.xml ☆
<servlet>
<servlet-name>sample</servlet-name>
<servlet-class>com.imooc.servlet.SampleServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>sample</servlet-name>
<url-pattern>/sample</url-pattern>
</servlet-mapping>
============================================
☆ SampleServlet.java ☆
package com.imooc.servlet;
import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class SampleServlet extends HttpServlet {
public void service(HttpServletRequest request, HttpServletResponse response) throws IOException {
PrintWriter out = response.getWriter(); //向浏览器输出的数据流
out.println("<a href='http://www.baidu.com'>Baidu</a>");
}
}
请求参数
- 请求参数是指浏览器通过请求向Tomcat提交的数据
- 请求参数通常是用户输入的数据,待Servlet进行处理
- 参数名1 = 值1 & 参数名2 = 值2 & 参数名n = …
Servlet接收请求参数
- request.getParameter() – 接收单个参数
- request.getParameterValues() – 接收多个同名参数
☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ SampleServlet.java ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆
package com.imooc.servlet;
import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class SampleServlet extends HttpServlet {
//service是请求处理的核心方法,无论是get或者post都会被service()方法处理
public void service(HttpServletRequest request, HttpServletResponse response) throws IOException {
String name = request.getParameter("name");
String mobile = request.getParameter("mobile");
String sex = request.getParameter("sex");
String[] specs = request.getParameterValues("spec");
PrintWriter out = response.getWriter(); //向浏览器输出的数据流
out.println("<h1>name:" + name + "</h1>");
out.println("<h1>mobile:" + mobile + "</h1>");
out.println("<h1>sex:" + sex + "</h1>");
for(int i = 0; i < specs.length; i++) {
out.println("<h2>spec:" + specs[i] + "</h2>");
}
out.println("<a href='http://www.baidu.com'>Baidu</a>");
}
}
☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ studnet.html ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>学员信息登记表</title>
</head>
<body>
<h1>学员信息登记表</h1>
<form action="http://localhost:8080/Test_Tomcat_war_exploded/sample" method="get" >
姓名:<input name="name"/>
<br/>
电话:<input name="mobile"/>
<br/>
性别:
<select name="sex" style="width:100px;padding:5px;">
<option value="male" >男</option>
<option value="female">女</option>
</select>
<br/>
特长:
<input type="checkbox" name="spec" value="English"/>英语
<input type="checkbox" name="spec" value="Program"/>编程
<input type="checkbox" name="spec" value="Speech"/>演讲
<input type="checkbox" name="spec" value="Swimming"/>游泳
<br/>
<input type="submit" value="提交">
<br/>
</form>
</body>
</html>
Get与Post请求方法
- Get方式(可读性好) 是将数据通过在URL附加数据显性向服务器发送数据[明文] Get请求 - doGet()方法
http:// localhost:8080/Test_Tomcat_war_exploded/sample?name = zhangsan
- Post方式(更加隐蔽) 会将数据存放在“请求体”中隐性向服务器发送数据[隐性请求体] Post请求 - doPost()方法
http:// localhost:8080/Test_Tomcat_war_exploded/sample
请求体:name=zhangsan
所有请求 - service()方法
☆ ☆ ☆ ☆ ☆ ☆ Get与Post请求方法 ☆ ☆ ☆ ☆ ☆ ☆
#### Get与Post处理方式
- 所有请求-service()方法
- Get请求-doGet()方法
- Post请求-doPost()方法
#### Get与Post应用场景
- Get常用于不包含敏感信息的查询功能
- Post用于安全性要求较高的功能或者服务器的“写”操作
- 用户登录
- 用户注册
- 更新公司账目
HTML默认以get方式提交,可以改变方式
<form action="http://localhost:8080/Test_Tomcat_war_exploded/sample"
method="post"
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
public class RequestMethodServlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response) throws IOException {
String name = request.getParameter("name");
response.getWriter().println("<h1 style = 'color:green'>"+name+"</h1>");
}
public void doPost(HttpServletRequest request, HttpServletResponse response) throws IOException {
String name = request.getParameter("name");
response.getWriter().println("<h1 style = 'color:red'>"+name+"</h1>");
}
}
Servlet生命周期
装载 - web.xml
创建 - 构造函数
public FirstServlet(){
System.out.println(“正在创建FirstServlet对象”);
}**初始化 - init() **[启动时加载 类似于LOL入场进度条]
@Override
public void init(ServletConfig config) throws ServletException {
System.out.println(“正在初始化FirstServlet对象”);
}提供服务 - service()
@Override
protected void service(HttpServletRequest request, HttpServletResponse response) throws IOException {
String name = request.getParameter(“name”); //接收请求发来的参数
String html = “hi,” + name + “!
“;
System.out.println(“返回給浏览器的响应数据为:” + html);
PrintWriter out = response.getWriter();
out.println(html);//将html发送回浏览器
}销毁 - destroy() [重启的时候会施行销毁]
@Override
public void destroy() {
System.out.println(“正在销毁FirstServlet对象”);
}
使用注解简化配置
- Servlet 3.x 之后引入了“注解Annotation”特性
- 注解用于简化web应用程序的配置过程
- Servlet核心注解:**@WebServlet** [简化配置 以防.xml的依赖越来越多]
@WebServlet(“/anno”) 把servlet类绑定到/anno
设置loadOnStartup后必须要强制设置地址
@WebServlet(urlPatterns=”/unused”, loadOnStartup=2)
@WebServlet("/anno")
public class AnnotationServlet extends HttpServlet{}
AnnotationServlet是Servlet类把它绑定到标志("/anno")上
//http://localhost:8080/Test_Tomcat_war_exploded/anno
启动时加载Servlet [模仿开发项目场景]
- web.xml使用< load-on-startup >设置启动加载
- < load-on-startup > 0~9999 < /load-on-startup >
为加载顺序 0的优先级最高 - 启动时加载在工作中常用于系统的预处理
CreateServlet.java
package com.imooc.servlet;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
public class CreatServlet extends HttpServlet {
@Override
public void init() throws ServletException {
System.out.println("正在创建数据库");
}
}
ImportServlet.java
package com.imooc.servlet;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
public class ImportServlet extends HttpServlet {
@Override
public void init() throws ServletException {
System.out.println("正在导入数据");
}
}
AnalysisServlet.java
package com.imooc.servlet;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
public class AnalysisServlet extends HttpServlet {
@Override
public void init() throws ServletException {
System.out.println("正在分析结果");
}
}
web.xml
< url-pattern > /hi < /url-pattern >提供服务时才会写
因为这三个servlet只是启动的时候运行 不提供服务不用写url
<servlet>
<servlet-name>create</servlet-name>
<servlet-class>com.imooc.servlet.CreatServlet</servlet-class>
<load-on-startup>0</load-on-startup> //在启动时最先被加载
</servlet>
<servlet>
<servlet-name>import</servlet-name>
<servlet-class>com.imooc.servlet.ImportServlet</servlet-class>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet>
<servlet-name>analysis</servlet-name>
<servlet-class>com.imooc.servlet.AnalysisServlet</servlet-class>
<load-on-startup>2</load-on-startup>
</servlet>
若是不写入xml则需要注解@WebServlet
import javax.servlet.ServletConfig;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
@WebServlet(urlPatterns = "/unused", loadOnStartup = 1)
public class ImportServlet1 extends HttpServlet {
@Override
public void init(ServletConfig config) throws ServletException {
System.out.println("正在导入数据1");
}
}
其中必须@WebServlet(urlPatterns = “/unused”, loadOnStartup = 1)
必须要地址url
.jpg)
JSP(Java Server Pages)入门
JSP是J2EE的功能模块,由Web服务器执行
JSP的作用就是降低动态网页开发难度
JSP的出现:Servlet有缺点
- 静态HTML与动态Java代码混合在一起,难以维护
- Servlet利用out.println()语句输出,开发效率低下
- Eclipse很难在开发中发现错误,调试困难
JSP特点:
①.使用简单, 短时间学习便可上手使用
②.可将Java代码与HTML分离, 降低开发难度
③.JSP的本质就是Servlet
JSP中的写java代码块 <% … %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
<table>
<tr>
<th>year</th>
<th>salary</th>
</tr>
<%
for (int i = 0; i <= 50; i++){
out.println("<tr>");
out.println("<td>" + i + "</td>");
int sal = 0;
if (i <= 5){
sal = 1500 + i * 150;
} else if (i > 5 && i <= 10) {
sal = 1500 + 150 * 5 + 300 * (i-5);
} else if (i > 10) {
sal = 1500 + 150 * 5 + 300 * 5 + 375 * (i-10);
}
out.println("<td>" + sal + "</td>");
out.println("</tr>");
}
%>
</table>
</body>
</html>
JSP的执行过程
网页通过JSP(Tomcat) 进行转译成为Servlet源代码 然后编译成Servlet字节码 最后返回到网页呈现
JSP的基本语法
JSP代码块
JSP代码块用于JSP中嵌入Java代码
JSP代码块语法:<% java代码 %>
JSP声明构造块
JSP声明构造块用于声明变量或方法
JSP声明构造块语法:<%! 声明语句 %>
JSP输出指令
JSP输出指令用于在JSP页面中显示java代码执行结果
JSP输出指令语法:<%= java代码 %>
例如:<%= “< b >” + name + “< /b >” %>
JSP处理指令
JSP处理指令用于提供JSP执行过程中的辅助信息
JSP处理指令语法:<%@ jsp指令 %>
例如:<%@ page import = “java.util.*” %>
JSP常用处理指令
<%@ page %> 定义当前JSP页面全局设置
<%@ include file = “url…”%> 将其他JSP页面与当前JSP页面合并
<%@ taglib %> 引入JSP标签库
JSP中注释的区别
<%– 注释 –%> JSP注释,被注释语句不做任何处理
//、/../ 用于注释<% %>java代码,被注释代码不执行
< !– html – > HTML注释,被注释的语句不会被浏览器解释
综合训练:质数算法
列出1000内的质数(除1以外,只能被1和自身整除的自然数)
要求1:使用List保存所有有效的质数
要求2:将结果打印到页面,格式为”< h1 > X是质数 < /h1 >”
<%@ page import="java.util.List" %>
<%@ page import="java.util.ArrayList" %>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%!
boolean isPrime(int num){
boolean flag = true;
for (int j = 2; j < num; j++) {
if (num % j ==0){
flag = false;
break;
}
}
return flag;
}
%>
<%
List<Integer> primes = new ArrayList();
for (int i = 2; i <= 1000; i++){
boolean flag = isPrime(i);
if (flag == true){
// out.println("<h1>" + i + "</h1>");
primes.add(i);
}
}
%>
<%
for (int p : primes){
// out.println("<h1>" + p + "是质数</h1>");
%>
<h1 style="color: green"><%=p %>是质数</h1>
<%
}
%>
JSP页面重用
<%@ include file = “url…”%> 将其他JSP页面与当前JSP页面合并
☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ news.jsp ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@include file="include/header.jsp"%>
<%
out.println("<h1>新闻标题</h1>");
out.println("<p>新闻正文</p>");
%>
<%@include file="include/footer.jsp"%>
☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ header.jsp ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
体育|推荐|财经|娱乐
☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ footer.jsp ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<hr/>
Copyright 1999-2023
JSP&Servlet进阶
HTTP请求的结构
- HTTP请求包含三部分:请求行、请求头、请求体
eclipse导入jar包 (工程名 - Properties - Java Build Path - Libraries - Add EXternal JARs)
查看F12网络 - All 可查看内部详细信息常规
input.html
get请求把数据放在url中 post请求把数据放在请求体中
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body> <!-- 工程名 + 映射地址 -->
<form action="/request-struc/request" method="post">
<input name="username"/>
<input name="password" type="password"/>
<input type="submit"/>
</form>
</body>
</html>
巧用请求头开发多端应用
根据请求头去对应不同的设备
同样的网址在手机和电脑上所呈现的内容是不一样的
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
@WebServlet("/ua")
public class UserAgentServlet extends HttpServlet {
public UserAgentServlet() {
}
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
String userAgent = req.getHeader("User-Agent");
resp.setContentType("text/html; charset=utf-8");
resp.getWriter().println(userAgent);
String output = "";
if (userAgent.indexOf("Windows NT")!=-1){
output = "<h1>这是PC端首页</h1>";
} else if (userAgent.indexOf("iPhone")!=-1 || userAgent.indexOf("Android")!=-1) {
output = "<h1>这是移动端首页</h1>";
}
resp.getWriter().println(output);
}
}
响应的结构 (服务器返回給浏览器的显示结果)
HTTP请求包含三部分:响应行、响应头、响应体
状态码 | 错误描述 |
---|---|
200 | 服务器处理成功 |
404 | 无法找到文件 |
500 | 内部服务器错误 |
403 | 服务器拒绝访问 |
301、302 | 请求重定向 |
400 | 无效的请求 |
401 | 未经过授权 |
503 | 服务器超负载或正停机维护,无法处理请求 |
ContentType的作用
ContentType决定浏览器采用何种方式对响应体进行处理
response.setContentType(“text/html; charset=utf-8”);
MIME类型 | 描述 |
---|---|
text/plain | 纯文本 |
text/html | HTML文档 |
text/xml | XML文档 |
application/x-msdownload | 需要下载的资源 |
image/jpeg image/gif image/… |
图片资源 |
protected void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
String output = "<h1><a href='http://www.baidu.com'><span>百度</span></a></h1>";
response.setContentType("text/html; charset=utf-8");
response.getWriter().println(output);
}
请求转发与重定向 [二次跳转与定位]
多个Servlet(JSP)之间跳转有两种方式:
- request.getRequestDispatcher().forward() - 请求转发[请求自发器]
请求转发是服务器跳转,指挥产生一次请求 - response.sendRedirect() - 响应重定向
响应重定向是浏览器端跳转,会产生两次请求 - request.setAttribute(属性名,属性值) - 设置请求属性
Object attr = request.getAttribute(属性名) - 获取请求属性
请求允许创建自定义属性
CheckLoginServlet.java
package servlet;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
@WebServlet("/direct/check")
public class CheckLoginServlet extends HttpServlet {
public CheckLoginServlet() {
}
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
System.out.println("用户登录成功");
//创建自定义属性
req.setAttribute("username","admin");
//实现了请求转发的功能[从服务器内部由第一个servlet转到第二个] forward(请求 + 响应)
req.getRequestDispatcher("/direct/index").forward(req, resp);
//响应重定向需要增加contextPath[将请求第一次处理完后将响应重新发送一个新的请求給index servlet]
resp.sendRedirect("/direct/index"); //[结果已被重定向]
}
}
==============================================================
indexServlet.java
package servlet;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
@WebServlet("/direct/index")
public class indexServlet extends HttpServlet {
public indexServlet() {
}
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
//接收创建的自定义属性
String username = (String)req.getAttribute("username");
resp.getWriter().println("This is index page!current username is " + username);
}
}
浏览器Cookie [浏览器重启但用户登录不会消失]
- Cookie是浏览器保存在本地的文本内容
- Cookie常用于保存登录状态、用户资料等小文本
- Cookie具有时效性,Cookie内容会伴随请求发送給Tomcat
- request.getCookies() 用户获取所有的Cookie
- cookie.setMaxAge() 用户设置cookie保存的时间(单位:秒s)
ImoocLoginServlet.java
package cookie;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
@WebServlet("/cookies/login")
public class ImoocLoginServlet extends HttpServlet {
public ImoocLoginServlet() {
}
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
System.out.println("用户登录成功");
Cookie cookie = new Cookie("user","admin");
cookie.setMaxAge(60 * 60 * 24 * 7); //单位是秒 七天内有效
resp.addCookie(cookie);
resp.getWriter().println("login success");
}
}
================================================================
ImoocIndexServlet.java
package cookie;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
@WebServlet("/cookies/index")
public class ImoocIndexServlet extends HttpServlet {
public ImoocIndexServlet() {
}
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
Cookie[] cs = req.getCookies();
String user = null;
for (Cookie c : cs){
System.out.println(c.getName() + ":" + c.getValue());
if (c.getName().equals("user")){
user = c.getValue();
break;
}
}
if (user == null){
resp.getWriter().println("user not login");
}else {
resp.getWriter().println("user:" + user);
}
}
}
Session-用户会话
- Session(用户会话) 用于保存与 ”浏览器窗口“ 对应的数据
- Session的数据存储在Tomcat服务器的内存中,具有时效性
- Session通过浏览器Cookie的SessionId值提取用户数据
Session类似于是浏览器单独存储的空间,每个浏览器窗口所对应的Session空间是不同的;
Session是与浏览器窗口绑定的且把数据存储在Tomcat内存中的对象

SessionLoginServlet.java
package session;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.io.IOException;
@WebServlet("/session/login")
public class SessionLoginServlet extends HttpServlet {
public SessionLoginServlet() {
}
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
System.out.println("用户登录成功");
//获取到用户会话Session对象
HttpSession session = req.getSession();
String sessionId = session.getId(); //A99EA3178EDC7C490E29D8EC46930FC6
System.out.println(sessionId);
session.setAttribute("name","张三");
req.getRequestDispatcher("/session/index").forward(req,resp); //请求转发
}
}
============================================================================
SessionIndexServlet.java
package session;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.io.IOException;
@WebServlet("/session/index")
public class SessionIndexServlet extends HttpServlet {
public SessionIndexServlet() {
}
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
HttpSession session = req.getSession();
String sessionId = session.getId(); //A99EA3178EDC7C490E29D8EC46930FC6
System.out.println(sessionId);
String name = (String)session.getAttribute("name");
resp.setContentType("text/html;charset=utf-8");
resp.getWriter().println("这是首页,当前用户为: " + name);
}
}
Cookie 与 Session 区别
区别:
cookie数据保存在客户端,session数据保存在服务端。session
简单的说,当你登陆一个网站的时候,如果web服务器端使用的是session,那么所有的数据都保存在服务器上,客户端每次请求服务器的时候会发送当前会话session_id,服务器根据当前session_id判断相应的用户数据标志,以确定用户是否登陆或具有某种权限。由于数据是存储在服务器上面,所以你不能伪造。cookie
session_id是服务器和客户端连接时候随机分配的,如果浏览器使用的是cookie,那么所有数据都保存在浏览器端,比如你登陆以后,服务器设置了cookie用户名,那么当你再次请求服务器的时候,浏览器会将用户名一块发送给服务器,这些变量有一定的特殊标记。服务器会解释为cookie变量,所以只要不关闭浏览器,那么cookie变量一直是有效的,所以能够保证长时间不掉线。如果你能够截获某个用户的cookie变量,然后伪造一个数据包发送过去,那么服务器还是 认为你是合法的。所以,使用cookie被攻击的可能性比较大。
如果cookie设置了有效值,那么cookie会保存到客户端的硬盘上,下次在访问网站的时候,浏览器先检查有没有cookie,如果有的话,读取cookie,然后发送给服务器。
所以你在机器上面保存了某个论坛cookie,有效期是一年,如果有人入侵你的机器,将你的cookie拷走,放在他机器下面,那么他登陆该网站的时候就是用你的身份登陆的。当然,伪造的时候需要注意,直接copy cookie文件到 cookie目录,浏览器是不认的,他有一个index.dat文件,存储了 cookie文件的建立时间,以及是否有修改,所以你必须先要有该网站的 cookie文件,并且要从保证时间上骗过浏览器
两个都可以用来存私密的东西,session过期与否,取决于服务器的设定。cookie过期与否,可以在cookie生成的时候设置进去。
四、区别对比:
(1) cookie数据存放在客户的浏览器上,session数据放在服务器上
(2) cookie不是很安全,别人可以分析存放在本地的COOKIE并进行COOKIE欺骗,如果主要考虑到安全应当使用session
(3) session会在一定时间内保存在服务器上。当访问增多,会比较占用你服务器的性能,如果主要考虑到减轻服务器性能方面,应当使用COOKIE
(4) 单个cookie在客户端的限制是3K,就是说一个站点在客户端存放的COOKIE不能3K。
(5) 所以:将登陆信息等重要信息存放为SESSION;其他信息如果需要保留,可以放在COOKIE中
ServletContext
- ServletContext(Servlet上下文对象),是Web应用全局对象
- 一个Web应用只会创建一个ServletContext对象
- ServletContext随着Web应用启动而自动创建
如果是session 则关闭一次浏览器sessionId就会发生变化 重新加载session
只要设置了自定义属性就会在全局生效
Java Web三大作用域对象 [作用域和生命周期依次递增]
- HttpServletRequest - 请求对象
[网页请求 Tomcat响应一次后销毁] - HttpSession - 用户会话对象
[保存与浏览器窗口的数据 网页请求 Tomcat响应后有30分钟没有被访问则销毁] - ServletContext - web应用全局对象
[Web启动时被创建]
能用小作用域完成开发的功能就尽量不要使用大作用域
Web应用的中文乱码由来
- Tomcat默认使用字符集ISO-8859-1,属于西欧字符集
- 解决乱码的核心思路是将ISO-8859-1转换为UTF-8
- Servlet中请求与响应都需要设置UTF-8字符集
Ⅰ.麻烦且不实用
String utf8Ename = new String(ename.getBytes("iso-8859-1"), "utf-8");
String utf8EAddress = new String(address.getBytes("iso-8859-1"), "utf-8");
Ⅱ.简便且实用
写在★★doPost★★下面的第一行
request.setCharacterEncoding("UTF-8");
//对于Tomocat8.x的版本, 默认get请求发送中文就是UTF-8, 因此无需转换
写在★★doGet★★下面
response.setContentType("text/html;charset=utf-8");
web.xml常用配置
- 修改web应用默认首页
- Servlet通配符映射及初始化参数
- 设置404、500等状态码默认页面
设置默认首页地址 => 在web.xml中 设置
设置后启动tomcat后自动弹出首页为student.html中的内容
<welcome-file-list>
<welcome-file>student.html</welcome-file>
</welcome-file-list>
根目录/二级页面也可以查找默认首页
模糊匹配:* [Servlet通配符]
@WebServlet(“/cookies/*”)
☆ ☆ ☆ ☆ web.xml ☆ ☆ ☆ ☆
<servlet>
<servlet-name>patternServlet</servlet-name>
<servlet-class>PatternServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>patternServlet</servlet-name>
<url-pattern>/pattern/*</url-pattern>
</servlet-mapping>
☆ ☆ ☆ ☆ PatternServlet.java ☆ ☆ ☆ ☆
public class PatternServlet extends HttpServlet{
@Override
protected void service(HttpServletRequest request,HttpServletReasponse reasponse){
//查询员工的基本信息 获取当前访问的URL
String url = request.getRequestURL().toString();
System.out.println(url);
String id = url.substring(url.lastIndexOf("/") + 1);
int eid = Integer.parseInt(id);
response.setContentType("text/html;charest=utf-8");
PrintWriter out = response.getWriter();
out.println(id);
if(eid == 1) {
out.println("张三");
}else if(eid == 2) {
out.println("李四");
}else {
out.println("其他员工");
}
}
}
全局配置
这样做以后就可以直接修改xml里面的东西就好了
<context-param>
<param-name>copyright</param-name>
<param-value>@ 2023 imooc.com 京ICP备 12003892号-22</param-value>
</context-param>
<context-param>
<param-name>title</param-name>
<param-value>慕课网-程序员的梦工厂</param-value>
</context-param>
@WebServlet("/servletcontext/init")
public class ServletContextInitServlet extends HttpServlet {
public ServletContextInitServlet() {
super();
}
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
ServletContext context = request.getServletContext();
String copyright = context.getInitParameter("copyright");
context.setAttribute("copyright", copyright);
String title = context.getInitParameter("title");
context.setAttribute("title", title);
response.getWriter().println("init success");
}
}
针对404、500出现透露信息的bug处理方式
☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ 404.html ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆
<!DOCTYPE html>
<html>
<head>
<meta charset = "UTF-8">
<title>Insert title here</title>
</head>
<body>
资源不存在
</body>
</html>
☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ 500.html ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆
<!DOCTYPE html>
<html>
<head>
<meta charset = "UTF-8">
<title>Insert title here</title>
</head>
<body>
服务器内部错误,请联系管理员
</body>
</html>
☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆ web.xml ☆ ☆ ☆ ☆ ☆ ☆ ☆ ☆
<!-- 指定错误页面 -->
<error-page>
<error-code>404</error-code>
<location>/error/404.html</location>
</error-page>
<error-page>
<error-code>500</error-code>
<location>/error/500.html</location>
</error-page>
======================================================================
可以把404\500.html随时转换成 404\500.jsp
仅需在顶加上<%@ page contentType="text/html;charset=utf-8" isErrorPage="true"%>
isErrorPage="true" 说明此jsp专门用于错误页面
<%@ page contentType="text/html;charset=utf-8" isErrorPage="true"%>
<!DOCTYPE html>
<html>
<head>
<meta charset = "UTF-8">
<title>Insert title here</title>
</head>
<body>
服务器内部错误,请联系管理员,错误信息如下:
<%
String msg = exception.getMessage();
out.print("<br>" + exception.getClass().getSimpleName() + ":" + msg);
<!-- NumberFormatException:For input String:"" -->
%>
</body>
</html>
JSP九大内置对象[面试/笔试重点]
内置对象 | 描述 |
---|---|
request | 请求对象 -HttpServletRequest |
response | 响应对象 -HttpServletResponse |
session | 用户会话 -HttpSession |
application | 应用全局对象 -ServletContext |
out | 输出对象 -PrintWriter |
page | 当前页面对象 -this |
pageContext | 页面上下文对象 -PageContext |
config | 应用配置对象 -ServletConfig |
exception | 应用异常对象 -Throwable |
<body> <!--内置了许多java的类-->
<%
String url = request.getRequesrURL().toString(); //HttpServletRequest
response.getWriter().println(url); //HttpServletResponse
%>
<%
out.println("<br>ABCCC");
session.setAttribute("user","张三");
out.println((String)session.getAttribute("user"));
%>
<%
String cp = application.getInitParameter("copyright"); //ServletContext
out.println("<hr/>");
out.println(cp);
pageContext.getRequest(); //pageContext就像一个中转站
pageContext.getResponse();
pageContext.getSession();
pageContext.getServletContext();
%>
</body>
Java Web打包与发布
- Java Web应用采用war包进行发布
- 发布路径为:{TOMCAT_HOME}/webapps
- Eclipse支持war包导出
IDEA怎么把web项目打成war包最详细图文教程_idea web项目打成war包_Keeling1720的博客-CSDN博客
IDEA 将项目打包war包_虚拟机安装tomcat_dadeity的博客-CSDN博客
EL(Expression Language)表达式
${student.name} => [自定义属性名. 子属性]
- EL表达式用于简化JSP的输出
- EL表达式的基本语法:**${表达式}**
- 示例:< h1 >学生姓名:**$(student.name)** < /h1 >
StudentServlet.java
protected void doGet(...){
Student stu = new Student();
stu.setName("子墨");
stu.setMobile(null);
String grade = "A";
request.setAttribute("student",stu);
request.setAttribute("grade",grade);
request.getRequestDispatcher("/info.jsp").forward(request, response);
}
☆ ☆ ☆ ☆ ☆ ☆ info.jsp ☆ ☆ ☆ ☆ ☆ ☆
<body>
<%
Student stu = (Student)request.getAttribute("student");
Student grade = (Student)request.getAttribute("grade");
out.println("姓名:"+ stu.getName())
out.println("姓名:"+ stu.getMobile())
out.println("姓名:"+ grade)
%>
</body>
☆ ☆ ☆ ☆ ☆ ☆ el_info.jsp ☆ ☆ ☆ ☆ ☆ ☆
<body>
姓名: ${requestScope.student.name}
手机: ${requestScope.student.mobile}
评级: ${requestScope.grade}
</body>
作用域对象
- requestScope是EL作用域对象
- EL表达式内置四种作用域对象
- 忽略书写作用域对象时,el则按作用域从小到大一次尝试获取
作用域对象 | 描述 |
---|---|
pageScope | 从当前页面取值 |
requestScope | 从当前请求中获取属性值 |
sessionScope | 从当前会话中获取属性值 |
applicationScope | 从当前应用获取全局属性值 |
姓名: ${requestScope.student.name} 其中的requestScope可以省略 el则按作用域从小到大一次尝试获取
EL表达式输出 [支持运算]
- 语法:${[作用域.]属性名[.子属性]}
- EL表达式支持对运算结果进行输出
- EL支持绝大多数对象输出,本质是执行toString()方法
${title}
${requestScope.student.name}
${emp.salary + 300}
${1<=3 && 2>4}
EL输出参数值
- EL表达式内置param对象来简化参数的输出
- 语法: ${param.参数名}
☆ ☆ ☆ ☆ ☆ ☆ el_info.jsp ☆ ☆ ☆ ☆ ☆ ☆
<body>
姓名: ${param.student.name}
手机: ${param.student.mobile}
评级: ${param.grade}
</body>
JSTL(JSP Standard Tag Libarary) 标签库
- JSTL用于简化JSP开发,提高代码的可读性与可维护性
- JSTL由SUN(Oracle)定义规范,由Apache Tomcat团队实现
安装JSTL标签库
- 将Jar文件复制到工程的 /WEB-INF/lib 目录
- 将Jar文件复制到Tomcat安装目录的lib目录
标签 | 描述 |
---|---|
< c:out > | 用于在JSP中显示数据,就像<%= … > |
< c:set > | 用于保存数据 |
< c:remove > | 用于删除数据 |
< c:catch > | 用来处理产生错误的异常状况,并且将错误信息储存起来 |
< c:if > | 与我们在一般程序中用的if一样 |
< c:choose > | 本身只当做<c:when>和<c:otherwise>的父标签 |
< c:when > | <c:choose>的子标签,用来判断条件是否成立 |
< c:otherwise > | <c:choose>的子标签,接在<c:when>标签后,当<c:when>标签判断为false时被执行 |
< c:import > | 检索一个绝对或相对 URL,然后将其内容暴露给页面 |
< c:forEach > | 基础迭代标签,接受多种集合类型 |
< c:forTokens > | 根据指定的分隔符来分隔内容并迭代输出 |
< c:param > | 用来给包含或重定向的页面传递参数 |
< c:redirect > | 重定向至一个新的URL. |
< c: | 使用可选的查询参数来创造一个URL |
JSTL的标签库种类
- JSTL按功能划分可分为五类标签库
类别 |
---|
核心标签库 - core |
格式化输出标签库 - fmt |
SQL操作标签库 - sql |
XML操作标签库 - xml |
函数标签库 - functions |
引用JSTL核心库 [“< c:?? >”]
- 核心标签库 - core 是JSTL最重要的标签库,提供了JSTL的基础功能
- <%@ taglib prefix = “c” uri = “http://java.sun.com/jsp/jstl/core" %> 引入标签库
< c: ?? > … < /c:?? >
< c:out >输出
C标签c:forEach的用法
<c:forEach var="name" items="Collection" varStatus="statusName" begin="begin" end="end" step="step">/c:forEach>
该标签根据循环条件遍历集合 Collection 中的元素。 var 用于存储从集合中取出的元素;items 指定要遍历的集合;varStatus 用于存放集合中元素的信息
这个标签的目的就是要遍历
items: 就是你要遍历的集合,就是要遍历的全部内容要放在这个下面
var: 就是这个集合下面的每一个元素,比如一个集合{1,2,3,4,5},那么var表示的就是1或者2或者3...
begin: 默认从0开始,表示从第几个开始取元素
end: 和begin对应,表示到第几个元素终止
step: 步进,默认是1,表示一个一个跳,还是任意数字跳
varStatus: 表示集合中每个元素的相关信息,有4种状态:index(所在位置,即索引).count(总共已迭代的次数).first(是否为第一个位置),last(是否为最后一个位置)
request.getAttribute表示从request范围取得设置的属性,必须要先setAttribute设置属性,才能通过getAttribute来取得,设置与取得的为Object对象类型 。
1.放的时候:Double res = new Double(result);//包装
request.setAttribute(“result”, res);//再设置进去
2.取的时候:Double res = (Double)request.getAttribute(“result”);
double result = res.doublue();
另外,需要注意的是使用request.setAttribute时不能使redirect而是forward。即是将请求转发而不是重定向.
<%@ page contentType="text/html;charset=GBK" %>
<%@page import="java.util.List" %>
<%@page import="java.util.ArrayList" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<html>
<head>
<title>JSTL: -- forEach标签实例</title>
</head>
<body>
<h4><c:out value="forEach实例"/></h4>
<hr>
<%
List a = new ArrayList();
a.add("贝贝");
a.add("晶晶");
a.add("欢欢");
a.add("莹莹");
a.add("妮妮");
request.setAttribute("a",a);
%>
<B><c:out value="不指定begin和end的迭代"/></B><br>
<c:forEach var="fuwa" items="${a}">
<c:out value="${fuwa}"/><br>
</c:forEach>
<B><c:out value="指定bigin和end的迭代"/></B><br>
<c:forEach var="fuwa" items="${a}" begin="1" end="3" step="2">
<c:out value="${fuwa}"/><br>
</c:forEach>
<B><c:out value="输出整个迭代信息"/></B><br>
<c:forEach var="fuwa" items="${a}" begin="3" end="4" step="1" varStatus="s">
<c:out value="${fuwa}"/>的四种属性:<br>
所在位置,即索引:<c:out value="${s.index}"/><br>
总共已迭代的次数:<c:out value="${s.count}"/><br>
是否为第一个位置:<c:out value="${s.first}"/><br>
是否为最后一个位置:<c:out value="${s.last}"/><br>
</c:forEach>
</body>
</html>
forEach实例
---------------------------------------------------------
不指定begin和end的迭代
贝贝
晶晶
欢欢
莹莹
妮妮
指定bigin和end的迭代
晶晶
莹莹
输出整个迭代信息
莹莹的四种属性:
所在位置,即索引:3
总共已迭代的次数:1
是否为第一个位置:true
是否为最后一个位置:false
妮妮的四种属性:
所在位置,即索引:4
总共已迭代的次数:2
是否为第一个位置:false
是否为最后一个位置:true
判断标签
- JSTL核心库提供了两组判断的标签
- < c : if > - 单分支判断
- < c:choose >、< c:when>、< c:otherwise > - 多分支判断
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
@WebServlet("/jstl")
public class JstlServlet extends HttpServlet {
public JstlServlet() {
}
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
req.setAttribute("score",78);
req.setAttribute("grade","B");
req.getRequestDispatcher("/core.jsp").forward(req,resp);
}
}
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!-- 在Java或者JSP文件中输入 Alt + / 可出现智能提示 -->
<%@ taglib uri = "http://java.sun.com/jsp/jstl/core" prefix = "c" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
<h1>${requestScope.score}</h1>
<c:if test = "${score >= 60 }">
<h1 style = "color:green">恭喜,你已通过测试</h1>
</c:if>
<c:if test = "${score < 60 }">
<h1 style = "color:red">对不起,再接再厉</h1>
</c:if>
</body>
</html>
遍历集合
- < c:forEach >标签用于遍历集合(Collection)中的每一个对象
c:if 和c:when 的区别
(1)c:when必须嵌套在c:choose
(2)<c:if /> 或者 <c:if >< /c:if> <c:when > < /c:when >
(3)c:if 可以放回判断语句执行结果的值 而c:when不能
例如:<c:if test=”XXX” var=”result” />
<c:out value=”${result}”>
(4)when 可以有otherwise.相当于else. 而用if没有else配对.
<c:forEach var="p" items="${persons}" varStatus="idx">
第${idx.index + 1}位 <br/>
姓名: ${p.name} 性别: ${p.sex} 年龄:${p.age}
</c:forEach>
JstlServlet.java
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
@WebServlet("/jstl")
public class JstlServlet extends HttpServlet {
public JstlServlet() {
}
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
req.setAttribute("score",20);
req.setAttribute("grade","E");
List list = new ArrayList();
list.add(new Company("腾讯", "www.tencent.com"));
list.add(new Company("百度", "www.baidu.com"));
list.add(new Company("慕课网", "www.imooc.com"));
//把list放在当前请求中
req.setAttribute("companies", list);
req.getRequestDispatcher("/core.jsp").forward(req,resp);
}
}
core.jsp
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!-- 在Java或者JSP文件中输入 Alt + / 可出现智能提示 -->
<%@ taglib uri = "http://java.sun.com/jsp/jstl/core" prefix = "c" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
<h1>${requestScope.score}</h1>
<c:if test = "${score >= 60 }">
<h1 style = "color:green">恭喜,你已通过测试</h1>
</c:if>
<c:if test = "${score < 60 }">
<h1 style = "color:red">对不起,再接再厉</h1>
</c:if>
${grade}
<c:choose>
<c:when test="${grade == 'A'}">
<h2>你很优秀</h2>
</c:when>
<c:when test="${grade == 'B'}">
<h2>不错哟</h2>
</c:when>
<c:when test="${grade == 'C'}">
<h2>水平一般,需要提高</h2>
</c:when>
<c:when test="${grade == 'D'}">
<h2>需要努力,不要气馁</h2>
</c:when>
<c:otherwise>
<h2>一切随缘吧</h2>
</c:otherwise>
</c:choose>
<!-- forEach标签用于遍历集合
List companys = (List)request.getAttribute("companys")
for(Company c : companys){
out.print("...")
}
idx = index
idx.index属性代表循环的索引值(0开始)
-->
<c:forEach items="${requestScope.companies}" var="c">
<h2 style="color: green">${idx.index}.${c.cname}-${c.url}</h2>
</c:forEach>
</body>
</html>
fmt格式化标签库
- fmt格式化标签库URl : http://java.sun.com/jsp/jstl/fmt
- < fmt:formatDate value = “” pattern = “” > 格式化日期标签
- < fmt:formatNumber value = “” pattern = “”> 格式化数字标签,百分比,货币。
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
@WebServlet("/jstl")
public class JstlServlet extends HttpServlet {
public JstlServlet() {
}
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
req.setAttribute("score",20);
req.setAttribute("grade","E");
List list = new ArrayList();
list.add(new Company("腾讯", "www.tencent.com"));
list.add(new Company("百度", "www.baidu.com"));
list.add(new Company("慕课网", "www.imooc.com"));
//把list放在当前请求中
req.setAttribute("companies", list);
req.getRequestDispatcher("/core.jsp").forward(req,resp);
}
}
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib prefix="fmt" uri="http://java.sun.com/jsp/jstl/fmt" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<html>
<head>
<title>Title</title>
</head>
<body>
<%
request.setAttribute("amt", 123456.789);
request.setAttribute("now", new java.util.Date());
request.setAttribute("html","<a href='index.html'>index</a>");
request.setAttribute("nothing",null);
%>
<h2>${now }</h2>
<!--
formatDate pattern
yyyy - 四位年
MM - 两位月
dd - 两位日
HH - 24小时制
hh - 12小时制
mm - 分钟
ss - 秒数
SSS - 毫秒
-->
<h2>
<fmt:formatDate value="${requestScope.now}" pattern="yyyy年MM月dd日HH时mm分ss秒SSS毫秒"/>
</h2>
<h2>${amt}</h2>
<h2>¥<fmt:formatNumber value = "${amt}" pattern="0,000.00"></fmt:formatNumber></h2>
<h2>null默认值:<c:out value="${nothing}" default="无"></c:out></h2>
<h2><c:out value="${html}" escapeXml="true"></c:out></h2> <!--true时进行转译-->
</body>
</html>
使用IDEA写的web项目无法加载css、js或图片等文件的解决方法
- 直接把css、js、图片等文件放在web目录下,这样就可以实现轻松访问!
- 在web-inf目录下找到web.xml文件,添加以下代码也可以实现正常访问!
Employee.java
public class Employee {
private Integer empno;
private String ename;
private String department;
private String job;
private Float salary;
......
}
CreateServlet.java
import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.List;
@WebServlet("/create")
public class CreateServlet extends HttpServlet {
public CreateServlet() {
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
req.setCharacterEncoding("UTF-8");
String empno = req.getParameter("empno");
String ename = req.getParameter("ename");
String department = req.getParameter("department");
String job = req.getParameter("job");
String salary = req.getParameter("salary");
System.out.println(empno);
Employee emp = new Employee(Integer.parseInt(empno),ename,department,job,Float.parseFloat(salary));
ServletContext context = req.getServletContext();
List employees = (List) context.getAttribute("employees");
employees.add(emp); //追加
context.setAttribute("employees", employees);
req.getRequestDispatcher("/employee.jsp").forward(req,resp);
}
}
ListServlet.java
import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
@WebServlet("/Login")
public class ListServlet extends HttpServlet {
public ListServlet() {
}
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { //获取对象
ServletContext context = req.getServletContext();
if (context.getAttribute("employees")==null) {
List list = new ArrayList();
Employee emp = new Employee(7731, "刘志敏", "市场部", "客户代表", 10000f);
list.add(emp);
list.add(new Employee(8871, "潘春尧", "研发部", "运维工程师", 80000f));
context.setAttribute("employees", list); //把list存放进去
}//servlet中传递值
req.getRequestDispatcher("/employee.jsp").forward(req,resp);
}
}
employee.jsp
<%@ page contentType="text/html;charset=utf-8" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%@ taglib prefix="fmt" uri="http://java.sun.com/jsp/jstl/fmt" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width,initial-scale=1">
<title>员工列表</title>
<link href="./css/bootstrap.css" type="text/css" rel="stylesheet"/>
<script type="text/javascript" src="./js/jquery-1.11.1.min.js"></script>
<script type="text/javascript" src="./js/bootstrap.js"></script>
<style type="text/css">
.pagination {
margin: 0px
}
.pagination > li > a, .pagination > li > span {
margin: 0 5px;
border: 1px solid #dddddd;
}
.glyphicon {
margin-right: 3px;
}
.form-control[readonly] {
cursor: pointer;
background-color: white;
}
#dlgPhoto .modal-body{
text-align: center;
}
.preview{
max-width: 500px;
}
</style>
<script>
$(function () {
$("#btnAdd").click(function () {
$('#dlgForm').modal()
});
})
</script>
</head>
<body>
<div class="container">
<div class="row">
<h1 style="text-align: center">IMOOC员工信息表</h1>
<div class="panel panel-default">
<div class="clearfix panel-heading ">
<div class="input-group" style="width: 500px;">
<button class="btn btn-primary" id="btnAdd"><span class="glyphicon glyphicon-zoom-in"></span>新增
</button>
</div>
</div>
<table class="table table-bordered table-hover">
<thead>
<tr>
<th>序号</th>
<th>员工编号</th>
<th>姓名</th>
<th>部门</th>
<th>职务</th>
<th>工资</th>
<th> </th>
</tr>
</thead>
<tbody>
<c:forEach items="${applicationScope.employees}" var="emp" varStatus="idx">
<tr>
<td>${idx.index + 1}</td>
<td>${emp.empno}</td>
<td>${emp.ename}</td>
<td>${emp.department}</td>
<td>${emp.job}</td>
<td style="color: red;font-weight: bold">¥<fmt:formatNumber value="${emp.salary}" pattern="0,000.00"></fmt:formatNumber></td>
</tr>
</c:forEach>
<tr>
<td>3</td>
<td>7839</td>
<td>张丽</td>
<td>研发部</td>
<td>运维工程师</td>
<td style="color: red;font-weight: bold">¥8,820.00</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
<!-- 表单 -->
<div class="modal fade" tabindex="-1" role="dialog" id="dlgForm">
<div class="modal-dialog" role="document">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">×</span>
</button>
<h4 class="modal-title">新增员工</h4>
</div>
<div class="modal-body">
<form action="/untitled_war_exploded/create" method="post" >
<div class="form-group">
<label for="empno">员工编号</label>
<input type="text" name="empno" class="form-control" id="empno" placeholder="请输入员工编号">
</div>
<div class="form-group">
<label for="ename">员工姓名</label>
<input type="text" name="ename" class="form-control" id="ename" placeholder="请输入员工姓名">
</div>
<div class="form-group">
<label>部门</label>
<select id="dname" name="department" class="form-control">
<option selected="selected">请选择部门</option>
<option value="市场部">市场部</option>
<option value="研发部">研发部</option>
<option value="后勤部">后勤部</option>
</select>
</div>
<div class="form-group">
<label>职务</label>
<input type="text" name="job" class="form-control" id="sal" placeholder="请输入职务">
</div>
<div class="form-group">
<label for="sal">工资</label>
<input type="text" name="salary" class="form-control" id="sal" placeholder="请输入工资">
</div>
<div class="form-group" style="text-align: center;">
<button type="submit" class="btn btn-primary">保存</button>
</div>
</form>
</div>
</div><!-- /.modal-content -->
</div><!-- /.modal-dialog -->
</div><!-- /.modal -->
</body>
</html>