Springboot项目-实战2-实现

🍎数据处理

接口接收数据并进行数据清洗

  1. 基本信息
Java Spring Boot环境中,可以使用Spring Data JPA和Hibernate ORM来操作SQLite数据库,来实现如何创建一个接收并同步数据到服务器端数据库的RESTful API接口;
参考博客:https://blog.csdn.net/u013735734/article/details/136361244#%E9%85%8D%E7%BD%AE%20SQLite%20&%20JPA

项目基础配置:
需要确保配置:Spring Data JPA和SQLite连接
参考博客:https://blog.csdn.net/zyd573803837/article/details/109263219

mysql读取到redis

通过实现CommandLineRunner接口重写run方法可以实现。

具体的run方法中,使用xxxMapper读取mysql数据,然后向RedisOpreation对象写入数据。

@Component
public class RedisDataLoader implements CommandLineRunner {

    @Autowired
    private RedisOperations redisOperations;

    @Autowired
    private XXXMapper xxxMapper;

    @Override
    public void run(String... args) throws Exception {
        Object object = xxxMapper.selectById(1);
        redisOperations.set(key, object);
    }
}

接口返回参数对象

通常不同的运行情况,返回的对象是不同的。
通过采用构造方法-重载形式,可以实现该效果。
通过重载不同的静态方法,实现调用不同的构造方案。
该类需要实现Seriaizable。
需要添加@JsonInclude(JsonInclude.Include.NON_NULL),不返回参数值为null的。

@Slf4j
@Data
@JsonInclude(JsonInclude.Include.NON_NULL)
public class ResultDto implements Serializable {

    private String xx1;
    private String xx2;
    private String xx3;
    
    public ResultDto(String xx1, String xx2, String xx3){
        this.xx1 = xx1;
        this.xx2 = xx2;
        this.xx3 = xx3;
    }

    public ResultDto(String xx1, String xx2){
        this.xx1 = xx1;
        this.xx2 = xx2;
    }

    public static ResultDto result(String xx1, String xx2, String xx3){
        return new ResultDto(xx1, xx2, xx3);
    }
	
	public static ResultDto result(String xx1, String xx2){
        return new ResultDto(xx1, xx2);
    }
}

返回参数分析

一般采用JSON格式,该格式是轻量级的数据交换格式,易于人阅读和编写;
但返回值格式需要经过如下过程加以判断:

1. 使用@RestController@Controller + @ResponseBody
表示控制类的返回值直接写入HTTP的响应体,而不作为视图模型返回给视图层;

2. 返回值类型
可以是原生的java对象(map)、自定义对象或者String。如果返回的是java对象,Spring自动转换为JSON对象;

3. 响应头Content-Type
当返回为JSON格式时,响应头的Content-Tpye字段会被赋值为application/json

存储

  1. 存储容量计算
long keyMemory = RamUsageEstimator.sizeOf(keysCache)/1024;
// 理解:
RamUsageEstimator.sizeOf(keysCache) --》 评估keysCache对象在内存中所占用的空间;
/1024 --》 将对象占用内存的大小,设置单位为KB;

Gson

定义:
	Gson 是一个流程的java库,用于实现java对象与JSON格式,相互转换;

案例:
	Gson gson = new GsonBuilder().setDateFormat("yyyy-MM-dd HH:mm:ss").create();
	// setDateFormat,表示在执行序列化/反序列化的时候,日期时间按照上述格式转化;
	gson.fromJson // Json -》 java对象
	gson.toJson // java对象 -》 Json
	

JsonObject和JSONObject

两者都用于处理JSON数据,但属于不同的库;
JSONObject:
	来自于org.json包,提供多种方法操作JSON数据,如添加键值对、获取特定键的值;
JsonObject:
	来自于com.google.gson包,可以用来将Java对象转化为JSON表示形式,也可以将JSON字符串转换成Java对象。

问题1:

GsonBuilderUtil.GSON_DEFAULT.fromJson(jsonStr,new TypeToken<TreeMap<String, String>>() {}.getType());


Base64安全方式与非安全方式

来自于包package java.util.Base64;这个类

