黑马旅游网-学习笔记Part03
黑马旅游网-学习笔记Part03
今日目标
Mybatis介绍和核心概念Java操作数据库
- Mybatis基本配置 🍐
- 实操Mybatis的入门案例✏️
- 结合Servlet项目完成登录案例和通过名字查询用户案例 ✏️
Redis入门
Nginx反向代理服务器
前置知识
- 环境变量
- jdk 8 +
- MySQL 5.7以上
- maven-3.6.1
- IDEA
- 知识要求
- JDBC
- MySQL
- Java基础
- Maven
- Junit(单元测试)
1. Mybatis简介和入门案例
Mybatis简介和入门案例

MyBatis 是一个持久层框架,用于简化 Java 应用程序与关系型数据库的交互。它通过将 SQL 语句与 Java 代码进行映射,提供了一种方便且灵活的方式来访问和操作数据库。
MyBatis 解决了传统 JDBC 编程中的一些问题,包括:
- 简化数据库访问jdbc操作非常繁琐:MyBatis 提供了简洁的 API 和灵活的配置方式,减少了编写繁琐的 JDBC 代码的工作量。
- 提供对象-关系映射:MyBatis 可以将数据库表中的数据映射到 Java 对象上,通过对象来进行数据的操作和处理,减少了手动处理结果集的复杂性。
- 支持动态 SQL:MyBatis 允许在 XML 配置文件中编写动态 SQL 语句,根据不同条件生成不同的 SQL,提供了更大的灵活性和可扩展性。
- 提供缓存机制:MyBatis 提供了一级缓存和二级缓存的支持,可以提高数据访问性能,减少对数据库的频繁访问。
MyBatis 在许多应用场景中发挥着重要作用,包括但不限于:
- 数据库访问:MyBatis 可以用于任何需要与关系型数据库进行交互的应用程序,包括 Web 应用、后台系统、数据处理等。
- 数据持久化:MyBatis 提供了一种简单且高效的方式来执行数据库的增删改查操作,适用于各种规模的应用程序。
- 性能优化:MyBatis 的缓存机制可以帮助提高数据访问性能,减少对数据库的频繁访问,特别适用于对数据读取要求较高的场景。
- 复杂 SQL 操作:MyBatis 支持编写动态 SQL 语句,可以根据不同的条件生成不同的 SQL,处理复杂的查询和数据操作。
当使用 MyBatis 框架时,以下是配置要求的一些主要方面:
数据源配置:需要配置数据库的连接信息,包括数据库驱动、连接 URL、用户名和密码等。这些配置通常在 MyBatis 的配置文件中进行设置。
Mapper 文件配置:需要为每个数据访问对象(DAO)编写对应的 Mapper 文件,用于定义 SQL 语句和结果映射。Mapper 文件通常使用 XML 格式 ,也可以使用注解的方式进行配置。
映射配置:Mapper 文件中需要配置每个 SQL 语句与 Java 方法之间的映射关系,包括 SQL 语句的编写、参数映射和结果映射。可以使用 XML 格式或注解方式进行映射配置。
配置文件:MyBatis 需要一个主配置文件(通常命名为 mybatis-config.xml )来指定全局配置,例如类型别名、插件、缓存设置等。此外,还需要配置数据源和事务管理器等。
使用框架和依赖:在项目中使用 MyBatis 框架时,需要添加相应的依赖,例如 mybatis 和 mybatis-spring。这些依赖需要在项目的构建文件(如 Maven 的 pom.xml)中进行配置。
事务管理:如果需要在数据访问过程中进行事务管理,需要配置事务管理器,并确保每个数据访问操作在正确的事务上下文中执行。
运行环境配置:在一些特定的场景下,可能需要进行一些额外的配置,例如分页插件的配置、缓存设置的调优等。
如果左边的知识,了解了,那么可以进行Mybatis初体验了!!👇
入门案例操作
- 创建 Maven 项目如果有Maven工程,可以直接用:创建一个新的 Maven 项目,并在 pom.xml 文件中添加 MyBatis 相关的依赖,例如 mybatis、mybatis-spring 等。
- 配置数据库连接:在配置文件中配置数据库连接信息,包括数据库驱动、连接 URL、用户名和密码等。
- 编写数据映射文件:创建一个 XML 文件,定义数据表与 Java 对象的映射关系,包括 SQL 语句、参数映射和结果映射等。
- 编写数据访问接口:创建一个 Java 接口,定义数据访问的方法,使用注解或 XML 配置与数据映射文件进行关联。
- 配置 MyBatis:在配置文件中配置 MyBatis 的相关信息,包括数据源、事务管理器、数据映射文件的路径等。
- 编写业务逻辑代码:编写业务逻辑的 Java 代码,调用数据访问接口来执行数据库操作。
- 测试和运行:编写测试代码,验证数据库操作的正确性,然后运行应用程序,观察结果是否符合预期。
目标1:查询用户id为22的用户信息 🎯
- 创建表格user表
- 往表中插入下列假数据
-- 删除原有数据库
DROP TABLE IF EXISTS `user`;
CREATE TABLE `user` (
`id` bigint(20) NOT NULL AUTO_INCREMENT,
`name` varchar(32) NOT NULL,
`password` varchar(32) NOT NULL DEFAULT '12345678',
`age` int(10) NOT NULL,
`hobby` varchar(50) DEFAULT NULL,
`description` varchar(200) NOT NULL,
`department` varchar(255) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=46 DEFAULT CHARSET=utf8;
-- ----------------------------
-- Records of user
-- ----------------------------
INSERT INTO `user` VALUES ('8', '赵灵儿', '12345678', '20', '阵法、法术修炼', '纯真善良的女子,拥有强大的阴阳之力', '阴阳家');
INSERT INTO `user` VALUES ('9', '楚留香', '12345678', '32', '剑术、侠义行侠', '风流倜傥的豪客,以智慧和剑术征服江湖', '江湖人士');
INSERT INTO `user` VALUES ('10', '白浅', '12345678', '26', '宫廷舞蹈、仙法修炼', '美丽高贵的仙子,守护爱与正义的力量', '青丘派');
INSERT INTO `user` VALUES ('11', '苏明玉', '12345678', '29', '医术、家族事务', '聪明伶俐的女医生,心系家族兴衰', '苏家');
INSERT INTO `user` VALUES ('12', '陆雪琪', '12345678', '24', '法术、仙法修炼', '冷傲美丽的仙子,坚守本心与正义', '青云门');
INSERT INTO `user` VALUES ('13', '李逍遥', '12345678', '28', '剑术、侠义行侠', '潇洒自如的剑客,为爱与正义奋斗', '天墉城');
INSERT INTO `user` VALUES ('14', '陆展元', '12345678', '31', '龙族法术、海洋探险', '勇敢善良的龙族王子,探索海洋奥秘', '东海龙宫');
INSERT INTO `user` VALUES ('15', '程灵素', '12345678', '27', '仙法、仙岛事务', '温柔善良的仙子,守护仙岛和平', '蓬莱仙岛');
INSERT INTO `user` VALUES ('16', '戚芳', '12345678', '23', '武功、家族事务', '机智勇敢的女子,为家族荣誉而战', '戚家');
INSERT INTO `user` VALUES ('17', '李寻欢', '12345678', '30', '剑术、侠义行侠', '聪明机智的江湖人物,正义心十足', '大宛城');
INSERT INTO `user` VALUES ('18', '萧炎', '12345678', '25', '功夫、修炼', '机缘巧合下拥有强大火焰之力的少年', '草庙村');
INSERT INTO `user` VALUES ('19', '陆九淳', '12345678', '29', '家族事务、剑术修炼', '家族责任重于一切的江湖少年', '陆家');
INSERT INTO `user` VALUES ('20', '韩立', '12345678', '22', '灵力修炼、阵法研究', '机智聪明的年轻修士,掌握神奇的法术', '韩家');
INSERT INTO `user` VALUES ('21', '顾惜朝', '12345678', '28', '法术修炼、守护门派', '心地善良的女子,为守护门派而战', '古玄门');
INSERT INTO `user` VALUES ('22', '九霄真人', '12345678', '35', '仙法修炼、教导弟子', '威严正直的仙人,指导后辈修仙道路', '蓝霞宫');
INSERT INTO `user` VALUES ('23', '姬昌', '12345678', '33', '阴阳术、仙法修炼', '智勇双全的江湖人物,掌握阴阳之力', '太阴派');
INSERT INTO `user` VALUES ('24', '西门吹雪', '12345678', '30', '剑术、侠义行侠', '风流倜傥的剑客,执着追求剑道境界', '独孤家');
INSERT INTO `user` VALUES ('25', '夏冰', '12345678', '26', '魔法修炼、冰雪之力', '美丽神秘的女子,掌握冰雪之力', '幻冥宗');
INSERT INTO `user` VALUES ('26', '杨影枫', '12345678', '27', '暗器、侠义行侠', '冷酷无情的刺客,为正义而战', '影家');
INSERT INTO `user` VALUES ('27', '白素素', '12345678', '24', '文学创作、人界事务', '善良纯真的女子,用文字记录人间百态', '人界');
INSERT INTO `user` VALUES ('28', '独孤剑', '12345678', '32', '剑术、侠义行侠', '心系家族的剑客,剑法高超', '独孤家');
INSERT INTO `user` VALUES ('29', '楚九霄', '12345678', '28', '阵法、家族事务', '机智聪明的年轻人,心系家族荣耀', '楚家');
INSERT INTO `user` VALUES ('30', '谢晓峰', '12345678', '31', '拳脚功夫、江湖恩怨', '正直勇敢的江湖豪杰,忠于兄弟情义', '铁血帮');
INSERT INTO `user` VALUES ('31', '叶孤城', '12345678', '29', '剑术、侠义行侠', '冷酷无情的剑客,追求剑道极致', '武境城');
INSERT INTO `user` VALUES ('32', '李逸风', '12345678', '25', '修炼、探险', '热血青年,勇往直前探索未知世界', '蓝枫大陆');
INSERT INTO `user` VALUES ('33', '萧霜', '12345678', '27', '冰雪法术、守护宗门', '冷艳高傲的女子,守护冰霜宗的利益', '冰霜宗');
INSERT INTO `user` VALUES ('34', '楚玉峰', '12345678', '30', '家族事务、阵法修炼', '机智聪明的年轻人,家族责任重于一切', '楚家');
INSERT INTO `user` VALUES ('35', '陆雪琪', '12345678', '24', '法术、修行', '美丽冷傲的仙子,修炼法术追求修行境界', '青云门');
INSERT INTO `user` VALUES ('36', '明月心', '12345678', '26', '琴音、舞蹈', '温柔善良的女子,以音乐传递爱与希望', '云裳派');
INSERT INTO `user` VALUES ('37', '程灵素', '12345678', '27', '仙法修炼、仙岛事务', '温柔善良的仙子,守护仙岛和平', '蓬莱仙岛');
INSERT INTO `user` VALUES ('38', '韩非', '12345678', '23', '学术研究、阵法修炼', '聪明睿智的年轻人,研究阵法和学术', '韩家');
INSERT INTO `user` VALUES ('39', '陆展元', '12345678', '31', '龙族法术、海洋探险', '勇敢善良的龙族王子,探索海洋奥秘', '东海龙宫');
INSERT INTO `user` VALUES ('40', '戚芳', '12345678', '23', '武功、家族事务', '机智勇敢的女子,为家族荣誉而战', '戚家');
INSERT INTO `user` VALUES ('41', '楚轩辕', '12345678', '28', '家族事务、剑术修炼', '家族责任重于一切的剑客', '楚家');
INSERT INTO `user` VALUES ('42', '秦王', '12345678', '35', '政务、战争', '智勇双全的帝王,统一六国的志向', '秦国');
INSERT INTO `user` VALUES ('43', '李寻欢', '12345678', '30', '剑术、侠义行侠', '聪明机智的江湖人物,正义心十足', '大宛城');
INSERT INTO `user` VALUES ('44', '唐三藏', '12345678', '45', '佛法修行、西行取经', '慈悲心肠的高僧,带领徒弟西天取经', '大唐');
INSERT INTO `user` VALUES ('45', '吴青烟', '12345678', '26', '法术修行、江湖事务', '冷艳高傲的女子,修炼法术追求江湖大业', '青云门');
总体效果图👇 👇

- 创建 Maven 项目并添加依赖
在
pom.xml
文件的dependencies
标签内添加
<!--单元测试-->
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.13.2</version>
</dependency>
<!-- mybatis依赖-->
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis</artifactId>
<version>3.5.2</version>
</dependency>
<!--mysql驱动-->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.47</version>
</dependency>
<!-- 下面的依赖要配合 resource文件夹中logback.xml一起用,主要显示日志-->
<!-- 添加logback-classic依赖 -->
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-classic</artifactId>
<version>1.2.3</version>
</dependency>
<!-- 添加logback-core依赖 -->
<dependency>
<groupId>ch.qos.logback</groupId>
<artifactId>logback-core</artifactId>
<version>1.2.3</version>
</dependency>
<!-- lombok插件 实体类避免写setget方法-->
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.16.18</version>
</dependency>
- 配置数据库连接:在配置文件中配置数据库连接信息,包括数据库驱动、连接 URL、用户名和密码等。
在
resources
文件夹下,创建mybatis-config.xml
文件,并将下述数据粘贴到其中,并仔细阅读注释,并修改数据名字和用户名和密码 以及阴影区域
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE configuration
PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-config.dtd">
<configuration>
<properties resource="jdbc.properties"/>
<typeAliases>
<package name="cn.itcast.domain"/>
</typeAliases>
<!--
environments:配置数据库连接环境信息。可以配置多个environment,通过default属性切换不同的environment
-->
<environments default="development">
<environment id="development">
<transactionManager type="JDBC"/>
<dataSource type="POOLED">
<!--数据库连接信息-->
<property name="driver" value="${jdbc.driver}"/>
<property name="url" value="${jdbc.url}" />
<property name="username" value="${jdbc.username}"/>
<property name="password" value="${jdbc.password}"/>
</dataSource>
</environment>
</environments>
<mappers>
<!--加载sql映射文件-->
<package name="cn.itcast.mapper"/>
</mappers>
</configuration>
- 在jdbc.properties文件中配置密码和数据:
jdbc.driver=com.mysql.jdbc.Driver
jdbc.url=jdbc:mysql://localhost:3306/mybatis?useUnicode=true&characterEncoding=UTF-8&serverTimezone=UTC
jdbc.username=root
jdbc.password=1234
- 添加日志配置文件logback.xml
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<!--
CONSOLE :表示当前的日志信息是可以输出到控制台的。
-->
<appender name="Console" class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<pattern>[%level] %cyan([%thread]) %boldGreen(%logger{15}) - %msg %n</pattern>
</encoder>
</appender>
<!-- todo 填写包名 -->
<logger name="cn.itcast" level="DEBUG" additivity="false">
<appender-ref ref="Console"/>
</logger>
<!--
level:用来设置打印级别,大小写无关:TRACE, DEBUG, INFO, WARN, ERROR, ALL 和 OFF
, 默认debug
<root>可以包含零个或多个<appender-ref>元素,标识这个输出位置将会被本日志级别控制。
-->
<root level="DEBUG">
<appender-ref ref="Console"/>
</root>
</configuration>
- 编写数据映射文件:创建一个 XML 文件,定义数据表与 Java 对象的映射关系,包括 SQL 语句、参数映射和结果映射等。
在resource文件夹下,创建下述文件夹(注意:输入不要用点,而要这样写cn/itheima/mapper)
创建domain包,根据数据库字段,创建对应实体

创建UserMapper.xml文件,将下述代码粘贴到文件中

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="cn.itcast.mapper.UserMapper">
<select id="findAllUser" resultType="user">
SELECT * from user
</select>
</mapper>

- 编写数据访问接口:创建一个 Java 接口,定义数据访问的方法,使用注解或 XML 配置与数据映射文件进行关联。

1.编写业务逻辑代码:编写业务逻辑的 Java 代码,调用数据访问接口来执行数据库操作。
public class MybatisTest {
@Test
public void selectById() throws IOException {
System.out.println("测试");
// 1.使用MyBatis提供的Resources类加载mybatis的配置文件
Reader reader = Resources.getResourceAsReader("mybatis-config.xml");
// 2.构建sqlSession的工厂
SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(reader);
// 3.sqlSession的工厂获得sqlSession
SqlSession sqlSession = sqlSessionFactory.openSession();
//4.sqlSession获得UserMapper接口的代理实现类
UserMapper mapper = sqlSession.getMapper(UserMapper.class);
//5.代理对象mapper对用其方法,查询数据库
final List<User> allUser = mapper.findAllUser();
//6.打印结果
System.out.println(allUser);
}
}
运行效果: 👇

MybatisX是一款基于IDEA的快速开发Mybatis的插件,为效率而生。
MybatisX的安装:

可以通过MybatisX快速定位:

注意:如果出现了找不到包的情况,可以在maven中执行
mvn -U idea:idea
命令
目标2:完成用户和密码登录的功能需求 🎯
- 编写数据访问接口
public interface UserMapper {
User selectByUserAndPassword(@Param("name") String name, @Param("password") String password);
}
- 编写数据映射文件
#{变量}
表示占位符,获取变量中的数据
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="cn.itcast.mapper.UserMapper">
<select id="selectByUserAndPassword" resultType="cn.itcast.domain.User">
SELECT * from user where name=#{name} and password=#{password}
</select>
</mapper>
- 测试类测试
public class MybatisTest {
public static void main(String[] args) throws IOException {
// 1.使用MyBatis提供的Resources类加载mybatis的配置文件
Reader reader = Resources.getResourceAsReader("mybatis-config.xml");
// 2.构建sqlSession的工厂
SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(reader);
// 3.sqlSession的工厂获得sqlSession
SqlSession sqlSession = sqlSessionFactory.openSession();
//4.sqlSession获得UserMapper接口的代理实现类
UserMapper mapper = sqlSession.getMapper(UserMapper.class);
//5.代理对象mapper对用其方法,查询数据库
User user = mapper.selectByUserAndPassword("韩立","12345678");
//6.打印结果
System.out.println(user);
}
}

public class MybatisFactoryUtil {
// 1. 在内存中只有一份实例----->单例模式(懒汉式和饿汉式)
static SqlSessionFactory build;
static{
InputStream resourceAsStream = null;
try {
resourceAsStream = Resources.getResourceAsStream("mybatis-config.xml");
} catch (IOException e) {
e.printStackTrace();
}
build = new SqlSessionFactoryBuilder().build(resourceAsStream);
}
/**
* 饿汉式
* @return
*/
public static SqlSessionFactory getSqlSessionFactory(){
return build;
}
}
改造后:
public class MybatisTest {
public static void main(String[] args) throws IOException {
//通过工厂类获得SqlSession
SqlSession sqlSession = MybatisFactoryUtil.getSqlSessionFactory().openSession();
//4.sqlSession获得UserMapper接口的代理实现类
UserMapper mapper = sqlSession.getMapper(UserMapper.class);
//5.代理对象mapper对用其方法,查询数据库
User user = mapper.selectByUserAndPassword("韩立","12345678");
//6.打印结果
System.out.println(user);
}
}
目标3:完成查询姓韩的员工查询,如果传入null或者‘’返回全部员工 🎯
- 编写数据访问接口
public interface UserMapper {
List<User> selectByName(@Param("name") String name);
}
- 编写数据映射文件,书写动态sql
if标签负责条件判断 where标签负责条件和去除多余的and 或者or字段
<select id="selectByName" resultType="cn.itcast.domain.User">
SELECT * from user
<where>
<if test="name!=null and name != ''">
and name like concat('%',#{name},'%')
</if>
</where>
</select>
- 测试类测试
public static void main(String[] args) throws IOException {
//通过工厂类获得SqlSession
SqlSession sqlSession = MybatisFactoryUtil.getSqlSessionFactory().openSession();
//4.sqlSession获得UserMapper接口的代理实现类
UserMapper mapper = sqlSession.getMapper(UserMapper.class);
//5.代理对象mapper对用其方法,查询数据库
List<User> users = mapper.selectByName("韩");
//6.打印结果
System.out.println(users);
}

2. Redis简介和入门
前言

Redis是一个基于 内存 的key-value结构 数据库。Redis 是互联网技术领域使用最为广泛的存储中间件Enum 。
Redis存储的是key-value结构的数据,其中key是字符串类型,value有5种常用的数据类型:
- 字符串(string):普通字符串,Redis中最简单的数据类型通用存储
- 哈希(hash):也叫散列,类似于Java中的HashMap结构可存对象
- 列表(list):按照插入顺序排序,可以有重复元素,类似于Java中的LinkedList可存列表
- 集合(set):无序集合,没有重复元素,类似于Java中的HashSet可实现唯一key,可求差集、并集、交集
- 有序集合(sorted set/zset):集合中每个元素关联一个分数(score),根据分数升序排序,没有重复元素可用来做实时在线排行榜

Redis 的 Java 客户端很多,常用的几种:
- Jedis今天学习这个
- Lettuce
- Spring Data Redis

我用夸克网盘分享了「湖南信息职业技术学院实训」,点击链接即可保存。打开「夸克APP」,无需下载在线播放视频,畅享原画5倍速,支持电视投屏。
链接:https://pan.quark.cn/s/644bb4446f79
提取码:BPAd
Jedis 是 Redis 的 Java 版本的客户端实现。
使用 Jedis 操作 Redis 的步骤:
- 启动Redis-Server
- 在工程中添加依赖
- 获取连接,执行操作,关闭连接
- 尝试其他数据类型
按照下述步骤,启动redis-server,在windows下不要关掉cmd窗口哦!!!

maven 坐标:
<dependency>
<groupId>redis.clients</groupId>
<artifactId>jedis</artifactId>
<version>2.8.0</version>
</dependency>

示例代码:
/**
* 使用Jedis操作Redis
*/
public class JedisTest {
@Test
public void testRedis(){
// 配置ip和端口
JedisShardInfo jedisShardInfo = new JedisShardInfo("127.0.0.1", 6379);
// 设置密码
jedisShardInfo.setPassword("123456");
//1 获取连接
Jedis jedis = new Jedis(jedisShardInfo);
//2 执行具体的操作
jedis.set("school","itcast");
// 从缓存中获得数据
String value = jedis.get("school");
System.out.println(value);
//3 关闭连接
jedis.close();
}
}
各个数据类型示例代码:
/**
* 使用Jedis操作Redis
*/
public class JedisTest {
@Test
public void testRedis(){
// 配置ip和端口
JedisShardInfo jedisShardInfo = new JedisShardInfo("ip地址", 6379);
//设置密码
jedisShardInfo.setPassword("123456");
//1 获取连接
Jedis jedis = new Jedis(jedisShardInfo);
// TODO: 字符串
//2 执行具体的操作
jedis.set("name","222222");
// 从缓存中获得数据
String value = jedis.get("name");
System.out.println(value);
// TODO: hash
jedis.hset("hset1","name","李四");
String hget = jedis.hget("hset1", "name");
System.out.println(hget);
// TODO: list列表
jedis.lpush("list1","1","2","3","4");
List<String> list1 = jedis.lrange("list1", 0, -1);
System.out.println(list1);
// TODO: 集合set
jedis.sadd("set1", "a", "a", "b", "c");
Set<String> set1 = jedis.smembers("set1");
System.out.println(set1);
// TODO: 有序集合set
jedis.zadd("zset1",3.9,"aa");
jedis.zadd("zset1",3.8,"bb");
jedis.zadd("zset1",2.9,"cc");
jedis.zadd("zset1",9.0,"gg");
// Redis Zrevrange 命令返回有序集中,指定区间内的成员。其中成员的位置按分数值递减(从大到小)来排列。
Set<String> zset1 = jedis.zrevrange("zset1", 0, -1);
System.out.println(zset1);
//3 关闭连接
jedis.close();
}
}
3. Redis缓存Mybatis数据
Redis缓存Mybatis数据

问题:上述场景非常普遍,受制于数据库性能,随着并发增加,系统IO压力非常大,用户体验下降!
解决方案 :因此,需要将热门数据缓存到Redis中,执行先查缓存,如果缓存存在,直接返回,如果缓存不存在,在查询数据库,并将数据存在缓存中,下一次查询将不会直接查数据库
代码操作
将性全部数据缓存到redis中,下次查的时候都不会进入数据库,减少数据库的压力
public static void main(String[] args) throws IOException {
//通过工厂类获得SqlSession
SqlSession sqlSession = MybatisFactoryUtil.getSqlSessionFactory().openSession();
//4.sqlSession获得UserMapper接口的代理实现类
UserMapper mapper = sqlSession.getMapper(UserMapper.class);
//5.代理对象mapper对用其方法,查询数据库
List<User> users = mapper.findAllUser();
//6.打印结果
users.stream().forEach(s-> System.out.println(s));
}

MybatisFactoryUtil工具类代码:
public class MybatisFactoryUtil {
// 1. 在内存中只有一份实例----->单例模式(懒汉式和饿汉式)
static SqlSessionFactory build;
static{
InputStream resourceAsStream = null;
try {
resourceAsStream = Resources.getResourceAsStream("mybatis-config.xml");
} catch (IOException e) {
e.printStackTrace();
}
build = new SqlSessionFactoryBuilder().build(resourceAsStream);
}
/**
* 饿汉式
* @return
*/
public static SqlSessionFactory getSqlSessionFactory(){
return build;
}
}
在pom文件中,导入json转对象的依赖
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>fastjson</artifactId>
<version>1.2.83</version>
</dependency>
如果报包找不到,勾选委贷后,配上
-Dfile.encoding=GBK
解决乱码问题
public class MybatisTest2 {
public static void main(String[] args) throws IOException {
// 配置ip和端口
JedisShardInfo jedisShardInfo = new JedisShardInfo("127.0.0.1", 6379);
// 设置密码
// jedisShardInfo.setPassword("123456");
//1 获取连接
Jedis jedis = new Jedis(jedisShardInfo);
String usersjson = jedis.get("users");
if (usersjson!=null && usersjson.length()>0){
// redis存在数据,直接返回数据
System.out.println("输出缓存中的数据:");
System.out.println(usersjson);
return;
}
// 缓存中没有数据,先从数据库中查询,然后存放到数据库中
System.out.println("从数据库中查询数据....");
//通过工厂类获得SqlSession
SqlSession sqlSession = MybatisFactoryUtil.getSqlSessionFactory().openSession();
//4.sqlSession获得UserMapper接口的代理实现类
UserMapper mapper = sqlSession.getMapper(UserMapper.class);
//5.代理对象mapper对用其方法,查询数据库
List<User> users = mapper.findAllUser();
String jsonString = JSON.toJSONString(users);
System.out.println("将数据存入Redis缓存中...");
jedis.set("users",jsonString);
System.out.println("输出数据...");
System.out.println(jsonString);
}
}

4.Nginx服务器
前言

Nginx是一款轻量级的Web服务器/反向代理服务器及电子邮件(IMAP/POP3)代理服务器。其特点是占有内存少,并发能力强 ,事实上nginx的并发能力在同类型的网页服务器中表现较好,中国大陆使用nginx的网站有:百度、京东、新浪、网易、腾讯、淘宝等。
Nginx是由伊戈尔·赛索耶夫为俄罗斯访问量第二的Rambler.ru站点(俄文:Рамблер)开发的,第一个公开版本0.1.0发布于2004年10月4日。
1.下载
在Nginx的官网的下载页面中(http://nginx.org/en/download.html),就展示了当前Nginx版本,并提供了下载的连接。 如下:

在本项目中,我们所学习的Nginx选择的是稳定版本的1.16这个版本,我们可以直接从官网下载,当然在我们的课程资料中也已经提供了该版本的安装包。
2.window启动
下载完成后,解压缩,运行 cmd,使用命令进行操作,不要直接双击 nginx.exe ,一定要在 dos 窗口启动 ,不要直接双击 nginx.exe,这样会导致修改配置后重启、停止 nginx 无效,需要手动关闭任务管理器内的所有 nginx 进程,再启动才可以。
使用命令行到达 nginx 的加压缩后的目录
# cd 到你的解压缩目录
cd D:\nginx-1.16.1
3、启动 nginx 服务,启动时会一闪而过是正常的(注意下方的 gif 动图中)
start nginx
4、查看任务进程是否存在,dos 或打开任务管理器都行
tasklist /fi "imagename eq nginx.exe"
Gif动画教程🎥



重点目录和文件如下:
目录/文件 | 说明 | 备注 |
---|---|---|
conf | 配置文件的存放目录 | |
conf/nginx.conf | Nginx 的核心配置文件 | conf 下有很多 nginx 的配置文件,我们主要操作这个核心配置文件 |
html | 存放静态资源(html, css, ) | 部署到 Nginx 的静态资源都可以放在 html 目录中 |
logs | 存放 nginx 日志(访问日志、错误日志等) |
nginx的配置文件(conf/nginx.conf)整体上分为三部分: 全局块、events块、http块 。这三块的分别配置什么样的信息呢,看下表:
区域 | 职责 |
---|---|
全局块 | 配置和nginx运行相关的全局配置 |
events块 | 配置和网络连接相关的配置 |
http块 | 配置代理、缓存、日志记录、虚拟主机等配置 |
修改了nginx.conf核心配置文件之后,在启动Nginx服务之前,可以先检查一下conf/nginx.conf文件配置的是否有错误,命令如下:
nginx -t
Nginx可以作为静态web服务器来部署静态资源。这里所说的静态资源是指在服务端真实存在,并且能够直接展示的一些文件,比如常见的html页面、css文件、js文件、图片、视频等资源。
相对于Tomcat,Nginx处理静态资源的能力更加高效,所以在生产环境下,一般都会将静态资源部署到Nginx中。
将静态资源部署到Nginx非常简单,只需要将文件复制到Nginx安装目录下的html目录中即可。
server {
listen 80; #监听端口
location / { #匹配客户端请求url
root html; #指定静态资源根目录
index index.html; #指定默认首页
}
}
我们部署自己的静态资源?
1. 简单:把静态资源放入nginx安装目录下的html文件夹下
2. 在nginx安装目录下新建文件夹:travel
将静态资源放进去
配置localhost中 root 属性的值travel
需求:编辑一个html页面,部署到nginx中,使用浏览器访问
1). 正向代理
正向代理服务器是一个位于客户端和原始服务器(origin server)之间的服务器,为了从原始服务器取得内容,客户端向代理发送一个请求并指定目标(原始服务器),然后代理向原始服务器转交请求并将获得的内容返回给客户端。
正向代理的典型用途是为在防火墙内的局域网客户端提供访问Internet的途径。
正向代理一般是在客户端设置代理服务器,通过代理服务器转发请求,最终访问到目标服务器。

2). 反向代理
反向代理服务器位于用户与目标服务器之间,但是对于用户而言,反向代理服务器就相当于目标服务器,即用户直接访问反向代理服务器就可以获得目标服务器的资源,反向代理服务器负责将请求转发给目标服务器。用户不需要知道目标服务器的地址,也无须在用户端作任何设定,对于用户来说,访问反向代理服务器是完全无感知的。

那么在本小节,我们就是要使用nginx来作为反向代理服务器使用。 在nginx中,我们可以在nginx.conf中配置反向代理:
server {
listen 82;
server_name localhost;
location / {
proxy_pass http://192.168.200.201:8080; #反向代理配置,将请求转发到指定服务
}
}
上述配置的含义为: 当我们访问nginx的82端口时,根据反向代理配置,会将请求转发到 http://192.168.200.201:8080 对应的服务上。
早期的网站流量和业务功能都比较简单,单台服务器就可以满足基本需求,但是随着互联网的发展,业务流量越来越大并且业务逻辑也越来越复杂,单台服务器的性能及单点故障问题就凸显出来了,因此需要多台服务器组成应用集群,进行性能的水平扩展以及避免单点故障出现。
应用集群: 将同一应用部署到多台机器上,组成应用集群,接收负载均衡器分发的请求,进行业务处理并返回响应数据
负载均衡器: 将用户请求根据对应的负载均衡算法分发到应用集群中的一台服务器进行处理

此处的负载均衡器,我们将会使用Nginx来实现,而Nginx的负载均衡是基于反向代理的,只不过此时所代理的服务器不是一台,而是多台。
负载均衡操作验证👇👇
1). 将资料中提供的两个jar包,上传到192.168.200.201服务器上
jar | 运行端口 | 请求链接 | 响应数据 |
---|---|---|---|
![]() | |||
8080 | /hello | 8080 | |
![]() | |||
8081 | /hello | 8081 |
我们在测试时,并没有那么多服务器,我们可以在一台服务器中启动多个服务,运行在不同的端口号上进行测试。
2). 运行上传上来的两个jar包,运行端口分别是 8080 , 8081
由于我们执行 java -jar 指令会占用前台窗口,所以我们可以开启两个窗口进行测试。


如果是win 直接运行以下指令 java -jar helloworld-1.0-SNAPSHOT.jar --server.port=8080 java -jar helloworld-1.0-SNAPSHOT2.jar --server.port=8081
3). 在nginx中配置负载均衡
打开nginx的配置文件nginx.conf并增加如下配置:
upstream targetserver{
server 192.168.31.134:8080;
server 192.168.31.134:8081;
}
server {
listen 8080;
server_name localhost;
location / {
proxy_pass http://targetserver;
}
}
具体的配置位置如下:

4). 重新加载nginx配置文件,访问
nginx -s reload
测试时,我们直接访问nginx的8080端口(http://192.168.200.200:8080), 此时nginx会根据负载均衡策略,将请求转发到后面的两台服务器。

在上述的测试过程中,我们看到请求均衡的转发到了8080和8081,因为模式的负载均衡策略是轮询。
注意: 上述所有涉及到的端口号,都需要在对应的服务器的防火墙中开放,或者彻底关闭防火墙