SpringBoot整合Redis使用Restful風格實現CRUD功能

前言

本篇文章主要介紹的是SpringBoot整合Redis,使用Restful風格實現的CRUD功能。html

Redis 介紹

Redis 是徹底開源免費的,遵照BSD協議,是一個高性能的key-value數據庫。 Redis 與其餘 key - value緩存產品有如下三個特色:java

  • Redis支持數據的持久化,能夠將內存中的數據保存在磁盤中,重啓的時候能夠再次加載進行使用。
  • Redis不只僅支持簡單的key-value類型的數據,同時還提供list,set,zset,hash等數據結構的存儲。
  • Redis支持數據的備份,即master-slave模式的數據備份。

更多的使用說明能夠查看官方的文檔。 官方文檔: redis.ionode

SpringBoot整合Redis

說明:若是想直接獲取工程那麼能夠直接跳到底部,經過連接下載工程代碼。git

開發準備

環境要求 JDK:1.8 SpringBoot:1.5.15.RELEASE Redis:3.2或以上。github

Tips:Redis的偶數爲穩定版本,奇數爲非穩定版本,因此在使用的時候最好使用偶數的版本!web

Reids的能夠看我以前的寫的這篇文章: Redis安裝教程redis

首先仍是Maven的相關依賴:spring

<properties>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
    <java.version>1.8</java.version>
    <fastjson>1.2.41</fastjson>
    <springboot>1.5.15.RELEASE</springboot>
  </properties>

  <dependencies>
		<dependency>
			<groupId>org.springframework.boot</groupId> 
			<artifactId>spring-boot-starter-web</artifactId>
			<version>${springboot}</version>
		</dependency>

		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-devtools</artifactId>
			<optional>true</optional>
			<version>${springboot}</version>
		</dependency>
		
		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-test</artifactId>
			<version>${springboot}</version>
			<scope>test</scope>
		</dependency>
  		
		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-data-redis</artifactId>
			<version>${springboot}</version>
		</dependency>
  
		<dependency>
			<groupId>com.alibaba</groupId>
			<artifactId>fastjson</artifactId>
			<version>${fastjson}</version>
		</dependency>
  
  </dependencies>
複製代碼

添加了相應的maven依賴以後,咱們再來查看配置。 Redis配置的說明在下面中已經說的很詳細了,這裏就不在過多說明了,不過須要注意的是若是Redis是集羣版的話,須要使用這個spring.redis.cluster.nodes這個配置,該配置爲Redis的Host加上Port,多個之間用,逗號隔開。 application.properties的配置以下:數據庫

# Redis服務器地址
# 單機版配置
spring.redis.host = 127.0.0.1
spring.redis.port = 6379
# redis最大重連數
redis.cluster.max-redirects=3
# Redis服務器鏈接密碼(默認爲空)
redis.password=
# 最大空閒數  
redis.maxIdle=5  
# 鏈接池的最大數據庫鏈接數。
redis.maxTotal=5 
# 最大創建鏈接等待時間。若是超過此時間將接到異常。設爲-1表示無限制。  
redis.maxWaitMillis=1000  
# 鏈接的最小空閒時間 默認1800000毫秒(30分鐘)  
redis.minEvictableIdleTimeMillis=300000  
# 每次釋放鏈接的最大數目,默認3  
redis.numTestsPerEvictionRun=3 
# 逐出掃描的時間間隔(毫秒) 若是爲負數,則不運行逐出線程, 默認-1  
redis.timeBetweenEvictionRunsMillis=30000  
# 是否在從池中取出鏈接前進行檢驗,若是檢驗失敗,則從池中去除鏈接並嘗試取出另外一個  
redis.testOnBorrow=true  
# 在空閒時檢查有效性, 默認false  
redis.testWhileIdle=true  
複製代碼

代碼編寫

首先是編寫Redis的配置類,對Redis這塊進行配置。 在使用SpringBoot整合Redis的時候,SpringBoot是能夠根據配置自動完成Redis的相關配置,不過爲了更靈活一點,咱們這邊仍是手動加載一下配置,配置成本身想要的那種效果吧。 首先,配置一個Redis的鏈接池,使用redis.clients.jedis.JedisPoolConfig這個類來進行實現,相關的配置在代碼的註釋中說明得很詳細了,這裏就不在過多講述了; 而後,再來配置一個Redis的工廠,加載Redis的鏈接池配置,這裏咱們也能夠進行一下設置,若是Redis設置了密碼,咱們就加載改密碼,不然就不進行加載。 繼而,咱們再來設置數據存入Redis的序列化的方式並開啓事務。這裏也順便說下爲何要設置序列化器,若是不設置,那麼在用實體類(未序列化)進行存儲的時候,會提示錯誤: Failed to serialize object using DefaultSerializer; 固然,也能夠不設置,不過存儲的實體類必須進行序列化。 最後,咱們再來實例化RedisTemplate的對象,加載上述的配置。在使用的時候,只須要使用以下的方式注入就可使用了json

@Autowired
RedisTemplate<String, Object> redisTemplate;
複製代碼

Redis的配置類的代碼以下:

/**
 * 
 * @Title: RedisConfig
 * @Description: redis初始化配置
 * @Version:1.0.0
 * @author pancm
 * @date 2018年6月7日
 */
@Component
public class RedisConfig {

	@Value("${redis.maxIdle}")
	private Integer maxIdle;

	@Value("${redis.maxTotal}")
	private Integer maxTotal;

	@Value("${redis.maxWaitMillis}")
	private Integer maxWaitMillis;

	@Value("${redis.minEvictableIdleTimeMillis}")
	private Integer minEvictableIdleTimeMillis;

	@Value("${redis.numTestsPerEvictionRun}")
	private Integer numTestsPerEvictionRun;

	@Value("${redis.timeBetweenEvictionRunsMillis}")
	private long timeBetweenEvictionRunsMillis;

	@Value("${redis.testOnBorrow}")
	private boolean testOnBorrow;

	@Value("${redis.testWhileIdle}")
	private boolean testWhileIdle;

	@Value("${redis.cluster.max-redirects}")
	private Integer mmaxRedirectsac;

	@Value("${redis.password}")
	private String redispwd;

	/**
	 * JedisPoolConfig 鏈接池
	 * 
	 * @return
	 */
	@Bean
	public JedisPoolConfig jedisPoolConfig() {
		JedisPoolConfig jedisPoolConfig = new JedisPoolConfig();
		// 最大空閒數
		jedisPoolConfig.setMaxIdle(maxIdle);
		// 鏈接池的最大數據庫鏈接數
		jedisPoolConfig.setMaxTotal(maxTotal);
		// 最大創建鏈接等待時間
		jedisPoolConfig.setMaxWaitMillis(maxWaitMillis);
		// 逐出鏈接的最小空閒時間 默認1800000毫秒(30分鐘)
		jedisPoolConfig.setMinEvictableIdleTimeMillis(minEvictableIdleTimeMillis);
		// 每次逐出檢查時 逐出的最大數目 若是爲負數就是 : 1/abs(n), 默認3
		jedisPoolConfig.setNumTestsPerEvictionRun(numTestsPerEvictionRun);
		// 逐出掃描的時間間隔(毫秒) 若是爲負數,則不運行逐出線程, 默認-1
		jedisPoolConfig.setTimeBetweenEvictionRunsMillis(timeBetweenEvictionRunsMillis);
		// 是否在從池中取出鏈接前進行檢驗,若是檢驗失敗,則從池中去除鏈接並嘗試取出另外一個
		jedisPoolConfig.setTestOnBorrow(testOnBorrow);
		// 在空閒時檢查有效性, 默認false
		jedisPoolConfig.setTestWhileIdle(testWhileIdle);
		return jedisPoolConfig;
	}



	
	/**
	 * 配置工廠
	 */
	@Bean
	public JedisConnectionFactory JedisConnectionFactory(JedisPoolConfig jedisPoolConfig) {
		JedisConnectionFactory JedisConnectionFactory = new JedisConnectionFactory(jedisPoolConfig);
		if (redispwd == null || redispwd.length() == 0) {
			JedisConnectionFactory.setPassword(redispwd);
		}
		return JedisConnectionFactory;
	}

	