Base64 是一种常用的二进制到文本的编码方案,常用于将二进制数据(如图片、音频等)转换成可以在文本环境中安全传输的格式。
不安全方式:
public static Encoder getEncoder() {
         return Encoder.RFC4648;
}
// 返回一个遵循 RFC 4648 标准的 Base64 编码器。RFC 4648 描述了 Base64 编码的标准形式,其中使用的字符包括大写字母、小写字母、数字、加号 (+) 和斜线 (/)。编码后的字符串还会使用等号 (=) 作为填充字符。
public static Decoder getDecoder() {
         return Decoder.RFC4648;
    }

安全方式:
public static Encoder getUrlEncoder() {
    return Encoder.RFC4648_URLSAFE;
}
// 返回一个 URL 和文件名安全的 Base64 编码器。这种编码方式遵循 RFC 4648 中描述的 URL 和文件名安全的 Base64 变体。在这种情况下,加号 (+) 被替换为下划线 (_),斜线 (/) 被替换为减号 (-);
public static Decoder getUrlDecoder() {
         return Decoder.RFC4648_URLSAFE;
    }

案例:

public void  testxhj(){
        String data = "127.0.0.1";
        byte[] encode = getUrlEncoder().encode(data.getBytes());
        System.out.println("urlencoder:->"+new String(encode));
        // urlencoder:->MTI3LjAuMC4x
        // urlencoder:->MTI3LjAuMC4x
//        String encode1 = Base64.encode(data.getBytes());
        String encode1 = getEncoder().encodeToString(data.getBytes());
        System.out.println("encoder:->"+encode1);
        // encoder:->MTI3LjAuMC4x
        // encoder:->MTI3LjAuMC4x
        // 每次加密后的输出结果一样
        byte[] decode = getUrlDecoder().decode(encode);
        System.out.println("url-url decoder:——>"+new String(decode));
        // url-url decoder:——>127.0.0.1
//        byte[] decode1 = getDecoder().decode(encode.toString());
//        System.out.println("url-xxx decoder:——>"+new String(decode1)); // 异常
        byte[] decodex = getUrlDecoder().decode(encode1);
        System.out.println("xxx-url decoder:——>"+new String(decodex));
        // xxx-url decoder:——>127.0.0.1
        byte[] decodex1 = getDecoder().decode(encode1);
        System.out.println("xxx-xxx decoder:——>"+new String(decodex1));
        // xxx-xxx decoder:——>127.0.0.1
}

数据读取

redis读取

本地Cache读取

具体实现:

public class XxxeCache {
	public volatile static Map<String, xxxInfoVo> mapper = new HashMap<>();

	@Autowired
    private xxxInfoService xxxInfoService;

	@PostConstruct
    public void init(){
        List<xxxInfoVo> xxxList = xxxInfoService.list();
        Map<String, xxxInfoVo> xxxMap = new HashMap<>();
        xxxList.forEach(cp -> {
            xxxMap.put(cp.getId(),cp);
        });
        mapper = xxxMap;
        log.info("[初始化][服务信息] -> 初始化信息 {} ",mapper.size());
    }
}

注意:
	需要借助数据库读取方式;

数据库读取

枚举类型

@Getter
public enum xxxEnum {
    XXX_KEY("xxx", "xxx"),
    private String name;
    private String type;

    xxxEnum(String name, String type) {
        this.name = name;
        this.type = type;
    }
}

BaseMapper接口

int updateById(@Param("et") T entity);
	更新数据库记录 :根据传入的实体对象更新数据库中的某一条记录。
	参数绑定 :通过 @Param("et") 将实体对象绑定到 SQL 语句中。
	返回结果 :返回受影响的行数,用于判断更新是否成功。

🍎函数使用

Math类

Math.min 和 Math.max函数

        int min = Math.min(111111, 111111);// 如果两个数相同,则返回其中任意一个。
        int max = Math.max(22,22);// 如果两个数相同,返回其中任意一个。
        System.out.println(min);
        System.out.println(max);

stream操作

情况1:

Collection<LzKey> lzKeys
LzKey errorKey = lzKeys.stream().filter(lzKey -> !validateId(lzKey.getId())).findAny().orElse(null);

