Sharding-JDBC分布式事务详解与实战

news2024/11/18 23:45:00

在这里插入图片描述

🚀 ShardingSphere 🚀

🌲 算法刷题专栏 | 面试必备算法 | 面试高频算法 🍀
🌲 越难的东西,越要努力坚持,因为它具有很高的价值,算法就是这样✨
🌲 作者简介:硕风和炜,CSDN-Java领域优质创作者🏆,保研|国家奖学金|高中学习JAVA|大学完善JAVA开发技术栈|面试刷题|面经八股文|经验分享|好用的网站工具分享💎💎💎
🌲 恭喜你发现一枚宝藏博主,赶快收入囊中吧🌻
🌲 人生如棋,我愿为卒,行动虽慢,可谁曾见我后退一步?🎯🎯

🚀 ShardingSphere 🚀

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

🍔 目录

    • 🍀 一.Sharding-JDBC分布式事务详解
      • 🥦 1.1 本地事务 & 事务四大特性
      • 🥦 1.2 分布式事务
      • 🥦 1.3 LOCAL vs XA vs BASE
    • 🍀 二.Sharding-JDBC分布式事务实战
      • 🥦 2.1 数据环境准备
      • 🥦 2.2 创建SpringBoot程序 - 导入依赖
      • 🥦 2.3 创建SpringBoot程序 - 实体类
      • 🥦 2.4 创建SpringBoot程序 - 数据库Mapper接口 & 主启动类
      • 🥦 2.5 创建SpringBoot程序 - 数据加密配置文件
    • 🍀 三.Sharding-JDBC分布式事务实战测试
      • 🥦 3.1 编写测试接口 - 不做任何事务处理
      • 🥦 3.2 编写测试接口 - 添加本地事务处理注解
      • 🥦 3.3 编写测试接口 - 添加分布式事务XA
    • 🍀 四.总结
    • 💬 五.共勉

🍀 一.Sharding-JDBC分布式事务详解

🥦 1.1 本地事务 & 事务四大特性

数据库事务需要满足 ACID(原子性、一致性、隔离性、持久性)四个特性:

  • 原子性(Atomicity)指事务作为整体来执行,要么全部执行,要么全不执行;
  • 一致性(Consistency)指事务应确保数据从一个一致的状态转变为另一个一致的状态;
  • 隔离性(Isolation)指多个事务并发执行时,一个事务的执行不应影响其他事务的执行;
  • 持久性(Durability)指已提交的事务修改数据会被持久保存。

  在单一数据节点中,事务仅限于对单一数据库资源的访问控制,称之为本地事务。 几乎所有的成熟的关系型数据库都提供了对本地事务的原生支持。 但是在基于微服务的分布式应用环境下,越来越多的应用场景要求对多个服务的访问及其相对应的多个数据库资源能纳入到同一个事务当中,分布式事务应运而生。

  关系型数据库虽然对本地事务提供了完美的 ACID 原生支持。 但在分布式的场景下,它却成为系统性能的桎梏。 如何让数据库在分布式场景下满足 ACID 的特性或找寻相应的替代方案,是分布式事务的重点工作。

Sharding-JDBC分布式事务详解官方指导手册

