springboot+dubbo+redis+RabbitMQ 项目整合实例【附完整源码】

往期精选

  ●  卸磨杀驴!程序员心中的悲愤与无奈

  ●  2018.06.27阿里云宕机50分钟

  ●  程序员/架构师/技术经理/技术总监是干什么的

  ●  记一次内存溢的出分析经历——带给我的痛苦

  ●  10步代码详解springboot集成数据库

  ●  程序员加薪的技巧

  ●  史上最全的java进阶书籍

  ●  性能优化的一般性原则与方法

    记录服务上线一年来的点点滴滴

  ●  传播正能量——做一个快乐的程序员  

  ●  初探性能调优——2个月到4小时的性能提升

  ●  java程序员到了必须掌握springboot的时候了

来源:https://blog.csdn.net/qq_28125445

作者:夏佐

关于springboot, 之前零零碎碎地写了一些,今天从项目实战角度给大家分享一下我的一点经验。

话不多说,先从项目的目录结构讲起。(文章最后贴了源码下载地址

如图:

项目分层:

parent(顶级 )pom

    -- api(公共API、DTO等)jar

    -- foundation(公共基设)jar

    -- modules(前端consumer)pom

        -- www(官网)jar

        -- admin(后台)jar

        -- ......

     -- service(provider,本应该拆分,我这里只写了一个) pom

         -- user(用户中心)jar

         -- order(订单中心)jar

         -- ......

所用技术: springboot、dubbo、zookeeper、mybatis、redis、RabbitMQ、druid、swagger等

效果截图:

自动生成的swagger接口文档,可直接测试:



使用druid的SQL监控,记录慢SQL:

dubbo admin:

RabbitMQ admin:

项目截图:

部分代码:

消费者(暴露给前端的controller)

package com.ysk.admin.controller;

import java.util.List;

import org.springframework.web.bind.annotation.GetMapping;

import org.springframework.web.bind.annotation.RequestBody;

import org.springframework.web.bind.annotation.RequestMapping;

import org.springframework.web.bind.annotation.RequestMethod;

import org.springframework.web.bind.annotation.RequestParam;

import org.springframework.web.bind.annotation.RestController;

import com.alibaba.dubbo.config.annotation.Reference;

import com.ysk.api.model.User;

import com.ysk.api.service.UserService;

@RestController

@RequestMapping("/")

public class TestController {

@Reference(version = "1.0.0")

private UserService testService;

@GetMapping("hello")

public String hello() {

return testService.sayHello("Hello springboot and dubbo!");

}

@GetMapping("user")

public User user() {

return testService.findUser();

}

@GetMapping("list")

public List<User> list(@RequestParam(defaultValue = "1") int page,

@RequestParam(defaultValue = "10") int pageSize) {

return testService.getUser(page, pageSize);

}

@RequestMapping(value = "add", method = RequestMethod.POST)

public List<User> add(@RequestBody User user) {

System.out.println(user.toString());

return null;

}

// 从redis获取某个用户

@RequestMapping(value = "getuserfromredis", method = RequestMethod.GET)

public User getRedis(@RequestParam String key) {

return testService.getUserForRedis(key);

}

}
package com.ysk.admin;

import org.apache.log4j.Logger;

import org.springframework.boot.SpringApplication;

import org.springframework.boot.autoconfigure.SpringBootApplication;

import org.springframework.context.annotation.ImportResource;

@SpringBootApplication

@ImportResource({ "classpath:config/spring-dubbo.xml" })

public class App {

private static Logger logger = Logger.getLogger(App.class);

public static void main(String[] args) {

SpringApplication.run(App.class, args);

logger.info("SpringBoot Start Success");

}

}

提供者(具体的实现与逻辑)

package com.ysk.service.impl;

import java.text.SimpleDateFormat;

import java.util.Date;

import java.util.List;

import org.springframework.beans.factory.annotation.Autowired;

import com.alibaba.dubbo.config.annotation.Service;

import com.github.pagehelper.PageHelper;

import com.ysk.api.model.User;

import com.ysk.api.service.UserService;

import com.ysk.resource.UserMapper;

import com.ysk.service.RedisService;

@Service(version = "1.0.0", interfaceClass = UserService.class)

public class UserServiceImpl implements UserService {

@Autowired

private UserMapper userMapper;

@Autowired

private RedisService redisService;

@Override

public String sayHello(String str) {

SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");

return dateFormat.format(new Date()) + ": " + str;

}

@Override

public User findUser() {

User user = new User();

user.setId(1001);

user.setName("张三");

user.setAge(20);

user.setAddress("上海徐汇");

return user;

}

@Override

public List<User> getUser(int page, int pageSize) {

PageHelper.startPage(page, pageSize);

return userMapper.getUsers();

}

@Override

public User getUserForRedis(String key) {

User user = new User();

user.setId(1008);

user.setName("刘德华");

user.setAge(60);

user.setAddress("中国香港");

redisService.set(user.getId() + "", user);

return (User) redisService.get(key);

}

}
package com.ysk.config;

import java.util.Properties;

import org.springframework.aop.framework.autoproxy.BeanNameAutoProxyCreator;

import org.springframework.context.annotation.Bean;

import org.springframework.context.annotation.Configuration;

import org.springframework.transaction.PlatformTransactionManager;

import org.springframework.transaction.interceptor.TransactionInterceptor;

@Configuration

public class TransactionConfiguration {

@Bean(name = "transactionInterceptor")

public TransactionInterceptor transactionInterceptor(PlatformTransactionManager platformTransactionManager) {

TransactionInterceptor transactionInterceptor = new TransactionInterceptor();

// 事务管理器

transactionInterceptor.setTransactionManager(platformTransactionManager);

Properties transactionAttributes = new Properties();

// 新增

transactionAttributes.setProperty("insert*", "PROPAGATION_REQUIRED,-Throwable");

// 修改

transactionAttributes.setProperty("update*", "PROPAGATION_REQUIRED,-Throwable");

// 删除

transactionAttributes.setProperty("delete*", "PROPAGATION_REQUIRED,-Throwable");

// 查询

transactionAttributes.setProperty("select*", "PROPAGATION_REQUIRED,-Throwable, readOnly");

transactionInterceptor.setTransactionAttributes(transactionAttributes);

return transactionInterceptor;

}

// 代理到ServiceImpl的Bean

@Bean

public BeanNameAutoProxyCreator transactionAutoProxy() {

BeanNameAutoProxyCreator transactionAutoProxy = new BeanNameAutoProxyCreator();

transactionAutoProxy.setProxyTargetClass(true);

transactionAutoProxy.setBeanNames("*ServiceImpl");

transactionAutoProxy.setInterceptorNames("transactionInterceptor");

return transactionAutoProxy;

}

}
package com.ysk.config;

import org.springframework.amqp.core.Binding;

import org.springframework.amqp.core.BindingBuilder;

import org.springframework.amqp.core.Queue;

import org.springframework.amqp.core.TopicExchange;

import org.springframework.context.annotation.Bean;

import org.springframework.context.annotation.Configuration;

@Configuration

public class RabbitConfiguration {

// 声明队列

@Bean

public Queue queue1() {

return new Queue("hello.queue1", true); // true表示持久化该队列

}

@Bean

public Queue queue2() {

return new Queue("hello.queue2", true);

}

// 声明交互器

@Bean

TopicExchange topicExchange() {

return new TopicExchange("topicExchange");

}

// 绑定

@Bean

public Binding binding1() {

return BindingBuilder.bind(queue1()).to(topicExchange()).with("key.1");

}

@Bean

public Binding binding2() {

return BindingBuilder.bind(queue2()).to(topicExchange()).with("key.#");

}

}
package com.ysk.config;

import org.springframework.cache.CacheManager;

import org.springframework.cache.annotation.CachingConfigurerSupport;

import org.springframework.cache.annotation.EnableCaching;

import org.springframework.context.annotation.Bean;

import org.springframework.context.annotation.Configuration;

import org.springframework.data.redis.cache.RedisCacheManager;

import org.springframework.data.redis.connection.RedisConnectionFactory;

import org.springframework.data.redis.core.RedisTemplate;

@Configuration  

@EnableCaching

public class RedisConfiguration extends CachingConfigurerSupport {

@Bean

public CacheManager cacheManager(RedisTemplate<?,?> redisTemplate) {

CacheManager cacheManager = new RedisCacheManager(redisTemplate);

return cacheManager;

}

@Bean

public RedisTemplate<String, String> redisTemplate(RedisConnectionFactory factory) {

RedisTemplate<String, String> redisTemplate = new RedisTemplate<String, String>();

redisTemplate.setConnectionFactory(factory);

return redisTemplate;

}

}

spring.datasource.url = jdbc:mysql://localhost:3306/test?useUnicode=true&characterEncoding=UTF-8

spring.datasource.username = root

spring.datasource.password = root

spring.datasource.driverClassName = com.mysql.jdbc.Driver

#连接池的配置信息

spring.datasource.initial-size=5

spring.datasource.min-idle=5

spring.datasource.max-idle=8

spring.datasource.max-active=20

spring.datasource.max-wait=60000

spring.datasource.timeBetweenEvictionRunsMillis=60000

spring.datasource.minEvictableIdleTimeMillis=300000

spring.datasource.validationQuery=SELECT 1 FROM DUAL

spring.datasource.testWhileIdle=true

spring.datasource.testOnBorrow=false

spring.datasource.testOnReturn=false

spring.datasource.poolPreparedStatements=true

spring.datasource.maxPoolPreparedStatementPerConnectionSize=20

spring.datasource.filters=stat,wall,log4j

spring.datasource.connectionProperties=druid.stat.mergeSql=true;druid.stat.slowSqlMillis=200

server.port=8082

server.context-path=/

logging.level.com.ysk.resource=debug

# MyBatis 配置

mybatis.mapper-locations=classpath:/mapper/*Mapper.xml

mybatis.type-aliases-package=com.ysk.api.model


#druid 配置

druid.username=admin

druid.password=admin

druid.allow=127.0.0.1

druid.reset.enable=true


#redis  

spring.redis.hostName=127.0.0.1

spring.redis.port=6379    

spring.redis.pool.maxActive=8    

spring.redis.pool.maxWait=-1    

spring.redis.pool.maxIdle=8    

spring.redis.pool.minIdle=0    

spring.redis.timeout=0


#rabbitMQ

spring.rabbitmq.host=10.99.2.10

spring.rabbitmq.port=5672

spring.rabbitmq.username=admin

spring.rabbitmq.password=admin123

spring.rabbitmq.publisher-confirms=true

spring.rabbitmq.publisher-returns=true

spring.rabbitmq.template.mandatory=true


# 最小消息监听线程数

spring.rabbitmq.listener.concurrency=2

spring.rabbitmq.listener.max-concurrency=2

附上源码:https://pan.baidu.com/s/1FRyL2sWJxx29DaJ0YWhcvQ

(或者公众号回复"sdrr")

欢迎大家加入Java高级架构/互联网(严禁培训机构、广告群,最干净的技术交流群):614527642 

微信平台本人收集个大量资源(4000G架构资源),只做分享,欢迎大家关注获取,保证免费,非任何机构

更多精彩请扫码关注微信公众号——  名称java版web项目   id :java_project

                                    

  • 1
    点赞
  • 11
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值