The Swift-cfenv package provides structures and methods to parse Cloud Foundry-provided configuration variables, such as the port number, IP address, and URL of the application. It also provides default values when running the application locally.
This library determines if you are running your application "locally" or on the cloud (i.e. as a Cloud Foundry application), based on whether the
VCAP_APPLICATION configuration variable is set. If not set, it is assumed you are running in "local" mode instead of "cloud mode".
For the implementation of this Swift package, we used as inspiration a similar module that had been developed for Node.js applications, node-cfenv.
The latest version of Swift-cfenv works with the
Swift 4.0 or newer. You can download this version of the Swift binaries by following this link.
The latest version of Swift-cfenv relies on the Configuration package to load and merge configuration data from multiple sources, such as environment variables or JSON files. In previous versions of Swift-cfenv, the library was responsible for accessing the environment variables directly. Moving forward, newer versions of Swift-cfenv will continue to depend on the configuration data loaded into a
ConfigurationManager instance. For further details on the Configuration package, see its README file.
To leverage the Swift-cfenv package in your Swift application, you should specify a dependency for it in your
import PackageDescription let package = Package( name: "MyAwesomeSwiftProject", ... dependencies: [ .package(url: "https://github.com/IBM-Swift/Swift-cfenv.git", .upToNextMajor(from: "5.0.0")), ... ] ...
Once the Package.swift file of your application has been updated accordingly, you can import the
Configuration modules in your code:
import Configuration import CloudFoundryEnv ... let configFileURL: URL = ... ... let configManager = ConfigurationManager() // To load configuration data from a file or environment variables: //configManager.load(url: configFileURL) // .load(.environmentVariables) // Use the given port and binding host values to create a socket for our server... let ip: String = configManager.bind let port: Int = configManager.port ... // Once the server starts, print the url value print("Server is starting on \(configManager.url).")
The code snippet above gets the binding host and port values through the
ConfigurationManager object, which your Swift application creates and populates according to its needs (e.g. a JSON file, environment variables, etc.). Swift-cfenv queries the
ConfigurationManager instance to obtain those configuration properties that pertain to Cloud Foundry. These values are then used for binding the server. Also, the URL value for the application (also obtained from configuration properties) can be used for logging purposes as shown above.
The main purpose of this library is to simplify accessing the configuration values provided by Cloud Foundry.
Running your application in Cloud Foundry vs. locally
The following configuration properties are set when your application is running in Cloud Foundry as environment variables:
When running in Cloud Foundry, Swift-cfenv expects these properties to be loaded in the
ConfigurationManager instance your application instantiates.
VCAP_APPLICATION isn't found when querying
ConfigurationManager, it is then assumed that your application is running locally. For such cases, the
ConfigurationManager instance returns values that are still useful for starting your application. Therefore, this Swift package can be used when running in Cloud Foundry and when running locally.
ConfigurationManager is a class provided by the Configuration Swift package. Swift-cfenv simply adds extension points to this class, which gives you direct access to the Cloud Foundry configuration data. In your Swift application, you probably will first load configuration data from a local JSON file (this allows you to run locally) and then from environment variables.
If you would like to create a JSON file that your application can leverage for local development, we recommend creating one that follows the following format:
name- A string value for the name of the application. If this property is not specified in the JSON file, the
nameproperty of the
VCAP_APPLICATIONenvironment variable is used.
protocol- The protocol used in the generated URLs. It overrides the default protocol used when generating the URLs for the
vcap- JSON object that provides values when running locally for the
VCAP_SERVICESenvironment variables. This JSON object can have an
applicationfield and/or a
servicesfield, whose values are the same as the values serialized in the
VCAP_SERVICESvariables. Please, note that, when running locally, the
urlsextended properties of the
ConfigurationManagerinstance are not based on the
vcapapplication object (it defaults to
localhostin those cases). Also, note that the
vcapproperty is ignored if not running locally.
An instance of the
ConfigurationManager class has the following extended properties:
isLocal: Bool property is set to true if the VCAP_APPLICATION environment variable was set.
app: A JSON object version of the VCAP_APPLICATION environment variable.
services: A JSON object version of the VCAP_SERVICES environment variable.
name: A string that contains the name of the application.
port: An integer that contains the HTTP port number.
bind: A string with the ip address for binding the server.
urls: A string array that contains the URLs for accessing the servers.
url: The first string in the urls array.
If no value can be determined for the
port property, a default port of 8080 is assigned to it. Note that 8080 is the default port value used by applications running on Diego.
If running locally, the protocol used for the URLs will be
http, otherwise it will be
https. You can override this logic by specifying a particular protocol using the
protocol property on the
If the actual hostnames cannot be determined when running on the cloud (i.e. in Cloud Foundry), the url and urls values will have
localhost as their hostname value.
The following are the instance method extensions for a
getServices(): Returns all services bound to the application in a dictionary. The key in the dictionary is the name of the service, while the value is a Service object. Please note that this returned value is different than the
servicesproperty returned from the
getServices(type: String): Returns an array of Service objects that match the value of the service
typeparameter should be the label of the service (or a regular expression to look up the service by its label).
getService(spec: String): Returns a Service object for the specified Cloud Foundry service. The
specparameter should be the name of the service or a regular expression to look up the service. If there is no service that matches the
specparameter, this method returns nil.
getServiceURL(spec: String, replacements: [String:Any]?): Returns a service URL generated from the
VCAP_SERVICESenvironment variable for the specified service or nil if service cannot be found. The
specparameter should be the name of the service or a regular expression to look up the service. The
replacementsparameter is a dictionary with the properties (e.g.
port, etc.) found in Foundation's URLComponents class. To generate the service URL, the
urlproperty in the service credentials is first used to create an instance of the URLComponents object. The initial set of properties in the URLComponents instance can then be overridden by properties specified in the optional
replacementsdictionary parameter. If there is not a
urlproperty in the service credentials, this method returns nil. Having said this, note that you have the capability to override the
urlproperty in the service credentials, with a
urland a value that specifies the name of the property in the service credentials that contains the base URL. For instance, you may find this useful in the case there is no
urlproperty in the service credentials.
getServiceCreds(spec: String): Returns a dictionary that contains the credentials for the specified service. The
specparameter should be the name of the service or a regular expression to look up the service. If there is no service that matches the
specparameter, this method returns nil. In the case there is no credentials property for the specified service, an empty dictionary is returned.
App is a structure that contains the following
VCAP_APPLICATION environment variable properties:
id: A GUID string identifying the application.
name: A string that contains the name assigned to the application.
uris: A string array that contains the URIs assigned to the application.
version: A GUID string identifying a version of the application.
instanceId: A GUID string that identifies the application instance.
instanceIndex: An integer that represents the index number of the instance.
limits: An App.Limits object that contains memory, disk, and number of files for the application instance (see below).
port: An integer that contains the port number of the application instance.
spaceId: A GUID string identifying the application’s space.
startedAtTs: An NSTimeInterval instance that contains the Unix epoch timestamp for the time the application instance was started.
startedAt: An NSDate object that contains the time when the application instance was started.
The App.Limits structure contains the memory, disk, and number of files for an application instance:
memory: An integer that represents memory for the application (this value is commonly specified in the manifest file).
disk: An integer that represents the disk space for the application (this value is commonly specified in the manifest file).
fds: An integer that represents the number of files.
Service is a class that contains the following properties for a Cloud Foundry service:
name: A string that contains the name assigned to the service instance.
label: A string that contains the name of the service offering.
plan: A string that states the service plan selected when the service instance was created. If the service has no plan, the string 'N/A' is assigned to this field.
tags: An array of strings that contains values to identify a service instance.
credentials: An optional dictionary that contains the service credentials required to access the service instance. Note that the credential properties for accessing a service could be completely different from one to another. For instance, the credentials dictionary for a service may simply contain a
uriproperty while the credentials dictionary for another service may contain a
Testing on the IBM Cloud
To test this Swift library on the IBM Cloud, you can follow the steps described in this section which use the IBM Cloud command line.
Create a dummy service named
bx service user-provided-create cf-dummy-service -p "url, username, password, database"
The IBM Cloud command line will then prompt you for the following (please enter some reasonable values):
url> http://swift-cfenv-service.test.com username> username00 password> password00 database> CloudantDB
Once the dummy service is created, you can clone IBM Cloud's swift-helloworld application using the following command:
git clone https://github.com/IBM-Bluemix/swift-helloworld.git
Then push the swift-helloworld application using the following command:
bx app push
Once the application is successfully pushed, you need to bind the service you created previously to the new application and then restage the application:
bx service bind swift-helloworld cf-dummy-service
bx app restage swift-helloworld
After the application is restaged, you can visit the route (i.e. URL) assigned to the app and you should see the output of various Swift-cfenv invocations.
This Swift package is licensed under Apache 2.0. Full license text is available in LICENSE.
You may find interesting
6.0.3 - 2019-04-11 13:21:16
- Build in Swift 5 mode (#73)
v6.0.2 - 2018-04-19 20:56:22
This release eliminates the errors caused by migration to Swift 4.1.
v6.0.0 - 2017-11-20 16:10:04
- Updates to latest version of Configuration
v5.0.0 - 2017-11-02 16:15:30
- Full migration to Swift 4.0.
- Uses new version of Configuration (2.0.0).
v4.1.0 - 2017-09-29 20:14:35
Provides support for Swift 4.0
v4.0.0 - 2017-03-28 22:11:44
This new major release adds support for Swift 3.1.
v2.0.2 - 2017-01-24 19:22:40
- Added new method for finding services by type.
- Changed default port from
8080is the new default port in Diego environments).
Servicea class (so it can be extended).
- Added a new constructor to
v1.9.3 - 2017-01-05 15:26:14
Migration to Swift 3.0.2.
v1.9.0 - 2016-12-13 15:29:31
Removed dependency on SwiftyJSON. Now, Swift-cfenv uses JSONSerialization from Foundation instead.
v1.8.0 - 2016-11-04 18:18:19
Migrated library to use Swift 3.0.1.
v1.7.0 - 2016-09-15 14:53:43
Updated to use Swift 3.0.
v1.6.0 - 2016-09-01 14:43:35
Migration to Swift 3 08-30 binaries.
v1.5.0 - 2016-08-12 20:40:29
Migration to Swift 3 07-25 binaries.
v1.4.0 - 2016-08-01 15:12:04
Migration to Swift 3 06-20 binaries.
v1.3.0 - 2016-07-19 18:35:09
Migration to Swift 3 06-06 binaries.
v1.2.0 - 2016-06-09 15:42:13
- Renamed module from CloudEnvironment to CloudFoundryEnv.
- Renamed structure from CloudEnvironment to CloudFoundryEnv.
v1.1.0 - 2016-06-03 03:57:44
- Renamed module from
- Renamed structure from
v1.0.0 - 2016-05-06 12:32:47
- Migrated package to use latest Swift 3 binaries (5-03).
- Validated that issue #7 is now fixed.
v0.0.4 - 2016-04-28 20:52:14
- Same functionality as in v0.0.3.
- Migrated package to use latest Swift 3 binaries (4-25).
v0.0.3 - 2016-04-07 17:08:31
- Issue #7 is now resolved (i.e., the getServiceURL() method now returns the expected string when using either or both of the the following replacement fields: query and queryItems.
- Same functionality as in v0.0.2.
v0.0.2 - 2016-04-07 15:40:30
- Compatible with the DEVELOPMENT-SNAPSHOT-2016-03-24-a version of the Swift binaries.
- New CFEnvironment.xcodeproj file for development using Xcode.
- Refactored code to be more "Swifty."
- Updated test cases to support latest version of the XCTest framework.
- Same functionality as in v0.0.1.
v0.0.1 - 2016-04-06 00:12:13
- Compatible with the DEVELOPMENT-SNAPSHOT-2016-03-01-a version of the Swift binaries.
- Parses Cloud Foundry-provided environment variables (e.g. VCAP_SERVICES, VCAP_APPLICATION) to obtain useful configuration properties such as the port number, IP address, and URL of the application.
- It also provides default values when running the application locally.
- Determines if you are running your application "locally" or on the cloud (i.e. Cloud Foundry app), based on whether the VCAP_APPLICATION environment variable is set. If not set, it is assumed you are running in "local" mode instead of "cloud mode".