🥦 1.2 分布式事务

  ShardingSphere 对外提供 begin/commit/rollback 传统事务接口,通过 LOCAL,XA,BASE 三种模式提供了分布式事务的能力。

  • LOCAL 事务:LOCAL 模式基于 ShardingSphere 代理的数据库 begin/commit/rolllback 的接口实现, 对于一条逻辑 SQL,ShardingSphere 通过 begin 指令在每个被代理的数据库开启事务,并执行实际 SQL,并执行 commit/rollback。 由于每个数据节点各自管理自己的事务,它们之间没有协调以及通信的能力,也并不互相知晓其他数据节点事务的成功与否。 在性能方面无任何损耗,但在强一致性以及最终一致性方面不能够保证。
  • XA 事务:采用的是 X/OPEN 组织所定义的 DTP 模型 所抽象的 AP(应用程序), TM(事务管理器)和 RM(资源管理器) 概念来保证分布式事务的强一致性。 其中 TM 与 RM 间采用 XA 的协议进行双向通信,通过两阶段提交实现。 与传统的本地事务相比,XA 事务增加了准备阶段,数据库除了被动接受提交指令外,还可以反向通知调用方事务是否可以被提交。 TM 可以收集所有分支事务的准备结果,并于最后进行原子提交,以保证事务的强一致性。
  • 柔性事务:如果将实现了 ACID 的事务要素的事务称为刚性事务的话,那么基于 BASE 事务要素的事务则称为柔性事务。 BASE 是基本可用、柔性状态和最终一致性这三个要素的缩写。
    • 基本可用(Basically Available)保证分布式事务参与方不一定同时在线;
    • 柔性状态(Soft state)则允许系统状态更新有一定的延时,这个延时对客户来说不一定能够察觉;
    • 最终一致性(Eventually consistent)通常是通过消息传递的方式保证系统的最终一致性。

在 ACID 事务中对隔离性的要求很高,在事务执行过程中,必须将所有的资源锁定。 柔性事务的理念则是通过业务逻辑将互斥锁操作从资源层面上移至业务层面。 通过放宽对强一致性要求,来换取系统吞吐量的提升。

🥦 1.3 LOCAL vs XA vs BASE

  基于 ACID 的强一致性事务基于 BASE 的最终一致性事务都不是银弹,只有在最适合的场景中才能发挥它们的最大长处。 Apache ShardingSphere 集成了 SEATA 作为柔性事务的使用方案。 可通过下表详细对比它们之间的区别,以帮助开发者进行技术选型。
在这里插入图片描述

🍀 二.Sharding-JDBC分布式事务实战

🥦 2.1 数据环境准备

191.168.10.132服务器上创建ljw_position_db0数据库,然后在数据库中创建dept职位表和dept_detail职位描述表 ;
191.168.10.133服务器上创建ljw_position_db1数据库,然后在数据库中创建dept职位表和dept_detail职位描述表 。
在这里插入图片描述

在这里插入图片描述

