mirror of https://github.com/hashicorp/consul
Website: GH-781 and cleanup for docs/internals/acl.html.
parent
61a7b99569
commit
ba3071c147
|
@ -9,78 +9,84 @@ description: |-
|
||||||
# ACL System
|
# ACL System
|
||||||
|
|
||||||
Consul provides an optional Access Control List (ACL) system which can be used to control
|
Consul provides an optional Access Control List (ACL) system which can be used to control
|
||||||
access to data and APIs. The ACL system is a
|
access to data and APIs. The ACL is
|
||||||
[Capability-based system](http://en.wikipedia.org/wiki/Capability-based_security) that relies
|
[Capability-based](http://en.wikipedia.org/wiki/Capability-based_security), relying
|
||||||
on tokens to which fine grained rules can be applied. It is very similar to
|
on tokens to which fine grained rules can be applied. It is very similar to
|
||||||
[AWS IAM](http://aws.amazon.com/iam/) in many ways.
|
[AWS IAM](http://aws.amazon.com/iam/) in many ways.
|
||||||
|
|
||||||
|
## Scope
|
||||||
|
|
||||||
|
When the ACL system was launched in Consul 0.4, it was only possible to specify
|
||||||
|
policies for the KV store. In Consul 0.5, ACL policies were extended to service
|
||||||
|
registrations.
|
||||||
|
|
||||||
## ACL Design
|
## ACL Design
|
||||||
|
|
||||||
The ACL system is designed to be easy to use, fast to enforce, flexible to new
|
The ACL system is designed to be easy to use, fast to enforce, and flexible to new
|
||||||
policies, all while providing administrative insight. It has been modeled on
|
policies, all while providing administrative insight.
|
||||||
the AWS IAM system, as well as the more general object-capability model. The system
|
|
||||||
is modeled around "tokens".
|
|
||||||
|
|
||||||
Every token has an ID, name, type and rule set. The ID is a randomly generated
|
Every token has an ID, name, type, and rule set. The ID is a randomly generated
|
||||||
UUID, making it unfeasible to guess. The name is opaque and human readable.
|
UUID, making it unfeasible to guess. The name is opaque to Consul and human readable.
|
||||||
The type is either "client" meaning it cannot modify ACL rules, and is restricted
|
The type is either "client" (meaning the token cannot modify ACL rules) or "management"
|
||||||
by the provided rules, or is "management" and is allowed to perform all actions.
|
(meaning the token is allowed to perform all actions).
|
||||||
|
|
||||||
The token ID is passed along with each RPC request to the servers. Agents
|
The token ID is passed along with each RPC request to the servers. Agents
|
||||||
can be configured with an [`acl_token`](/docs/agent/options.html#acl_token) property
|
can be configured with an [`acl_token`](/docs/agent/options.html#acl_token) property
|
||||||
to provide a default token, but the token can also be specified by a client on a
|
to provide a default token, but the token can also be specified by a client on a
|
||||||
[per-request basis](/docs/agent/http.html). ACLs are new as of Consul 0.4, meaning
|
[per-request basis](/docs/agent/http.html). ACLs were added in Consul 0.4, meaning
|
||||||
prior versions do not provide a token. This is handled by the special "anonymous"
|
prior versions do not provide a token. This is handled by the special "anonymous"
|
||||||
token. Anytime there is no token provided, the rules defined by that token are
|
token. If no token provided, the rules associated with the anonymous token are
|
||||||
automatically applied. This allows policy to be enforced on legacy clients.
|
automatically applied. This allows policy to be enforced on legacy clients.
|
||||||
|
|
||||||
Enforcement is always done by the server nodes. All servers must be configured
|
Enforcement is always done by the server nodes. All servers must be configured
|
||||||
to provide an [`acl_datacenter`](/docs/agent/options.html#acl_datacenter) which
|
to provide an [`acl_datacenter`](/docs/agent/options.html#acl_datacenter) which
|
||||||
enables ACL enforcement but also specifies the authoritative datacenter. Consul does not
|
enables ACL enforcement but also specifies the authoritative datacenter. Consul does not
|
||||||
replicate data cross-WAN, and instead relies on [RPC forwarding](/docs/internal/architecture.html)
|
replicate data cross-WAN and instead relies on [RPC forwarding](/docs/internal/architecture.html)
|
||||||
to support Multi-Datacenter configurations. However, because requests can be
|
to support Multi-Datacenter configurations. However, because requests can be made
|
||||||
made across datacenter boundaries, ACL tokens must be valid globally. To avoid
|
across datacenter boundaries, ACL tokens must be valid globally. To avoid
|
||||||
replication issues, a single datacenter is considered authoritative and stores
|
replication issues, a single datacenter is considered authoritative and stores
|
||||||
all the tokens.
|
all the tokens.
|
||||||
|
|
||||||
When a request is made to any non-authoritative server with a token, it must
|
When a request is made to a server in a non-authoritative datacenter server, it
|
||||||
be resolved into the appropriate policy. This is done by reading the token
|
must be resolved into the appropriate policy. This is done by reading the token
|
||||||
from the authoritative server and caching a configurable
|
from the authoritative server and caching the result for a configurable
|
||||||
[`acl_ttl`](/docs/agent/options.html#acl_ttl). The implication
|
[`acl_ttl`](/docs/agent/options.html#acl_ttl). The implication
|
||||||
of caching is that the cache TTL is an upper bound on the staleness of policy
|
of caching is that the cache TTL is an upper bound on the staleness of policy
|
||||||
that is enforced. It is possible to set a zero TTL, but this has adverse
|
that is enforced. It is possible to set a zero TTL, but this has adverse
|
||||||
performance impacts, as every request requires refreshing the policy.
|
performance impacts, as every request requires refreshing the policy via a
|
||||||
|
cross-datacenter WAN call.
|
||||||
|
|
||||||
Another possible issue is an outage of the
|
The Consul ACL center is also built to accommodate for an outage of the
|
||||||
[`acl_datacenter`](/docs/agent/options.html#acl_datacenter) or networking
|
[`acl_datacenter`](/docs/agent/options.html#acl_datacenter) or networking
|
||||||
issues preventing access. In this case, it may be impossible for non-authoritative
|
issues preventing access to it. In this case, it may be impossible for
|
||||||
servers to resolve tokens. Consul provides a number of configurable
|
servers in non-authoritative datacenters to resolve tokens. Consul provides
|
||||||
[`acl_down_policy`](/docs/agent/options.html#acl_down_policy)
|
a number of configurable [`acl_down_policy`](/docs/agent/options.html#acl_down_policy)
|
||||||
choices to tune behavior. It is possible to deny or permit all actions, or to ignore
|
choices to tune behavior. It is possible to deny or permit all actions or to ignore
|
||||||
cache TTLs and enter a fail-safe mode.
|
cache TTLs and enter a fail-safe mode. The default is to ignore cache TTLs
|
||||||
|
for any previously resolved tokens and to deny any uncached tokens.
|
||||||
|
|
||||||
ACLs can also act in either a whitelist or blacklist mode depending
|
ACLs can also act in either a whitelist or blacklist mode depending
|
||||||
on the configuration of
|
on the configuration of
|
||||||
[`acl_default_policy`](/docs/agent/options.html#acl_default_policy). If the default
|
[`acl_default_policy`](/docs/agent/options.html#acl_default_policy). If the default
|
||||||
policy is to deny all actions, then token rules can be set to allow or whitelist
|
policy is to deny all actions, then token rules can be set to allow or whitelist
|
||||||
actions. In the inverse, the allow all default behavior is a blacklist,
|
actions. In the inverse, the allow all default behavior is a blacklist
|
||||||
where rules are used to prohibit actions.
|
where rules are used to prohibit actions. By default, Consul will allow all
|
||||||
|
actions.
|
||||||
|
|
||||||
### Blacklist mode and `consul exec`
|
### Blacklist mode and `consul exec`
|
||||||
|
|
||||||
If you set [`acl_default_policy`](/docs/agent/options.html#acl_default_policy)
|
If you set [`acl_default_policy`](/docs/agent/options.html#acl_default_policy)
|
||||||
to `deny`, the `anonymous` token won't have the permission to read the default
|
to `deny`, the `anonymous` token won't have permission to read the default
|
||||||
`_rexec` prefix, and therefore token-less Consul agents (using the `anonymous` token)
|
`_rexec` prefix; therefore, Consul agents using the `anonymous` token
|
||||||
won't be able to perform [`consul exec`](/docs/commands/exec.html) actions.
|
won't be able to perform [`consul exec`](/docs/commands/exec.html) actions.
|
||||||
|
|
||||||
There is a subtle interaction there. The agents will need permission to
|
Here's why: the agents need read/write permission to the `_rexec` prefix for
|
||||||
read/write to the `_rexec` prefix for [`consul exec`](/docs/commands/exec.html) to
|
[`consul exec`](/docs/commands/exec.html) to work properly. They use that prefix
|
||||||
work properly. They use that as the transport for most data, only the edge trigger
|
as the transport for most data.
|
||||||
uses the event system.
|
|
||||||
|
|
||||||
You can do this by allowing the `anonymous` token to access that prefix, or by
|
You can enable [`consul exec`](/docs/commands/exec.html) from agents that are not
|
||||||
providing tokens to the agents that enable it. The former can be done by giving
|
configured with a token by allowing the `anonymous` token to access that prefix.
|
||||||
this rule to the `anonymous` token:
|
This can be done by giving this rule to the `anonymous` token:
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
key "_rexec/" {
|
key "_rexec/" {
|
||||||
|
@ -88,10 +94,14 @@ key "_rexec/" {
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
|
Alternatively, you can, of course, add an explicit
|
||||||
|
[`acl_token`](/docs/agent/options.html#acl_token) to each agent, giving it access
|
||||||
|
to that prefix.
|
||||||
|
|
||||||
### Bootstrapping ACLs
|
### Bootstrapping ACLs
|
||||||
|
|
||||||
Bootstrapping the ACL system is done by providing an initial [`acl_master_token`
|
Bootstrapping the ACL system is done by providing an initial [`acl_master_token`
|
||||||
configuration](/docs/agent/options.html#acl_master_token), which will be created
|
configuration](/docs/agent/options.html#acl_master_token) which will be created
|
||||||
as a "management" type token if it does not exist. Note that the [`acl_master_token`
|
as a "management" type token if it does not exist. Note that the [`acl_master_token`
|
||||||
](/docs/agent/options.html#acl_master_token) is only installed when a server acquires
|
](/docs/agent/options.html#acl_master_token) is only installed when a server acquires
|
||||||
cluster leadership. If you would like to install or change the
|
cluster leadership. If you would like to install or change the
|
||||||
|
@ -101,14 +111,33 @@ for all servers. Once this is done, restart the current leader to force a leader
|
||||||
|
|
||||||
## Rule Specification
|
## Rule Specification
|
||||||
|
|
||||||
A core part of the ACL system is a rule language which is used
|
A core part of the ACL system is a rule language which is used to describe the policy
|
||||||
to describe the policy that must be enforced. We make use of
|
that must be enforced. Consul supports ACLs for both [K/Vs](/intro/getting-started/kv.html)
|
||||||
|
and [services](/intro/getting-started/services.html).
|
||||||
|
|
||||||
|
Key policies are defined by coupling a prefix with a policy. The rules are enforced
|
||||||
|
using a longest-prefix match policy; Consul picks the most specific policy possible. The
|
||||||
|
policy is either "read", "write" or "deny". A "write" policy implies "read", and there is no
|
||||||
|
way to specify write-only. If there is no applicable rule, the
|
||||||
|
[`acl_default_policy`](/docs/agent/options.html#acl_default_policy) is applied.
|
||||||
|
|
||||||
|
Service policies are defined by coupling a service name and a policy. The rules are
|
||||||
|
enforced using an exact match policy. The default rule, applied to any service that doesn't
|
||||||
|
have a matching policy, is provided using the empty string. The policy is either "read",
|
||||||
|
"write", or "deny". A "write" policy implies "read", and there is no way to specify write-only.
|
||||||
|
If there is no applicable rule, the
|
||||||
|
[`acl_default_policy`](/docs/agent/options.html#acl_default_policy) is
|
||||||
|
applied. Currently, only the "write" level is enforced for registration of
|
||||||
|
services; services can always be read.
|
||||||
|
|
||||||
|
The policy for the "consul" service is always "write" as it is managed internally by Consul.
|
||||||
|
|
||||||
|
We make use of
|
||||||
the [HashiCorp Configuration Language (HCL)](https://github.com/hashicorp/hcl/)
|
the [HashiCorp Configuration Language (HCL)](https://github.com/hashicorp/hcl/)
|
||||||
to specify policy. This language is human readable and interoperable
|
to specify policy. This language is human readable and interoperable
|
||||||
with JSON making it easy to machine generate.
|
with JSON making it easy to machine-generate.
|
||||||
|
|
||||||
As of Consul 0.4, it is only possible to specify policies for the
|
Specification in the HCL format looks like:
|
||||||
KV store. Specification in the HCL format looks like:
|
|
||||||
|
|
||||||
```javascript
|
```javascript
|
||||||
# Default all keys to read-only
|
# Default all keys to read-only
|
||||||
|
@ -119,17 +148,17 @@ key "foo/" {
|
||||||
policy = "write"
|
policy = "write"
|
||||||
}
|
}
|
||||||
key "foo/private/" {
|
key "foo/private/" {
|
||||||
# Deny access to the private dir
|
# Deny access to the dir "foo/private"
|
||||||
policy = "deny"
|
policy = "deny"
|
||||||
}
|
}
|
||||||
|
|
||||||
# Default all services to allowing registration
|
# Default all services to allow registration
|
||||||
service "" {
|
service "" {
|
||||||
policy = "write"
|
policy = "write"
|
||||||
}
|
}
|
||||||
|
|
||||||
service "secure" {
|
service "secure" {
|
||||||
# Deny registration access to secure service
|
# Deny registration access to service named "secure"
|
||||||
policy = "read"
|
policy = "read"
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
@ -160,20 +189,3 @@ This is equivalent to the following JSON input:
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
Key policies provide both a prefix and a policy. The rules are enforced
|
|
||||||
using a longest-prefix match policy. This means we pick the most specific
|
|
||||||
policy possible. The policy is either "read", "write" or "deny". A "write"
|
|
||||||
policy implies "read", and there is no way to specify write-only. If there
|
|
||||||
is no applicable rule, the
|
|
||||||
[`acl_default_policy`](/docs/agent/options.html#acl_default_policy) is applied.
|
|
||||||
|
|
||||||
Services policies provide both a service name and a policy. The rules are
|
|
||||||
enforced using an exact match policy. The default rule is provided using
|
|
||||||
the empty string. The policy is either "read", "write", or "deny". A "write"
|
|
||||||
policy implies "read", and there is no way to specify write-only. If there
|
|
||||||
is no applicable rule, the
|
|
||||||
[`acl_default_policy`](/docs/agent/options.html#acl_default_policy) is
|
|
||||||
applied. Currently, only the "write" level is enforced for registration of
|
|
||||||
services. The policy for the "consul" service is always "write" as it is
|
|
||||||
managed internally.
|
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue