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

Add Secret store #6075

Closed
wants to merge 6 commits into from
Closed

Add Secret store #6075

wants to merge 6 commits into from

Conversation

alexlarsson
Copy link
Contributor

This is a continuation of #5836, and the discussions about it we had on last weeks irc meeting. It implements a secret store that you can access via:

  • docker secret list
  • docker secret add a-name a-file
  • docker secret rm a-name

You can then grant access to a specific secret by using docker run --grant-secret a-name image.
The granted secrets are stored (by name) in the hostconfig, and will be re-granted on restarting the container (assuming the secret is still in the store). Additionally any files stored in /etc/docker/secrets are considered "host based" secrets and will be granted to all containers on the host.

On container start the secrets are copied into a tmpfs in /run/secrets, so they will not ever be part of any image based on the container.

There are no docs yet, I'll be working on that next.

@@ -72,6 +73,7 @@ func (cli *DockerCli) CmdHelp(args ...string) error {
{"run", "Run a command in a new container"},
{"save", "Save an image to a tar archive"},
{"search", "Search for an image in the docker index"},
{"secret", "Maintain secrets database"},
Copy link
Contributor

Choose a reason for hiding this comment

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

"Maintain a secrets database" or "Maintain a database of secrets"

@alexlarsson
Copy link
Contributor Author

Update fixes the doc misspelling

@cyphar
Copy link
Contributor

cyphar commented May 29, 2014

+1 for secrets which are added to a container's fs during run-time. This would be invaluable for ssh keys and other secrets. This is a feature which would make a project I'm working on much simpler.

@alexlarsson
Copy link
Contributor Author

Updated to latest master

return err
}
for _, s := range data {
container.command.CreateFiles[filepath.Join("/run/secrets", s.Name)] = s.Data
Copy link
Contributor

Choose a reason for hiding this comment

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

did you consider /var/run or /var/tmp instead?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

/var/run is typically a symlink to /run in "modern" distros. See e.g. https://wiki.debian.org/ReleaseGoals/RunDirectory
I don't think /var/tmp makes sense, its semantically less like a temporary file, more like a runtime transient file.

@timthelion
Copy link
Contributor

@alexlarsson would you mind answering this: https://groups.google.com/forum/#!topic/docker-user/aWStVPCwq6w ?

@cyphar
Copy link
Contributor

cyphar commented Jun 2, 2014

Out of interest, why --grant-secret and not just --secret or --secrets?

@alexlarsson
Copy link
Contributor Author

@cyphar It grants access to a predefined secret rather than define a secret, so it felt right. I'm open to changing that of course, if we want it to be shorter then --secret would be better.

@timthelion
Copy link
Contributor

--grant-secret is better, less ambiguos.

@shykes
Copy link
Contributor

shykes commented Jun 4, 2014

+1 on --grant-secret

@crosbymichael
Copy link
Contributor

@alexlarsson why can these files not be bind mounted?

} else {
hostBased := ""
if out.GetBool("HostBased") {
hostBased = "*"
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 use [OK] instead of * like in docker search ?

/cc @crosbymichael @shykes

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Well, that signifies "trusted" to which "ok" seems to make sense. Here it is a bit more generic boolean. Maybe [x] ?

Copy link
Contributor

Choose a reason for hiding this comment

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

Maybe [HOST] or just [H]?

@alexlarsson
Copy link
Contributor Author

@crosbymichael We want to copy the files for real into the container so that later changes to the secret store does not affect running containers. For instance, it should be possible to remove a secret from the store once a container is started with it. Furthermore, we might have secrets that are not necessarily stored as regular files in the filesystem in the future (in an earlier patch the secrets were never on the host fs at all for instance).

That said, we could perhaps use bind mounts at a higher level. I.e. mount the tmpfs on the host, copy files to it, then bind mount it into the container and unmount the host version. I'll have a look at that.

@alexlarsson
Copy link
Contributor Author

@crosbymichael Here is the alternative implementation using a tmpfs from the host bind-mounted in:
alexlarsson@d92b083

If you prefer that approach we can drop a bunch of the libcontainer commits when this is squashed in.

If you implent CmdFoo with an extra boolean first arg, and CmdFooList
and CmdFooAdd as usual the code will make this just work.

Docker-DCO-1.1-Signed-off-by: Alexander Larsson <alexl@redhat.com> (github: alexlarsson)
The secrets store keeps track of a set of named secrets, such as API
keys or ssh keys that you can later access from containers.

There are two types of secrets, the host based ones, which are stored
in /etc/docker/secrets, and are automatically applied to all containers,
and user secrets which you can add via "docker secret add <name> <file>"
and which can be granted permission to by name.

You can also list secrets with "docker secret list" and remove them
with "docker secret rm".

Docker-DCO-1.1-Signed-off-by: Alexander Larsson <alexl@redhat.com> (github: alexlarsson)
If you run something like
  docker run --grant-secret foo image

Then the "foo" secret will be copied into a /run/secrets tmpfs in the
container. Additionally, all host-based secrets will be copied into
all containers running on a specific host.

Docker-DCO-1.1-Signed-off-by: Alexander Larsson <alexl@redhat.com> (github: alexlarsson)
This is useful if you want to use secrets during docker build which will
not be recorded in the final image.

Docker-DCO-1.1-Signed-off-by: Alexander Larsson <alexl@redhat.com> (github: alexlarsson)
Docker-DCO-1.1-Signed-off-by: Alexander Larsson <alexl@redhat.com> (github: alexlarsson)
Docker-DCO-1.1-Signed-off-by: Alexander Larsson <alexl@redhat.com> (github: alexlarsson)
@alexlarsson
Copy link
Contributor Author

I rebased on master with the alternative approach from above.
Note, this depends on this PR for libcontainer to avoid a race condition: docker-archive/libcontainer#22


Lists the names and details of all the secrets that are installed in
the docker daemon secret store. Access to these secrets can be granted
to containers at user disgression.
Copy link
Contributor

Choose a reason for hiding this comment

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

I presume you mean discretion :)

@vbatts
Copy link
Contributor

vbatts commented Jun 24, 2014

@SvenDowideit how about the commit I've added here https://github.com/vbatts/docker/compare/alexlarsson-secrets

@SvenDowideit
Copy link
Contributor

@vbatts @alexlarsson better, but still i don't think its enough. I would suggest adding a mention to the --grant-secrets cli summary; something like the selected secret file will be added in /run/secrets, and the docker build and docker run cli.md and man pages really do need to talk about what a secret is (it seems you've hinted that a secret is actually a single file, and that it will go into /run/secret, but you've not actually explicitly said so.

now to the harder part....

Does this mean /run/secret is now special, and any base image with that dir will lose access, or are you just inserting a file? Also... can I have more than one secret?

these questions should be answered for the reader in the cli documentation - otherwise they're left not knowing - and obviously, if its documented, there should be tests for that.

@timthelion
Copy link
Contributor

/etc/docker/secrets is also completely undocumented.

@vbatts
Copy link
Contributor

vbatts commented Jun 25, 2014

@SvenDowideit @timthelion k. I'll work on this.

@vbatts
Copy link
Contributor

vbatts commented Jun 26, 2014

@SvenDowideit @timthelion see #6697

@vbatts
Copy link
Contributor

vbatts commented Jun 26, 2014

As a note, I've identified a couple of items regarding this feature that I will either fix or get clarity on.

  • docker secret add can not handle adding directories, but the /etc/docker/secrets handles directories fine
  • duplicate file names can not be added through docker secret add, but can exist if a duplicate is added to /etc/docker/secrets/ after the first is added through the cli
  • despite /run/secrets being create as 0700, once mounted tmpfs it's sticky world readable 1777 inside the container

Also, i'm not sure how to handle the uniqueness of file names, and having them appear in the container in a consistent way. Perhaps to have a markup, similar to --volume, so there could be --grant-secret=:content.pem to have the uniquely named file from the host/store, be available in the container as "content.pem".

@timthelion
Copy link
Contributor

@vbatts I think that the existence of /etc/docker/secrets should really be reconsidered. When this was discussed at the a contributers IRC meeting which lead to this PR the idea of having /etc/docker/secrets was not really agreed upon. The whole point of this PR was supposed to be "to have something simple that can make it into 1.0". That is obviously a mute point now. It would be much better to have a docker secret set-group global command or something like that.

@SvenDowideit
Copy link
Contributor

are we moving to #6697, and thus should close this to avoid losing info due to split conversation?

@vbatts
Copy link
Contributor

vbatts commented Jun 30, 2014

@SvenDowideit I'm not opposed to moving the conversation. Most of the meat of the design is on this issue.

@timthelion I can't disagree with you. I've only gotten involved on this request recently. Perhaps having a syntax like docker secret add --global foo.cert would be simpler and more understandable. Also, gating everything at add helps with the duplicate/conflicted name bug in the current implementation. And docker secret rm ... would still work the same. The issue becomes that "host secrets" implies an ACL that docker does not currently have full support of. Even adding a flag like --globabl so that the secret file is in all new containers, means that any user that is in the 'docker' group can add/rm with global secrets. Where as, as a sysadmin of the host I could ensure that this file is in all new containers, and a user in the 'docker' group could not remove that secret. This is a use case that is not easily done just-in-docker.

@erikh
Copy link
Contributor

erikh commented Aug 1, 2014

The changes here in server/buildfile.go conflict with recent changes to this functionality. Can you rebase?

@timthelion
Copy link
Contributor

@SvenDowideit Yes, please close this in favor of #6697, this is getting confusing :(

@tiborvass
Copy link
Contributor

Closing in favor of #6697 (which is carrying this PR)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet