Skip to content

Commit

Permalink
Network policy integration documentation
Browse files Browse the repository at this point in the history
  • Loading branch information
salv-orlando committed Oct 23, 2016
1 parent 6de9249 commit d844bd7
Showing 1 changed file with 124 additions and 0 deletions.
124 changes: 124 additions & 0 deletions docs/nw_policies.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,124 @@
Kubernetes Network Policies Support
===================================

Support is disabled by default, and should be enabled launching the watcher
`--watch-policies` option. When launched with this option the watcher process
will monitor Kubernetes namespaces, and for each namespace will monitor
network policies.

Network policy OVN integration has been tested against Kubernetes v1.4, where
network policies are a beta API. The integration will not work with Kubernetes
v1.3, where network policies where in alpha state and implemented via
ThirdPartyResources.

The watcher process will only implement network policies on those namespaces
whose default isolation behavior is set to __DefaultDeny__. Any other value
for the namespace isolation annotation will be ignored, and the namespace
will be treated as non-isolated.

The isolation annotation for an isolated namespace should have the following
value:

```
net.beta.kubernetes.io/network-policy: |
{
"ingress": {
"isolation": "DefaultDeny"
}
}
```

It is also worth noting that:

- The value of the property must be in JSON format. The Kubernetes API
server expects a string and will not perform any JSON validation.
The watcher processes will however only try to parse this string as
JSON. Any failure in parsing will result in the namespace being
considered non-isolated
- As the server only expects a string, this value should be passed as such
when annotating with kubectl, and quotes must be properly escaped. More
information are available on the [Kubernetes docs page for network
policies](http://kubernetes.io/docs/user-guide/networkpolicies/#
configuring-namespace-isolation-policy)

Theory of operation
--------------------

This section briefly discusses how the network policy integration for OVN
operates with regards to pod, namespace, and policy events.


Policy workflow for pod operations
-----------------------------------

Network policies are enforced via OVN ACLs. The ACLs are generated before the
pod is started. ACLs are generated only for each network policies whose pod
selector matches the pod being started. A distinct ACL is generated for each
rule in the network policy object. In particular:
- Port and protocols in the 'ports' clause for a policy are converted into
`tcp.dst` and `udp.dst` expressions in the match rule;
- The IP addresses for pods matched by pod or namespace selector are in a
unique address set for the rule. The address set is then referenced in the
`ip.src` expression of the match rule;
- The pod's OVN logical port is always part of the ACL match; therefore each
ACLs always applies to a single pod.
- Every ACL has the same priority, which is anyway higher than the baseline
'drop' ACL which is added for every pod created in isolated namespaces.

Policy enforcement is synchronous with creation of the pod's logical port.
When the CNI plugin receives network information for a given pod, the
watcher process already enforced network policies for that pod.

Upon pod deletion, every ACL configured for the pod is destroyed, and the
pod's ip address removed from the policy address sets.

Pod labels affect policy rules' from clauses. Whenever a change is detected
in pod labels, address sets for policies might need to be recalculated. The
current logic - inefficiently - recalculates all address sets every time a
change in pod labels is detected.

_Note:_ The current integration does not recalculate address sets upon
namespace events, which might affect policy rules' namespace selectors.
This is a limitation that will be addressed in the near future.

Policy workflow for namespace operations
-----------------------------------------

The workflow above applies - obviously - only if the namespace where the pod
is being created is isolated. If the pod is instead created in a
non-isolated namespace, an ACL for explicitly white listing traffic directed
to that pod is created.

Whenever namespace isolation is switched on or off, ACLs for every pod in
the namespace are recalculated. This process is however not synchronous with
the namespace operation, as that operation simply changes the value of
the namespace isolation annotation on the Kubernetes API server.

_Note_: Unfortunately Kubernetes (as of version 1.4) does not offer any
facility to assess whether policy processing has been completed or not, and
in the first case whether it completed successfully or not.


Workflow for policy operations
-------------------------------

Network policies rules are translated in 'pseudo-ACL', which are simply
in-memory data structures that contain abstract data for creating match rules
for OVN ACLs.
When a policy is created, its pod selector is analyzed to check for which pods
the policy must be enforced. Then pseudo-ACLs for those policies are
translated into actual ACLs building a match rule which also includes the OVN
logical port for the pod in the match expression.

When a network policy is deleted, all of its address sets are destroyed,
together with the ACLs for all pods that match the policy pod selector.

_Note_: As policy objects are accessed only through a namespace scope, the
watcher process maintains a distinct watcher thread for every namespace.
For this reason the logs will show a creation of a distinct network policy
watcher for every namespace in the Kubernetes cluster.

Implementation details
----------------------

TBD

0 comments on commit d844bd7

Please sign in to comment.