苍穹外卖DAY5
Redis入门 数据类型 常用命令 在Java中操作Redis
其他部分请移至:Redis基础速览
在Java中操作Redis - Spring Data Redis
<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
# application.ymlredis:host: ${sky.redis.host}port: ${sky.redis.port}password: ${sky.redis.password}database: ${sky.redis.database}# application-dev.ymlredis:host: 192.168.124.129port: 6379password: 123456database: 10
database:指定使用Redis的哪个数据库,Redis服务启动后默认有16个数据库,编号分别是从0到15。可以通过修改Redis配置文件来指定数据库的数量。
如果默认的库只有一个,就需要修改redis配置文件:
/*** 配置类,创建RedisTemplate对象*/
@Configuration
@Slf4j
public class RedisConfiguration {@Beanpublic RedisTemplate redisTemplate(RedisConnectionFactory redisConnectionFactory) {log.info("开始创建redis模板对象...");RedisTemplate redisTemplate = new RedisTemplate();// 设置redis的连接工厂对象redisTemplate.setConnectionFactory(redisConnectionFactory);// 设置redis key的序列化器redisTemplate.setKeySerializer(new StringRedisSerializer());return redisTemplate;}
}
Spring Boot 框架会自动装配 RedisTemplate 对象,但是默认的key序列化器为
JdkSerializationRedisSerializer,导致我们存到Redis中后的数据和原始数据有差别,故设置为
StringRedisSerializer序列化器。
编写单元测试:
package com.sky.test;import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.data.redis.connection.DataType;
import org.springframework.data.redis.core.*;import java.util.List;
import java.util.Set;
import java.util.concurrent.TimeUnit;@SpringBootTest
public class SpringDataRedisTest {@Autowiredprivate RedisTemplate redisTemplate;/*** 通过该RedisTemplate对象获取操作5种数据类型相关对象*/@Testpublic void TestRedisTemplate() {System.out.println(redisTemplate);ValueOperations valueOperations = redisTemplate.opsForValue(); // String数据操作HashOperations hashOperations = redisTemplate.opsForHash(); // hash类型操作ListOperations listOperations = redisTemplate.opsForList(); // list类型操作SetOperations setOperations = redisTemplate.opsForSet(); // set类型操作ZSetOperations zSetOperations = redisTemplate.opsForZSet(); // zset类型操作}/*** 操作字符串(String)类型数据*/@Testpublic void testString() {// set 添加或修改已存在的一个String类型的键值对redisTemplate.opsForValue().set("name","小猫");// get 根据key获取String类型的valueString name = (String) redisTemplate.opsForValue().get("name");System.out.println(name); // 打印key对应的值// setex 添加一个String类型的键值对,并设置有效期redisTemplate.opsForValue().set("code","1234", 3, TimeUnit.MINUTES); // 枚举:分钟// setnx 添加一个String类型的键值对,前提是这个key不存在,否则不执行redisTemplate.opsForValue().setIfAbsent("lock","1");redisTemplate.opsForValue().setIfAbsent("lock","2");}/*** 操作哈希类(Hash)型数据*/@Testpublic void testHash() {HashOperations hashOperations = redisTemplate.opsForHash();// hset 添加或修改hash类型的key的field值hashOperations.put("100","name","tom");hashOperations.put("100","age","20");// hget 获取一个hash类型的key的field值String name = (String) hashOperations.get("100", "name");System.out.println(name);// hkeys 获取一个hash类型的key中的所有fieldSet keys = hashOperations.keys("100");System.out.println(keys);// hvals 获取一个hash类型的key中的valueList values = hashOperations.values("100");System.out.println(values);// hdel 删除fieldhashOperations.delete("100","age");}/*** 操作列表(List)类型数据*/@Testpublic void testList() {ListOperations listOperations = redisTemplate.opsForList();// lpush 从列表左侧插入一个或多个元素listOperations.leftPushAll("mylist","a","b","c");listOperations.leftPush("mylist","d");// lrange 返回一段角标范围内的所有元素List mylist = listOperations.range("mylist",0,-1);System.out.println(mylist);// rpop 移除并返回列表右侧第一个元素listOperations.rightPop("mylist");// 列表长度Long size = listOperations.size("mylist");System.out.println(size);}/*** 操作集合(Set)类型的数据*/@Testpublic void testSet() {SetOperations setOperations = redisTemplate.opsForSet();// sadd 向set中添加一个或多个元素setOperations.add("set1","a","b","c","d");setOperations.add("set2","a","b","x","y");// smembers 获取set中的所有元素Set menbers = setOperations.members("set1");System.out.println(menbers);// scard 返回set中的元素个数Long size = setOperations.size("set1");System.out.println(size);// sinter 求交集Set intersect = setOperations.intersect("set1","set2");System.out.println(intersect);// sunion 求并集Set union = setOperations.union("set1","set2");System.out.println(union);// srem 移除set中的指定元素setOperations.remove("set1","a","b");}/*** 操作有序集合(SortedSet)类型的数据*/@Testpublic void testZset() {ZSetOperations zSetOperations = redisTemplate.opsForZSet();// zadd 添加一个或多个元素,如果已存在则更新scorezSetOperations.add("zset1","a",10);zSetOperations.add("zset1","b",12);zSetOperations.add("zet1","c",9);// zrange 获取按照score排名后,指定排名内的元素Set zset1 = zSetOperations.range("zet1",0,-1);System.out.println(zset1);// zincrby 指定元素自增指定步长zSetOperations.incrementScore("zset1","c",10);// zrem 删除指定元素zSetOperations.remove("zset1","a","b");}/*** 通用命令操作*/@Testpublic void testCommon() {// keys 查询redis数据库中指定的key,*就是查所有的keySet keys = redisTemplate.keys("*");System.out.println(keys);// exist 查询某个key是否存在Boolean name = redisTemplate.hasKey("name");Boolean set1 = redisTemplate.hasKey("set1");// type 查询某个key指定的value是什么类型for (Object key : keys) {DataType type = redisTemplate.type(key);System.out.println(type.name());}// 删除指定keyredisTemplate.delete("mylist");}
}
店铺营业状态设置
需求分析
营业状态分为营业中和打烊中,若当前餐厅处于营业状态,自动接收任何订单,客户可在小程序进行下单操作;若当前餐厅处于打烊状态,不接受任何订单,客户便无法在小程序进行下单操作。
代码开发
/*** 配置类,创建RedisTemplate对象*/
@Configuration
@Slf4j
public class RedisConfiguration {@Beanpublic RedisTemplate redisTemplate(RedisConnectionFactory redisConnectionFactory) {log.info("开始创建redis模板对象...");RedisTemplate redisTemplate = new RedisTemplate();// 设置redis的连接工厂对象redisTemplate.setConnectionFactory(redisConnectionFactory);// 设置redis key的序列化器redisTemplate.setKeySerializer(new StringRedisSerializer());return redisTemplate;}
}/*** 管理端*/
@RestController
@RequestMapping("admin/shop")
@Api(tags="店铺相关接口")
@Slf4j
public class ShopController {public static final String KEY = "SHOP_STATUS";@Autowiredprivate RedisTemplate redisTemplate;/*** 设置营业状态* @return*/@PutMapping("/{status}")@ApiOperation("设置店铺营业状态")public Result setstatus(@PathVariable Integer status) { // data为非必须 所以可以不加泛型类型log.info("设置店铺营业状态{}", status == 1 ? "营业中" : "打烊中");redisTemplate.opsForValue().set(KEY,status);return Result.success();}/*** 获取营业状态* @return*/@GetMapping("/status")@ApiOperation("获取店铺营业状态")public Result<Integer> getstatus() {Integer status = (Integer) redisTemplate.opsForValue().get(KEY);log.info("获取到的营业状态为:{}", status == 1 ? "营业中" : "打烊中");return Result.success(status);}
}/*** 用户端*/
@RestController("userShopController")
@RequestMapping("/user/shop")
@Api(tags = "用户端相关接口")
@Slf4j
public class ShopController {public static final String KEY = "SHOP_STATUS";@Autowiredprivate RedisTemplate redisTemplate;@GetMapping("/status")@ApiOperation("获取营业状态")public Result<Integer> getstatus() {Integer status = (Integer) redisTemplate.opsForValue().get(KEY);log.info("获取到的营业状态为:{}", status == 1 ? "营业中" : "打烊中");return Result.success(status);}
}/*** 用户端knife4j接口文档*/@Beanpublic Docket docket2(){log.info("准备生成接口文档...");ApiInfo apiInfo = new ApiInfoBuilder().title("苍穹外卖项目接口文档").version("2.0").description("苍穹外卖项目接口文档").build();Docket docket = new Docket(DocumentationType.SWAGGER_2).groupName("用户端接口").apiInfo(apiInfo).select()//指定生成接口需要扫描的包.apis(RequestHandlerSelectors.basePackage("com.sky.controller.user")).paths(PathSelectors.any()).build();return docket;}