Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Bindable Secrets Resource #994

Open
wants to merge 11 commits into
base: main
Choose a base branch
from
293 changes: 293 additions & 0 deletions toc/rfc/rfc-draft-bindable-secrets.md
tcdowney marked this conversation as resolved.
Show resolved Hide resolved
Original file line number Diff line number Diff line change
@@ -0,0 +1,293 @@
# Meta
[meta]: #meta
- Name: Bindable Secrets
- Start Date: 2024-10-08
- Author(s): @tcdowney @gerg
- Status: Draft
- RFC Pull Request: https://github.com/cloudfoundry/community/pull/994

## Summary

**tl;dr** Kubernetes-style Secrets for Cloud Foundry

This RFC proposes adding a `secret` resource to the V3 Cloud Foundry API, similar in design and purpose to the Kubernetes [Secret resource](https://kubernetes.io/docs/concepts/configuration/secret/). Cloud Foundry Secrets will store arbitrary data as encrypted fields in Cloud Controller's database or (optionally) in [CredHub](https://docs.cloudfoundry.org/credhub/) and inject it into app containers via `tmpfs`-mounted files at a given path, using a mechanism similar to [RFC 0030 - Add Support for File based Service Binding Information](https://github.com/cloudfoundry/community/blob/main/toc/rfc/rfc-0030-add-support-for-file-based-service-binding.md).

## Problem

Cloud Foundry currently supports app configuration via environment variables. Other application platforms, such as Kubernetes, support app configuration at runtime [via volume-mounted files](https://kubernetes.io/docs/concepts/configuration/secret/#using-secrets-as-files-from-a-pod). Many apps are adopting this file-based configuration approach, since environment variables have length limits and files can be updated without having to recreate the container. This RFC proposes introducing file-based configuration to support these sorts of apps on Cloud Foundry — without requiring app code changes.

### What About User-Provided Services?

Why can't developers use user-provided service instances (UPSIs) and service bindings for file-based app configuration? Some apps may have file-based config that don't naturally fit into the service binding model. For example, if an app relies on a config file at a certain path, that plath may not be configurable to `$SERVICE_BINDING_ROOT`. This is especially the case for commercial off-the-shelf software (COTS).
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

question Do you think its likely people will want to create Secrets that contain service info and mount them at $SERVICE_BINDING_ROOT so libraries like https://github.com/spring-cloud/spring-cloud-bindings can read them? Would anything in this design stop that? I suppose the developer would have to know what the $SERVICE_BINDING_ROOT value is and explicit bind to that mount path? Or alternatively, do you think for services users should really be using UPS?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

RFC 0030 - Add Support for File based Service Binding Information requires to configure an app feature flag and then switches all service bindings from VCAP_SERVICES to files under $SERVICE_BINDING_ROOT.

I could imagine that secrets and secret bindings could allow a smoother migration path from VCAP_SERVICES to file based service bindings by allowing both mechanisms in parallel.

If secret bindings are allowed to mount under $SERVICE_BINDING_ROOT, a prioritisation is needed between service bindings and secret bindings.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hmm, I can see arguments for both. My gut tells me that service bindings should take priority, but I also think it is most flexible for devs if secrets take precedence.

For example, imagine you have a MySQL instance hosted on one instance of CF that creates publicly reachable service instances (exposed via TCP routes) and you want to bind to these from apps on other Cloud Foundry installations. One workflow would be to make a Service Key on the "services CF" and then create UPSIs on the ones where your apps are running based on that key.

Problem is an UPSI does not have the correct type that helper library might expect (and not all libraries look at tags). If you could use a secret for this then you could explicitly set the keys to what you want to as a dev. But semantically the UPSI still makes more sense here -- so maybe that interface just needs to be more flexible.

Thoughts @Samze @stephanme @Gerg ?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copy link
Member

@beyhan beyhan Oct 15, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think having secret bindings under$SERVICE_BINDING_ROOT will make also the interface between CC and Diego simpler. Most probably we will need to introduce only the ServiceBindingFiles: as new structure. Also, activation of the filed based approach via the app feature flag can be reused. Additionally, there is also a validation and setup code for the $SERVICE_BINDING_ROOT which makes sure that we have enough disk space for alle the container mounts on the Diego VMs as specified in

Additionally, the application environment is stored in the `CCDB` and `BBS DB` that is why we should define a limit for the size of it, which makes it possible to be stored in the according DBs and doesn’t impact the performance of the communication between Cloud Controller and the Diego API. That is why this RFC suggests a limit of `1MB`, which is roughly ten times higher than the current one of 130KB. This is subject for evaluation during the implation of this RFC.
. If we introduce another mount point for the secret bindings we have to define limits and implement validation for that. Most probably having the $SERVICE_BINDING_ROOT as root for the secret bindings will increases the adoption efforts of the mentioned commercial off-the-shelf software in https://github.com/tcdowney/community/blob/c767d5e0c61c04f8a5be1a45fb285b942794a7ad/toc/rfc/rfc-draft-bindable-secrets.md?plain=1#L21.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We acknowledge that there is some overlap between bindable secrets and user-provided service instances ("UPSIs"); and also to some extent "managed" (broker provided) services ("MSIs"), particularly when/if RFC 0030 - Add Support for File based Service Binding Information is implemented too. I can foresee folks struggling to differentiate: should I use a bindable secret or an UPSI?

If we do this right, we could simplify the platform - for example by making UPSIs and MSI subtypes of bindable secrets, and deprecating UPSIs. If we do this wrong then we could add a forever confusion about what's the right choice, and then have to document and train folks out of the mess.

Perhaps this is too radical, but I'd be interested on folk's thoughts about:

  • deprecating UPSIs and changing the commands to recommended a bindable secret instead (but not breaking anything yet)
  • teaching that MSIs are a special type of bindable secrets rather than a different concept

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

  • deprecating UPSIs and changing the commands to recommended a bindable secret instead (but not breaking anything yet)

My thoughts on this. I think we can have a chance here if we could offer the migration of UPSis to bindable secrets without requiring any changes in the application code. That means, the libraries parsing service binding information need to be adjusted and do the heavy lifting. I'm not sure whether this means also, that bindable secrets need to support not only file based approach for the service binding but also environment based because the move from UPSis to bindable secrets will mean also to opt-in into the file based service binding approach.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Deprecating UPSIs and replacing it with bindable secrets avoids the confusion of two solutions for a very similar problem.

I don't think that we can change the existing functionality for UPSis with VCAP_SERVICES. But if a deprecation shall be a bit more serious than just the word "deprecated" in the docs, we could take out UPSis from RFC0030 File-based Service Bindings.

Existing CF apps (using VCAP_SERVICES) need to be changed anyway when switching to file-based bindings, be it RFC0030 service bindings or bindable secrets.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think we should deprecate UPSI's. They are still semantically distinct from a generic Secret -- they provide a way to provision services off platform (either on a separate Cloud Foundry instance or via some other mechanisms) and provide service information to apps through similar a similar UX as a fully managed service.

I think although Secrets could be used to accomplish something similar, we would be going against over a decade of ingrained UX for CF developers. I also think supporting file-based service bindings for UPSIs is important for service offerings (both older CF oriented ones and newer K8s ones) that may not conform exactly to what the various service binding loading application libraries expect. If a specific key is slightly different, for example, an UPSI can be used to massage its presentation to what the library would need.

I guess in short, there are actually some use-cases that file-based UPSIs would provide that I am interested in leveraging and I wouldn't want to gate them behind a non-implemented (and not yet approved) Secrets proposal. 😅

Copy link
Member

@Gerg Gerg Oct 29, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I agree with Tim.

Similarly, there is "duplication" between cf cups and cf set-env: letting you set environment variables in app containers. You could theoretically achieve logical "service bindings" with cf set-env, and you could configure your app using UPSIs. However, we still keep both of those around because they serve semantically different purposes, are intended for different user workflows, and affect different segments of the app container's environment variables.

They may be implemented with the same mechanics under the hood, but that doesn't mean we need to expose that to our users.


## Proposal

Add two new resources to the V3 Cloud Foundry API: `secret` and the `secret_binding`, along with associated CRUD API endpoints.

### Why Top-Level Resources?

Why not represent secrets as sub-resources of apps like environment variables? Secrets may be shared across multiple apps. For example, a "logical app" may actually be several Cloud Foundry apps resources that need to share certain configuration, certificates, or other credentials. By scoping the `secret` at the `space` level, we can easily support this. Similarly, an app using the blue-green deployment pattern can easily share configuration between versions.

### `secret` and `secret_binding` Resources
The `secret` will be a `space`-scoped resource (similar to a `route` or a `service_instance`) that can be bound to one or more `app`s in the `space` using a `secret_binding`.
tcdowney marked this conversation as resolved.
Show resolved Hide resolved

#### Example `secret` Object

```json
{
"guid": "4f00b75b-3455-48f1-ba4a-f3b82ebad943",
"created_at": "2020-03-10T15:49:29Z",
"updated_at": "2020-03-10T15:49:29Z",
"name": "my-secret",
"type": "opaque",
"credhub_credential_id": null,
"relationships": {
"space": {
"data": {
"guid": "5a84d315-9513-4d74-95e5-f6a5501eeef7"
}
}
},
"metadata": {
"labels": {},
"annotations": {}
},
"links": {
"self": {
"href": "https://api.example.org/v3/service_instances/c89b3280-fe8d-4aa0-a42e-44465bb1c61c"
},
"space": {
"href": "https://api.example.org/v3/spaces/5a84d315-9513-4d74-95e5-f6a5501eeef7"
},
"secret_bindings": {
"href": "https://api.example.org/v3/secret_bindings?secret_guids=4f00b75b-3455-48f1-ba4a-f3b82ebad943"
},
"value": {
"href": "https://api.example.org/v3/secrets/4f00b75b-3455-48f1-ba4a-f3b82ebad943/value"
}
}
}
```

A `secret` has a type that identifies its contents. To start we will support the `opaque` credential type (corresponds to the `json` [CredHub credential type](https://docs.cloudfoundry.org/credhub/credential-types.html)) which is designed to hold arbitrary user-defined data. In the future, this can be expanded to support more semantic secret types such as those [supported by Kubernetes](https://kubernetes.io/docs/concepts/configuration/secret/#secret-types) or other CredHub-supported types like `certificate`. `opaque` secrets consist of a JSON object whose keys map to files and values map to file content.
tcdowney marked this conversation as resolved.
Show resolved Hide resolved

#### Example `secret_binding` Object

```json
{
"guid": "dde5ad2a-d8f4-44dc-a56f-0452d744f1c3",
"created_at": "2015-11-13T17:02:56Z",
"updated_at": "2016-06-08T16:41:26Z",
"mount_path": "/etc/my-conf/",
"metadata": {
"annotations": {},
"labels": {}
},
"relationships": {
"app": {
"data": {
"guid": "74f7c078-0934-470f-9883-4fddss5b8f13"
}
},
"secret": {
"data": {
"guid": "4f00b75b-3455-48f1-ba4a-f3b82ebad943"
}
}
},
"links": {
"self": {
"href": "https://api.example.org/v3/service_credential_bindings/dde5ad2a-d8f4-44dc-a56f-0452d744f1c3"
},
"secret": {
"href": "https://api.example.org/v3/secrets/4f00b75b-3455-48f1-ba4a-f3b82ebad943"
},
"app": {
"href": "https://api.example.org/v3/apps/74f7c078-0934-470f-9883-4fddss5b8f13"
}
}
}
```

The `mount_path` field defines the `tmpfs` directory that will contain files for the `secret`'s content. For example, consider an `opaque`-type `secret` with the following `value`:

```json
"value": {
"application.yml" : "---\napplication:\n ...",
"secret.txt": "my-secret"
}
```

The above `secret` would mount files named `application.yml` and `secret.txt` at the path configured in the binding.

### Creating a `secret`
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There's not a lot in this doc yet about permissions. I infer that an app dev with access to an App will be able to create and bind secrets, and that makes sense, but what if we go further? In the past folks have talked about an Independent Service Manger (ISM) that's a bit like a service broker, but is independent of the platform and might not implement OSBAPI. What if there was a way to give an off-platform service the ability to create secrets, but have no access to Apps? For example if I'm connecting to a MySQL on AWS, I might use AWS Credential Manager to rotate my password every few days. What if a Lambda on AWS could be triggered by this change, and update a secret in CF? We would not want that Lambda to have access to Apps, or other secrets on CF. But it would be ok if could update its own secret. Equally we might allow LetsEncrypt to update a secret that's a certificate. Maybe this is out of scope for now, but it would be nice to make sure we don't block anything like that in the future.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, I think this is out of scope for now. I will add a section around permissions mentioning that Secrets can be created and managed by users with the SpaceDeveloper role since this will treat them the same as other sensitive resources like app environment variables and service binding credentials.


To create a `secret`, users will use a new CLI command: `cf create-secret`.

```console
cf create-secret SECRET_NAME -t opaque -p <CREDENTIALS_INLINE>
```

```console
cf create-secret SECRET_NAME -t opaque -f <FILE_PATH_TO_CREDENTIALS_FILE>
```

* `-t` the secret `type`, defaults to `opaque`
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If we do not have a different type right now is it worth it to add this flag?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, we don't need it for now. I'll update this and remove the flag.

* `-p` reads inline/literal credentials
* `-f` reads credentials from a file
tcdowney marked this conversation as resolved.
Show resolved Hide resolved

This command will ultimately create a `POST` request to `/v3/secrets`. Example `curl` invocation:

```console
curl "https://api.example.org/v3/secrets" \
-X POST \
-H "Authorization: bearer [token]" \
-H "Content-type: application/json" \
-d '{
"type": "opaque",
"name": "my-app-secrets",
"value": {
"application.yml" : "---\napplication:\n ...",
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

How do we create this secret via CLI?
will we have a file with the following yaml

application.yaml: |-
  ---
  application:
    test
secret.txt: my-secret

?

"secret.txt": "my-secret"
}
"metadata": {
"annotations": {},
"labels": {}
},
"relationships": {
"space": {
"data": {
"guid": "7304bc3c-7010-11ea-8840-48bf6bec2d78"
}
}
}
}'
```

### Updating a `secret`
Users will be able to update a `secret` using similar commands:

```console
cf update-secret SECRET_NAME SECRET_TYPE -p <CREDENTIALS_INLINE>
```

```console
cf update-secret SECRET_NAME SECRET_TYPE -f <FILE_PATH_TO_CREDENTIALS_FILE>
```

Initially apps will need to be restarted to receive `secret` updates, but eventually we may be able to support updates that don't require a restart.
The "Update secret" endpoint in the CF API will take a `PATCH` request. Example `curl` invocation:

```console
curl "https://api.example.org/v3/secrets/[guid]" \
-X PATCH \
-H "Authorization: bearer [token]" \
-H "Content-type: application/json" \
-d '{
"type": "opaque",
"value": {
"application.yml" : "---\napplication:\n ...",
"secret.txt": "updated-secret-value"
}
"metadata": {
"annotations": {},
"labels": {}
}
}'
```

### Reading a `secret` and Its Value
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there going to be an endpoint to get the full secret "object"?
Is there going to be a CLI command to retrieve the secret?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There probably should be a CLI command, but as it stands having a separate endpoint for the non-sensitive bits of the Secret and the Secret value has parity with how env vars and service binding credentials work. This is mostly necessary because of how permissions work in Cloud Controller (we want some roles to be able to see the existence of a Secret / Binding to an app, but not its contents).

The CLI could call both endpoints for SpaceDeveloper users and show more details if that's desired.

Users that have permission to view environment variables for an app will be able to view `secret` values within a `space`. We will introduce a separate endpoint for retrieving these (similar to how app environment variables and service instance credentials are retrieved): `GET /v3/secrets/:guid/value`.

```console
curl "https://api.example.org/v3/secrets/[guid]/value" \
-X GET \
-H "Authorization: bearer [token]"

"value" : {
"some-json-key" : "some-json-value"
}
```

To support this, Cloud Controller will need to have both read and write permissions for the `secret`'s corresponding credential in CredHub.

### Creating a `secret_binding`
To create `secret_bindings`, users will use a new CLI command: `cf bind-secret`. This will create a `POST` request to `/v3/secret_bindings`.
tcdowney marked this conversation as resolved.
Show resolved Hide resolved

```console
cf bind-secret APP_NAME SECRET_NAME MOUNT_PATH
```

### CLI Changes
Work will need to be done to implement the following commands:
- `cf create-secret`
- `cf update-secret`
- `cf bind-secret`
tcdowney marked this conversation as resolved.
Show resolved Hide resolved
- `cf secrets`
- `cf secret`
- `cf delete-secret`
- `cf unbind-secret`

In addition, modifications may be made to existing CLI commands to surface `secrets` and `secret_bindings`. For example, adding bound `secret`s to `cf app` output.

### Cloud Controller Changes
New database tables will need to be created to store `secret`s and `secret_binding`s. CRUD APIs will need to be created for these resources. We will also need an API to support viewing a `secret`'s value.

### BBS changes
BBS was recently updated to support `ServiceBindingFiles` as part of RFC 0030. A `secret`'s value may result in one or more files being created in the `tmpfs` mounted directory defined by the `MountPath` parameter.

```
action := &models.RunAction{
Path: "/path/to/executable",
Args: []string{"some", "args to", "pass in"},
Dir: "/path/to/working/directory",
User: "username",
EnvironmentVariables: []*models.EnvironmentVariable{
{
Name: "ENVNAME",
Value: "ENVVALUE",
},
},
ServiceBindingFiles: []*models.Files{
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thought Maybe its too late, but do we need both ServiceBindingFiles and Secret fields here? Can these both be considered just two lists of files to mount where the value can be either explicit or de-referenced from Credhub, and Files for the purpose of ServiceBinding mounting just happen to share the same mount path SERVICE_BINDING_ROOT

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, I agree.

@beyhan do you have thoughts on how to make this cleaner? How far along is the Service Binding Files work for us to potentially generalize the BBS interface?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think my comment #994 (comment) is also relevant here.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I know this may be too late, but is the name of the field ServiceBindingFiles set in stone? I'm wondering if we could make it more generic -- even VolumeMountedFiles or something. I just don't know how far along the file-based service binding implementation is at this point.

cc @Gerg

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ideally I would have noticed this in the file-based binding RFC, but this does feel like CF-level concepts leaking into BBS's domain model. Historically, BBS has tried to separate itself from CF concepts (e.g. app vs LRP).

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ideally I would have noticed this in the file-based binding RFC, but this does feel like CF-level concepts leaking into BBS's domain model. Historically, BBS has tried to separate itself from CF concepts (e.g. app vs LRP).

I think at the stage which we are with the implementation it should be possible to change ServiceBindingFiles to VolumeMountedFiles. @stephanme, @PlamenDoychev any thoughts on this?

Copy link
Member

@beyhan beyhan Oct 24, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I opened #1008 to address the point about leaking CF-level concepts into BBS's domain model.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks @beyhan , I will update this RFC to reflect those changes.

{
Name: "/etc/cf-instance-binding",
Value: "VALUE",
},
},
Secrets: []*models.Secret{
{
Name: "SECRET_NAME",
MountPath: "/etc/conf/",
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@winkingturtle-vmw @ameowlia

Are there any paths we'd need to prevent here that would interfere with Diego or otherwise be bad? Allow app devs to drop arbitrary files anywhere could be bad.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we have the secret fail to mount + fail to start the app, if the mount path is already an existing directory on the container filesystem?

These mounts would replace the directory structure they're mounted on top of, rather than be additive, right? If so, this should prevent most problems related to masking system directories/files, or accidentally masking app code or other required resources in the app container.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

❓ Could we make a dir where the secrets always go to? Where users could make nested dirs if they want. But this way we could limit exactly where they are putting things and not need to worry about it?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The downside of limiting secret paths to a single directory is for off-the-shelf apps that are picky about where their secret files should be (there is additional discussion around this in other threads).

Value: "credhub-credential-id:<CREDHUB_CREDENTIAL_ID>",
},
{
Name: "OTHER_SECRET_NAME",
MountPath: "/etc/conf/",
Value: "<SECRET_CONTENT_AS_JSON>",
},
},
ResourceLimits: &models.ResourceLimits{
Nofile: 1000,
},
LogSource: "some-log-source",
SuppressLogOutput: false,
}
```

### Launcher Changes?
The launcher (or something else) will need to be updated to retrieve credentials from CredHub for `Secret Bindings`. It currently already does this for CredHub references contained within `VCAP_SERVICES` using the app container's instance identity credentials. Is there something other than the launcher that should have this responsibility?

Alternatively, credentials could be fetched by Cloud Controller (it does this already for Service Keys) and passed through directly to Diego. This has the disadvantage of increasing the size of the DesiredLRP and storing storing the secret contents in Diego's database.

### Other Considerations
Copy link
Member

@sethboyles sethboyles Oct 11, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

question: Any thoughts about how secrets would be managed in app/space manifests?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good call out. I think they should work like services with an array of secret names which will create secret bindings, I'll add a section on this.

Whether or not secrets themselves should be defined in a v2 space manifest is in another question. 🤔

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Whether or not secrets themselves should be defined in a v2 space manifest is in another question.

@tcdowney what do you mean by this?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@Gerg is working on a draft proposal of a "v2" version of the CF App manifest that is more declarative and includes the ability to configure other space scoped resources. This is still WIP, but he has a version of it here:
https://github.com/Gerg/community/blob/rfc_v2-app-manifests/toc/rfc/rfc-draft-v2-app-manifests.md#add-secrets



#### CredHub Maximum Secret Size
Kubernetes Secrets and ConfigMaps have a [maximum size of 1 MiB](https://kubernetes.io/docs/concepts/configuration/configmap/#motivation). The [maximum size of a CredHub credential is 64Kb](https://docs.cloudfoundry.org/credhub/credential-types.html). For `secrets` that are stored in CredHub, we will need to limit our Secrets to 64KB or increase the CredHub limit.

For `secrets` that are stored in Cloud Controller we could support an operator configurable limit up to 1 MiB.

#### (Future) Rotatable Secrets
If we make the `*Files` parameters on the `DesiredLRP` mutable in BBS, then Cloud Controller could update the `secret`s in the `DesiredLRP`, without requiring container recreation.

For certain CredHub credential types such as `certificate` or `password`, we may be able to expose CredHub credential rotation/[regeneration](https://docs.cloudfoundry.org/api/credhub/version/main/#_regenerate_credentials_endpoint) functionality.