多数据源及其连接池的配置、事务管理器的注册和使用

news2024/9/21 12:22:14

(ps:如果只有这几个数据源,请选择一个默认的数据源和对应的事务管理器均加上@Primary注解)示例:

1.在yml文件中配置多数据源/池的信息
 

spring:
  datasource:
    type: com.alibaba.druid.pool.DruidDataSource
    druid:
      initial-size: 5
      min-idle: 5
      max-active: 20
      max-wait: 60000
      time-between-eviction-runs-millis: 60000
      min-evictable-idle-time-millis: 300000
      validation-query: select 'x'
      test-whileidle: true
      test-on-borrow: false
      test-on-return: false
      pool-prepared-statements: false
      max-pool-prepared-statement-per-connection-size: -1
      filters: stat,wall,slf4j
      use-global-data-source-stat: true
      connection-properties: druid.stat.mergeSql=true;druid.stat.slowSqlMillis=5000
      web-stat-filter:
        enabled: true
        url-pattern: /*
        exclusions: /druid/*,*.js,*.gif,*.jpg,*.png,*.css,*.ico
      stat-view-servlet:
        enabled: true
        url-pattern: /druid/*
        reset-enable: false
        login-username: xxxx
        login-password: xxxx
        allow: "*" # 允许所有IP访问
#        deny:

auth_record:
  dev:
    datasource:
      url: xxxx
      username: xxxx
      password: xxxx
      driverClassName: com.mysql.cj.jdbc.Driver
  test:
    datasource:
      url: xxxx
      username: xxxx
      password: xxxx
      driverClassName: com.mysql.cj.jdbc.Driver
  pre:
    datasource:
      url: jdbc:xxxx
      username: xxxx
      password: xxxx
      driverClassName: com.mysql.cj.jdbc.Driver
data:
  dev:
    datasource:
      url: xxxx
      username: xxxx
      password: xxxx
      driverClassName: com.mysql.cj.jdbc.Driver
  test:
    datasource:
      url: jdbc:xxxx
      username: xxxx
      password: xxxx
      driverClassName: com.mysql.cj.jdbc.Driver
  pre:
    datasource:
      url: xxxx
      username: xxxx
      password: xxxx
      driverClassName: com.mysql.cj.jdbc.Driver

2.在实体类中使用@Value分别将各个源的信息注入(这里只展示一个实体);

@Data
@Configuration
public class AuthDevMySQLParams {

    @Value("${auth_record.dev.datasource.driverClassName}")
    private String driverClassName;

    @Value("${auth_record.dev.datasource.username}")
    private String userName;

    @Value("${auth_record.dev.datasource.password}")
    private String password;

    @Value("${auth_record.dev.datasource.url}")
    private String mysqlUrl;
}

3.将连接池的配置同样注入给实体

@Data
@Configuration
public class DriudParams {

    @Value("${spring.datasource.druid.initial-size}")
    private int initialSize;

    @Value("${spring.datasource.druid.min-idle}")
    private int minIdle;

    @Value("${spring.datasource.druid.max-active}")
    private int maxActive;

    @Value("${spring.datasource.druid.max-wait}")
    private long maxWait;

    @Value("${spring.datasource.druid.time-between-eviction-runs-millis}")
    private long timeBetweenEvictionRunsMillis;

    @Value("${spring.datasource.druid.min-evictable-idle-time-millis}")
    private long minEvictableIdleTimeMillis;

    @Value("${spring.datasource.druid.validation-query}")
    private String validationQuery;

    @Value("${spring.datasource.druid.test-whileidle}")
    private boolean testWhileIdle;

    @Value("${spring.datasource.druid.test-on-borrow}")
    private boolean testOnBorrow;

    @Value("${spring.datasource.druid.test-on-return}")
    private boolean testOnReturn;

    @Value("${spring.datasource.druid.pool-prepared-statements}")
    private boolean poolPreparedStatements;

    @Value("${spring.datasource.druid.max-pool-prepared-statement-per-connection-size}")
    private int maxPoolPreparedStatementPerConnectionSize;

    @Value("${spring.datasource.druid.filters}")
    private String filters;

    @Value("${spring.datasource.druid.use-global-data-source-stat}")
    private boolean useGlobalDataSourceStat;

    @Value("${spring.datasource.druid.connection-properties}")
    private String connectionProperties;

}

4.创建对应连接池的数据源
 

@Component
public class CreateDataSourceBean {

    @Autowired
    private AuthPreMySQLParams authPreMySQLParams;

    @Autowired
    private AuthTestMySQLParams authTestMySQLParams;

    @Autowired
    private DataTestMySQLParams dataTestMySQLParams;

    @Autowired
    private DataPreMySQLParams dataPreMySQLParams;

    @Autowired
    private AuthDevMySQLParams authDevMySQLParams;

    @Autowired
    private DataDevMySQLParams dataDevMySQLParams;


    @Autowired
    private DriudParams driudParams;

    @Bean(name = "dataDevDataSource")
    public DataSource CreateDataDevDataSource() throws SQLException {
        DruidDataSource dataSource = new DruidDataSource();
        dataSource.setUrl(dataDevMySQLParams.getMysqlUrl());
        dataSource.setUsername(dataDevMySQLParams.getUserName());
        dataSource.setPassword(dataDevMySQLParams.getPassword());
        dataSource.setDriverClassName(dataDevMySQLParams.getDriverClassName());

        return SetDataSourceProperty(dataSource);
    }

    @Bean(name = "authDevDataSource")
    public DataSource CreateAuthDevDataSource() throws SQLException {
        DruidDataSource dataSource = new DruidDataSource();
        dataSource.setUrl(authDevMySQLParams.getMysqlUrl());
        dataSource.setUsername(authDevMySQLParams.getUserName());
        dataSource.setPassword(authDevMySQLParams.getPassword());
        dataSource.setDriverClassName(authDevMySQLParams.getDriverClassName());

        return SetDataSourceProperty(dataSource);
    }

    @Bean(name = "authPreDataSource")
    public DataSource CreateAuthPreDataSource() throws SQLException {
        DruidDataSource dataSource = new DruidDataSource();
        dataSource.setUrl(authPreMySQLParams.getMysqlUrl());
        dataSource.setUsername(authPreMySQLParams.getUserName());
        dataSource.setPassword(authPreMySQLParams.getPassword());
        dataSource.setDriverClassName(authPreMySQLParams.getDriverClassName());

        return SetDataSourceProperty(dataSource);
    }

    @Bean(name = "authTestDataSource")
    public DataSource CreateAuthTestDataSource() throws SQLException {
        DruidDataSource dataSource = new DruidDataSource();
        dataSource.setUrl(authTestMySQLParams.getMysqlUrl());
        dataSource.setUsername(authTestMySQLParams.getUserName());
        dataSource.setPassword(authTestMySQLParams.getPassword());
        dataSource.setDriverClassName(authTestMySQLParams.getDriverClassName());

        return SetDataSourceProperty(dataSource);
    }

    @Bean(name = "dataTestDataSource")
    public DataSource CreateDataTestDataSource() throws SQLException {
        DruidDataSource dataSource = new DruidDataSource();
        dataSource.setUrl(dataTestMySQLParams.getMysqlUrl());
        dataSource.setUsername(dataTestMySQLParams.getUserName());
        dataSource.setPassword(dataTestMySQLParams.getPassword());
        dataSource.setDriverClassName(dataTestMySQLParams.getDriverClassName());

        return SetDataSourceProperty(dataSource);
    }

    @Bean(name = "dataPreDataSource")
    public DataSource CreateDataPreDataSource() throws SQLException {
        DruidDataSource dataSource = new DruidDataSource();
        dataSource.setUrl(dataPreMySQLParams.getMysqlUrl());
        dataSource.setUsername(dataPreMySQLParams.getUserName());
        dataSource.setPassword(dataPreMySQLParams.getPassword());
        dataSource.setDriverClassName(dataPreMySQLParams.getDriverClassName());

        return SetDataSourceProperty(dataSource);
    }

    private DruidDataSource SetDataSourceProperty(DruidDataSource dataSource) throws SQLException {
        //  具体配置
        dataSource.setInitialSize(driudParams.getInitialSize());
        dataSource.setMinIdle(driudParams.getMinIdle());
        dataSource.setMaxActive(driudParams.getMaxActive());
        dataSource.setMaxWait(driudParams.getMaxWait());
        dataSource.setTimeBetweenEvictionRunsMillis(driudParams.getTimeBetweenEvictionRunsMillis());
        dataSource.setMinEvictableIdleTimeMillis(driudParams.getMinEvictableIdleTimeMillis());
        dataSource.setValidationQuery(driudParams.getValidationQuery());
        dataSource.setTestWhileIdle(driudParams.isTestWhileIdle());
        dataSource.setTestOnBorrow(driudParams.isTestOnBorrow());
        dataSource.setTestOnReturn(driudParams.isTestOnReturn());
        dataSource.setPoolPreparedStatements(driudParams.isPoolPreparedStatements());
        dataSource.setMaxPoolPreparedStatementPerConnectionSize(driudParams.getMaxPoolPreparedStatementPerConnectionSize());
        dataSource.setFilters(driudParams.getFilters());
        dataSource.setUseGlobalDataSourceStat(driudParams.isUseGlobalDataSourceStat());
        dataSource.setConnectionProperties(driudParams.getConnectionProperties());

        return dataSource;
    }
}

5.至此已经完成了多数据源的配置,后续想要使用只需通过bean注入即可拿到
使用示例:(若不用try cathch 记得返回连接池的连接.close() )
 

@Service
public class YourService {

    private final DataSource dataSource;

    @Autowired
    public YourService(DataSource dataSource) {
        this.dataSource = dataSource;
    }

    public void performJdbcQuery() throws SQLException {
        Connection connection = null;
        PreparedStatement preparedStatement = null;
        ResultSet resultSet = null;

        try {
            connection = dataSource.getConnection();
            String sql = "SELECT * FROM your_table";
            preparedStatement = connection.prepareStatement(sql);
            resultSet = preparedStatement.executeQuery();

            while (resultSet.next()) {
                Long id = resultSet.getLong("id");
                String name = resultSet.getString("name");
                // Process the retrieved data as needed
            }
        } finally {
            if (resultSet != null) {
                resultSet.close();
            }
            if (preparedStatement != null) {
                preparedStatement.close();
            }
            if (connection != null) {
                connection.close();
            }
        }
    }
}

6.上面的方法每次都需要手动的去拼接sql,在实现的过程中很容易出错

所以还可以使用SqlSessionFactory扫描对应路径下的xml文件(其中正常编写xml格式的sql语句)
示例(创建SqlSessionFactory的方法在该代码最后):

@Configuration
@MapperScan(basePackages = AuthPreDataSourceConfig.PACKAGE, sqlSessionFactoryRef = "authPreSqlSessionFactory")

public class AuthPreDataSourceConfig {
    /**
     * 配置多数据源 关键就在这里 这里配置了不同的mapper对应不同的数据源
     */
    static final String PACKAGE = "io.metersphere.python_exec.mapper.authorizedRecords.pre";
    static final String MAPPER_LOCATION = "classpath:mapper/authorizedRecords/pre/*.xml";

    /**
     * 连接数据库信息 这个其实更好的是用配置中心完成
     */
    @Value("${auth_record.pre.datasource.url}")
    private String url;

    @Value("${auth_record.pre.datasource.username}")
    private String username;

    @Value("${auth_record.pre.datasource.password}")
    private String password;

    @Value("${auth_record.pre.datasource.driverClassName}")
    private String driverClassName;


    /**
     * 下面的配置信息可以读取配置文件,其实可以直接写死 如果是多数据源的话 还是考虑读取配置文件
     */
    @Value("${spring.datasource.druid.initial-size}")
    private int initialSize;

    @Value("${spring.datasource.druid.min-idle}")
    private int minIdle;

    @Value("${spring.datasource.druid.max-active}")
    private int maxActive;

    @Value("${spring.datasource.druid.max-wait}")
    private int maxWait;

    @Value("${spring.datasource.druid.time-between-eviction-runs-millis}")
    private int timeBetweenEvictionRunsMillis;

    @Value("${spring.datasource.druid.min-evictable-idle-time-millis}")
    private int minEvictableIdleTimeMillis;

    @Value("${spring.datasource.druid.validation-query}")
    private String validationQuery;

    @Value("${spring.datasource.druid.test-whileidle}")
    private boolean testWhileIdle;

    @Value("${spring.datasource.druid.test-on-borrow}")
    private boolean testOnBorrow;

    @Value("${spring.datasource.druid.test-on-return}")
    private boolean testOnReturn;

    @Value("${spring.datasource.druid.pool-prepared-statements}")
    private boolean poolPreparedStatements;

    @Value("${spring.datasource.druid.max-pool-prepared-statement-per-connection-size}")
    private int maxPoolPreparedStatementPerConnectionSize;

    @Value("${spring.datasource.druid.filters}")
    private String filters;

    @Value("${spring.datasource.druid.connection-properties}")
    private String connectionProperties;



    @Bean(name = "authPreDataSource")
    public DataSource authPreDataSource() {
        DruidDataSource dataSource = new DruidDataSource();
        dataSource.setUrl(url);
        dataSource.setUsername(username);
        dataSource.setPassword(password);
        dataSource.setDriverClassName(driverClassName);

        //具体配置
        dataSource.setInitialSize(initialSize);
        dataSource.setMinIdle(minIdle);
        dataSource.setMaxActive(maxActive);
        dataSource.setMaxWait(maxWait);
        dataSource.setTimeBetweenEvictionRunsMillis(timeBetweenEvictionRunsMillis);
        dataSource.setMinEvictableIdleTimeMillis(minEvictableIdleTimeMillis);
        dataSource.setValidationQuery(validationQuery);
        dataSource.setTestWhileIdle(testWhileIdle);
        dataSource.setTestOnBorrow(testOnBorrow);
        dataSource.setTestOnReturn(testOnReturn);
        dataSource.setPoolPreparedStatements(poolPreparedStatements);
        dataSource.setMaxPoolPreparedStatementPerConnectionSize(maxPoolPreparedStatementPerConnectionSize);

        /**
         * 这个是用来配置 druid 监控sql语句的 非常有用 如果你有两个数据源 这个配置哪个数据源就坚实哪个数据源的sql 同时配置那就都监控
         */
        try {
            dataSource.setFilters(filters);
        } catch (SQLException e) {
            e.printStackTrace();
        }
        dataSource.setConnectionProperties(connectionProperties);
        return dataSource;
    }

    @Bean(name = "authPreTransactionManager")
    public DataSourceTransactionManager authPreTransactionManager() {
        return new DataSourceTransactionManager(authPreDataSource());
    }

    @Bean(name = "userPreSqlSessionFactory")
    public SqlSessionFactory authPreSqlSessionFactory(@Qualifier("authPreDataSource") DataSource preDataSource)
            throws Exception {
        final SqlSessionFactoryBean sessionFactory = new SqlSessionFactoryBean();
        sessionFactory.setDataSource(preDataSource);
        sessionFactory.setMapperLocations(new PathMatchingResourcePatternResolver().getResources(AuthPreDataSourceConfig.MAPPER_LOCATION));

//        //分页插件
//        Interceptor interceptor = new PageInterceptor();
//        Properties properties = new Properties();
//        //数据库
//        properties.setProperty("helperDialect", "mysql");
//        //是否将参数offset作为PageNum使用
//        properties.setProperty("offsetAsPageNum", "true");
//        //是否进行count查询
//        properties.setProperty("rowBoundsWithCount", "true");
//        //是否分页合理化
//        properties.setProperty("reasonable", "false");
//        interceptor.setProperties(properties);
//        sessionFactory.setPlugins(new Interceptor[] {interceptor});

        return sessionFactory.getObject();
    }
}

7.事务管理器的使用

我们可以在第四步中加入(选择对应的数据源注册对应的事务管理器bean)

   @Bean(name = "dataDevTransactionManager")
    public DataSourceTransactionManager transactionManager(@Qualifier("dataDevDataSource") DataSource dataSource) {
        return new DataSourceTransactionManager(dataSource);
    }

然后在service类上加入@Transactional注解选择对应的事务管理器
 

@Slf4j
@Transactional(transactionManager = "dataDevTransactionManager")
public class AuthPreCopyServiceImpl implements AuthService {

@Transactional注解源代码

@Target({ElementType.TYPE, ElementType.METHOD}) // 表明该注解可以应用在类和方法上
@Retention(RetentionPolicy.RUNTIME) // 保留期间为运行时,这样可以通过反射获取注解信息
@Inherited // 表示该注解可以被子类继承
@Documented // 表示该注解将被包含在 JavaDoc 中
@Reflective // 这可能是一个自定义的元注解,用于指示该注解支持反射操作
public @interface Transactional {
    @AliasFor("transactionManager")
    String value() default ""; // 别名为 transactionManager,可以用于指定事务管理器名称

    @AliasFor("value")
    String transactionManager() default ""; // 别名为 value,可以用于指定事务管理器名称

    String[] label() default {}; // 用于指定事务的标签,可能用于更细粒度的事务控制

