Skip to content

Commit 8ee0d77

Browse files
committed
Add network egress resource
Signed-off-by: Philip Laine <philip.laine@gmail.com>
1 parent c5bc182 commit 8ee0d77

28 files changed

Lines changed: 2079 additions & 64 deletions

PROJECT

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -123,4 +123,12 @@ resources:
123123
kind: ClusterProxy
124124
path: github.com/netbirdio/kubernetes-operator/api/v1alpha1
125125
version: v1alpha1
126+
- api:
127+
crdVersion: v1
128+
namespaced: true
129+
controller: true
130+
domain: netbird.io
131+
kind: NetworkEgress
132+
path: github.com/netbirdio/kubernetes-operator/api/v1alpha1
133+
version: v1alpha1
126134
version: "3"

README.md

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -23,9 +23,10 @@ helm upgrade --install --create-namespace -n netbird netbird-operator oci://ghcr
2323

2424
| Kind | API Version |
2525
|------|-------------|
26+
| [SetupKey](docs/api-reference.md#setupkey) | `netbird.io/v1alpha1` |
2627
| [Group](docs/api-reference.md#group) | `netbird.io/v1alpha1` |
27-
| [NetworkResource](docs/api-reference.md#networkresource) | `netbird.io/v1alpha1` |
2828
| [NetworkRouter](docs/api-reference.md#networkrouter) | `netbird.io/v1alpha1` |
29-
| [SetupKey](docs/api-reference.md#setupkey) | `netbird.io/v1alpha1` |
29+
| [NetworkResource](docs/api-reference.md#networkresource) | `netbird.io/v1alpha1` |
30+
| [NetworkEgress](docs/api-reference.md#networkegress) | `netbird.io/v1alpha1` |
3031
| [SidecarProfile](docs/api-reference.md#sidecarprofile) | `netbird.io/v1alpha1` |
3132
| [ClusterProxy](docs/api-reference.md#clusterproxy) | `netbird.io/v1alpha1` |
Lines changed: 116 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,116 @@
1+
// SPDX-License-Identifier: BSD-3-Clause
2+
3+
package v1alpha1
4+
5+
import (
6+
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
7+
)
8+
9+
// NetworkEgressSpec defines the desired state of NetworkEgress.
10+
type NetworkEgressSpec struct {
11+
// NetworkRouterRef is a reference to the network and router where the resource will be created.
12+
// +kubebuilder:validation:XValidation:rule="self == oldSelf",message="Value is immutable"
13+
NetworkRouterRef CrossNamespaceReference `json:"networkRouterRef"`
14+
15+
// Target for egress traffic.
16+
Target NetworkEgressTarget `json:"target"`
17+
18+
// Ports to the resource to route.
19+
Ports []NetworkEgressPort `json:"ports"`
20+
}
21+
22+
// EgressTarget describes a single allowed egress destination.
23+
// Exactly one of IP or FQDN must be set.
24+
// +kubebuilder:validation:XValidation:rule="(has(self.ip) ? 1 : 0) + (has(self.fqdn) ? 1 : 0) == 1",message="exactly one of ip or fqdn must be set"
25+
type NetworkEgressTarget struct {
26+
// IP targets a single specific IP address (not a CIDR range).
27+
// +optional
28+
IP *IPTarget `json:"ip,omitempty"`
29+
30+
// FQDN targets an exact domain name (no wildcards).
31+
// +optional
32+
FQDN *FQDNTarget `json:"fqdn,omitempty"`
33+
}
34+
35+
// IPTarget is a single IPv4 or IPv6 address.
36+
type IPTarget struct {
37+
// Address is a single IP address.
38+
// +kubebuilder:validation:Required
39+
// +kubebuilder:validation:XValidation:rule="isIP(self)",message="address must be a valid IPv4 or IPv6 address"
40+
Address string `json:"address"`
41+
}
42+
43+
// FQDNTarget matches traffic by an exact domain name (no wildcards).
44+
type FQDNTarget struct {
45+
// Hostname is a fully qualified domain name to match exactly.
46+
// +kubebuilder:validation:Required
47+
// +kubebuilder:validation:Pattern=`^([a-zA-Z0-9]([a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?\.)+[a-zA-Z]{2,}$`
48+
Hostname string `json:"hostname"`
49+
}
50+
51+
type NetworkEgressPort struct {
52+
// Name of the port.
53+
// +required
54+
// +kubebuilder:validation:MinLength=1
55+
Name string `json:"name,omitempty"`
56+
57+
// The port that will be exposed by this service.
58+
// +required
59+
// +kubebuilder:validation:Minimum=1
60+
// +kubebuilder:validation:Maximum=65535
61+
Port int32 `json:"port"`
62+
}
63+
64+
// NetworkEgressStatus defines the observed state of NetworkEgress.
65+
type NetworkEgressStatus struct {
66+
// ObservedGeneration is the last reconciled generation.
67+
// +optional
68+
ObservedGeneration int64 `json:"observedGeneration,omitempty"`
69+
70+
// Conditions holds the conditions for the NetworkEgress.
71+
// +listType=map
72+
// +listMapKey=type
73+
// +optional
74+
Conditions []metav1.Condition `json:"conditions,omitempty"`
75+
}
76+
77+
// +kubebuilder:object:root=true
78+
// +kubebuilder:subresource:status
79+
// +kubebuilder:resource
80+
// +kubebuilder:printcolumn:name="Ready",type="string",JSONPath=".status.conditions[?(@.type==\"Ready\")].status",description=""
81+
// +kubebuilder:printcolumn:name="Age",type="date",JSONPath=".metadata.creationTimestamp",description=""
82+
83+
// NetworkEgress is the Schema for the networkegresses API.
84+
type NetworkEgress struct {
85+
metav1.TypeMeta `json:",inline"`
86+
metav1.ObjectMeta `json:"metadata,omitempty"`
87+
88+
// +required
89+
Spec NetworkEgressSpec `json:"spec"`
90+
91+
// +kubebuilder:default={"observedGeneration":-1}
92+
Status NetworkEgressStatus `json:"status,omitempty"`
93+
}
94+
95+
// GetConditions returns the status conditions of the object.
96+
func (n *NetworkEgress) GetConditions() []metav1.Condition {
97+
return n.Status.Conditions
98+
}
99+
100+
// SetConditions sets the status conditions on the object.
101+
func (n *NetworkEgress) SetConditions(conditions []metav1.Condition) {
102+
n.Status.Conditions = conditions
103+
}
104+
105+
// +kubebuilder:object:root=true
106+
107+
// NetworkEgressList contains a list of NetworkEgress
108+
type NetworkEgressList struct {
109+
metav1.TypeMeta `json:",inline"`
110+
metav1.ListMeta `json:"metadata,omitzero"`
111+
Items []NetworkEgress `json:"items"`
112+
}
113+
114+
func init() {
115+
SchemeBuilder.Register(&NetworkEgress{}, &NetworkEgressList{})
116+
}

api/v1alpha1/zz_generated.deepcopy.go

Lines changed: 173 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)