-- 职位表
CREATE TABLE `dept` (
  `Id` bigint(11) NOT NULL AUTO_INCREMENT,
  `name` varchar(256) DEFAULT NULL,
  `salary` varchar(50) DEFAULT NULL,
  `city` varchar(256) DEFAULT NULL,
  PRIMARY KEY (`Id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;

-- 职位描述表
CREATE TABLE `dept_detail` (
  `Id` bigint(11) NOT NULL AUTO_INCREMENT,
  `pid` bigint(11) NOT NULL DEFAULT '0',
  `description` text,
  PRIMARY KEY (`Id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;

在这里插入图片描述

🥦 2.2 创建SpringBoot程序 - 导入依赖

引入依赖 (注意: 在这里使用ShardingSphere4.1版本为案例进行分布式事务的实战)

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.2.5.RELEASE</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>

    <properties>
        <java.version>1.8</java.version>
    </properties>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
            <scope>runtime</scope>
        </dependency>

        <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
            <optional>true</optional>
        </dependency>

        <dependency>
            <groupId>org.mybatis.spring.boot</groupId>
            <artifactId>mybatis-spring-boot-starter</artifactId>
            <version>2.1.3</version>
        </dependency>

        <dependency>
            <groupId>com.baomidou</groupId>
            <artifactId>mybatis-plus-boot-starter</artifactId>
            <version>3.4.1</version>
        </dependency>

        <dependency>
            <groupId>com.baomidou</groupId>
            <artifactId>mybatis-plus-generator</artifactId>
            <version>3.4.1</version>
        </dependency>

        <dependency>
            <groupId>org.apache.shardingsphere</groupId>
            <artifactId>sharding-jdbc-spring-boot-starter</artifactId>
            <version>4.1.0</version>
        </dependency>

        <dependency>
            <groupId>org.apache.shardingsphere</groupId>
            <artifactId>sharding-core-common</artifactId>
            <version>4.1.0</version>
        </dependency>

        <dependency>
            <groupId>org.apache.commons</groupId>
            <artifactId>commons-lang3</artifactId>
            <version>3.10</version>
        </dependency>

        <dependency>
            <groupId>cn.hutool</groupId>
            <artifactId>hutool-all</artifactId>
            <version>5.5.8</version>
        </dependency>

        <dependency>
            <groupId>com.github.xiaoymin</groupId>
            <artifactId>knife4j-spring-boot-starter</artifactId>
            <version>2.0.5</version>
        </dependency>

        <dependency>
            <groupId>com.google.guava</groupId>
            <artifactId>guava</artifactId>
            <version>20.0</version>
            <scope>compile</scope>
        </dependency>


        <!-- XA模式-->
        <dependency>
            <groupId>org.apache.shardingsphere</groupId>
            <artifactId>sharding-transaction-xa-core</artifactId>
            <version>4.1.0</version>
        </dependency>

    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>
        </plugins>
    </build>

🥦 2.3 创建SpringBoot程序 - 实体类

与数据库表中对应的实体类

@TableName("dept")
@Data
@ToString
public class Dept{

    @TableId(type = IdType.AUTO)
    private Long id;

    private String name;

    private String salary;

    private String city;
}
@TableName("dept_detail")
@Data
@ToString
public class DeptDetail {
    
    @TableId(type = IdType.AUTO)
    private Long id;

    private Long pid;

    private String description;

}

🥦 2.4 创建SpringBoot程序 - 数据库Mapper接口 & 主启动类

编写对应的数据库持久层UserMapper接口

@Repository
public interface DeptMapper extends BaseMapper<Dept> {

}

@Repository
public interface DeptDetailMapper extends BaseMapper<DeptDetail> {

}

@Repository注解的类需要交给我们的Spring容器进行管理,因此需要我们在主启动类加上扫描接口的注解。

@SpringBootApplication
@MapperScan("com.ljw.mapper")
public class ShardingSphereApplication {

    public static void main(String[] args) {
        SpringApplication.run(ShardingSphereApplication.class, args);
    }
}

🥦 2.5 创建SpringBoot程序 - 数据加密配置文件

配置读写分离相关配置的信息

# 应用名称
spring.application.name=sharding-jdbc-transaction

# 打印SQl
spring.shardingsphere.props.sql-show=true

# 端口
server.port=8888


# 配置数据源
spring.shardingsphere.datasource.names=db0,db1

# 数据源1
spring.shardingsphere.datasource.db0.type=com.zaxxer.hikari.HikariDataSource
spring.shardingsphere.datasource.db0.driver-class-name=com.mysql.jdbc.Driver
spring.shardingsphere.datasource.db0.jdbc-url=jdbc:mysql://192.168.10.132:3306/ljw_position_db0?useUnicode=true&characterEncoding=utf-8&useSSL=false
spring.shardingsphere.datasource.db0.username=root
spring.shardingsphere.datasource.db0.password=root

# 数据源2
spring.shardingsphere.datasource.db1.type=com.zaxxer.hikari.HikariDataSource
spring.shardingsphere.datasource.db1.driver-class-name=com.mysql.jdbc.Driver
spring.shardingsphere.datasource.db1.jdbc-url=jdbc:mysql://192.168.10.133:3306/ljw_position_db1?useUnicode=true&characterEncoding=utf-8&useSSL=false
spring.shardingsphere.datasource.db1.username=root
spring.shardingsphere.datasource.db1.password=root

# 分库策略
spring.shardingsphere.sharding.tables.position.database-strategy.inline.sharding-column=id
spring.shardingsphere.sharding.tables.position.database-strategy.inline.algorithm-expression=db$->{id % 2}

spring.shardingsphere.sharding.tables.position_detail.database-strategy.inline.sharding-column=pid
spring.shardingsphere.sharding.tables.position_detail.database-strategy.inline.algorithm-expression=db$->{pid % 2}

# 分布式主键生成
spring.shardingsphere.sharding.tables.position.key-generator.column=id
spring.shardingsphere.sharding.tables.position.key-generator.type=SNOWFLAKE

spring.shardingsphere.sharding.tables.position_detail.key-generator.column=id
spring.shardingsphere.sharding.tables.position_detail.key-generator.type=SNOWFLAKE

🍀 三.Sharding-JDBC分布式事务实战测试

🥦 3.1 编写测试接口 - 不做任何事务处理

@RestController
@RequestMapping("/dept")
public class DeptController {

    @Autowired
    private DeptMapper deptMapper;

    @Autowired
    private DeptDetailMapper deptDetailMapper;

    @RequestMapping("/save")
    public String saveDept(){
        for(int i=0;i<6;i++){
            Dept dept = new Dept();
            dept.setName("Java高级开发工程师" + i);
            dept.setSalary("40K");
            dept.setCity("北京");
            deptMapper.insert(dept);
            // 注意 : 模拟出现 BUG -> 然后去数据库中验证数据是否插入!
            if(i == 4){
                throw new RuntimeException("模拟出现 BUG -> 然后去数据库中验证数据是否插入!");
            }
            DeptDetail deptDetail = new DeptDetail();
            deptDetail.setPid(dept.getId());
            deptDetail.setDescription("这是Java高级开发工程师具体的职位描述" + i);
            deptDetailMapper.insert(deptDetail);
        }
        return "Save Successfully!";
    }
}

启动项目打开浏览器,访问接口http://localhost:8888/dept/save,到数据库中验证数据!

在这里插入图片描述

程序出现异常,检查数据库, 发现数据库的数据插入了,但是数据是不完整。

在这里插入图片描述

🥦 3.2 编写测试接口 - 添加本地事务处理注解

主启动类添加@EnableTransactionManagement注解,开启声明式事务

@EnableTransactionManagement
@SpringBootApplication
@MapperScan("com.ljw.mapper")
public class ShardingSphereApplication {

    public static void main(String[] args) {
        SpringApplication.run(ShardingSphereApplication.class, args);
    }
}

方法上添加@Transactional注解

@RestController
@RequestMapping("/dept")
public class DeptController {

    @Autowired
    private DeptMapper deptMapper;

    @Autowired
    private DeptDetailMapper deptDetailMapper;

	@Transactional
    @RequestMapping("/save")
    public String saveDept(){
        for(int i=0;i<6;i++){
            Dept dept = new Dept();
            dept.setName("Java高级开发工程师" + i);
            dept.setSalary("40K");
            dept.setCity("北京");
            deptMapper.insert(dept);
            // 注意 : 模拟出现 BUG -> 然后去数据库中验证数据是否插入!
            if(i == 4){
                throw new RuntimeException("模拟出现 BUG -> 然后去数据库中验证数据是否插入!");
            }
            DeptDetail deptDetail = new DeptDetail();
            deptDetail.setPid(dept.getId());
            deptDetail.setDescription("这是Java高级开发工程师具体的职位描述" + i);
            deptDetailMapper.insert(deptDetail);
        }
        return "Save Successfully!";
    }
}

启动项目打开浏览器,访问接口http://localhost:8888/dept/save,到数据库中验证数据(项目启动之前要把数据库中原来的数据删除!)!

在这里插入图片描述

程序出现错误,检查数据库, 发现数据库中没有任何数据,说明数据发生了回滚的操作。

在这里插入图片描述

问题来了:
问题1: 为什么会出现回滚操作呢?此时是分布式环境呀? 难道@Transactional注解可以解决分布式事务吗?(@Transactional不能解决分布式事务)

  • Sharding-JDBC中的本地事务在以下两种情况是完全支持的:

    • 支持非跨库事务,比如仅分表、在单库中操作;
    • 支持因逻辑异常导致的跨库事务(这点非常重要),比如上述的操作,跨两个库插入数据,中间存在逻辑的错误哦!
  • 本地事务不支持的情况:

    • 不支持因网络、硬件异常导致的跨库事务;例如:同一事务中,跨两个库更新,更新完毕后、未提交之前,第一个库宕机,则只有第二个库数据提交。

      对于因网络、硬件异常导致的跨库事务无法支持很好理解,在分布式事务中无论是两阶段还是三阶段提交都是直接或者间接满足以下两个条件:

      ​ 1.有一个事务协调者 2.事务日志记录
      本地事务并未满足上述条件,自然是无法支持

问题2:为什么逻辑异常导致的跨库事务能够支持?

  • Sharding-JDBC中的一条SQL会经过改写,拆分成不同数据源的SQL,比如一条select语句,会按照其中分片键拆分成对应数据源的SQL,然后在不同数据源中的执行,最终会提交或者回滚。

🥦 3.3 编写测试接口 - 添加分布式事务XA

导入sharding-transaction-xa-core依赖

<!--XA模式-->
<dependency>
    <groupId>org.apache.shardingsphere</groupId>
    <artifactId>sharding-transaction-xa-core</artifactId>
    <version>4.1.0</version>
</dependency>

方法上添加@ShardingTransactionType(TransactionType.XA)注解

@RestController
@RequestMapping("/dept")
public class DeptController {

    @Autowired
    private DeptMapper deptMapper;

    @Autowired
    private DeptDetailMapper deptDetailMapper;

	@Transactional
	@ShardingTransactionType(TransactionType.XA)
    @RequestMapping("/save")
    public String saveDept(){
        for(int i=0;i<6;i++){
            Dept dept = new Dept();
            dept.setName("Java高级开发工程师" + i);
            dept.setSalary("40K");
            dept.setCity("北京");
            deptMapper.insert(dept);
            // 注意 : 模拟出现 BUG -> 然后去数据库中验证数据是否插入!
            if(i == 4){
                throw new RuntimeException("模拟出现 BUG -> 然后去数据库中验证数据是否插入!");
            }
            DeptDetail deptDetail = new DeptDetail();
            deptDetail.setPid(dept.getId());
            deptDetail.setDescription("这是Java高级开发工程师具体的职位描述" + i);
            deptDetailMapper.insert(deptDetail);
        }
        return "Save Successfully!";
    }
}

启动项目打开浏览器,访问接口http://localhost:8888/dept/save,到数据库中验证数据!(项目启动之前记得清除数据!)

在这里插入图片描述

程序出现错误,检查数据库, 发现数据库中没有任何数据,说明数据发生了回滚的操作。

在这里插入图片描述

🍀 四.总结

本篇文章主要讲解了Sharding-JDBC分布式事务详解与实战,实操过程非常重要,大家一定要动手亲自实践一下,必须掌握。下节预告,ShardingProxy实战,大家敬请期待呦!!!。

💬 五.共勉

最后,我想和大家分享一句一直激励我的座右铭,希望可以与大家共勉!

在这里插入图片描述

在这里插入图片描述

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

最强,Python接口自动化测试-自动化用例编写(超细整理)

目录&#xff1a;导读 前言一、Python编程入门到精通二、接口自动化项目实战三、Web自动化项目实战四、App自动化项目实战五、一线大厂简历六、测试开发DevOps体系七、常用自动化测试工具八、JMeter性能测试九、总结&#xff08;尾部小惊喜&#xff09; 前言 我们在百度搜索天…

从 7 分钟到 10 秒,Mybatis 批处理太强了!

这篇文章会一步一步带你从一个新手的角度慢慢揭开批处理的神秘面纱&#xff0c;对于初次写Mybatis批处理的同学可能会有很大的帮助&#xff0c;建议收藏点赞~ 处理批处理的方式有很多种&#xff0c;这里不分析各种方式的优劣&#xff0c;只是概述 ExecutorType.BATCH 这种的用…

打印插件 hiprint 使用、回单打印PDF保存本地、将列表数据打印成pdf文件保存到本地

文章底部有个人公众号&#xff1a;热爱技术的小郑。主要分享开发知识、有兴趣的可以关注一手。 前言 最近做了一个回单打印的功能、核心功能是、渲染出来的回单列表&#xff0c;用户可以浏览回单数据。可以同时勾选多个要打印的回单数据。将回单打印成pdf文件、同时下载保存到…

多线程进阶篇----常用方法

文章目录 线程状态线程方法线程礼让线程优先级守护线程 线程同步生产者消费者问题解决方式一&#xff1a;管程法方法二&#xff1a;标志位法 死锁总结 线程状态 线程有5种状态&#xff0c;新生态、就绪态、阻塞态、运行态、死亡态 在该图上&#xff0c;就绪状态和运行状态是一…

webpack联邦模块介绍及在dumi中使用问题整理

提示&#xff1a;文章写完后&#xff0c;目录可以自动生成&#xff0c;如何生成可参考右边的帮助文档 文章目录 前言一、ModuleFederationPlugin参数含义&#xff1f;二、如何在dumi中使用及问题整理1. 如何在dumi中使用(这个配置是好使的)2.相关问题整理2.1 问题12.2 问题2 总…

Android 之 动画合集之属性动画 -- 初见

本节引言&#xff1a; 本节给带来的是Android动画中的第三种动画——属性动画(Property Animation)&#xff0c; 记得在上一节Android 之 动画合集之补间动画为Fragment 设置过渡动画的时候&#xff0c;说过&#xff0c;App包和V4包下的Fragment调用setCustomAnimations()对应…

白皮书精彩案例分享 | 数字孪生:让治水用水有了“智慧大脑”

山有百藏而不言&#xff0c;水润万物而不语。中国属于大河文明&#xff0c;农业历来在经济中占主导地位&#xff0c;其中水利灌溉是保证农业生产和提高农业产量的重要因素。 然而&#xff0c;由于过去水利工程建设缺乏预见性&#xff0c;传统水利工程在作出贡献的同时&#xf…

JavaScript 简单实现观察者模式和发布订阅模式

JavaScript 简单实现观察者模式和发布订阅模式 1. 观察者模式1.1 如何理解1.2 代码实现 2. 发布订阅模式2.1 如何理解2.2 代码实现 1. 观察者模式 1.1 如何理解 概念&#xff1a;观察者模式定义对象间的一种一对多的依赖关系&#xff0c;当一个对象的状态发生改变时&#xff…

重生之我要学C++第三天(类和对象)

我重生了&#xff0c;这篇文章就深入的探讨C中的类和对象。 一.类的引入和定义 类的引入&#xff1a;在C语言中&#xff0c;结构体内部只能定义变量或者结构体&#xff0c;C中对结构体进行了升级->类&#xff0c;C的类中既可以定义变量&#xff0c;又可以定义函数。类中的变…

TSINGSEE青犀视频安防监控视频平台EasyCVR新增密码复杂度提示

智能视频监控平台TSINGSEE青犀视频EasyCVR可拓展性强、视频能力灵活、部署轻快&#xff0c;可支持的主流标准协议有国标GB28181、RTSP/Onvif、RTMP等&#xff0c;以及支持厂家私有协议与SDK接入&#xff0c;包括海康Ehome、海大宇等设备的SDK等&#xff0c;能对外分发RTSP、RTM…

BERT模型和Big Bird模型对比

BERT模型简介 BERT模型是基于Transformers的双向编码器表示&#xff08;BERT&#xff09;&#xff0c;在所有层中调整左右情境&#xff08;学习上下层语义信息&#xff09;。 Transformer是一种深度学习组件&#xff0c;能够处理并行序列、分析更大规模的数据、加快模型训练速…

sftp和scp协议,哪个传大文件到服务器传输速率快?

环境&#xff1a; 1.Win scp 6.1.1 2.XFTP 7 3.9.6G压缩文件 4.Centos 7 5.联想E14笔记本Win10 6.HW-S1730S-S48T4S-A交换机 问题描述&#xff1a; sftp和scp协议&#xff0c;哪个传大文件到服务器速度快&#xff1f; 1.SFTP 基于SSH加密传输文件&#xff0c;可靠性高&am…

Profinet转EtherNet/IP网关连接AB PLC的应用案例

西门子S7-1500 PLC&#xff08;profinet&#xff09;与AB PLC以太网通讯&#xff08;EtherNet/IP&#xff09;。本文主要介绍捷米特JM-EIP-PN的Profinet转EtherNet/IP网关&#xff0c;连接西门子S7-1500 PLC与AB PLC 通讯的配置过程&#xff0c;供大家参考。 1, 新建工程&…

护网行动:ADSelfService Plus引领企业网络安全新纪元

随着信息技术的飞速发展&#xff0c;企业网络的重要性变得愈发显著。然而&#xff0c;随之而来的网络安全威胁也日益增多&#xff0c;网络黑客和恶意软件不断涌现&#xff0c;给企业的数据和机密信息带来巨大风险。在这个信息安全威胁层出不穷的时代&#xff0c;企业急需一款强…

API攻击原理,以及如何识别和预防

攻击者知道在针对API时如何避开WAF和API网关。以下是一些公司应对API攻击快速增长的示例。 5月初&#xff0c;Pen Test Partners 安全研究员 Jan Masters 发现&#xff0c;他竟然能够在未经身份验证的情况下&#xff0c;向Peloton的官方API提出可获取其它用户私人数据的请求&am…

TEE GP(Global Platform)功能认证产品

TEE之GP(Global Platform)认证汇总 一、功能认证产品介绍 选择Functional和TEE Initial Configuration v1.1&#xff0c;然后SEARCH&#xff0c;可以看到TEE对应的功能认证产品。 二、CK810MFT V3.8, ERAGON V3, ALIBABA CLOUD LINK TEE V1.2.0 参考&#xff1a; GlobalPlatf…

知乎高赞|什么是低代码,强烈推荐!

本文摘自知乎用户吴多益的文章《从实现原理看低代码》&#xff0c;与以往抽象的定义不同&#xff0c;本文是从代码的角度定义低代码&#xff0c;有非常高的学习价值&#xff01;欢迎大家去看原文。 在讨论各个低代码方案前&#xff0c;首先要明确「低代码」究竟是什么&#xff…

微信联系人批量删除功能如何操作?删除的联系人如何恢复?

继微信推出了朋友圈置顶功能后&#xff0c;微信又推出了"批量删除好友的功能" &#xff0c;具体的操作步骤如下&#xff1a; 第一步 是点击聊天界面上的搜索框"搜索" 第二步 "搜索"排序字母&#xff0c;点击"更多联系人" 第三步 搜…

GNN的一篇入门 :A Gentle Introduction to Graph Neural Networks

原文链接 A Gentle Introduction to Graph Neural Networks (distill.pub)https://distill.pub/2021/gnn-intro/ 内容简介&#xff1a;本文是“A Gentle Introduction to Graph Neural Networks”的阅读笔记&#xff0c;因为第一次接触GNN&#xff0c;很多深奥的概念不懂&…

a柱透明屏好处和挑战详解

a柱透明屏是一种新型的汽车技术&#xff0c;它可以将车辆的a柱部分变得透明&#xff0c;提高驾驶员的视野和安全性。这项技术的出现&#xff0c;将为驾驶员提供更好的驾驶体验和更高的安全性能。 a柱是汽车车身结构中的一部分&#xff0c;位于车辆前部&#xff0c;连接车顶和车…