1 package vpnconfig
2
3 import (
4 "context"
5 "errors"
6 "net"
7
8 "sigs.k8s.io/controller-runtime/pkg/client"
9
10 metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
11
12 "edge-infra.dev/pkg/edge/api/types"
13 v1cluster "edge-infra.dev/pkg/edge/apis/cluster/v1alpha1"
14 v1vpnconfig "edge-infra.dev/pkg/sds/remoteaccess/k8s/apis/vpnconfigs/v1"
15 "edge-infra.dev/pkg/sds/remoteaccess/service"
16 "edge-infra.dev/pkg/sds/remoteaccess/wireguard/vpn"
17 )
18
19 func Update(ctx context.Context, c client.Client, sm types.SecretManagerService, vpn *vpn.VPN, vpnConfig *v1vpnconfig.VPNConfig, cluster *v1cluster.Cluster) error {
20
21 if err := vpn.UpdateRelay(ctx, c); err != nil {
22 return err
23 }
24 if err := vpn.UpdateClient(ctx, c); err != nil {
25 return err
26 }
27
28
29 lbIP, err := service.GetLoadBalancerExternalIP(ctx, c)
30 if err != nil {
31 return err
32 } else if lbIP == nil {
33 return errors.New("load balancer does not have an external IP")
34 }
35
36
37 if err := vpn.ConfigureSubnet(ctx, c); err != nil {
38 return err
39 }
40
41
42 if err := updateVPNConfigIPAddress(vpnConfig, vpn); err != nil {
43 return err
44 }
45
46
47 if err := vpn.UpdateStore(ctx, c, vpnConfig, cluster); err != nil {
48 return err
49 }
50
51 _, subnet, err := net.ParseCIDR(vpn.GetSubnetCIDR())
52 if err != nil {
53 return err
54 }
55
56
57 if err := vpn.Store(vpnConfig.ClusterEdgeID()).UpdateWireguardSecret(
58 ctx,
59 c,
60 subnet,
61 vpn.Client().GetIPAddress(),
62 lbIP,
63 vpn.Relay().GetPublicKey(),
64 sm,
65 cluster,
66 ); err != nil {
67 return err
68 }
69
70
71 if err := vpn.Store(vpnConfig.ClusterEdgeID()).UpdateEmissaryMapping(ctx, c, cluster.GetName()); err != nil {
72 return err
73 }
74
75
76 if err := vpn.Client().UpdateWireguardSecret(
77 ctx,
78 c,
79 subnet,
80 lbIP,
81 vpn.Relay().GetPublicKey(),
82 vpn.Stores(),
83 ); err != nil {
84 return err
85 }
86
87
88 return vpn.Relay().UpdateWireguardSecret(
89 ctx,
90 c,
91 subnet,
92 vpn.Client().GetIPAddress(),
93 vpn.Client().GetPublicKey(),
94 vpn.Stores(),
95 )
96 }
97
98 func updateVPNConfigIPAddress(vpnConfig *v1vpnconfig.VPNConfig, vpn *vpn.VPN) error {
99 if isValid, err := checkIPAddressIsValid(vpnConfig, vpn); err != nil {
100 return err
101 } else if isValid {
102 return nil
103 }
104
105
106 ip, err := vpn.RequestAvailableIPAddress(vpnConfig.ClusterEdgeID())
107 if err != nil {
108 return err
109 }
110
111
112 if vpnConfig.Status == nil {
113 vpnConfig.Status = &v1vpnconfig.VPNConfigStatus{}
114 }
115 vpnConfig.Status.IP = ip.String()
116 return nil
117 }
118
119 func checkIPAddressIsValid(vpnConfig *v1vpnconfig.VPNConfig, vpn *vpn.VPN) (bool, error) {
120
121 if isInSubnet, err := vpn.IPAddressIsInSubnet(vpnConfig.IP()); err != nil {
122 return false, err
123 } else if !isInSubnet {
124 return false, nil
125 }
126
127
128 if vpn.CheckIPAddressIsAvailable(vpnConfig.IP()) {
129 return true, nil
130 }
131
132
133 if vpn.CheckIPAddressIsAssignedToStore(vpnConfig.IP(), vpnConfig.ClusterEdgeID()) {
134 return true, nil
135 }
136
137 return false, nil
138 }
139
140 func Remove(ctx context.Context, c client.Client, sm types.SecretManagerService, vpn *vpn.VPN, vpnConfig *v1vpnconfig.VPNConfig, cluster *v1cluster.Cluster) error {
141
142 if !vpn.HasStore(vpnConfig.ClusterEdgeID()) {
143 if err := vpn.UpdateStore(ctx, c, vpnConfig, cluster); err != nil {
144 return err
145 }
146 }
147
148
149 if err := vpn.Store(vpnConfig.ClusterEdgeID()).RemoveWireguardSecret(ctx, c, sm); err != nil {
150 return err
151 }
152
153
154 if err := vpn.Store(vpnConfig.ClusterEdgeID()).RemoveEmissaryMapping(ctx, c); err != nil {
155 return err
156 }
157
158
159 vpn.RemoveStore(vpnConfig.ClusterEdgeID())
160
161
162 lbIP, err := service.GetLoadBalancerExternalIP(ctx, c)
163 if err != nil {
164 return err
165 } else if lbIP == nil {
166 return errors.New("load balancer does not have an external IP")
167 }
168
169 _, subnet, err := net.ParseCIDR(vpn.GetSubnetCIDR())
170 if err != nil {
171 return err
172 }
173
174
175 if err := vpn.Client().UpdateWireguardSecret(
176 ctx,
177 c,
178 subnet,
179 lbIP,
180 vpn.Relay().GetPublicKey(),
181 vpn.Stores(),
182 ); err != nil {
183 return err
184 }
185
186
187 return vpn.Relay().UpdateWireguardSecret(
188 ctx,
189 c,
190 subnet,
191 vpn.Client().GetIPAddress(),
192 vpn.Client().GetPublicKey(),
193 vpn.Stores(),
194 )
195 }
196
197 func AddOwnerReference(vpnConfig *v1vpnconfig.VPNConfig, cluster *v1cluster.Cluster) {
198 vpnConfig.SetOwnerReferences([]metav1.OwnerReference{createOwnerReferenceToCluster(cluster)})
199 }
200
201 func createOwnerReferenceToCluster(cluster *v1cluster.Cluster) metav1.OwnerReference {
202 return metav1.OwnerReference{
203 APIVersion: cluster.APIVersion,
204 Kind: cluster.Kind,
205 Name: cluster.GetName(),
206 UID: cluster.GetUID(),
207 }
208 }
209
View as plain text