如何管理 Dataflow Java 管道中的属性和秘密值?
How to manage properties and secret values in Dataflow Java pipelines?
我有一些用 Java 编写的数据流管道,在不同 environments/projects(开发、UAT、生产)的 GCP 上 运行。目前,环境配置(主要是 Cloud SQL 实例和 BigQuery 数据集的连接参数)使用 Java class 中的静态映射进行管理(key = env,value = 属性映射)和一个实用程序 class,用于从云存储动态加载其他文件。
在这种情况下管理配置的最佳做法(如果有)是什么?
本质上,我看到两种配置参数:
- 普通值(在 Spring 应用程序中您将存储在普通 属性 文件中的东西)
- 秘密值(属性 文件包含必须加密的数据 - username/password 用于数据库,API 密钥 - 在 K8S 上下文中可以作为秘密安装的东西)
谢谢。
在 Google 云平台中处理秘密值的一种方法是使用秘密管理器处理对存储密码的加密和访问控制。
在您的 Java 代码中,您可以使用 Google Cloud Secret Manager maven 模块来获取存储的秘密值
我想您会发现本教程对如何 Access Secret Manager from Dataflow Pipeline
很有帮助
"As of today, Dataflow does not provide native support for storing and
accessing secrets. To secure those secrets, the common approach is to
use Cloud KMS to encrypt the secret and decrypt it when running the
data pipeline. With the newly launched Secret Manager, we can now
store those secrets in Secret Manager and access them from our
pipeline to provide better security and ease of use."
以下代码使用 Secret Manager SDK 访问给定 JDBC URL 秘密名称的秘密。
private static String jdbcUrlTranslator(String jdbcUrlSecretName) {
try (SecretManagerServiceClient client = SecretManagerServiceClient.create()) {
AccessSecretVersionResponse response = client.accessSecretVersion(jdbcUrlSecretName);
return response.getPayload().getData().toStringUtf8();
} catch (IOException e) {
throw new RuntimeException("Unable to read JDBC URL secret");
}
}
public static void main(String[] args) {
PipelineOptionsFactory.register(MainPipelineOptions.class);
MainPipelineOptions options =
PipelineOptionsFactory.fromArgs(args)
.withValidation()
.as(MainPipelineOptions.class);
NestedValueProvider<String, String> jdbcUrlValueProvider =
NestedValueProvider.of(
options.getJdbcUrlSecretName(), MainPipeline::jdbcUrlTranslator);
Pipeline pipeline = Pipeline.create(options);
pipeline
.apply("SQL Server - Read Sales.Customers_Archive",
JdbcIO.<KV<Integer, String>>read()
.withDataSourceConfiguration(
JdbcIO.DataSourceConfiguration.create(
StaticValueProvider.of("com.microsoft.sqlserver.jdbc.SQLServerDriver"),
jdbcUrlValueProvider)
);
// Other transforms
pipeline.run();
}
我有一些用 Java 编写的数据流管道,在不同 environments/projects(开发、UAT、生产)的 GCP 上 运行。目前,环境配置(主要是 Cloud SQL 实例和 BigQuery 数据集的连接参数)使用 Java class 中的静态映射进行管理(key = env,value = 属性映射)和一个实用程序 class,用于从云存储动态加载其他文件。
在这种情况下管理配置的最佳做法(如果有)是什么?
本质上,我看到两种配置参数:
- 普通值(在 Spring 应用程序中您将存储在普通 属性 文件中的东西)
- 秘密值(属性 文件包含必须加密的数据 - username/password 用于数据库,API 密钥 - 在 K8S 上下文中可以作为秘密安装的东西)
谢谢。
在 Google 云平台中处理秘密值的一种方法是使用秘密管理器处理对存储密码的加密和访问控制。
在您的 Java 代码中,您可以使用 Google Cloud Secret Manager maven 模块来获取存储的秘密值
我想您会发现本教程对如何 Access Secret Manager from Dataflow Pipeline
很有帮助"As of today, Dataflow does not provide native support for storing and accessing secrets. To secure those secrets, the common approach is to use Cloud KMS to encrypt the secret and decrypt it when running the data pipeline. With the newly launched Secret Manager, we can now store those secrets in Secret Manager and access them from our pipeline to provide better security and ease of use."
以下代码使用 Secret Manager SDK 访问给定 JDBC URL 秘密名称的秘密。
private static String jdbcUrlTranslator(String jdbcUrlSecretName) {
try (SecretManagerServiceClient client = SecretManagerServiceClient.create()) {
AccessSecretVersionResponse response = client.accessSecretVersion(jdbcUrlSecretName);
return response.getPayload().getData().toStringUtf8();
} catch (IOException e) {
throw new RuntimeException("Unable to read JDBC URL secret");
}
}
public static void main(String[] args) {
PipelineOptionsFactory.register(MainPipelineOptions.class);
MainPipelineOptions options =
PipelineOptionsFactory.fromArgs(args)
.withValidation()
.as(MainPipelineOptions.class);
NestedValueProvider<String, String> jdbcUrlValueProvider =
NestedValueProvider.of(
options.getJdbcUrlSecretName(), MainPipeline::jdbcUrlTranslator);
Pipeline pipeline = Pipeline.create(options);
pipeline
.apply("SQL Server - Read Sales.Customers_Archive",
JdbcIO.<KV<Integer, String>>read()
.withDataSourceConfiguration(
JdbcIO.DataSourceConfiguration.create(
StaticValueProvider.of("com.microsoft.sqlserver.jdbc.SQLServerDriver"),
jdbcUrlValueProvider)
);
// Other transforms
pipeline.run();
}