// 理解:
lzKeys.stream() --》 集合转换成流Stream,可以对其中的元素继续流式操作;
.filter(lzKey -> !validateId(lzKey.getId())) --》 过滤出通过getId获取到的lzKey对象无法通过validateId验证的lzKey
.findAny() --》 从结果中随机选择一个元素
.orElse(null) --》 如果存在元素就返回元素,不存在就返回null

情况2:

下划线是java7以及之后版本的数字分割符,即50000000 等于 5000_0000

情况3:

Collection<LzKey> lzKeys
Map<Integer, List<LzKey>> map = lzKeys.stream().collect(Collectors.groupingBy(lzKey -> getTableIndex(lzKey.getId())));

// 理解;
lzKeys.stream() --》 将lzKeys列表转化成一个流;
.collect(....) --》 流操作的终止操作之一,收集元素并将其转化为Map类型;
Collectors.groupingBy(....) --Collector工厂方法,用于创建一个Collector实例,元素根据分类函数groupingBy进行分组;
lzKey -> getTableIndex(lzKey.getId()) --》 根据id得到tableIndex,其作为Map的key,值为lzKeys组成的列表;

情况4:

List<Integer> indexList = list.stream().map(LzKey::getId).collect(Collectors.toList());
// 理解:
list.stream() --》 基于list集合创建流
map(LzKey::getId) --》 将list集合中的lzKey对象的id元素提取出来
collect(Collectors.toList()) --》将提取出来的id组成新的List

Collections.shuffle(indexList, ThreadLocalRandom.current());
// 理解:
对indexList进行随机重排,参数2 确保多线程环境下速记数生成的安全性;

Thread线程

extends Thread:

public class function extends Thread{}
public function(int a,
                          long b,
                          int c) {
        super("ConsumerKeyThread");
        setDaemon(true);
        this.a = a;
        this.b = b;
        this.c = c;
}
// 理解:
super("ConsumerKeyThread") --》 调用父类的构造方法,传入字符串s,作为新线程的名字;
setDaemon(true) --》将创建的线程设置为守护线程;
守护线程是一种特殊的过程,它在后台运行,不会组织程序的退出,当所有的非守护线程都结束时,守护线程也将自动终止;

队列

  1. 阻塞队列
private ArrayBlockingQueue<LzKey> bufferKeys
// 理解:
定义阻塞队列;用于存储和管理LzKey对象;

List集合

  1. list遍历元素
list.forEach(key -> cache.put(key)); 
// 理解:
遍历list中的每个元素,并对元素执行cache.put操作,将每个元素都存入cache中。
  1. 问题:add出现nullPointerException
问题:
一个list集合执行add命令,报java.lang.NullPointerException: null  这是什么原因
分析:
List本身没有初始化,导致使用add方法的时候会报错;
list是由map.get(key)获取到的,但是key对应的value为null,也会报上述错误。

🍎功能

统计

  1. Guage
// 学习:
GaugePrometheus 支持的一种指标类型,它可以记录任意浮点数值,既可以增加也可以减少,适合用来表示像内存使用量、活跃连接数这类可以随时变化的值。

Gauge CHANGE_GAUGE = Gauge.build()
            .name("server")
            .help("number of current.")
            .labelNames(NAME)
            .register();
// 理解:
Gauge.build() --》 构建一个新的Gauge对象;
.name() --》 指定名字;
.help() --》 添加描述信息;
.labelNames() --》设置标签,区分相同类型指标的不同实例;
.register() --》 构建好的Gauge注册到Prometheus的客户端库中;

加密

SM3
使用1:

String str = "12345";
String secret = "000000";
String checkSign = SmUtil.sm3WithSalt(secret.getBytes()).digestHex(str);
// secret.getBytes() 将字符串转换成字节数组
// SmUtil.sm3WithSalt() 生成SM3的盐值
// .digestHex() 执行散列运算,将转换为字节流,并将结果转为16进制字符串格式;
String out = SmUtil.sm3(str);
System.out.println(checkSign);
System.out.println(out);

日志以及aspect对接口的时间影响

描述:
	某接口中,存在大量的日志处理以及通过aspect在返回结果前进行处理,这样会导致接口返回消耗更多的时间?
