Point `Service` of type `ExternalName` to internal service if externalName is like `*.svc.cluster.local`
Is your feature request related to a problem?
Yes.
I need to create services that point to services in other namespaces. It doesn't work in the vcluster as it works in the host cluster.
Which solution do you suggest?
Map any VCluster Kind: Service, spec.type: ExternalName, externalName: [<pod>.][<svc>[.<namespace>]][.svc[.cluster.local|<custom_suffix>]] only to resources inside the VCluster.
*All resources are inside a vcluster created with vcluster create vcluster -n vcluster
...
---
apiVersion: v1
kind: Service
metadata:
name: svc-a
namespace: a
spec:
type: ClusterIP
ports:
- name: http
port: 80
targetPort: http
selector:
# ...
---
apiVersion: v1
kind: Service
metadata:
name: svc-b
namespace: b
spec:
type: ExternalName
# map from:
externalName: svc-a.a.svc.cluster.local
# to: (right now, only this 👇 fqdn works)
# externalName: svc-a-x-a-x-vcluster.vcluster.svc.cluster.local
ports:
- name: http
port: 80
targetPort: 80
Which alternative solutions exist?
Use e.g. svc-a-x-a-x-vcluster.vcluster.svc.cluster.local
Additional context
vcluster v0.24.1
Are both ClusterIP type and ExternalName type services synced from the physical k8s?
@mayooot
Are both ClusterIP type and ExternalName type services synced from the physical k8s?'
Seems so
$ kubectl --context kind-kind get svc -A
NAMESPACE NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
default kubernetes ClusterIP 10.96.0.1 <none> 443/TCP 130m
kube-system kube-dns ClusterIP 10.96.0.10 <none> 53/UDP,53/TCP,9153/TCP 130m
vcluster kube-dns-x-kube-system-x-vcluster ClusterIP 10.96.126.182 <none> 53/UDP,53/TCP,9153/TCP 6m52s
vcluster svc-a-x-a-x-vcluster ClusterIP 10.96.235.165 <none> 80/TCP 57s
vcluster svc-b-x-b-x-vcluster ExternalName <none> svc-a.a.svc.cluster.local 80/TCP 57s
vcluster vcluster ClusterIP 10.96.116.14 <none> 443/TCP,10250/TCP 7m39s
vcluster vcluster-headless ClusterIP None <none> 443/TCP 7m39s
vcluster vcluster-node-kind-control-plane ClusterIP 10.96.97.89 <none> 10250/TCP 6m52s
$ kubectl --context vcluster_vcluster_vcluster_kind-kind get svc -A
NAMESPACE NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
a svc-a ClusterIP 10.96.235.165 <none> 80/TCP 2m30s
b svc-b ExternalName <none> svc-a.a.svc.cluster.local 80/TCP 2m30s
default kubernetes ClusterIP 10.96.116.14 <none> 443/TCP 8m25s
kube-system kube-dns ClusterIP 10.96.126.182 <none> 53/UDP,53/TCP,9153/TCP 8m25s
$ kubectl --context vcluster_vcluster_vcluster_kind-kind run tmp-shell --restart=Never --rm -it --image arunvelsriram/utils -- dig A svc-b.b.svc.cluster.local +short
svc-a.a.svc.cluster.local.
10.96.235.165
pod "tmp-shell" deleted
$ kubectl --context kind-kind run tmp-shell --restart=Never --rm -it --image arunvelsriram/utils -- dig A svc-b-x-b-x-vcluster.vcluster.svc.cluster.local +short
# >>> no result. should return `svc-a-x-a-x-vcluster.vcluster.svc.cluster.local` so that the ingress controller on the host works
pod "tmp-shell" deleted
The behavior I want only works after
$ kubectl --context vcluster_vcluster_vcluster_kind-kind -n b patch svc/svc-b --patch='{"spec":{"externalName":"svc-a-x-a-x-vcluster.vcluster.svc.cluster.local"}}'
service/svc-b patched
$ kubectl --context kind-kind run tmp-shell --restart=Never --rm -it --image arunvelsriram/utils -- dig A svc-b-x-b-x-vcluster.vcluster.svc.cluster.local +short
svc-a-x-a-x-vcluster.vcluster.svc.cluster.local.
10.96.235.165
pod "tmp-shell" deleted
$ kubectl --context vcluster_vcluster_vcluster_kind-kind run tmp-shell --restart=Never --rm -it --image arunvelsriram/utils -- dig A svc-b.b.svc.cluster.local +short
# >>> BUT breaks inside vcluster
pod "tmp-shell" deleted
The behavior I want only works after
$ kubectl --context vcluster_vcluster_vcluster_kind-kind -n b patch svc/svc-b --patch='{"spec":{"externalName":"svc-a-x-a-x-vcluster.vcluster.svc.cluster.local"}}'
service/svc-b patched
$ kubectl --context kind-kind run tmp-shell --restart=Never --rm -it --image arunvelsriram/utils -- dig A svc-b-x-b-x-vcluster.vcluster.svc.cluster.local +short
svc-a-x-a-x-vcluster.vcluster.svc.cluster.local.
10.96.235.165
pod "tmp-shell" deleted
When you update the ExternalName type service within the vcluster, this will be result in the ExternalName type service being unavilable in the vcluster?
Overall, our requiremente is to use Service synchronized from vcluster in physical cluster.
I read the source code and the general idea is as follows:
- modify
pkg/controllers/resources/servicesbelow the file, in the synchronization Service judgmentvObj.Spec.Type == corev1.ServiceTypeExternalName && vObj.Spec.ExternalName has ".svc.cluster.local". - find out whether the Service pointed by
ExternalNameexists in Vcluster. If so, change the value of ExternalName, updateand to the format with '-x-' . If not, don't change it.
@lucasfcnunes @matskiv Does this look good to you?
@mayooot
When you update the ExternalName type service within the vcluster, this will be result in the ExternalName type service being unavilable in the vcluster?
Yep. It breaks. *I edited my comment to add this case.
modify pkg/controllers/resources/services below the file, in the synchronization Service judgment vObj.Spec.Type == corev1.ServiceTypeExternalName && vObj.Spec.ExternalName has ".svc.cluster.local" .
Seems the way to go. Notice that the complete service hostname string can be as complex as follows [<pod>.][<svc>[.<namespace>]][.svc[.cluster.local|<custom_suffix>]].
Hi, Is this being worked upon? I can take it up otherwise.