【问题标题】:Switch between local database and Google Cloud SQL programmatically以编程方式在本地数据库和 Google Cloud SQL 之间切换
【发布时间】:2020-05-17 22:41:45
【问题描述】:

我正在使用 Spring Boot 开发一个项目,该项目到目前为止只使用本地 Postgres 数据库。但是,我们现在正在努力将应用程序部署到涉及使用 Cloud SQL 的 Google 云平台。我找到了一些关于如何连接到 Cloud SQL 的指南,并决定关注this one

但是,我们不能同时在 Cloud SQL 中运行单独的开发数据库,​​因此希望继续使用本地 Postgres 数据库进行开发。为此,我编写了以下代码:

@Configuration
@EnableTransactionManagement
public class PersistenceContext {
    @Bean
    public DriverManagerDataSource dataSource() {
        DriverManagerDataSource dataSource = new DriverManagerDataSource();
        dataSource.setUrl(System.getenv("DB_URL"));
        dataSource.setUsername(System.getenv("DB_USER"));
        dataSource.setPassword(System.getenv("DB_PASS"));

        String dbInstance = System.getenv("DB_INSTANCE");

        if (dbInstance != null && !dbInstance.isEmpty()) {
            Properties connectionProperties = new Properties();
            connectionProperties
                .setProperty("socketFactory", "com.google.cloud.sql.postgres.SocketFactory");
            connectionProperties.setProperty("cloudSqlInstance", dbInstance);

            dataSource.setConnectionProperties(connectionProperties);
        }

        return dataSource;
    }
}

有了这个,我希望简单地不指定云 SQL 套接字工厂和 dbInstance 将允许我使用本地数据库。但是,当尝试仅使用 DB url、用户和密码变量集运行应用程序时,我遇到了以下异常:

java.lang.IllegalArgumentException:必须以<PROJECT_ID>:<REGION>:<INSTANCE_ID> 格式提供实例连接名称。

完整的堆栈跟踪可以在here找到

DB URL 配置如下:

DB_URL:jdbc:postgresql://localhost:5432/soundshare

如何以编程方式在数据库之间切换? (如果可以避免的话,我宁愿不将数据库详细信息存储在配置文件中)

谢谢!

【问题讨论】:

  • 完整的堆栈跟踪是什么,你在开发环境中的DB_URL 是什么?
  • @Kayaman 我已将堆栈跟踪的链接以及在开发环境中配置的环境变量添加到原始帖子。
  • 啊,您有一个尝试连接到云的 GcpAutoConfigurer。您可能想要使用 Spring 配置文件,因此您可以为配置文件 dev 禁用它。我会告诉你怎么做,但目前我的工作内存中有 3 个不同版本的 Spring,它们都以完全不同的方式配置......
  • 或者用手动配置替换自动配置。
  • 通过为测试和生产设置单独的 application.properties 来切换,而不是在代码中切换。用代码来做是不好的做法,因为你在生产/测试中会有死代码

标签: java postgresql spring-boot google-cloud-platform google-cloud-sql


【解决方案1】:

所以像@Thomas Andolf 提到的那样,在代码中自己编写并不是一个好主意,基本上是在重新发明轮子。有几种方法可以“外部化”您的配置。

https://docs.spring.io/spring-boot/docs/1.2.2.RELEASE/reference/html/boot-features-external-config.html

我个人喜欢尽可能使用 os 环境变量,因为我在部署为容器时也可以轻松携带 swap。

这是我正在处理的项目的 application.properties 文件的横截面:

spring.datasource.url=${ospec_db_url} spring.datasource.username=${ospec_db_user:somedefault} spring.datasource.password=${ospec_db_password}

在我的开发系统上,我只设置了环境变量,它就会被拾取。就我而言,我有一个包含如下变量的文本文件:

导出 ospec_db_url=jdbc:postgresql://localhost:5432/ospec_db
导出 ospec_db_password=somebadasspassword

我只是获取文本文件并应用它。我可以轻松地在这样做的项目之间切换。当你为 K8s 打包时,你可以从秘密文件中读取到你的环境变量,当你去云时,你可以将值作为变量传递到你的启动脚本中。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2012-05-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-09-29
    相关资源
    最近更新 更多