SpringCloud Gateway 集成 Sentinel 详解 及实现动态监听Nacos规则配置实时更新流控规则

目录
    • 一、前言
    • 二、版本选择和适配
      • 2.1、本文使用各组件版本
      • 2.2、官方推荐版本
    • 三、部署sentinel-dashboard
      • 3.1、下载 sentinel-dashboard jar包
      • 3.2、启动 sentinel-dashboard
    • 四、Gateway 集成 Sentinel实现控制台配置流控规则测试
      • 4.1、添加Gateway 集成 Sentinel 包
      • 4.2、添加 Gateway 服务启动JVM参数
        • 4.2.1、配置说明
        • 4.2.2、启动说明
          • 4.2.2.1、使用 jar 包启动Gateway添加JVM启动参数
          • 4.2.2.2、IDEA中配置JVM启动参数(IDEA版本2022.2.1)
      • 4.3、启动 Gateway 注册到 Sentinel-dashboard 实现接口流控规则动态配置
        • 4.3.1、启动 Gateway 注册到 Sentinel-dashboard
        • 4.3.2、通过 Sentinel-dashboard 配置指定接口限流
      • 4.4、注意事项
    • 五、Gateway 集成 Sentinel 常用配置
      • 5.1、热加载
      • 5.2、降级处理配置(这里提供代码配置和使用配置文件配置)
        • 5.2.1、通过代码配置(配置文件配置比代码配置优先级高)
        • 5.2.2、通过配置文件配置
    • 六、自定义本地加载流控规则
      • 6.1、通过代码加载流控规则
      • 6.2、通过本地配置文件加载流控规则
        • 6.2.1、API分组规则json文件编写(gateway-sentinel-api-groups.json)
        • 6.2.2、流控规则json文件编写(gateway-sentinel-flow-rules.json)
        • 6.2.3、配置文件配置加载API分组和流控规则json文件
    • 七、动态监听Nacos规则配置实时更新流控规则实现(推荐)
      • 7.1、添加sentinel集成nacos包
      • 7.2、Nacos配置中心添加API分组规则json(gateway-sentinel-api-groups)
      • 7.3、Nacos配置中心添加流控规则json(gateway-sentinel-flow-rules)
      • 7.4、配置文件配置加载Nacos配置中心API分组和流控规则json
      • 7.5、测试效果

一、前言

SentinelSpringCloud Alibaba 家族的服务保护组件,很多项目在前中期没有遇到流量突增不太注意服务保护的重要性,当流量突增打爆应用服务或数据库时束手无策,可以不配置流控规则,但是需要时一定可以热加载使用,本文会对集成Sentinel以及动态拉取Nacos配置规则实现热加载流控规则进行讲解。

官网地址

二、版本选择和适配

使用 SpringCloud Alibaba 家族组件,要注意一下版本兼容问题,避免出现一些奇怪的问题,这里会说明本文使用的各组件版本,以及 SpringCloud Alibaba 推荐的各版本适配。

2.1、本文使用各组件版本

部分组件对版本兼容要求其实没有那么高,比如Nacos,不一定要按照官方推荐版本,差几个小版本没有什么影响,我本地使用的一直是Nacos2.0.2,代码集成实现基本都一样。

JDK:1.8.0
Spring-Boot:2.3.12.RELEASE
Spring-Cloud:Hoxton.SR12
Spring-Cloud-Alibaba:2.2.9.RELEASE
Nacos:2.0.2
Sentinel:1.8.5

2.2、官方推荐版本

官方版本说明
在这里插入图片描述

三、部署sentinel-dashboard

3.1、下载 sentinel-dashboard jar包

这里使用sentinel-dashboard-1.8.5,这里提供两个下载地址,需要其它版本可以自行去github下载。
github下载地址
百度网盘地址
在这里插入图片描述

3.2、启动 sentinel-dashboard
java -Dserver.port=8180 -Dsentinel.dashboard.auth.username=sentinel -Dsentinel.dashboard.auth.password=123456 -Dcsp.sentinel.dashboard.server=localhost:8180 -Dproject.name=sentinel-dashboard -jar sentinel-dashboard-1.8.5.jar
  • -Dserver.port=8180
    sentine 服务控制台端口
  • -Dsentinel.dashboard.auth.username=sentinel
    sentine 控制台登录账号,不设置默认sentinel
  • -Dsentinel.dashboard.auth.password=123456
    sentine 控制台登录密码,不设置默认sentinel
  • -Dcsp.sentinel.dashboard.server=localhost:8180
    将控制台自身注册到server
  • -Dproject.name=sentinel-dashboard
    控制台服务自己项目名称