    Propagation propagation() default Propagation.REQUIRED; // 事务传播行为,默认为 REQUIRED

    Isolation isolation() default Isolation.DEFAULT; // 事务隔离级别,默认为 DEFAULT

    int timeout() default -1; // 事务超时时间,默认为 -1 表示不超时

    String timeoutString() default ""; // 事务超时时间的字符串表示,用于兼容性

    boolean readOnly() default false; // 是否为只读事务,默认为 false

    Class<? extends Throwable>[] rollbackFor() default {}; // 触发回滚的异常类型,默认为空数组,表示仅回滚 RuntimeException 和 Error

    String[] rollbackForClassName() default {}; // 触发回滚的异常类型名称,默认为空数组

    Class<? extends Throwable>[] noRollbackFor() default {}; // 不触发回滚的异常类型,默认为空数组

    String[] noRollbackForClassName() default {}; // 不触发回滚的异常类型名称,默认为空数组
}

8.事务的传播行为和隔离级别

事务的传播行为 (Propagation Behavior)
事务的传播行为定义了在一个方法调用另一个方法时,事务应该如何被传播或创建。Spring框架提供了以下几种传播行为:
PROPAGATION_REQUIRED: 如果当前存在事务,则加入该事务;如果当前没有事务,则创建一个新的事务。这是最常用的传播行为。
PROPAGATION_SUPPORTS: 如果当前存在事务,则加入该事务;如果当前没有事务,则以非事务的方式继续执行。
PROPAGATION_MANDATORY: 强制要求当前存在一个事务,如果没有,则抛出异常。
PROPAGATION_REQUIRES_NEW: 创建一个新的事务,如果当前存在事务,则挂起当前事务。
PROPAGATION_NOT_SUPPORTED: 以非事务方式执行操作,并挂起当前事务(如果有)。
PROPAGATION_NEVER: 以非事务方式执行,如果当前存在事务,则抛出异常。
PROPAGATION_NESTED: 如果当前存在事务,则在嵌套事务内执行;如果当前没有事务,则其行为类似于PROPAGATION_REQUIRED。


事务的隔离级别 (Isolation Levels)
事务的隔离级别定义了事务如何处理并发操作,以及它对其他事务的可见性。常见的隔离级别包括:
ISOLATION_DEFAULT: 使用底层数据库系统的默认隔离级别。
ISOLATION_READ_UNCOMMITTED: 允许脏读,即一个事务可以读取到另一个事务尚未提交的数据。
ISOLATION_READ_COMMITTED: 防止脏读,但允许不可重复读和幻读。
ISOLATION_REPEATABLE_READ: 防止脏读和不可重复读,但可能允许幻读。
ISOLATION_SERIALIZABLE: 提供最强的隔离级别,防止所有并发问题,但可能会导致性能下降。

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

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

相关文章

nodejs + vue3 模拟 fetchEventSouce进行sse流式请求

先上效果图: 前言: 在GPT爆发的时候,各项目都想给自己的产品加上AI,蹭上AI的风口,因此在最近的一个需求,就想要给项目加入Ai的功能,原本要求的效果是,查询到对应的数据后,完全展示出来,也就是常规的post请求,后来这种效果遇到了一个很现实的问题:长时间的等待。我…

SCI三区|儿童学习优化算法KLO:基于社会进化和认知学习的优化算法

目录 1.背景2.算法原理2.1算法思想2.2算法过程 3.结果展示4.参考文献5.代码获取 1.背景 2024年&#xff0c;ST Javed受到社会环境下家庭儿童的早期社会学习行为启发&#xff0c;提出了儿童学习优化算法&#xff08;Kids Learning Optimizer, KLO&#xff09;。 2.算法原理 2.…

使用MySQLInstaller配置MySQL

操作步骤 1.配置High Availability 默认选项Standalone MySQL Server classic MySQL Replication 2.配置Type and Networking ◆端口默认启用TCP/P网络 ◆端口默认为3306 3.配置Account and Roles 设置root账户的密码、添加其他管理员 4.配置Windows Service ◆配置MySQL Serv…

day4单向链表

主程序 #include "fun.h" int main(int argc, const char *argv[]) { node_p Lcreate_head();//创建链表 printf("########################链表的头插尾插\n"); insert_head(L,45);//头插 insert_head(L,45); insert_tail(L,45);/…

imx6ull/linux应用编程学习(14) MQTT基础知识

什么是mqtt&#xff1f; 与HTTP 协议一样&#xff0c; MQTT 协议也是应用层协议&#xff0c;工作在 TCP/IP 四层模型中的最上层&#xff08;应用层&#xff09;&#xff0c;构建于 TCP/IP协议上。 MQTT 最大优点在于&#xff0c;可以以极少的代码和有限的带宽&#xff0c;为连接…

极客时间:使用Autogen Builder和本地LLM(Microsoft Phi3模型)在Mac上创建本地AI代理

每周跟踪AI热点新闻动向和震撼发展 想要探索生成式人工智能的前沿进展吗&#xff1f;订阅我们的简报&#xff0c;深入解析最新的技术突破、实际应用案例和未来的趋势。与全球数同行一同&#xff0c;从行业内部的深度分析和实用指南中受益。不要错过这个机会&#xff0c;成为AI领…

Jenkins教程-15-常用插件-Blue Ocean

上一小节我们学习了Jenkins定时任务构建的方法&#xff0c;本小节我们讲解一下Jenkins常用插件Blue Ocean的使用方法。 Blue Ocean 提供了一套可视化操作界面来帮助创建、编辑 Pipeline 任务。 Blue Ocean 特性&#xff1a; 流水线编辑器&#xff1a;用于创建贯穿始终的持续交…

JavaScript学习笔记(七)

45.9 JavaScript 可迭代对象 可迭代对象&#xff08;Iterables&#xff09;是可以使用 for..of 进行迭代的对象。 从技术上讲&#xff0c;可迭代对象必须实现 Symbol.iterator 方法。 45.9.1 遍历字符串 <body><p id"demo"></p><script>c…

关于centos7自带的nginx1.20.1开启https后,XP系统的IE6和IE8无法显示网页的问题

CentOS7自带的nginx-1.20.1是支持HTTP/2和TLS1.3的。 软件包名称&#xff1a;nginx-1.20.1-10.el7.x86_64 CentOS7默认开启了HTTP/2&#xff0c;但没有开启TLS1.3&#xff0c;以及IE6和IE8的https访问。 开启方法&#xff1a; ssl_ciphers HIGH:!aNULL:!MD5;改为ssl_ciphers…

1-3分钟爆款视频素材在哪找啊?这9个热门爆款素材网站分享给你

在如今快节奏的时代&#xff0c;短视频已成为吸引观众注意力的黄金手段。然而&#xff0c;要制作出1-3分钟的爆款视频&#xff0c;除了创意和剪辑技巧外&#xff0c;选择合适的素材至关重要。那么&#xff0c;哪里可以找到那些能让你的视频脱颖而出的爆款素材呢&#xff1f;不用…

【UE5.1】Chaos物理系统基础——05 蓝图绑定Chaos破裂或碰撞事件

步骤 1. 新建一个父类为Actor的蓝图&#xff0c;这里命名为“BP_ChaosExplosionEvent” 打开“BP_ChaosExplosionEvent”&#xff0c;添加一个变量&#xff0c;这里命名为“GC”&#xff0c;变量类型为“几何体集actor”&#xff0c;设置为可编辑实例 在事件图表中添加如下节点…

ELK+Filebeat+Kafka+Zookeeper

本实验基于ELFK已经搭好的情况下 ELK日志分析 架构解析 第一层、数据采集层 数据采集层位于最左边的业务服务器集群上&#xff0c;在每个业务服务器上面安装了filebeat做日志收集&#xff0c;然后把采集到的原始日志发送到Kafkazookeeper集群上。第二层、消息队列层 原始日志发…

通过端口转发实现docker容器运行时端口更改

通过端口转发实现docker容器运行时端口更改 前言启动容器查看容器ip地址端口转发 前言 关于修改docker正在运行中容器端口&#xff0c;网上大部分分为3类: 1. 删除原有容器重新创建;2. 改配置文件;3. 在现有容器上新提交镜像&#xff0c;用新镜像起新的容器。 1和3属于同一种流…

Matlab手搓线性回归-非正规方程法

原理&#xff1a;wxb&#xff0c;x是输入&#xff0c;求得的结果与真实值y求均方误差。 采用链式法则求导 参数更新&#xff0c;梯度下降法&#xff08;批量梯度下降&#xff09; 随机生成数据&#xff1a; m100&#xff1b;生成100个数据&#xff0c;并添加随机噪声 clear; …

9、Python之文本解析:字符串格式化的逆操作?

引言 前面的文章中&#xff0c;提到了关于Python中字符串中的相关操作&#xff0c;更多地涉及到了字符串的格式化&#xff0c;有些地方也称为字符串插值操作&#xff0c;本质上&#xff0c;就是把多个字符串拼接在一起&#xff0c;以固定的格式呈现。 关于字符串的操作&#…

2021版本的idea热部署的详细步骤

背景&#xff1a;我是自己用的是2021版本的idea,然后发现跟2023版本的热部署不太一样&#xff0c;所以&#xff0c;今天自己出一期这样的文章吧&#xff01;&#xff01;&#xff01;其他人配置的时候根据自己的情况&#xff0c;来阅读吧&#xff01; 第一步&#xff1a;方式一…

光伏项目开发合作模式

光伏项目开发合作模式多种多样&#xff0c;根据应用场景的不同&#xff0c;主要分为户用光伏项目合作模式和工商业光伏项目合作模式。本文将分别介绍这两种模式的特点和常见形式&#xff0c;帮助大家更好地了解光伏项目开发的市场运作。 一、户用光伏项目合作模式 1.用户全款购…

科研训练课程——2024/7/8

科研训练课程——2024/7/8 文章目录 前言课程任务&#xff08;可跳过&#xff09;了解1. LetPub2. Web of Science 总结 前言 本系列笔记为记录大二暑期学校课程—— 科研训练与写作&#xff0c;记录一下每天了解了什么吧&#xff08;苦逼又无聊的学习生涯又开始了。才刚结束啊…

matlab仿真 信道(上)

&#xff08;内容源自详解MATLAB&#xff0f;SIMULINK 通信系统建模与仿真 刘学勇编著第四章内容&#xff0c;有兴趣的读者请阅读原书&#xff09; 1.加性高斯白噪声信道&#xff08;AWGN &#xff09; clear all t0:0.001:10; xsin(2*pi*t);%原始信号 snr20;%设定加性白噪…

基于flask的猫狗图像预测案例

&#x1f4da;博客主页&#xff1a;knighthood2001 ✨公众号&#xff1a;认知up吧 &#xff08;目前正在带领大家一起提升认知&#xff0c;感兴趣可以来围观一下&#xff09; &#x1f383;知识星球&#xff1a;【认知up吧|成长|副业】介绍 ❤️如遇文章付费&#xff0c;可先看…