github.com/solo-io/service-mesh-hub@v0.9.2/test/e2e/istio/federation_test.go (about) 1 package istio_test 2 3 import ( 4 "context" 5 "fmt" 6 "net/http" 7 8 discoveryv1alpha2 "github.com/solo-io/service-mesh-hub/pkg/api/discovery.smh.solo.io/v1alpha2" 9 "github.com/solo-io/service-mesh-hub/pkg/api/networking.smh.solo.io/v1alpha2" 10 "github.com/solo-io/service-mesh-hub/pkg/mesh-networking/translation/utils/metautils" 11 "github.com/solo-io/service-mesh-hub/test/data" 12 "github.com/solo-io/service-mesh-hub/test/e2e" 13 "github.com/solo-io/service-mesh-hub/test/utils" 14 v1 "github.com/solo-io/skv2/pkg/api/core.skv2.solo.io/v1" 15 istionetworkingv1alpha3 "istio.io/client-go/pkg/apis/networking/v1alpha3" 16 metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" 17 "sigs.k8s.io/controller-runtime/pkg/client" 18 19 . "github.com/onsi/ginkgo" 20 . "github.com/onsi/gomega" 21 ) 22 23 var _ = Describe("Federation", func() { 24 var ( 25 err error 26 manifest utils.Manifest 27 ctx = context.Background() 28 ) 29 30 AfterEach(func() { 31 manifest.Cleanup(BookinfoNamespace) 32 }) 33 34 /* 35 These tests assume that federation has been established between mgmt and remote clusters. 36 */ 37 38 It("enables communication across clusters using global dns names", func() { 39 manifest, err = utils.NewManifest("federation-trafficpolicies.yaml") 40 Expect(err).NotTo(HaveOccurred()) 41 42 By("with federation enabled, TrafficShifts can be used for subsets across meshes ", func() { 43 // create cross cluster traffic shift 44 trafficShiftReviewsV3 := data.RemoteTrafficShiftPolicy("bookinfo-policy", BookinfoNamespace, &v1.ClusterObjectRef{ 45 Name: "reviews", 46 Namespace: BookinfoNamespace, 47 ClusterName: mgmtClusterName, 48 }, remoteClusterName, map[string]string{"version": "v3"}, 9080) 49 50 err = manifest.AppendResources(trafficShiftReviewsV3) 51 Expect(err).NotTo(HaveOccurred()) 52 err = manifest.KubeApply(BookinfoNamespace) 53 Expect(err).NotTo(HaveOccurred()) 54 55 // ensure status is updated 56 utils.AssertTrafficPolicyStatuses(dynamicClient, BookinfoNamespace) 57 58 // check we can eventually hit the v3 subset 59 Eventually(curlReviews, "30s", "1s").Should(ContainSubstring(`"color": "red"`)) 60 }) 61 }) 62 63 It("should output a VirtualService for the federated ServiceEntry", func() { 64 By("fault injection should be applied when sending requests to a federated ServiceEntry", func() { 65 manifest, err = utils.NewManifest("federation-trafficpolicies.yaml") 66 Expect(err).NotTo(HaveOccurred()) 67 68 // Create TrafficPolicy with fault injection applied to remote cluster 69 faultInjectionPolicy := &v1alpha2.TrafficPolicy{ 70 ObjectMeta: metav1.ObjectMeta{ 71 Name: "remote-fault-injection", 72 Namespace: BookinfoNamespace, 73 }, 74 TypeMeta: metav1.TypeMeta{ 75 Kind: "TrafficPolicy", 76 APIVersion: v1alpha2.SchemeGroupVersion.String(), 77 }, 78 Spec: v1alpha2.TrafficPolicySpec{ 79 SourceSelector: nil, 80 DestinationSelector: []*v1alpha2.TrafficTargetSelector{{ 81 KubeServiceRefs: &v1alpha2.TrafficTargetSelector_KubeServiceRefs{ 82 Services: []*v1.ClusterObjectRef{ 83 { 84 Name: "reviews", 85 Namespace: BookinfoNamespace, 86 ClusterName: remoteClusterName, 87 }, 88 }, 89 }, 90 }}, 91 FaultInjection: &v1alpha2.TrafficPolicySpec_FaultInjection{ 92 FaultInjectionType: &v1alpha2.TrafficPolicySpec_FaultInjection_Abort_{ 93 &v1alpha2.TrafficPolicySpec_FaultInjection_Abort{ 94 HttpStatus: http.StatusTeapot, 95 }, 96 }, 97 Percentage: 100, 98 }, 99 }, 100 } 101 102 err = manifest.AppendResources(faultInjectionPolicy) 103 Expect(err).NotTo(HaveOccurred()) 104 err = manifest.KubeApply(BookinfoNamespace) 105 Expect(err).NotTo(HaveOccurred()) 106 107 // ensure status is updated 108 utils.AssertTrafficPolicyStatuses(dynamicClient, BookinfoNamespace) 109 110 Eventually(curlRemoteReviews, "30s", "1s").Should(ContainSubstring("418")) 111 112 // Delete TrafficPolicy so it doesn't interfere with subsequent tests 113 manifest.KubeDelete(BookinfoNamespace) 114 }) 115 116 // TODO(harveyxia) move this to a unit test if possible 117 By("traffic mirrors and shifts should use correct hostname for federated ServiceEntry", func() { 118 manifest, err = utils.NewManifest("federation-trafficpolicies.yaml") 119 Expect(err).NotTo(HaveOccurred()) 120 121 // Create TrafficPolicy with fault injection applied to remote cluster 122 trafficPolicy := &v1alpha2.TrafficPolicy{ 123 ObjectMeta: metav1.ObjectMeta{ 124 Name: "remote-mirror-and-shift", 125 Namespace: BookinfoNamespace, 126 }, 127 TypeMeta: metav1.TypeMeta{ 128 Kind: "TrafficPolicy", 129 APIVersion: v1alpha2.SchemeGroupVersion.String(), 130 }, 131 Spec: v1alpha2.TrafficPolicySpec{ 132 SourceSelector: nil, 133 DestinationSelector: []*v1alpha2.TrafficTargetSelector{{ 134 KubeServiceRefs: &v1alpha2.TrafficTargetSelector_KubeServiceRefs{ 135 Services: []*v1.ClusterObjectRef{ 136 { 137 Name: "reviews", 138 Namespace: BookinfoNamespace, 139 ClusterName: remoteClusterName, 140 }, 141 }, 142 }, 143 }}, 144 Mirror: &v1alpha2.TrafficPolicySpec_Mirror{ 145 DestinationType: &v1alpha2.TrafficPolicySpec_Mirror_KubeService{ 146 KubeService: &v1.ClusterObjectRef{ 147 Name: "reviews", 148 Namespace: BookinfoNamespace, 149 ClusterName: mgmtClusterName, 150 }, 151 }, 152 Percentage: 50, 153 Port: 9080, 154 }, 155 TrafficShift: &v1alpha2.TrafficPolicySpec_MultiDestination{ 156 Destinations: []*v1alpha2.TrafficPolicySpec_MultiDestination_WeightedDestination{ 157 { 158 DestinationType: &v1alpha2.TrafficPolicySpec_MultiDestination_WeightedDestination_KubeService{ 159 KubeService: &v1alpha2.TrafficPolicySpec_MultiDestination_WeightedDestination_KubeDestination{ 160 Name: "reviews", 161 Namespace: BookinfoNamespace, 162 ClusterName: mgmtClusterName, 163 }, 164 }, 165 Weight: 50, 166 }, 167 }, 168 }, 169 }, 170 } 171 172 err = manifest.AppendResources(trafficPolicy) 173 Expect(err).NotTo(HaveOccurred()) 174 err = manifest.KubeApply(BookinfoNamespace) 175 Expect(err).NotTo(HaveOccurred()) 176 177 // ensure status is updated 178 utils.AssertTrafficPolicyStatuses(dynamicClient, BookinfoNamespace) 179 180 var getFederatedVirtualService = func() (*istionetworkingv1alpha3.VirtualService, error) { 181 env := e2e.GetEnv() 182 vsClient := env.Management.VirtualServiceClient 183 meta := metautils.FederatedObjectMeta( 184 &metav1.ObjectMeta{ 185 Name: "reviews", 186 Namespace: BookinfoNamespace, 187 ClusterName: remoteClusterName, 188 }, 189 &discoveryv1alpha2.MeshSpec_MeshInstallation{ 190 Namespace: "istio-system", 191 Cluster: mgmtClusterName, 192 }, 193 nil, 194 ) 195 return vsClient.GetVirtualService(ctx, client.ObjectKey{Name: meta.Name, Namespace: meta.Namespace}) 196 } 197 198 Eventually(func() bool { 199 virtualService, err := getFederatedVirtualService() 200 if err != nil { 201 return false 202 } 203 if len(virtualService.Spec.Http) > 0 { 204 httpRoute := virtualService.Spec.Http[0] 205 if httpRoute.GetMirror().GetHost() != fmt.Sprintf("reviews.%s.svc.cluster.local", BookinfoNamespace) { 206 return false 207 } 208 if len(httpRoute.GetRoute()) < 1 { 209 return false 210 } 211 if httpRoute.GetRoute()[0].GetDestination().GetHost() != fmt.Sprintf("reviews.%s.svc.cluster.local", BookinfoNamespace) { 212 return false 213 } 214 return true 215 } 216 return false 217 }, "30s", "1s").Should(BeTrue()) 218 }) 219 }) 220 })