在这里插入图片描述
在这里插入图片描述

四、Gateway 集成 Sentinel实现控制台配置流控规则测试

4.1、添加Gateway 集成 Sentinel 包

在原有网关项目基础上添加上这两个包,这两个包会将gateway集成sentinel,并且默认是自动配置的,无需手动配置。

        <dependency>
            <groupId>com.alibaba.cloud</groupId>
            <artifactId>spring-cloud-alibaba-sentinel-gateway</artifactId>
        </dependency>
        <dependency>
            <groupId>com.alibaba.cloud</groupId>
            <artifactId>spring-cloud-starter-alibaba-sentinel</artifactId>
        </dependency>
4.2、添加 Gateway 服务启动JVM参数
4.2.1、配置说明

Gateway 连接 Sentinel 控制台的配置,Sentinel1.7.0 版本以下不支持配置文件配置,推荐直接使用JVM参数配置。

  • 添加JVM启动参数:
    -Dcsp.sentinel.dashboard.server=127.0.0.1:8180
    -Dcsp.sentinel.api.port=18719
    -Dproject.name=kerwin-gateway
    -Dcsp.sentinel.app.type=1

  • 参数说明:
    -Dcsp.sentinel.dashboard.server:指定控制台地址和端口。
    -Dproject.name:在sentinel控制台中展示的项目名称。
    -Dcsp.sentinel.api.port:指定客户端监控 API 的端口(默认是 8719),如控制台修改规则,则会向该端口推送规则信息。
    -Dcsp.sentinel.app.type:从 1.6.3 版本开始,控制台支持网关流控规则管理。该启动参数设置成1会将您的服务标记为 API Gateway,在接入控制台时您的服务会自动注册为网关类型,然后您即可在控制台配置网关规则和 API 分组。

4.2.2、启动说明

这里提供服务打成jar包启动和使用IDEA开发工具添加JVM参数启动示例。

4.2.2.1、使用 jar 包启动Gateway添加JVM启动参数
java -Dcsp.sentinel.dashboard.server=127.0.0.1:8180 -Dcsp.sentinel.api.port=18719 -Dproject.name=kerwin-gateway -Dcsp.sentinel.app.type=1 -jar kerwin-gateway.jar
4.2.2.2、IDEA中配置JVM启动参数(IDEA版本2022.2.1)

不同版本IDEA可以配置入口不同,有需要可以自己查询
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

4.3、启动 Gateway 注册到 Sentinel-dashboard 实现接口流控规则动态配置

这里需要注意,Gateway 集成 Sentinel-dashboard 默认是懒加载的,需要调用一次接口才能注册到 Sentinel-dashboard,也可以直接在 Gateway 中配置成热加载,添加spring.cloud.sentinel.eager:true实现服务器启动了自动心跳注册。

4.3.1、启动 Gateway 注册到 Sentinel-dashboard

在这里插入图片描述

4.3.2、通过 Sentinel-dashboard 配置指定接口限流

这里需要注意,这个流控规则是按照组级别来的,一个组内所有匹配规则会共用一个阈值,如果需要在网关应用配置单独接口流控规则目前来看只能配置多个分组,然后单独配置规则。

  • 1、新增 API 分组
    在这里插入图片描述

  • 2、自定义分组内 API 匹配规则
    在这里插入图片描述

  • 3、新增网关流控规则
    在这里插入图片描述

  • 4、配置网关流控规则(这里需要注意,这个流控规则是按照组级别来的,一个组内所有匹配规则共用一个阈值)
    在这里插入图片描述

  • 5、测试限流规则
    快速请求两次可以看到服务端响应 Blocked by Sentinel: ParamFlowException,响应内容也是可以自定义的,这个会在后面说明。
    在这里插入图片描述

PS1秒内同时请求一次 /user/info 接口 和 /user/list 接口,也会响应Blocked by Sentinel: ParamFlowException,因为同一个分组共用一个阈值,如果要单独配置某一个接口目前看只能整多个分组。

4.4、注意事项

