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

Docs/intentions refactor docs day 2022 #16758

Merged
merged 26 commits into from
Mar 24, 2023
Merged
Changes from 1 commit
Commits
Show all changes
26 commits
Select commit Hold shift + click to select a range
945c132
converted intentions conf entry to ref CT format
trujillo-adam Mar 23, 2023
4034c6f
set up intentions nav
trujillo-adam Mar 23, 2023
8c06a18
add page for intentions usage
trujillo-adam Mar 23, 2023
35757aa
final intentions usage page
trujillo-adam Mar 23, 2023
1204b41
final intentions overview page
trujillo-adam Mar 23, 2023
eb19246
Merge branch 'main' into docs/intentions-refactor-docs-day-2022
trujillo-adam Mar 23, 2023
7339de8
fixed old relative links
trujillo-adam Mar 23, 2023
8c5bd0c
Merge branch 'docs/intentions-refactor-docs-day-2022' of github.com:h…
trujillo-adam Mar 23, 2023
9b6b69f
updated diagram for overview
trujillo-adam Mar 23, 2023
7e612a5
updated links to intentions content
trujillo-adam Mar 23, 2023
22a9066
fixed typo in updated links
trujillo-adam Mar 24, 2023
ad6e940
rename intentions overview page file to index
trujillo-adam Mar 24, 2023
b345201
rollback link updates to intentions overview
trujillo-adam Mar 24, 2023
8cd42d6
fixed nav
trujillo-adam Mar 24, 2023
0a45d1e
Updated custom HTML in API and CLI pages to MD
trujillo-adam Mar 24, 2023
9c1a513
applied suggestions from review to index page
trujillo-adam Mar 24, 2023
0b9bfea
moved conf examples from usage to conf ref
trujillo-adam Mar 24, 2023
aaef49e
missed custom HTML section
trujillo-adam Mar 24, 2023
c8e8894
applied additional feedback
trujillo-adam Mar 24, 2023
4c40599
Apply suggestions from code review
trujillo-adam Mar 24, 2023
a5ff062
updated headings in usage page
trujillo-adam Mar 24, 2023
0be6ddf
renamed files and udpated nav
trujillo-adam Mar 24, 2023
8b64fea
updated links to new file names
trujillo-adam Mar 24, 2023
7acd715
added redirects and final tweaks
trujillo-adam Mar 24, 2023
2bb6e9b
typo
trujillo-adam Mar 24, 2023
64f21a8
Merge branch 'main' into docs/intentions-refactor-docs-day-2022
trujillo-adam Mar 24, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
add page for intentions usage
  • Loading branch information
trujillo-adam committed Mar 23, 2023
commit 8c06a1883e2023a3e68ec10e2edd83b684acc9c0
341 changes: 341 additions & 0 deletions website/content/docs/connect/intentions/intentions-usage.mdx
Original file line number Diff line number Diff line change
@@ -0,0 +1,341 @@
---
layout: docs
page_title: Service Mesh Intentions
description: >-
Intentions define communication permissions in the service mesh between microservices. Learn about configuration basics, wildcard intentions, precedence and match order, and protecting intention management with ACLs.
---

# Service Mesh Intentions

-> **1.9.0 and later:** This guide only applies in Consul versions 1.9.0 and
later. The documentation for the legacy intentions system is
[here](/consul/docs/connect/intentions-legacy).

Intentions define access control for services via Connect and are used to
control which services may establish connections or make requests. Intentions
can be managed via the API, CLI, or UI.

Intentions are enforced on inbound connections or requests by the
[proxy](/consul/docs/connect/proxies) or within a [natively integrated
application](/consul/docs/connect/native).

Depending upon the [protocol] in use by the destination service, you can define
intentions to control Connect traffic authorization either at networking layer
4 (e.g. TCP) and application layer 7 (e.g. HTTP):