解决:
	日志通过异步处理,不影响主线程正常执行;
	aspect处理,优化处理逻辑;

war包和jar包的区别

war包:
	可以部署到支持java web容器的服务器,比如tomcat、jetty等。可结合容器的优势,实现多实例部署和负载均衡。
jar包:
	通过命令行或脚本可执行该jar包,适合单机部署;

探针 ServiceTrace

描述:
	创建ServiceTrace类,构建bind方法;

案例代码:
		public static final TransmittableThreadLocal<BusinessTrace> BUSINESS_TRACE = new TransmittableThreadLocal<>();
		// ThreadLocal 允许将数据绑定到当前线程,对于跨多个方法调用 或 再同一个线程中跟踪业务逻辑特别有用;
	    public static void bind(String serviceId, String serviceName){
	    // 初始化或更新与线程相关的上下文信息,通常用于日志记录和跟踪分布式系统中的事务;
        MDC.put(SystemConsts.SERVICE_ID, serviceId);
        MDC.put(SystemConsts.SERVICE_NAME, serviceName);
        // MDC 来存储键值对,是Logback或Log4j库的一部分,用于附加诊断信息到当前线程的日志事件中;
        BUSINESS_TRACE.set(BusinessTrace.builder()
        // 创建BusinessTrace对象,
                .cover(Boolean.FALSE)
                .threadId(getCurrentThreadId())
                // 获取当前线程的id
                .callerId(getCurrentCallerId())
                // 获取调用者的id
                .serviceId(serviceId)
                .serviceName(serviceName)
                .build());
    }

重定向

主要学习java中的重定向有哪些 以及实现形式,还有请求有什么相似?

xml数据excel化

实现代码:

🍇 本地xml文件--》excel
SAXReader reader = new SAXReader();
// SAXReader是dom4j库中的一个类,用于读取XML文档并将其转换为Document对象
InputStream in = Thread.currentThread().getContextClassLoader().getResourceAsStream(pathXml);
// 线程.获取当前线程.获取线程上下文类加载器.根据资源pathXml路径xml文件读取流文件
Document doc = reader.read(in);
// 将流文件解读为Document对象
Element rootElt = doc.getRootElement();
// 获取对象的根元素

🍇 远程网页xml文件 --》 excel
SAXReader reader = new SAXReader();
// SAXReader是dom4j库中的一个类,用于读取XML文档并将其转换为Document对象
URL url = new URL(pathUrl);
// 提供的字符串pathUrl创建一个URL对象
HttpURLConnection connection = (HttpURLConnection) url.openConnection();
// 打开到该URL的连接,并将其类型转换为HttpURLConnection
connection.setRequestMethod("GET");
// 设置HTTP请求的方法为GET,表示向服务器请求指定的页面信息
connection.connect();
// 建立与远程资源的实际连接
if (connection.getResponseCode() == HttpURLConnection.HTTP_OK)
// 判断从服务器收到的响应码,是否为200
InputStream inUrl = connection.getInputStream();
// 从HttpURLConnection对象中获取输入流
Document docUrl = reader.read(inUrl);
// 从创建的SAXReader对象读取从输入流中获取的XML数据,解析成Document对象
Element rootEle = docUrl.getRootElement();
// 获取对象的根元素

🍇 xml文件中元素的遍历
Element element = docUrl.getRootElement();
// 获取对象的根元素
for(Iterator iter = element.elementIterator(); element.hasNext();){
	Element elementx = (Element)element.next();
	Attribute id = elementx.attribute("xxx");
	String key = id.getName();
	// 获取元素的名称
	String value = id.getValue();
	// 获取元素的值
	System.out.println("key:"+key+","+"value:"+value);
	// key:id,value:URL
	// 元素一般为:<type id="URL" totalCount="3629156">
}

问题:数据读取失败

参考:https://blog.csdn.net/Ljm15832631631/article/details/72878560

🍎请求

hutool包的request请求

get请求

方式1:

Map<String,String> param = new HashMap<>();
param.put("appId",appId);
param.put("version", version);
param.put("algorithm", algorithm);
param.put("timestamp",timestamp);

HttpResponse response = HttpRequest.get(url).form(param).execute();
// 该方式可行;

Post请求

🍇 方式1:

JsonObject requestObj = new JsonObject();
JsonObject Head = new JsonObject();
JsonObject Body = new JsonObject();
JsonObject Attache = new JsonObject();

requestObj.add("HEAD",Head);
requestObj.add("BODY",Body);
requestObj.add("ATTACHED",Attache);

String param = gson.toJson(requestObj);
String httpRes = HttpRequest.post(url)
                .header(Header.ACCEPT_ENCODING, "") 
                .body(param)
                .execute().body();
JSONObject jsonresult = new JSONObject(httpRes);
// 该方法可行

🍇 方式2:

JsonObject requestJson = new JsonObject();
requestJson.addProperty("aaa",aaa);
Gson gson = new Gson();

HttpResponse result = HttpRequest.post(encryptLocalUrl)
                .body(gson.toJson(requestJson)).execute();
System.out.println("请求参数:-》"+requestJson);
// 该方式不可行,参数无法通过请求传递给接口;

HttpResponse result = HttpRequest.post(encryptLocalUrl)
                .form(param).execute();
// 通过这样的方式可以实现,且param是map集合;

🍇 方式3:

// 定义接口 URL
 String url = "http://localhost:8080/api/complexEndpoint";

 // 构造请求头
 String timestamp = String.valueOf(Instant.now().getEpochSecond()); // 当前时间戳
 String apikey = "abcdef123456"; // 示例 API Key
 String yyy1 = "value_yyy1";
 String yyy2 = "value_yyy2";

 // 构造请求体(JSON 格式)
JSONObject body= new JSONObject();
body.put("data", "example_data");
body.put("xxx1", "value_xxx1");
body.put("xxx2", "value_xxx2");
body.put("xxx3", "value_xxx3");

 // 创建 HttpClient
 HttpClient client = HttpClient.newHttpClient();

 // 创建 HttpRequest
 HttpRequest request = HttpRequest.newBuilder()
         .uri(new URI(url))
         .header("Content-Type", "application/json")
         .header("timestamp", timestamp)
         .header("apikey", apikey)
         .header("yyy1", yyy1)
         .header("yyy2", yyy2)
         .POST(HttpRequest.BodyPublishers.ofString(requestBody))
         .build();

 // 发送请求并获取响应
 HttpResponse<String> response = client.send(request, HttpResponse.BodyHandlers.ofString());

 // 解析响应
 int statusCode = response.statusCode();
 String responseBody = response.body();
 HttpHeaders responseHeaders = response.headers();

 // 打印响应状态码
 System.out.println("Status Code: " + statusCode);

 // 打印响应头中的参数
 String code = responseHeaders.firstValue("code").orElse("Code not found");
 String aaa1 = responseHeaders.firstValue("aaa1").orElse("aaa1 not found");
 String aaa2 = responseHeaders.firstValue("aaa2").orElse("aaa2 not found");

 System.out.println("Response Header - Code: " + code);
 System.out.println("Response Header - aaa1: " + aaa1);
 System.out.println("Response Header - aaa2: " + aaa2);

 // 打印响应体中的参数
 System.out.println("Response Body: " + responseBody);

请求传输内容

ByteBuffer

json

包装请求

描述:
	ServletRequestHttpServletRequestContentCachingRequestWrapper 之间的区别和联系?
	
分析:
	ServletRequestHttpServletRequest (两个是接口) 和 ContentCachingRequestWrapper(类)是 Java Servlet API 中处理 HTTP 请求时常用的接口和类。它们之间存在着继承和包装的关系,HttpServletRequest extends ServletRequestContentCachingRequestWrapper 包装 HttpServletRequest。

区别:
	HttpServletRequest 只能读取一次请求的内容;
	ContentCachingRequestWrapper 具体的实现类,可以缓存请求体的内容,使得请求体可以多次读取而不影响原始请求对象;	

自动化批量提交

所遇到的问题:

🍓问题:
	CloseableHttpResponse loginResponse = httpClient.execute(loginRequest)段代码报错 java.lang.NoClassDefFoundError: org/apache/hc/core5/http2/HttpVersionPolicy 