需要注意:如果不做特殊处理,通过Sentinel控制台配置的规则在应用服务重启后就没了,通过Sentinel控制台配置流控规则的本质其实就是将编辑好的规则加载到应用服务缓存中,并不会进行持久化,如果想要持久化Sentinel控制台配置的规则需要特殊处理,后续会进行说明。

五、Gateway 集成 Sentinel 常用配置

5.1、热加载
spring:
  cloud:
    sentinel:
      # 设置sentinel为热加载 默认为false
      eager: true
5.2、降级处理配置(这里提供代码配置和使用配置文件配置)
5.2.1、通过代码配置(配置文件配置比代码配置优先级高)
import com.alibaba.csp.sentinel.adapter.gateway.sc.callback.BlockRequestHandler;
import com.alibaba.csp.sentinel.adapter.gateway.sc.callback.GatewayCallbackManager;
import org.springframework.context.annotation.Configuration;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.web.reactive.function.server.ServerResponse;
import org.springframework.web.server.ServerWebExchange;
import reactor.core.publisher.Mono;

import javax.annotation.PostConstruct;

@Configuration
public class SentinelGatewayConfiguration {

    /**
     * 自定义降级处理响应
     */
    @PostConstruct
    public void init(){
        GatewayCallbackManager.setBlockHandler(new BlockRequestHandler() {
            @Override
            public Mono<ServerResponse> handleRequest(ServerWebExchange exchange, Throwable throwable) {
                return ServerResponse.status(HttpStatus.OK).contentType(MediaType.APPLICATION_JSON).bodyValue("{"code":500,"msg":"代码配置-被限流了!"}");
            }
        });
    }
}

在这里插入图片描述

5.2.2、通过配置文件配置
spring:
  cloud:
    sentinel:
      # 设置sentinel为热加载 默认为false
      eager: true
      scg:
        # 降级处理配置 也可以在代码中实现
        fallback:
          # 指定降级处理的模式为返回响应,也可以配置成重定向redirect,配置重定向需要指定重定向地址
          mode: 'response'
          response-status: 200
          response-body: '{"code":500,"msg":"配置文件配置-被限流了!"}'
          # mode 为 redirect 时使用
          redirect: 'https://blog.csdn.net/weixin_44606481'

在这里插入图片描述

六、自定义本地加载流控规则

因为 sentinel-dashboard 不会持久化手动配置的流控规则,一般情况下我们都会提前配置一些我们需要的规则,可以通过代码或者配置文件配置。

6.1、通过代码加载流控规则

Sentinel 的API管理存储在 GatewayApiDefinitionManager 类中,流控规则存储在 GatewayRuleManager 类中,添加好自己需要的配置即可。

import com.alibaba.csp.sentinel.adapter.gateway.common.SentinelGatewayConstants;
import com.alibaba.csp.sentinel.adapter.gateway.common.api.ApiDefinition;
import com.alibaba.csp.sentinel.adapter.gateway.common.api.ApiPathPredicateItem;
import com.alibaba.csp.sentinel.adapter.gateway.common.api.ApiPredicateItem;
import com.alibaba.csp.sentinel.adapter.gateway.common.api.GatewayApiDefinitionManager;
import com.alibaba.csp.sentinel.adapter.gateway.common.rule.GatewayFlowRule;
import com.alibaba.csp.sentinel.adapter.gateway.common.rule.GatewayRuleManager;
import org.springframework.context.annotation.Configuration;

import javax.annotation.PostConstruct;
import java.util.HashSet;
import java.util.Set;

@Configuration
public class SentinelGatewayRuleConfiguration {

    @PostConstruct
    public void initRule(){
        // 加载根据路由 ID 配置限流规则
        this.initGatewayFlowRules();
        // 加载根据API分组配置限流规则
        this.initApiDefinitions();
    }

    private void initGatewayFlowRules() {
        // 存储限流规则的集合
        Set<GatewayFlowRule> rules = GatewayRuleManager.getRules();
        if(rules == null){
            rules = new HashSet<>();
        }
        // 根据路由 ID 配置限流规则
        GatewayFlowRule rule1 = new GatewayFlowRule("kerwin-user")
                .setResourceMode(SentinelGatewayConstants.RESOURCE_MODE_ROUTE_ID)
                .setCount(1) // QPS阈值
                .setIntervalSec(1); // 间隔
        rules.add(rule1);
        // 加载限流规则
        GatewayRuleManager.loadRules(rules);
    }

