以编程方式使用 Spring Cloud

工程 | Ramnivas Laddad | 2014年7月29日 | ...

上一篇博客中,我向您展示了如何使用Spring Cloud的 Java 配置选项以声明方式获取服务连接器(如果您需要,还支持 XML 命名空间)。在本博客中,我们将仔细研究如何以编程方式使用 Spring Cloud。这将有助于在无法使用 Java 或 XML 配置的情况下。它还将揭示 Spring Cloud 的工作原理,并为本系列的下一篇博客做准备,我们将在其中讨论扩展 Spring Cloud。

要使用 Spring Cloud,我们需要访问 Cloud 类的一个对象。但是,您不能直接创建 Cloud 对象(它的构造函数不是公共的)。相反,您将通过 CloudFactory 获取它。

CloudFactory cloudFactory = new CloudFactory();
Cloud cloud = cloudFactory.getCloud();

以这种方式创建的云对象适用于应用程序运行的环境。例如,如果应用程序在 Cloud Foundry 中运行,则它被配置为理解如何向应用程序公开服务。请注意,创建 CloudFactory 实例的成本有点高,因此您应该尽量避免创建多个实例。如果您使用像 Spring 这样的依赖注入框架,它将负责避免多个实例;否则,只需自己管理。

一旦我们有了云对象,我们就可以获取应用程序实例信息、使用各种条件的服务信息对象以及使用指定条件的服务连接器。假设您想获取绑定到应用程序的所有服务的 ServiceInfo 对象,并打印关系型服务的 JDBC URL,您可以使用以下代码片段:

List<ServiceInfo> serviceInfos = cloud.getServiceInfos();
for (ServiceInfo serviceInfo : serviceInfos) {
    if (serviceInfo instanceof RelationalServiceInfo) {
        System.out.println(((RelationalServiceInfo) serviceInfo).getJdbcUrl());
    }
}

这将产生如下输出:

jdbc:postgresql://babar.elephantsql.com:5432/tbsonrjm?user=***&password=***

使用 getServiceInfos() 及其变体获取的对象包含足够的诸如 URL 和凭据之类的信息来创建服务连接器。在某些情况下,获取 ServiceInfo 对象可能就是您所需要的,因为您总是可以基于它创建合适的连接器(例如 DataSource)。但在大多数情况下,您会让 Spring Cloud 为服务创建一个合适的服务连接器。例如,如果您想直接获取“inventory-db”服务的 DataSource,您可以使用以下代码片段:

DataSource inventoryDataSource = 
    cloud.getServiceConnector("inventory-db", DataSource.class, null);

此方法有一个变体:getSingletonServiceConnector(),您可以按如下方式使用它:

DataSource inventoryDataSource = cloud.getSingletonServiceConnector(DataSource.class, null);

在这里,它将为绑定到应用程序的唯一关系型数据库服务返回一个 DataSource;如果没有此类服务或服务不止一个,它将抛出异常。我们将 null 作为最后一个参数传递给这两个方法,以使用所创建连接器的默认配置。但是,您可以传递所需的配置以进行覆盖。例如,在这里我们为要创建的数据源指定了连接池配置以及连接配置。

PoolConfig poolConfig = new PoolConfig(20, 200);
ConnectionConfig connectionConfig = new ConnectionConfig("characterEncoding=UTF-8");
DataSourceConfig serviceConfig = new DataSourceConfig(poolConfig, connectionConfig);
DataSource invetoryDataSource = cloud.getSingletonServiceConnector(DataSource.class, serviceConfig);

最后,有一个方法可以获取应用程序信息,其中包含应用程序 ID(取决于云,但通常是应用程序名称)、应用程序实例 ID 和松散定义的应用程序属性。让我们打印所有这些信息:

ApplicationInstanceInfo appInstanceInfo = cloud.getApplicationInstanceInfo();
System.out.println("Application id: " + appInstanceInfo.getAppId());
System.out.println("Application instance id: " + appInstanceInfo.getInstanceId());
for (Map.Entry<String, Object> entry: appInstanceInfo.getProperties().entrySet()) {
    System.out.println("Application property: " + entry.getKey() + "=" + entry.getValue());
}

当您在 Cloud Foundry 中运行的应用程序中执行此代码时,您会得到类似于以下内容的输出(此处已缩写)。如果同一个应用程序在 Heroku 中运行,它将产生类似的输出,但键集不同。

Application id: hello-spring-cloud
Application instance id: 8b523252a9d3478b92750ef27ad4e5b0
Application property: limits={mem=800, disk=1024, fds=16384}
Application property: application_version=b1257c57-2a5c-47aa-8ca7-5e8b6d9a7b9c
Application property: application_name=hello-spring-cloud
Application property: application_uris=[hello-spring-cloud.cfapps.io]
Application property: version=b1257c57-2a5c-47aa-8ca7-5e8b6d9a7b9c
Application property: name=hello-spring-cloud
Application property: space_name=development
Application property: space_id=5f629937-1821-4f48-9eb4-8c67c70c0df0
Application property: application_id=a345f90f-e075-4005-b003-f4ab86ad716a
Application property: instance_id=8b523252a9d3478b92750ef27ad4e5b0
Application property: instance_index=0
Application property: host=0.0.0.0
Application property: port=61023
Application property: start=2014-07-15 21:27:34 +0000
Application property: state_timestamp=1405459654

这几乎就是您以编程方式使用 Spring Cloud 所需要了解的一切。在下一篇博客中,我们将把重点转移到 Spring Cloud 的可扩展性方面。敬请期待。

获取 Spring 新闻通讯

通过 Spring 新闻通讯保持联系

订阅

领先一步

VMware 提供培训和认证,助您加速进步。

了解更多

获得支持

Tanzu Spring 提供 OpenJDK™、Spring 和 Apache Tomcat® 的支持和二进制文件,只需一份简单的订阅。

了解更多

即将举行的活动

查看 Spring 社区所有即将举行的活动。

查看所有