解决:
	引入依赖包:httpcore5-h2

🍓问题:
	CloseableHttpClient httpClient = HttpClients.createDefault() 报这个错误java.lang.NoClassDefFoundError: org/slf4j/LoggerFactory
解决:
	引入依赖包:org.slf4j

🍎 项目

数据对象定义之xxDo和xxVo

在这里插入图片描述

跨项目依赖问题

问题描述:
	项目a的子项目a1,项目b的子项目b1,a1想使用b1,如何实现?
实现:
	需要将b1包打包;
		打开b1所在项目,在idea的终端运行mvn clean install 命令,将生成的jar包放入本地maven的repository文件夹中;

最后

项目示例基于spring boot 最新版本(2.1.9)实现Spring BootSpring Cloud 学习示例,将持续更新…… 在基于Spring BootSpring Cloud 分布微服务开发过程中,根据实际项目环境,需要选择、集成符合项目需求的各种组件和积累各种解决方案。基于这样的背景下,我开源了本示例项目,方便大家快速上手Spring BootSpring Cloud 。 每个示例都带有详细的介绍文档、作者在使用过程中踩过的坑、解决方案及参考资料,方便快速上手为你提供学习捷径,少绕弯路,提高开发效率。 有需要写关于spring bootspring cloud示例,可以给我提issue哦 ## 项目介绍 spring boot demo 是一个Spring BootSpring Cloud的项目示例,根据市场主流的后端技术,共集成了30+个demo,未来将持续更新。该项目包含helloworld(快速入门)、web(ssh项目快速搭建)、aop(切面编程)、data-redis(redis缓存)、quartz(集群任务实现)、shiro(权限管理)、oauth2(四种认证模式)、shign(接口参数防篡改重放)、encoder(用户密码设计)、actuator(服务监控)、cloud-config(配置中心)、cloud-gateway(服务网关)、email(邮件发送)、cloud-alibaba(微服务全家桶)等模块 ### 开发环境 - JDK1.8 + - Maven 3.5 + - IntelliJ IDEA ULTIMATE 2019.1 - MySql 5.7 + ### Spring Boot 模块 模块名称|主要内容 ---|--- helloworld|[spring mvc,Spring Boot项目创建,单元测试](https://github.com/smltq/spring-boot-demo/blob/master/helloworld/HELP.md) web|[ssh项目,spring mvc,过滤器,拦截器,监视器,thymeleaf,lombok,jquery,bootstrap,mysql](https://github.com/smltq/spring-boot-demo/blob/master/web/HELP.md) aop|[aop,正则,前置通知,后置通知,环绕通知](https://github.com/smltq/spring-boot-demo/blob/master/aop/HELP.md) data-redis|[lettuce,redis,session redis,YAML配置,连接池,对象存储](https://github.com/smltq/spring-boot-demo/blob/master/data-redis/HELP.md) quartz|[Spring Scheduler,Quartz,分布式调度,集群,mysql持久化等](https://github.com/smltq/spring-boot-demo/blob/master/quartz/HELP.md) shiro|[授权、认证、加解密、统一异常处理](https://github.com/smltq/spring-boot-demo/blob/master/shiro/HELP.md) sign|[防篡改、防重放、文档自动生成](https://github.com/smltq/spring-boot-demo/blob/master/sign/HELP.md) security|[授权、认证、加解密、mybatis plus使用](https://github.com/smltq/spring-boot-demo/blob/master/security/HELP.md) mybatis-plus-generator|[基于mybatisplus代码自动生成](https://github.com/smltq/spring-boot-demo/blob/master/mybatis-plus-generator) mybatis-plus-crud|[基于mybatisplus实现数据库增、册、改、查](https://github.com/smltq/spring-boot-demo/blob/master/mybatis-plus-crud) encoder|[主流加密算法介绍、用户加密算法推荐](https://github.com/smltq/spring-boot-demo/blob/master/encoder/HELP.md) actuator|[autuator介绍](https://github.com/smltq/spring-boot-demo/blob/master/actuator/README.md) admin|[可视化服务监控、使用](https://github.com/smltq/spring-boot-demo/blob/master/admin/README.md) security-oauth2-credentials|[oauth2实现密码模式、客户端模式](https://github.com/smltq/spring-boot-demo/blob/master/security-oauth2-credentials/README.md) security-oauth2-auth-code|[基于spring boot实现oauth2授权模式](https://github.com/smltq/spring-boot-demo/blob/master/security-oauth2-auth-code/README.md) mybatis-multi-datasource|[mybatis、数据库集群、读写分离、读库负载均衡](https://github.com/smltq/spring-boot-demo/blob/master/mybatis-multi-datasource) template-thymeleaf|[thymeleaf实现应用国际化示例](https://github.com/smltq/spring-boot-demo/blob/master/template-thymeleaf) mq-redis|[redis之mq实现,发布订阅模式](https://github.com/smltq/spring-boot-demo/blob/master/mq-redis) email|[email实现邮件发送](https://github.com/smltq/spring-boot-demo/blob/master/email) jGit|[java调用git命令、jgit使用等](https://github.com/smltq/spring-boot-demo/blob/master/jGit) webmagic|[webmagic实现某电影网站爬虫示例](https://github.com/smltq/spring-boot-demo/blob/master/webmagic) netty|[基于BIO、NIO等tcp服务器搭建介绍](https://github.com/smltq/spring-boot-demo/blob/master/netty) ### Spring Cloud 模块 模块名称|主要内容 ---|--- cloud-oauth2-auth-code|[基于spring cloud实现oath2授权模式](https://github.com/smltq/spring-boot-demo/blob/master/cloud-oauth2-auth-code) cloud-gateway|[API主流网关、gateway快速上手](https://github.com/smltq/spring-boot-demo/blob/master/cloud-gateway) cloud-config|[配置中心(服务端、客户端)示例](https://github.com/smltq/spring-boot-demo/blob/master/cloud-config) cloud-feign|[Eureka服务注册中心、负载均衡、声明式服务调用](https://github.com/smltq/spring-boot-demo/blob/master/cloud-feign) cloud-hystrix|[Hystrix服务容错、异常处理、注册中心示例](https://github.com/smltq/spring-boot-demo/blob/master/cloud-hystrix) cloud-zuul|[zuul服务网关、过滤器、路由转发、服务降级、负载均衡](https://github.com/smltq/spring-boot-demo/blob/master/cloud-zuul) cloud-alibaba|[nacos服务中心、配置中心、限流等使用(系列示例整理中...)](https://github.com/smltq/spring-boot-demo/blob/master/cloud-alibaba) #### Spring Cloud Alibaba 模块 模块名称|主要内容 ---|--- nacos|[Spring Cloud Alibaba(一)如何使用nacos服务注册和发现](https://github.com/smltq/spring-boot-demo/blob/master/cloud-alibaba/README1.md) config|[Spring Cloud Alibaba(二)配置中心多项目、多配置文件、分目录实现](https://github.com/smltq/spring-boot-demo/blob/master/cloud-alibaba/README2.md) Sentinel|[Spring Cloud Alibaba(三)Sentinel之熔断降级](https://github.com/smltq/spring-boot-demo/blob/master/cloud-alibaba/README3.md) Dubbo|[Spring Cloud Alibaba(四)Spring Cloud与Dubbo的融合](https://github.com/smltq/spring-boot-demo/blob/master/cloud-alibaba/README4.md) RocketMQ|[Spring Cloud Alibaba(五)RocketMQ 异步通信实现](https://github.com/smltq/spring-boot-demo/blob/master/cloud-alibaba/README5.md) ### 其它 模块名称|主要内容 ---|--- leetcode|[力扣题解目录](https://github.com/smltq/spring-boot-demo/blob/master/leetcode) ## Spring Boot 概述 Spring Boot简化了基于Spring的应用开发,通过少量的代码就能创建一个独立的、产品级别的Spring应用。 Spring BootSpring平台及第三方库提供开箱即用的设置,这样你就可以有条不紊地开始。多数Spring Boot应用只需要很少的Spring配置。 Spring Boot是由Pivotal团队提供的全新框架,其设计目的是用来简化新Sprin
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值