- **Identity-based** - All intentions may enforce access based on identities
encoded within [TLS
certificates](/consul/docs/connect/connect-internals#mutual-transport-layer-security-mtls).
This allows for coarse all-or-nothing access control between pairs of
services. These work with for services with any [protocol] as they only
require awareness of the TLS handshake that wraps the opaque TCP connection.
These can also be thought of as **L4 intentions**.

- **Application-aware** - Some intentions may additionally enforce access based
on [L7 request
attributes](/consul/docs/connect/config-entries/service-intentions#permissions) in
addition to connection identity. These may only be defined for services with
a [protocol] that is HTTP-based. These can also be thought of as **L7
intentions**.

At any given point in time, between any pair of services **only one intention
controls authorization**. This may be either an L4 intention or an L7
intention, but at any given point in time only one of those applies.

The [intention match API](/consul/api-docs/connect/intentions#list-matching-intentions)
should be periodically called to retrieve all relevant intentions for the
target destination. After verifying the TLS client certificate, the cached
intentions should be consulted for each incoming connection/request to
determine if it should be accepted or rejected.

The default intention behavior is defined by the [`default_policy`](/consul/docs/agent/config/config-files#acl_default_policy) configuration.
If the configuration is set `allow`, then all service mesh Connect connections will be allowed by default.
If is set to `deny`, then all connections or requests will be denied by default.

## Intention Basics

You can define a [`service-intentions`](/consul/docs/connect/config-entries/service-intentions) configuration entry to create and manage intentions, as well as manage intentions through the Consul UI. You can also perform some intention-related tasks using the API and CLI commands. Refer to the [API](/consul/api-docs/connect/intentions) and [CLI](/consul/commands/intention) documentation for details.

The following example shows a `service-intentions` configuration entry that specifies two intentions. Refer to the [`service-intentions`](/consul/docs/connect/config-entries/service-intentions) documentation for the full data model and additional examples.

<CodeTabs>

```hcl
Kind = "service-intentions"
Name = "db"
Sources = [
{
Name = "web"
Action = "deny"
},
{
Name = "api"
Action = "allow"
}
]
```

```json
{
"Kind": "service-intentions",
"Name": "db",
"Sources": [
{
"Action": "deny",
"Name": "web"
},
{
"Action": "allow",
"Name": "api"
}
]
}
```

</CodeTabs>

This configuration entry defines two intentions with a common destination of `db`. The
first intention above is a deny intention with a source of `web`. This says
that connections from web to db are not allowed and the connection will be
rejected. The second intention is an allow intention with a source of `api`.
This says that connections from api to db are allowed and connections will be
accepted.

### Wildcard Intentions

You can use the `*` wildcard to match service names when defining an intention source or destination. The wildcard matches _any_ value, which enables you to set a wide initial scope when configuring intentions.

The wildcard is supported in Consul Enterprise `namespace` fields (see [Namespaces](/consul/docs/enterprise/namespaces) for additional information), but it _is not supported_ in `partition` fields (see [Admin Partitions](/consul/docs/enterprise/admin-partitions) for additional information).

In the following example, the `web` service cannot connect to _any_ service:

<CodeTabs>

```hcl
Kind = "service-intentions"
Name = "*"
Sources = [
{
Name = "web"
Action = "deny"
}
]
```

```json
{
"Kind": "service-intentions",
"Name": "*",
"Sources": [
{
"Action": "deny",
"Name": "web"
}
]
}
```

</CodeTabs>

The `db` service is configured to deny all connection in the following example:

<CodeTabs>

```hcl
Kind = "service-intentions"
Name = "db"
Sources = [
{
Name = "*"
Action = "deny"
}
]
```

```json
{
"Kind": "service-intentions",
"Name": "db",
"Sources": [
{
"Action": "deny",
"Name": "*"
}
]
}
```

</CodeTabs>

<EnterpriseAlert inline /> This example grants Prometheus access to any service in
any namespace.

<CodeTabs>

```hcl
Kind = "service-intentions"
Name = "*"
Namespace = "*"
Sources = [
{
Name = "prometheus"
Namespace = "monitoring"
Action = "allow"
}
]
```

```json
{
"Kind": "service-intentions",
"Name": "*",
"Namespace": "*",
"Sources": [
{
"Action": "allow",
"Name": "prometheus",
"Namespace": "monitoring"
}
]
}
```

</CodeTabs>

### Enforcement

For services that define their [protocol] as TCP, intentions mediate the
ability to **establish new connections**. When an intention is modified,
existing connections will not be affected. This means that changing a
connection from "allow" to "deny" today _will not_ kill the connection.

For services that define their protocol as HTTP-based, intentions mediate the
ability to **issue new requests**.

When an intention is modified, requests received after the modification will
use the latest intention rules to enforce access. This means that though
changing a connection from "allow" to "deny" today will not kill the
connection, it will correctly block new requests from being processed.

## Precedence and Match Order

Intentions are matched in an implicit order based on specificity, preferring
deny over allow. Specificity is determined by whether a value is an exact
specified value or is the wildcard value `*`.
The full precedence table is shown below and is evaluated
top to bottom, with larger numbers being evaluated first.

| Source Namespace | Source Name | Destination Namespace | Destination Name | Precedence |
| ---------------- | ----------- | --------------------- | ---------------- | ---------- |
| Exact | Exact | Exact | Exact | 9 |
| Exact | `*` | Exact | Exact | 8 |
| `*` | `*` | Exact | Exact | 7 |
| Exact | Exact | Exact | `*` | 6 |
| Exact | `*` | Exact | `*` | 5 |
| `*` | `*` | Exact | `*` | 4 |
| Exact | Exact | `*` | `*` | 3 |
| Exact | `*` | `*` | `*` | 2 |
| `*` | `*` | `*` | `*` | 1 |

The precedence value can be read from a
[field](/consul/docs/connect/config-entries/service-intentions#precedence) on the
`service-intentions` configuration entry after it is modified. Precedence cannot be
manually overridden today.

The numbers in the table above are not stable. Their ordering will remain
fixed but the actual number values may change in the future.

-> <EnterpriseAlert inline /> - Namespaces are an Enterprise feature. In Consul
OSS the only allowable value for either namespace field is `"default"`. Other
rows in this table are not applicable.

## Intention Management Permissions

Intention management can be protected by [ACLs](/consul/docs/security/acl).
Permissions for intentions are _destination-oriented_, meaning the ACLs
for managing intentions are looked up based on the destination value
of the intention, not the source.

Intention permissions are by default implicitly granted at `read` level
when granting `service:read` or `service:write`. This is because a
service registered that wants to use Connect needs `intentions:read`
for its own service name in order to know whether or not to authorize
connections. The following ACL policy will implicitly grant `intentions:read`
(note _read_) for service `web`.

<CodeTabs>

```hcl
service "web" {
policy = "write"
}
```

```json
{
"service": [
{
"web": [
{
"policy": "write"
}
]
}
]
}
```

</CodeTabs>

It is possible to explicitly specify intention permissions. For example,
the following policy will allow a service to be discovered without granting
access to read intentions for it.

```hcl
service "web" {
policy = "read"
intentions = "deny"
}
```

Note that `intentions:read` is required for a token that a Connect-enabled
service uses to register itself or its proxy. If the token used does not
have `intentions:read` then the agent will be unable to resolve intentions
for the service and so will not be able to authorize any incoming connections.

~> **Security Note:** Explicitly allowing `intentions:write` on the token you
provide to a service instance at registration time opens up a significant
additional vulnerability. Although you may trust the service _team_ to define
which inbound connections they accept, using a combined token for registration
allows a compromised instance to to redefine the intentions which allows many
additional attack vectors and may be hard to detect. We strongly recommend only
delegating `intentions:write` using tokens that are used by operations teams or
orchestrators rather than spread via application config, or only manage
intentions with management tokens.

## Performance and Intention Updates

The intentions for services registered with a Consul agent are cached
locally on that agent. They are then updated via a background blocking query
against the Consul servers.

Supported [proxies] (such as [Envoy]) also cache this data within their own
configuration so that inbound connections or requests require no Consul agent
involvement during authorization. All actions in the data path of connections
happen within the proxy.

Updates to intentions are propagated nearly instantly to agents since agents
maintain a continuous blocking query in the background for intention updates
for registered services. Proxies similarly use blocking queries to update
their local configurations quickly.

Because all the intention data is cached locally, the agents or proxies can
fail static. Even if the agents are severed completely from the Consul servers,
or the proxies are severed completely from their local Consul agent, inbound
connection authorization continues to work indefinitely. Changes to intentions
will not be picked up until the partition heals, but will then automatically
take effect when connectivity is restored.

[protocol]: /consul/docs/connect/config-entries/service-defaults#protocol
[proxies]: /consul/docs/connect/proxies
[envoy]: /consul/docs/connect/proxies/envoy