-
Notifications
You must be signed in to change notification settings - Fork 232
Expand file tree
/
Copy pathapplication-binding.html.md.erb
More file actions
330 lines (229 loc) · 14.2 KB
/
application-binding.html.md.erb
File metadata and controls
330 lines (229 loc) · 14.2 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
---
title: Delivering service credentials to an app
owner: Core Services
---
You can bind your apps to service instances for the purpose of generating credentials and delivering them to apps. For an overview of services, and documentation about other service management operations, see [Using services](index.html). <%= vars.custom_services %>
## <a id='bind'></a>Bind a service instance
Binding a service instance to your app triggers credentials to be provisioned for the service instance and delivered to the app runtime. CloudFoundry offers 3 different methods to deliver those credentials to the app.
For details about the different delivery methods and consumption of these credentials with your app, see [Credential Delivery Methods](#credential-delivery-methods).
Not all services support binding, as some services deliver value to users directly without integration with an app. In many cases, binding credentials are unique to an app, and another app bound to the same service instance receives different credentials, but this depends on the service.
<pre class="terminal">
$ cf bind-service my-app mydb
Binding service mydb to my-app in org my-org / space test as me@example.com...
OK
TIP: Use 'cf push' to ensure your env variable changes take effect
$ cf restart my-app
</pre>
<p class="note important">
You must restart or in some cases re-push your app for changes to be applied to the <a href="../deploy-apps/environment-variable.html">VCAP_SERVICES</a> environment variable and for the app to recognize these changes.</p>
<h3> <a id='credential-delivery-methods'></a> Credential Delivery Methods</h3>
After your service instance is created and bound to your app, the credentials, along with some metadata, are available in the app container and can be consumed by your app.
There are three delivery methods, which are mutually exclusive. The developer can choose which one to use and then must adjust the consumption in the app accordingly.
For details about consuming credentials specific to your development framework, see the Service Binding section in the documentation for your framework's
<a href="../../buildpacks/index.html">buildpack</a>.
<p class="note important">
If the application is unable to consume the credentials through the selected delivery method, it may cause downtime for the application. This is because the application won't be able to connect to the services it is bound to.
</p>
#### <a id='vcap-services'></a> Default VCAP_SERVICES environment variable
By default, credentials and additional metadata for all bound service instances are stored in the <a href="../deploy-apps/environment-variable.html">VCAP_SERVICES</a> environment variable.
There are two methods developers can use to have their apps consume binding credentials.
* **Parse the JSON yourself:** See the documentation for [VCAP_SERVICES](../deploy-apps/environment-variable.html#VCAP-SERVICES). Helper libraries are available for some frameworks.
* **Auto-configuration:** Some buildpacks create a service connection for you by creating additional environment variables, updating config files, or passing system parameters to the JVM.
For checking the binding data manually app developers can use `cf env`. See [View Env](../deploy-apps/environment-variable.html#view-env).
<p class="note important">
The maximum size of content of the VCAP_SERVICES environment variable is 130 KB. If you want to bind more services to the app or the services you want to bind provide lots of data, you can use one of the other methods.</p>
#### <a id='file-based-vcap-services'></a> File-based VCAP services
This delivery method is used when the app feature [file-based-vcap-services](https://v3-apidocs.cloudfoundry.org/index.html#app-features) is enabled.
The environment variable [VCAP_SERVICES_FILE_PATH](../deploy-apps/environment-variable.html#VCAP-SERVICES-FILE-PATH) will be made available in the app container and contains the path to a file containing the same content as the VCAP_SERVICES environment variable above.
The binding data can be viewed like this:
```
cf ssh <app_name> -c 'cat $VCAP_SERVICES_FILE_PATH'
```
<p class="note important">
The vcap_services file content cannot exceed 1 MB, otherwise an <code>IncompatibleBindings</code> error is raised.</p>
#### <a id='service-binding-k8s'></a> Service Binding K8s
This delivery method is used when the app feature [service-binding-k8s](https://v3-apidocs.cloudfoundry.org/index.html#app-features) is enabled.
The environment variable [SERVICE_BINDING_ROOT](../deploy-apps/environment-variable.html#SERVICE-BINDING-ROOT) is made available in the app container. It contains the path to the root folder of a file structure containing binding information.
This method is fully compatible with the specification on [servicebinding.io](https://servicebinding.io/), which is used by Kubernetes as well.
The binding data can be viewed like this:
```
cf ssh <app_name> -c 'find $SERVICE_BINDING_ROOT -type f -exec bash -c "echo {}: \$(cat {})" \;'
```
<p class="note important">
The bytesize of all files and their content combined cannot exceed 1 MB, otherwise an <code>IncompatibleBindings</code> error is raised.</p>
Here are some examples outlining the transformation of VCAP_SERVICES to the file structure:
Nested structures inside their value will be serialized as JSON objects. The same applies if the value is a list.
```
VCAP_SERVICES= {
"foo": [
{
"name": "foo",
"credentials": {
"simple": "value",
"deeply": {
"nested": "value"
},
"list": ["v", "a", "l", "u", "e"]
}
}
]
}
Service Binding Files:
foo/name: foo
foo/simple: value
foo/deeply: {"nested":"value"}
foo/list: ["v","a","l","u","e"]
```
Existing credential keys can be overwritten by other attributes -- [VCAP_SERVICES](../deploy-apps/environment-variable.html#VCAP-SERVICES) attributes plus type and provider. The full list of reserved file names is: binding-guid, binding-name, instance-guid, instance-name, name, label, tags, plan, syslog-drain-url, volume-mounts, type, and provider. Overwriting an existing key does not result in an error.
```
VCAP_SERVICES= {
"foo": [
{
"name": "foo",
"credentials": {
"name": "user",
"secret": "password"
}
}
]
}
Service Binding Files:
foo/name: foo
foo/secret: password
```
Empty lists or null values are omitted; that is, no file will be created.
```
VCAP_SERVICES= {
"foo": [
{
"name": "foo",
"binding_guid": "45436ca8-0a7c-45e3-9439-ca1b44db7a2b",
"syslog_drain_url": null,
"volume_mounts": []
}
]
}
Service Binding Files:
foo/name: foo
foo/binding-guid: 45436ca8-0a7c-45e3-9439-ca1b44db7a2b
```
Binding names must match `[a-z0-9\-.]{1,253}`. Keys resulting in filenames must match `[a-z0-9\-._]{1,253}`. Invalid binding names and keys result in an <code>IncompatibleBindings</code> error.
### <a id='arbitrary-params-binding'></a> Arbitrary parameters
Some services support additional configuration parameters with the bind request. These parameters are passed in a valid JSON object containing service-specific configuration parameters, provided either in-line or in a file. For a list of supported configuration parameters, see documentation for the particular service offering.
See the following examples:
<pre class="terminal">
$ cf bind-service rails-sample my-db -c '{"role":"read-only"}'
Binding service my-db to app rails-sample in org console / space development as user@example.com...
OK
</pre>
<pre class="terminal">
$ cf bind-service rails-sample my-db -c /tmp/config.json
Binding service my-db to app rails-sample in org console / space development as user@example.com... OK
</pre>
### <a id='bind-with-manifest'></a> Binding with app manifest
As an alternative to binding a service instance after pushing an app, you can use the app manifest to bind the service instance during `cf push`.
The following excerpt from an app manifest binds a service instance called `test-mysql-01` to the app on push.
```
services:
- test-mysql-01
```
The following excerpt from an app manifest binds a service instance called `db-test` with arbitrary parameters to the app on push. Arbitrary parameters used in this example are available in cf CLI 7.0 and later.
```
services:
- name: db-test
parameters:
schema: customschema
```
The following excerpt from the `cf push` command and response demonstrates that the cf CLI reads the manifest and binds the service instance to an app called `test-msg-app`.
<pre class="terminal">
$ cf push
Using manifest file /Users/Bob/test-apps/test-msg-app/manifest.yml
...
Binding service test-mysql-01 to test-msg-app in org My-Org / space development as Bob@<%=vars.app_domain%>
OK
</pre>
For more information about app manifests, see [Deploying with app manifests](../deploy-apps/manifest.html#services-block).
### <a id='service-binding-names'></a>Named service bindings
Service offering and service instance names vary across environments. App authors can discover the service instances their apps require, without having to know environment-specific service names. Developers can specify a service binding name to include in [VCAP_SERVICES](../deploy-apps/environment-variable.html).
To specify the service binding name, provide the `--binding-name` flag when binding an app to a service instance:
<pre class="terminal">
$ cf bind-service my-app my-service --binding-name postgres-database
OK
</pre>
The provided name is available in the `name` and `binding_name` properties in the [VCAP_SERVICES](../deploy-apps/environment-variable.html) environment variable:
```
"VCAP_SERVICES": {
"service-name": [
{
"name": "postgres-database",
"binding_name": "postgres-database",
...
}
]
}
```
## <a id='update-credentials'></a>Update service credentials
This section describes how to update service instance credentials.
When updating the credentials, you can restage the app immediately and experience app downtime.
If your app uses blue-green deployment, you can update service instance credentials with no downtime.
For more information about user-provided services, see [Update a user-provided service instance](user-provided.html#update) in _User-Provided Service Instances_.
### <a id='update-credentials-with-downtime'></a>With downtime
To update your service credentials:
1. [Unbind the service instance](#unbind) using the credentials you are updating by running:
<pre class="terminal">
$ cf unbind-service YOUR-APP YOUR-SERVICE-INSTANCE
</pre>
2. [Bind the service instance](#bind). This command adds your credentials to the [VCAP_SERVICES](../deploy-apps/environment-variable.html) environment variable.
<pre class="terminal">
$ cf bind-service YOUR-APP YOUR-SERVICE-INSTANCE
</pre>
3. Restart or re-push the app bound to the service instance so that the app recognizes your environment variable updates.
### <a id='update-credentials-without-downtime'></a>Without downtime
To update your service credentials without experiencing app downtime you can either employ a blue-green update scheme or use the new service credential binding rotation feature in combination with `--strategy rolling`.
#### <a id='blue-green-update'></a>Blue-green update
1. Start a blue-green update of the app. For more information, see [Using blue-green deployment to reduce downtime and risk](../deploy-apps/blue-green.html). Push the "Green" version of the app with the `--no-start` parameter to prevent the app from starting right away:
<pre class="terminal">
$ cf push YOUR-APP --no-start
</pre>
1. Bind the service instances to the newly-deployed "Green" app by running:
<pre class="terminal">
$ cf bind-service YOUR-APP YOUR-SERVICE-INSTANCE
</pre>
1. Start the "Green" app with `cf start`:
<pre class="terminal">
$ cf start YOUR-APP
</pre>
1. Unbind the service instances from the `Blue` app:
<pre class="terminal">
$ cf unbind-service YOUR-APP YOUR-SERVICE-INSTANCE
</pre>
#### <a id='service-credential-binding-rotation'></a>Service credential binding rotation (experimental)
The service credential binding rotation feature allows you to rotate credentials for a service instance using a rolling re-binding. This feature requires the following prerequisites:
- The Cloud Foundry platform must support at least 2 bindings per service instance. This is configured by the platform operator with the `cc.max_service_credential_bindings_per_app_service_instance` property in the Cloud Controller configuration.
- The service broker must support multiple bindings per service instance and application.
- You must use at least cf CLI v8.18.0.
- You must use the `--strategy rolling` update feature.
To rotate credentials for an already bound service instance with no downtime:
1. Create an additional service binding to your service instance by running:
<pre class="terminal">
$ cf bind-service YOUR-APP YOUR-SERVICE-INSTANCE --strategy multiple
</pre>
1. Trigger a rolling update of your application. The updated application instances will only see the new credentials:
<pre class="terminal">
$ cf restage YOUR-APP --strategy rolling
</pre>
1. Once the update has been completed, you can delete the old service bindings with the `cleanup-outdated-service-bindings` command. It only keeps the newest binding and deletes the old bindings:
<pre class="terminal">
$ cf cleanup-outdated-service-bindings YOUR-APP
</pre>
## <a id='unbind'></a>Unbind a service instance
Unbinding a service removes the credentials created for your app from the [VCAP_SERVICES](../deploy-apps/environment-variable.html) environment variable.
<pre class="terminal">
$ cf unbind-service my-app mydb
Unbinding app my-app from service mydb in org my-org / space test as me@example.com...
OK
</pre>
<p class="note important">
You must restart or in some cases re-push your app for changes to be applied to the <a href="../deploy-apps/environment-variable.html">VCAP_SERVICES</a> environment variable and for the app to recognize these changes.</p>
<p class="note important">
If there are multiple service bindings as described in <a href="#service-credential-binding-rotation">Service credential binding rotation</a>, make sure to use cf CLI v8.18.0 or later to unbind all service bindings.</p>