    private void initApiDefinitions() {
        Set<ApiDefinition> apiDefinitions = GatewayApiDefinitionManager.getApiDefinitions();
        if(apiDefinitions == null){
            apiDefinitions = new HashSet<>();
        }
        // 创建一个 API 分组
        ApiDefinition apiDefinition1 = new ApiDefinition("user服务API组");
        // API 分组 URL 匹配规则
        Set<ApiPredicateItem> apiPathPredicateItems = new HashSet<>();
        // 添加精确匹配 匹配为 /api-user/user/info 的url
        apiPathPredicateItems.add(new ApiPathPredicateItem().setPattern("/api-user/user/info")
                        .setMatchStrategy(SentinelGatewayConstants.URL_MATCH_STRATEGY_EXACT));
        // 添加前缀匹配 用于匹配以 /api-user/user 开头的URL
        apiPathPredicateItems.add(new ApiPathPredicateItem().setPattern("/api-user/user/**")
                .setMatchStrategy(SentinelGatewayConstants.URL_MATCH_STRATEGY_PREFIX));
//        // 添加正则匹配 用于匹配以 list 结尾的 URL
//        apiPathPredicateItems.add(new ApiPathPredicateItem().setPattern("^.*list$")
//                .setMatchStrategy(SentinelGatewayConstants.URL_MATCH_STRATEGY_REGEX));

        apiDefinition1.setPredicateItems(apiPathPredicateItems);
        apiDefinitions.add(apiDefinition1);

        // 根据 API 分组配置限流规则
        Set<GatewayFlowRule> rules = GatewayRuleManager.getRules();
        if(rules == null){
            rules = new HashSet<>();
        }
        GatewayFlowRule rule1 = new GatewayFlowRule(apiDefinition1.getApiName())
                .setResourceMode(SentinelGatewayConstants.RESOURCE_MODE_CUSTOM_API_NAME)
                .setCount(1) // QPS阈值
                .setIntervalSec(1); // 间隔
        rules.add(rule1);

        // 加载 API 分组定义
        GatewayApiDefinitionManager.loadApiDefinitions(apiDefinitions);
        // 加载限流规则
        GatewayRuleManager.loadRules(rules);
    }
}

项目启动后可以在Sentinel控制台看到代码配置的API分组和流控规则。

6.2、通过本地配置文件加载流控规则

通过代码手动配置会比较麻烦而且不易调整,Gateway集成Sentinel包提供了通过配置文件加载API分组和流控规则实现,这里会将API分组和流控规则都分别写入不同的json文件中,交由对于实现类去进行加载。

6.2.1、API分组规则json文件编写(gateway-sentinel-api-groups.json)

resource目录创建gateway-sentinel-api-groups.json将API分组规则内容填进去。

[
  {
    "apiName": "user服务API组",
    "predicateItems": [
      {
        "pattern": "/api-user/user/info",
        "matchStrategy": 0
      },
      {
        "pattern": "/api-user/user/**",
        "matchStrategy": 1
      }
    ]
  }
]