	/**
	 * 設置數據存入 redis 的序列化方式,並開啓事務
	 * 
	 * @param redisTemplate
	 * @param factory
	 */
	private void initDomainRedisTemplate(RedisTemplate<String, Object> redisTemplate, RedisConnectionFactory factory) {
		/*
		 * 設置 序列化器 .
		 * 若是不設置,那麼在用實體類(未序列化)進行存儲的時候,會提示錯誤: Failed to serialize object using DefaultSerializer;
		 */
		redisTemplate.setKeySerializer(new StringRedisSerializer());
		redisTemplate.setHashKeySerializer(new StringRedisSerializer());
		redisTemplate.setHashValueSerializer(new GenericJackson2JsonRedisSerializer());
		redisTemplate.setValueSerializer(new GenericJackson2JsonRedisSerializer());
		// 開啓事務
		redisTemplate.setEnableTransactionSupport(true);
		// 將鏈接工廠設置到模板類中
		redisTemplate.setConnectionFactory(factory);
	}
	
	/**
	 * 實例化 RedisTemplate 對象
	 * @return
	 */
	@Bean
	public RedisTemplate<String, Object> functionDomainRedisTemplate(RedisConnectionFactory redisConnectionFactory) {
		RedisTemplate<String, Object> redisTemplate = new RedisTemplate<>();
		initDomainRedisTemplate(redisTemplate, redisConnectionFactory);
		return redisTemplate;
	}
	
}
複製代碼

固然,若是本身想使用自定義的Redis工具類進行實現,那麼只需在該配置類中註冊一個Bean注入封裝一下就能夠了,而後在工具類中加載一下就能夠了。 配置類中添加:

@Bean(name = "redisUtil")
	public RedisUtil redisUtil(RedisTemplate<String, Object> redisTemplate) {
		RedisUtil redisUtil = new RedisUtil();
		redisUtil.setRedisTemplate(redisTemplate);
		return redisUtil;
	}' 複製代碼

Redis的工具類添加以下代碼:

private RedisTemplate<String, Object> redisTemplate;

	public void setRedisTemplate(RedisTemplate<String, Object> redisTemplate) {
		this.redisTemplate = redisTemplate;
	}
	
複製代碼

使用Redis工具類示例:

@Resource
	private RedisUtil redisUtil;
	
複製代碼

講完Redis的配置類以後,咱們再來進行編寫相應的實體類、dao層、service層和Controller層的代碼了。 因爲這塊的代碼比較簡單,並且格式和以前的項目基本相似,所以這裏我就簡單的貼下代碼了。

實體類

又是萬能的用戶表 (^▽^)

代碼以下:

public class User implements Serializable{
	private static final long serialVersionUID = 1L;
	/** 編號 */
	 private int id;
	 /** 姓名 */
	 private String name;
	 /** 年齡 */
	 private int age;
	 
	 public User(){
	 }

	public int getId() {
		return id;
	}
	
	public void setId(int id) {
		this.id = id;
	}

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public int getAge() {
		return age;
	}

	public void setAge(int age) {
		this.age = age;
	}

	public String toString() {
		return JSONObject.toJSONString(this);
	}
}
複製代碼

Dao 數據層

這裏我是使用的自定義的Redis工具類,其實也就是對RedisTemplate作了二次封裝。 由於使用的是set(集合)方式存儲的,因此我這邊把用戶數據的ID做爲key,用戶數據做爲value了。

實現類的代碼以下:

@Repository
public class UserDaoImpl implements UserDao {

	@Resource
	private RedisUtil redisUtil;
	

	@Override
	public void addUser(User user) {
		redisUtil.set(String.valueOf(user.getId()), user.toString());
	}


	@Override
	public void updateUser(User user) {
		redisUtil.set(String.valueOf(user.getId()), user.toString());
	}


	@Override
	public void deleteUser(int id) {
		redisUtil.del(String.valueOf(id));
	}

	
	@Override
	public User findByUserId(int id) {
		String data = redisUtil.get(String.valueOf(id)).toString();
		User user = JSON.parseObject(data, User.class);
		return  user;
	}
}

複製代碼

Service 業務層

業務層這邊處理比較簡單,成功就返回true,失敗就返回false。

實現類的代碼以下:

@Service
public class UserServiceImpl implements UserService {	

	private  final Logger logger = LoggerFactory.getLogger(this.getClass());
	@Autowired
    private UserDao userDao;	
	
	@Override
	public boolean addUser(User user) {
		boolean flag=false;
		try{
			userDao.addUser(user);
			flag=true;
		}catch(Exception e){
			logger.error("新增失敗!",e);
		}
		return flag;
	}

	@Override
	public boolean updateUser(User user) {
		boolean flag=false;
		try{
			userDao.updateUser(user);
			flag=true;
		}catch(Exception e){
			logger.error("修改失敗!",e);
		}
		return flag;
	}

	@Override
	public boolean deleteUser(int id) {
		boolean flag=false;
		try{
			userDao.deleteUser(id);
			flag=true;
		}catch(Exception e){
			logger.error("刪除失敗!",e);
		}
		return flag;
	}


	@Override
	public User findByUserId(int id) {
		return userDao.findByUserId(id);
	}
}

複製代碼

Controller 控制層

控制層這邊也比較簡單,使用Restful風格實現的CRUD功能。

代碼以下:

@RestController
@RequestMapping(value = "/api")
public class UserRestController {
	
	private  final Logger logger = LoggerFactory.getLogger(this.getClass());

	
	@Autowired
    private UserService userService;
 
	@PostMapping("/user")
    public boolean addUser(@RequestBody User user) {
    	logger.info("開始新增...");
        return userService.addUser(user);
    }
    
	@PutMapping("/user")
    public boolean updateUser(@RequestBody User user) {
    	logger.info("開始更新...");
        return userService.updateUser(user);
    }
	
	@DeleteMapping("/user")
    public boolean delete(@RequestParam(value = "id", required = true) int userId) {
    	logger.info("開始刪除...");
        return userService.deleteUser(userId);
    }
	

    @GetMapping("/user")
    public User findByUserId(@RequestParam(value = "id", required = true) int userId) {
    	logger.info("開始查詢全部數據...");
        return userService.findByUserId(userId);
    }
}

複製代碼

App 入口

和普通的SpringBoot項目基本同樣。

代碼以下:

@SpringBootApplication
public class App 
{
    public static void main( String[] args )
    {
		SpringApplication.run(App.class, args);
		System.out.println("程序正在運行...");
    }
}

複製代碼

功能測試

咱們成功啓動該程序以後,使用Postman工具來進行接口測試。

首先添加一條數據,使用POST方式進行請求

POST http://localhost:8180/api/user

Body參數爲:

{"id":1,"name":"xuwujing","age":18}

在這裏插入圖片描述
界面返回true,表示新增成功了!

而後在進行查詢,使用GET請求。

GET http://localhost:8180/api/user?id=1

返回:

{"id":1,"name":"xuwujing","age":18}

在這裏插入圖片描述

咱們再來使用RedisDesktopManager工具進行查詢看下,是否真的寫入到Redis中去了。

在這裏插入圖片描述
能夠看到已經成功寫入到Redis中了。

而後咱們再來更新下更新該數據,使用PUT方式請求。

PUT http://localhost:8180/api/user

這裏只是更改了下age年齡,Body參數爲:

{"id":1,"name":"xuwujing","age":19}

在這裏插入圖片描述
能夠看到已經成功更新了。

最後咱們再來查詢一遍看下是否成功更新。

GET http://localhost:8180/api/user?id=1

返回:

{"id":1,"name":"xuwujing","age":19}

在這裏插入圖片描述
能夠看到已經成功更新了。

其它

其實SpringBoot整合Redis整個項目很早以前就已經寫好而且上傳到Github了,可是一直沒有抽出時間寫篇博客講述(還有不少SpringBoot的項目也是如此),最近不是那麼的忙了,因而準備了下時間編寫本篇博文。後續我的Github上的SpringBoot項目中之後有時間的話,也會對其中的一些發表博文進行講解,不過那是之後的事了ヽ(ー_ー)ノ

關於SpringBoot整合Redis的文章就講解到這裏了,若有不妥,歡迎指正!

項目地址

SpringBoot整合Redis的項目工程地址: github.com/xuwujing/sp…

SpringBoot整個集合的地址: github.com/xuwujing/sp…

SpringBoot整合系列的文章

音樂推薦

原創不易,若是感受不錯,但願給個推薦!您的支持是我寫做的最大動力! 版權聲明: 做者:虛無境 博客園出處:www.cnblogs.com/xuwujing CSDN出處:blog.csdn.net/qazwsxpcm     我的博客出處:www.panchengming.com

相關文章
相關標籤/搜索