Promote volume drivers from experimental to master.

Remove volume stubs and use the experimental path as the only path.

Signed-off-by: David Calavera <david.calavera@gmail.com>
Upstream-commit: 356a7beb31
Component: cli
This commit is contained in:
David Calavera
2015-07-15 11:25:56 -07:00
committed by Tibor Vass
parent 1591eec643
commit 08e6f56c35
5 changed files with 79 additions and 51 deletions

View File

@ -0,0 +1,22 @@
<!--[metadata]>
+++
title = "Extend Docker"
description = "How to extend Docker with plugins"
keywords = ["extend, plugins, docker, documentation, developer"]
[menu.main]
identifier = "mn_extend"
name = "Extend Docker"
weight = 6
+++
<![end-metadata]-->
## Extending Docker
Currently, you can extend Docker by adding a plugin. This section contains the following topics:
* [Understand Docker plugins](plugins.md)
* [Write a volume plugin](plugins_volumes.md)
* [Docker plugin API](plugin_api.md)

View File

@ -0,0 +1,135 @@
<!--[metadata]>
+++
title = "Plugins API"
description = "How to write Docker plugins extensions "
keywords = ["API, Usage, plugins, documentation, developer"]
[menu.main]
parent = "mn_extend"
weight=1
+++
<![end-metadata]-->
# Docker Plugin API
Docker plugins are out-of-process extensions which add capabilities to the
Docker Engine.
This page is intended for people who want to develop their own Docker plugin.
If you just want to learn about or use Docker plugins, look
[here](plugins.md).
## What plugins are
A plugin is a process running on the same docker host as the docker daemon,
which registers itself by placing a file in one of the plugin directories described in [Plugin discovery](#plugin-discovery).
Plugins have human-readable names, which are short, lowercase strings. For
example, `flocker` or `weave`.
Plugins can run inside or outside containers. Currently running them outside
containers is recommended.
## Plugin discovery
Docker discovers plugins by looking for them in the plugin directory whenever a
user or container tries to use one by name.
There are three types of files which can be put in the plugin directory.
* `.sock` files are UNIX domain sockets.
* `.spec` files are text files containing a URL, such as `unix:///other.sock`.
* `.json` files are text files containing a full json specification for the plugin.
UNIX domain socket files must be located under `/run/docker/plugins`, whereas
spec files can be located either under `/etc/docker/plugins` or `/usr/lib/docker/plugins`.
The name of the file (excluding the extension) determines the plugin name.
For example, the `flocker` plugin might create a UNIX socket at
`/run/docker/plugins/flocker.sock`.
You can define each plugin into a separated subdirectory if you want to isolate definitions from each other.
For example, you can create the `flocker` socket under `/run/docker/plugins/flocker/flocker.sock` and only
mount `/run/docker/plugins/flocker` inside the `flocker` container.
Docker always searches for unix sockets in `/run/docker/plugins` first. It checks for spec or json files under
`/etc/docker/plugins` and `/usr/lib/docker/plugins` if the socket doesn't exist. The directory scan stops as
soon as it finds the first plugin definition with the given name.
### JSON specification
This is the JSON format for a plugin:
```json
{
"Name": "plugin-example",
"Addr": "https://example.com/docker/plugin",
"TLSConfig": {
"InsecureSkipVerify": false,
"CAFile": "/usr/shared/docker/certs/example-ca.pem",
"CertFile": "/usr/shared/docker/certs/example-cert.pem",
"KeyFile": "/usr/shared/docker/certs/example-key.pem",
}
}
```
The `TLSConfig` field is optional and TLS will only be verified if this configuration is present.
## Plugin lifecycle
Plugins should be started before Docker, and stopped after Docker. For
example, when packaging a plugin for a platform which supports `systemd`, you
might use [`systemd` dependencies](
http://www.freedesktop.org/software/systemd/man/systemd.unit.html#Before=) to
manage startup and shutdown order.
When upgrading a plugin, you should first stop the Docker daemon, upgrade the
plugin, then start Docker again.
## Plugin activation
When a plugin is first referred to -- either by a user referring to it by name
(e.g. `docker run --volume-driver=foo`) or a container already configured to
use a plugin being started -- Docker looks for the named plugin in the plugin
directory and activates it with a handshake. See Handshake API below.
Plugins are *not* activated automatically at Docker daemon startup. Rather,
they are activated only lazily, or on-demand, when they are needed.
## API design
The Plugin API is RPC-style JSON over HTTP, much like webhooks.
Requests flow *from* the Docker daemon *to* the plugin. So the plugin needs to
implement an HTTP server and bind this to the UNIX socket mentioned in the
"plugin discovery" section.
All requests are HTTP `POST` requests.
The API is versioned via an Accept header, which currently is always set to
`application/vnd.docker.plugins.v1+json`.
## Handshake API
Plugins are activated via the following "handshake" API call.
### /Plugin.Activate
**Request:** empty body
**Response:**
```
{
"Implements": ["VolumeDriver"]
}
```
Responds with a list of Docker subsystems which this plugin implements.
After activation, the plugin will then be sent events from this subsystem.
## Plugin retries
Attempts to call a method on a plugin are retried with an exponential backoff
for up to 30 seconds. This may help when packaging plugins as containers, since
it gives plugin containers a chance to start up before failing any user
containers which depend on them.

View File

@ -0,0 +1,55 @@
<!--[metadata]>
+++
title = "Extending Docker with plugins"
description = "How to add additional functionality to Docker with plugins extensions"
keywords = ["Examples, Usage, plugins, docker, documentation, user guide"]
[menu.main]
parent = "mn_extend"
weight=-1
+++
<![end-metadata]-->
# Understand Docker plugins
You can extend the capabilities of the Docker Engine by loading third-party
plugins.
## Types of plugins
Plugins extend Docker's functionality. They come in specific types. For
example, a [volume plugin](plugins_volume.md) might enable Docker
volumes to persist across multiple Docker hosts.
Currently Docker supports volume and network driver plugins. In the future it
will support additional plugin types.
## Installing a plugin
Follow the instructions in the plugin's documentation.
## Finding a plugin
The following plugins exist:
* The [Flocker plugin](https://clusterhq.com/docker-plugin/) is a volume plugin
which provides multi-host portable volumes for Docker, enabling you to run
databases and other stateful containers and move them around across a cluster
of machines.
* The [GlusterFS plugin](https://github.com/calavera/docker-volume-glusterfs) is
another volume plugin that provides multi-host volumes management for Docker
using GlusterFS.
* The [Keywhiz plugin](https://github.com/calavera/docker-volume-keywhiz) is
a plugin that provides credentials and secret management using Keywhiz as
a central repository.
## Troubleshooting a plugin
If you are having problems with Docker after loading a plugin, ask the authors
of the plugin for help. The Docker team may not be able to assist you.
## Writing a plugin
If you are interested in writing a plugin for Docker, or seeing how they work
under the hood, see the [docker plugins reference](plugin_api.md).

View File

@ -0,0 +1,158 @@
<!--[metadata]>
+++
title = "Volume plugins"
description = "How to manage data with external volume plugins"
keywords = ["Examples, Usage, volume, docker, data, volumes, plugin, api"]
[menu.main]
parent = "mn_extend"
+++
<![end-metadata]-->
# Write a volume plugin
Docker volume plugins enable Docker deployments to be integrated with external
storage systems, such as Amazon EBS, and enable data volumes to persist beyond
the lifetime of a single Docker host. See the [plugin documentation](plugins.md)
for more information.
# Command-line changes
A volume plugin makes use of the `-v`and `--volume-driver` flag on the `docker run` command. The `-v` flag accepts a volume name and the `--volume-driver` flag a driver type, for example:
$ docker run -ti -v volumename:/data --volume-driver=flocker busybox sh
This command passes the `volumename` through to the volume plugin as a
user-given name for the volume. The `volumename` must not begin with a `/`.
By having the user specify a `volumename`, a plugin can associate the volume
with an external volume beyond the lifetime of a single container or container
host. This can be used, for example, to move a stateful container from one
server to another.
By specifying a `volumedriver` in conjunction with a `volumename`, users can use plugins such as [Flocker](https://clusterhq.com/docker-plugin/) to manage volumes external to a single host, such as those on EBS.
# Create a VolumeDriver
The container creation endpoint (`/containers/create`) accepts a `VolumeDriver`
field of type `string` allowing to specify the name of the driver. It's default
value of `"local"` (the default driver for local volumes).
# Volume plugin protocol
If a plugin registers itself as a `VolumeDriver` when activated, then it is
expected to provide writeable paths on the host filesystem for the Docker
daemon to provide to containers to consume.
The Docker daemon handles bind-mounting the provided paths into user
containers.
### /VolumeDriver.Create
**Request**:
```
{
"Name": "volume_name"
}
```
Instruct the plugin that the user wants to create a volume, given a user
specified volume name. The plugin does not need to actually manifest the
volume on the filesystem yet (until Mount is called).
**Response**:
```
{
"Err": null
}
```
Respond with a string error if an error occurred.
### /VolumeDriver.Remove
**Request**:
```
{
"Name": "volume_name"
}
```
Create a volume, given a user specified volume name.
**Response**:
```
{
"Err": null
}
```
Respond with a string error if an error occurred.
### /VolumeDriver.Mount
**Request**:
```
{
"Name": "volume_name"
}
```
Docker requires the plugin to provide a volume, given a user specified volume
name. This is called once per container start.
**Response**:
```
{
"Mountpoint": "/path/to/directory/on/host",
"Err": null
}
```
Respond with the path on the host filesystem where the volume has been made
available, and/or a string error if an error occurred.
### /VolumeDriver.Path
**Request**:
```
{
"Name": "volume_name"
}
```
Docker needs reminding of the path to the volume on the host.
**Response**:
```
{
"Mountpoint": "/path/to/directory/on/host",
"Err": null
}
```
Respond with the path on the host filesystem where the volume has been made
available, and/or a string error if an error occurred.
### /VolumeDriver.Unmount
**Request**:
```
{
"Name": "volume_name"
}
```
Indication that Docker no longer is using the named volume. This is called once
per container stop. Plugin may deduce that it is safe to deprovision it at
this point.
**Response**:
```
{
"Err": null
}
```
Respond with a string error if an error occurred.