解释:

  • apiName:
    字符串,代表 API 组名称,这里是 “user服务API组”,用于统一管理相关 API。
  • predicateItems:
    数组,包含多个 predicateItem 对象,用于描述 API 的匹配模式。
  • predicateItem 内部元素:
    • pattern:
      字符串,使用不同风格的表达式。
      例如,“/api-user/user/info” 精确匹配该路径;“/api-user/user/**” 匹配 /api-user/user/ 下的所有路径(包括子路径)。
    • matchStrategy:
      整数,匹配策略:
      0:精确匹配,路径需与 pattern 完全一致。
      1:前缀匹配,路径以 pattern 开头即可。
      2:正则匹配,使用 pattern 作为正则表达式进行匹配。
6.2.2、流控规则json文件编写(gateway-sentinel-flow-rules.json)

resource目录创建gateway-sentinel-flow-rules.json将流控规则内容填进去。

[
  {
    "resource": "user服务API组",
    "resourceMode": 1,
    "count": 1,
    "intervalSec": 1,
    "burst": 0,
    "paramItem": null,
    "controlBehavior": 0,
    "maxQueueingTimeoutMs": 0
  },
  {
    "resource": "kerwin-user",
    "resourceMode": 0,
    "count": 1,
    "intervalSec": 1,
    "burst": 0,
    "paramItem": null,
    "controlBehavior": 0,
    "maxQueueingTimeoutMs": 0
  }
]

字段解释:

  • resource:资源名称,用于标识要进行流控的目标。可以是路由 ID、自定义 API 分组名称等。在网关场景中,资源可以代表一个具体的路由或者一组路由的集合。
  • resourceMode:
    • 0:代表资源模式,对应 SentinelGatewayConstants.RESOURCE_MODE_ROUTE_ID,表示基于 Route ID 进行资源匹配。
    • 1:API分组模式,对应 SentinelGatewayConstants.RESOURCE_MODE_CUSTOM_API_NAME,标识基于API分组进行资源匹配。
  • count:流控阈值,根据 grade 字段的不同,其代表的意义也不同。如果 grade 为 QPS 限流,count 表示每秒允许通过的请求数量;如果 grade 为并发线程数限流,count 表示允许的最大并发线程数。
  • grade:流控阈值类型,取值有两种。1 表示 QPS(每秒查询率)限流,0 表示并发线程数限流。
  • intervalSec:统计时间窗口,单位为秒。表示在多长时间内统计请求数量以判断是否触发流控。
  • controlBehavior:流控效果,即当请求超过阈值时的处理方式
    • 0:快速失败,请求超过阈值时直接拒绝并抛出异常
    • 2:匀速排队,请求会进入队列,按照固定速率处理,避免流量突发
  • burst:仅在 controlBehavior 为 0(快速失败)时有效,表示突发流量容忍值。在短时间内允许超过阈值的额外请求数量,用于应对突发流量场景。
  • maxQueueingTimeoutMs:仅在 controlBehavior 为 2(匀速排队)时有效,表示请求在队列中的最大排队时间,单位为毫秒。超过该时间的请求将被拒绝。
6.2.3、配置文件配置加载API分组和流控规则json文件

在配置文件中添加API分组和流控规则读取数据源配置,这里省略了其它Sentinel配置需要可以看之前配置内容添加。

spring:
  cloud:
    sentinel:
      # 设置sentinel为热加载 默认为false
      eager: true
      # API分组&流控规则配置文件配置
      datasource:
        ds1:
          file:
            file: classpath:gateway-sentinel-api-groups.json
            ruleType: gw-api-group # 网关API分组
            dataType: json
        ds2:
          file:
            file: classpath:gateway-sentinel-flow-rules.json
            ruleType: gw-flow # 网关流控规则
            dataType: json

这里就不贴图了,配置完成后启动看看Sentinel控制台是否有初始化这些配置,要记得开启热加载。

七、动态监听Nacos规则配置实时更新流控规则实现(推荐)

通过Nacos配置中心动态拉取加载流控规则和本地配置文件配置是类似的,编写的规则json是一样的,只是需要指定一下加载的数据源为Nacos读取,并且已经实现了动态加载,在Nacos配置中心修改规则会进行实时同步。

7.1、添加sentinel集成nacos包

sentinel读取nacos配置需要添加这个适配包。

        <dependency>
            <groupId>com.alibaba.csp</groupId>
            <artifactId>sentinel-datasource-nacos</artifactId>
        </dependency>
7.2、Nacos配置中心添加API分组规则json(gateway-sentinel-api-groups)

配置的内容和本文6.2.1中一致。
在这里插入图片描述

7.3、Nacos配置中心添加流控规则json(gateway-sentinel-flow-rules)

配置的内容和本文6.2.2中一致。
在这里插入图片描述

7.4、配置文件配置加载Nacos配置中心API分组和流控规则json
spring:
  cloud:
    sentinel:
      # 设置sentinel为热加载 默认为false
      eager: true
      # API分组&流控规则配置文件配置
      datasource:
        ds1:
          nacos:
            server-addr: 172.16.8.169:8848
            data-id: gateway-sentinel-api-groups
            namespace: springcloud-component-example
            group-id: DEFAULT_GROUP
            username: nacos
            password: nacos
            data-type: json
            rule-type: gw-api-group
        ds2:
          nacos:
            server-addr: 172.16.8.169:8848
            data-id: gateway-sentinel-flow-rules
            namespace: springcloud-component-example
            group-id: DEFAULT_GROUP
            username: nacos
            password: nacos
            data-type: json
            rule-type: gw-flow
7.5、测试效果
  • 1、启动网关服务,查看注册API分组和流控规则
    在这里插入图片描述
  • 2、Nacos配置中心修改流控规则
    在这里插入图片描述
  • 3、查看sentinel控制台同步情况
    在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/979300.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

星闪开发入门之常见报错整理(一)

系列文章目录 星闪开发入门之常见报错整理&#xff08;一&#xff09; 文章目录 系列文章目录前言一、ComX open fail, please check com is busy or not exist二、‌CMake下载失败三、配置文件出现语法错误四、路径过长导致编译报错五、ninja: build stopped: subcommand fai…

建筑兔零基础人工智能自学记录33|基础知识1

插入学习一下一些基础概念&#xff1a; 1、基本概念 人工智能&#xff1a;让机器像人一样思考。机器学习ML&#xff1a;计算机获取知识的过程。深度学习&#xff1a;机器的一种思考方式&#xff08;借助神经网络&#xff09;。 三者关系 2、机器学习的方式 监督学习&#x…

GPT-4.5 怎么样?如何升级使用ChatGPTPlus/Pro? GPT-4.5设计目标是成为一款非推理型模型的巅峰之作

GPT-4.5 怎么样&#xff1f;如何升级使用ChatGPTPlus/Pro? GPT-4.5设计目标是成为一款非推理型模型的巅峰之作 今天我们来说说上午发布的GPT-4.5&#xff0c;接下来我们说说GPT4.5到底如何&#xff0c;有哪些功能&#xff1f;有哪些性能提升&#xff1f;怎么快速使用到GPT-4.…

yolov8 目标追踪 (源码 +效果图)

1.在代码中 增加了s键开始追踪 e键结束追踪 显示移动距离(代码中可调标尺和像素的比值 以便接近实际距离) 2.绘制了监测区域 只在区域内的检测 3.规定了检测的类别 只有人类才绘制轨迹 import osimport cv2 from ultralytics import YOLO from collections import defaultdic…

Pytorch中的主要函数

目录 一、torch.manual_seed(seed)二、torch.cuda.manual_seed(seed)三、torch.rand(*size, outNone, dtypeNone, layouttorch.strided, deviceNone, requires_gradFalse)四、给大家写一个常用的自动选择电脑cuda 或者cpu 的小技巧五、torch.version.cuda&#xff1b;torch.bac…

PT2025 单触控双输出 LED 调光 IC

1. 产品概述 PT2025 是一款单键电容式触摸控制 ASIC &#xff0c;支持单通道触摸输入和单路 / 双路 PWM 输出&#xff0c;可 引脚配置 4 种模式。主要应用于触摸卫浴镜开关盒&#xff0c;具有介质自适应、高抗干扰、宽工作电压范 围、灯光无频闪、外围器件少的突出优…

Python基于机器学习的微博舆情情感分析系统,微博评论情感分析可视化系统(全新升级)

大家好&#xff0c;今天为大家带来的是Python基于机器学习的微博舆情情感分析系统&#xff0c;微博评论情感分析可视化系统&#xff0c;这个系统在原本的系统上进行优化升级。 算法从开源框架的 snlow &#xff0c;到支持机器学习的 lstm 算法可以手动输入语句&#xff0c;进行…

【02】Cocos游戏开发引擎从0开发一款游戏-cocos项目目录结构熟悉-调试运行项目-最重要的assets资源文件认识-场景sense了解-优雅草卓伊凡

【02】Cocos游戏开发引擎从0开发一款游戏-cocos项目目录结构熟悉-调试运行项目-最重要的assets资源文件认识-场景sense了解-优雅草卓伊凡 开发背景 接下来我们直接打开我们的项目开始进一步操作&#xff0c; 实战开发 导入项目 我把得到的项目解压到本地&#xff0c;我们开…

unity pico开发 三 移动 旋转 传送

文章目录 LocomtionSystem平滑移动转身碰撞体随相机改变身高传送添加射线两种传送区域TeleportationAreaTeleportationArea 美化传送射线 LocomtionSystem 在XR Origin上添加LocomtionSystem脚本&#xff0c;并拖拽XR Origin属性 这是移动的基础 平滑移动 在XR Origin上添加…

C语言整体梳理-基础篇-结构体

结构体详解 1.1结构体是什么&#xff1f; 结构体是一些值的集合&#xff0c;这些值成为成员变量&#xff0c;结构体的每个成员可以是不同类型的变量。 数组是相同类型的元素组成的集合&#xff0c;结构体可以是不同类型元素组成的集合。 1.2结构体的声明 1.2.1常规声明 s…

深度解读 AMS1117:从电气参数到应用电路的全面剖析

在电子设备的电源管理领域&#xff0c;线性稳压器扮演着至关重要的角色&#xff0c;而 AMS1117 凭借其出色的性能和广泛的适用性&#xff0c;成为众多工程师的热门选择。本文将依据相关资料&#xff0c;对 AMS1117 的特性、应用、电气参数等方面进行详细解读。 一、功能特性概…

LabVIEW中交叉关联算法

交叉关联算法通过统计多通道信号间的相关性&#xff0c;抑制各通道独立的本底噪声&#xff0c;保留共有的有效信号成分。其数学本质为对多个通道信号进行两两相乘并累加&#xff0c;最终通过归一化处理得到降噪后的输出信号。 这个VI演示了如何在LabVIEW中执行信号的互相关分析…

SAP-ABAP:SAP数据库视图(Database View)详解-创建

在SAP系统中&#xff0c;数据库视图&#xff08;Database View&#xff09; 是一种基于物理数据库表的虚拟表&#xff0c;通过关联多个表&#xff08;使用INNER JOIN&#xff09;生成逻辑数据集。它存储在数据库中&#xff0c;但本身不存储数据&#xff0c;仅通过查询动态生成结…

GPT-4.5来了

https://chat.xutongbao.top/

Vue3+Node/Express支付宝沙箱支付与确认支付

Vue3Node/Express支付宝沙箱支付与确认支付 支付宝沙箱配置进入沙箱选择自定义密钥 密钥工具下载生成密钥格式转换 自定义密钥设置Express安装依赖项目目录创建alipay.js请求&#xff08;打开支付&#xff09;代码router/pay.jsapp.js 前端代码前端封装接口前端调用 实现支付查…

Java数据结构第十四期:走进二叉树的奇妙世界(三)

专栏&#xff1a;数据结构(Java版) 个人主页&#xff1a;手握风云 目录 一、二叉树OJ练习题 1.1. 相同的树 1.2. 另一棵树的子树 1.3. 翻转二叉树 1.4. 平衡二叉树 1.5. 对称二叉树 一、二叉树OJ练习题 1.1. 相同的树 判断两棵树是否相同&#xff0c;我们是否只能遍历一…

生成式AI项目的生命周期

总结自视频&#xff08;吴恩达大模型入门课&#xff09;&#xff1a;9_13_generative-ai-project-lifecycle_哔哩哔哩_bilibili 生成周期如下图&#xff0c;包含四部分&#xff1a;任务范围&#xff08;Scope&#xff09;&#xff0c;选择大模型&#xff08;Select&#xff09…

基于POI的Excel下拉框自动搜索,包括数据验证的单列删除

目录 目标 例子 1.搜索下拉框页 2.数据源页 3.效果 代码以及注意事项 1.代码 2.注意事项 1.基于Excel的话&#xff0c;相当于加入了一个【数据验证】 2.代码中的一些方法说明 目标 期望在Excel利用代码创建具备自动搜索功能的下拉框 例子 1.搜索下拉框页 2.数据源…

一文弄懂TCP断开连接时候的四次挥手

部分内容来源&#xff1a;小林coding TCP四次挥手过程是怎样的 天下没有不散的宴席&#xff0c;对于 TCP 连接也是这样&#xff0c; TCP 断开连接是通过四次挥手方式 双方都可以主动断开连接&#xff0c;断开连接后主机中的「资源」将被释放&#xff0c;四次挥手的过程如下图…

DeepSeek-R1-Zero:基于基础模型的强化学习

注&#xff1a;此文章内容均节选自充电了么创始人&#xff0c;CEO兼CTO陈敬雷老师的新书《自然语言处理原理与实战》&#xff08;人工智能科学与技术丛书&#xff09;【陈敬雷编著】【清华大学出版社】 文章目录 DeepSeek大模型技术系列四DeepSeek大模型技术系列四》DeepSeek-…