When using redis, if the redisTemplate.execute method executes multiple redis commands, there will be a problem that the resource cannot be released. If it is changed to redisTemplate.executePipelined, it will not appear;
/** * Update user information and decrement the stock balance by 1 * * @param ppkey * Queue key: set+mobile * @param upkey * Stock remaining * aramparam rushuser * @return */ protected boolean updateUserAndDecrStock(final String ppkey, final String upkey, final RushUser rushuser) { boolean flag = false; try { redisTemplate.executePipelined(new RedisCallback<Boolean>() { @Override public Boolean doInRedis(RedisConnection connection) throws DataAccessException { byte[] upkeyb = redisTemplate.getStringSerializer().serialize(upkey); byte[] stockKey = redisTemplate.getStringSerializer().serialize(RedisCounterEnum.STOCK_COUNT.getCounterName());// Stock number (recorded when the snap-up is successful, increasing from 1) byte[] ppkeyb = redisTemplate.getStringSerializer().serialize(ppkey); connection.watch(upkeyb, stockKey); connection.multi(); Object counter = redisTemplate.opsForValue().get(upkey); Object stockNoObject = redisTemplate.opsForValue().get(RedisCounterEnum.STOCK_COUNT.getCounterName()); int count = Integer.valueOf(counter == null ? "0" : counter.toString()); int stock = Integer.valueOf(stockNoObject == null ? "0" : stockNoObject.toString()); if (count > 0) { connection.decr(upkeyb); String stockNo = (stock + 1) + ""; rushuser.setStockno(stockNo);// Set the stock number String value = ZGUtil.objectToJson(rushuser); connection.set(stockKey, redisTemplate.getStringSerializer().serialize(stockNo)); connection.set(ppkeyb, redisTemplate.getStringSerializer().serialize(value)); } connection.exec(); return null; } }); flag = true; } catch (Exception e) { logger.error(e.getMessage(), e); flag = false; } return flag; }