istio.io/istio@v0.0.0-20240520182934-d79c90f27776/pkg/config/validation/agent/extensionprovider_test.go (about)

     1  // Copyright Istio Authors
     2  //
     3  // Licensed under the Apache License, Version 2.0 (the "License");
     4  // you may not use this file except in compliance with the License.
     5  // You may obtain a copy of the License at
     6  //
     7  //     http://www.apache.org/licenses/LICENSE-2.0
     8  //
     9  // Unless required by applicable law or agreed to in writing, software
    10  // distributed under the License is distributed on an "AS IS" BASIS,
    11  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    12  // See the License for the specific language governing permissions and
    13  // limitations under the License.
    14  
    15  package agent
    16  
    17  import (
    18  	"testing"
    19  
    20  	meshconfig "istio.io/api/mesh/v1alpha1"
    21  )
    22  
    23  func TestValidateExtensionProviderService(t *testing.T) {
    24  	tests := []struct {
    25  		service string
    26  		valid   bool
    27  		name    string
    28  	}{
    29  		{
    30  			service: "127.0.0.1",
    31  			valid:   true,
    32  			name:    "pure ip4 address",
    33  		},
    34  		{
    35  			service: "2001:1::1",
    36  			valid:   true,
    37  			name:    "pure ip6 address",
    38  		},
    39  		{
    40  			service: "istio-pilot.istio-system.svc.cluster.local",
    41  			valid:   true,
    42  			name:    "standard kubernetes FQDN",
    43  		},
    44  		{
    45  			service: "istio-pilot.istio-system.svc.cluster.local:3000",
    46  			valid:   false,
    47  			name:    "standard kubernetes FQDN with port",
    48  		},
    49  		{
    50  			service: "bar/istio.io",
    51  			valid:   true,
    52  			name:    "extension provider service with namespace",
    53  		},
    54  		{
    55  			service: "bar/istio.io:3000",
    56  			valid:   false,
    57  			name:    "extension provider service with namespace and port",
    58  		},
    59  		{
    60  			service: "bar/foo/istio.io",
    61  			valid:   false,
    62  			name:    "extension provider service with namespace",
    63  		},
    64  	}
    65  	for _, tt := range tests {
    66  		tt := tt
    67  		t.Run(tt.name, func(t *testing.T) {
    68  			err := validateExtensionProviderService(tt.service)
    69  			valid := err == nil
    70  			if valid != tt.valid {
    71  				t.Errorf("Expected valid=%v, got valid=%v for %v", tt.valid, valid, tt.service)
    72  			}
    73  		})
    74  	}
    75  }
    76  
    77  func TestValidateExtensionProviderTracingZipkin(t *testing.T) {
    78  	cases := []struct {
    79  		name   string
    80  		config *meshconfig.MeshConfig_ExtensionProvider_ZipkinTracingProvider
    81  		valid  bool
    82  	}{
    83  		{
    84  			name: "zipkin normal",
    85  			config: &meshconfig.MeshConfig_ExtensionProvider_ZipkinTracingProvider{
    86  				Service: "zipkin.istio-system",
    87  				Port:    9411,
    88  			},
    89  			valid: true,
    90  		},
    91  		{
    92  			name: "zipkin service with namespace",
    93  			config: &meshconfig.MeshConfig_ExtensionProvider_ZipkinTracingProvider{
    94  				Service: "namespace/zipkin.istio-system",
    95  				Port:    9411,
    96  			},
    97  			valid: true,
    98  		},
    99  		{
   100  			name: "zipkin service with invalid namespace",
   101  			config: &meshconfig.MeshConfig_ExtensionProvider_ZipkinTracingProvider{
   102  				Service: "name/space/zipkin.istio-system",
   103  				Port:    9411,
   104  			},
   105  			valid: false,
   106  		},
   107  		{
   108  			name: "zipkin service with port",
   109  			config: &meshconfig.MeshConfig_ExtensionProvider_ZipkinTracingProvider{
   110  				Service: "zipkin.istio-system:9411",
   111  				Port:    9411,
   112  			},
   113  			valid: false,
   114  		},
   115  	}
   116  	for _, c := range cases {
   117  		t.Run(c.name, func(t *testing.T) {
   118  			err := validateExtensionProviderTracingZipkin(c.config)
   119  			valid := err == nil
   120  			if valid != c.valid {
   121  				t.Errorf("Expected valid=%v, got valid=%v for %v", c.valid, valid, c.config)
   122  			}
   123  		})
   124  	}
   125  }
   126  
   127  func TestValidateExtensionProviderTracingLightstep(t *testing.T) {
   128  	cases := []struct {
   129  		name   string
   130  		config *meshconfig.MeshConfig_ExtensionProvider_LightstepTracingProvider
   131  		valid  bool
   132  	}{
   133  		{
   134  			name: "lightstep normal",
   135  			config: &meshconfig.MeshConfig_ExtensionProvider_LightstepTracingProvider{
   136  				Service:     "collector.lightstep",
   137  				Port:        8080,
   138  				AccessToken: "abcdefg1234567",
   139  			},
   140  			valid: true,
   141  		},
   142  		{
   143  			name: "lightstep service with namespace",
   144  			config: &meshconfig.MeshConfig_ExtensionProvider_LightstepTracingProvider{
   145  				Service:     "namespace/collector.lightstep",
   146  				Port:        8080,
   147  				AccessToken: "abcdefg1234567",
   148  			},
   149  			valid: true,
   150  		},
   151  		{
   152  			name: "lightstep service with missing port",
   153  			config: &meshconfig.MeshConfig_ExtensionProvider_LightstepTracingProvider{
   154  				Service:     "10.0.0.100",
   155  				AccessToken: "abcdefg1234567",
   156  			},
   157  			valid: false,
   158  		},
   159  		{
   160  			name: "lightstep service with missing accesstoken",
   161  			config: &meshconfig.MeshConfig_ExtensionProvider_LightstepTracingProvider{
   162  				Service: "namespace/collector.lightstep",
   163  				Port:    8080,
   164  			},
   165  			valid: false,
   166  		},
   167  	}
   168  	for _, c := range cases {
   169  		t.Run(c.name, func(t *testing.T) {
   170  			err := validateExtensionProviderTracingLightStep(c.config)
   171  			valid := err == nil
   172  			if valid != c.valid {
   173  				t.Errorf("Expected valid=%v, got valid=%v for %v", c.valid, valid, c.config)
   174  			}
   175  		})
   176  	}
   177  }
   178  
   179  func TestValidateExtensionProviderTracingDatadog(t *testing.T) {
   180  	cases := []struct {
   181  		name   string
   182  		config *meshconfig.MeshConfig_ExtensionProvider_DatadogTracingProvider
   183  		valid  bool
   184  	}{
   185  		{
   186  			name: "datadog normal",
   187  			config: &meshconfig.MeshConfig_ExtensionProvider_DatadogTracingProvider{
   188  				Service: "datadog-agent.com",
   189  				Port:    8126,
   190  			},
   191  			valid: true,
   192  		},
   193  		{
   194  			name: "datadog service with namespace",
   195  			config: &meshconfig.MeshConfig_ExtensionProvider_DatadogTracingProvider{
   196  				Service: "namespace/datadog-agent.com",
   197  				Port:    8126,
   198  			},
   199  			valid: true,
   200  		},
   201  		{
   202  			name: "datadog service with invalid namespace",
   203  			config: &meshconfig.MeshConfig_ExtensionProvider_DatadogTracingProvider{
   204  				Service: "name/space/datadog-agent.com",
   205  				Port:    8126,
   206  			},
   207  			valid: false,
   208  		},
   209  		{
   210  			name: "datadog service with port",
   211  			config: &meshconfig.MeshConfig_ExtensionProvider_DatadogTracingProvider{
   212  				Service: "datadog-agent.com:8126",
   213  				Port:    8126,
   214  			},
   215  			valid: false,
   216  		},
   217  		{
   218  			name: "datadog missing port",
   219  			config: &meshconfig.MeshConfig_ExtensionProvider_DatadogTracingProvider{
   220  				Service: "datadog-agent.com",
   221  			},
   222  			valid: false,
   223  		},
   224  	}
   225  	for _, c := range cases {
   226  		t.Run(c.name, func(t *testing.T) {
   227  			err := validateExtensionProviderTracingDatadog(c.config)
   228  			valid := err == nil
   229  			if valid != c.valid {
   230  				t.Errorf("Expected valid=%v, got valid=%v for %v", c.valid, valid, c.config)
   231  			}
   232  		})
   233  	}
   234  }
   235  
   236  func TestValidateExtensionProviderTracingOpenCensusAgent(t *testing.T) {
   237  	cases := []struct {
   238  		name   string
   239  		config *meshconfig.MeshConfig_ExtensionProvider_OpenCensusAgentTracingProvider
   240  		valid  bool
   241  	}{
   242  		{
   243  			name: "opencensus normal",
   244  			config: &meshconfig.MeshConfig_ExtensionProvider_OpenCensusAgentTracingProvider{
   245  				Service: "opencensus-agent.com",
   246  				Port:    4000,
   247  			},
   248  			valid: true,
   249  		},
   250  		{
   251  			name: "opencensus service with namespace",
   252  			config: &meshconfig.MeshConfig_ExtensionProvider_OpenCensusAgentTracingProvider{
   253  				Service: "namespace/opencensus-agent.com",
   254  				Port:    4000,
   255  			},
   256  			valid: true,
   257  		},
   258  		{
   259  			name: "opencensus service with invalid namespace",
   260  			config: &meshconfig.MeshConfig_ExtensionProvider_OpenCensusAgentTracingProvider{
   261  				Service: "name/space/opencensus-agent.com",
   262  				Port:    4000,
   263  			},
   264  			valid: false,
   265  		},
   266  		{
   267  			name: "opencensus service with port",
   268  			config: &meshconfig.MeshConfig_ExtensionProvider_OpenCensusAgentTracingProvider{
   269  				Service: "opencensus-agent.com:4000",
   270  				Port:    4000,
   271  			},
   272  			valid: false,
   273  		},
   274  		{
   275  			name: "opencensus missing port",
   276  			config: &meshconfig.MeshConfig_ExtensionProvider_OpenCensusAgentTracingProvider{
   277  				Service: "opencensus-agent.com",
   278  			},
   279  			valid: false,
   280  		},
   281  	}
   282  	for _, c := range cases {
   283  		t.Run(c.name, func(t *testing.T) {
   284  			err := validateExtensionProviderTracingOpenCensusAgent(c.config)
   285  			valid := err == nil
   286  			if valid != c.valid {
   287  				t.Errorf("Expected valid=%v, got valid=%v for %v", c.valid, valid, c.config)
   288  			}
   289  		})
   290  	}
   291  }
   292  
   293  func TestValidateExtensionProviderEnvoyOtelAls(t *testing.T) {
   294  	cases := []struct {
   295  		name     string
   296  		provider *meshconfig.MeshConfig_ExtensionProvider_EnvoyOpenTelemetryLogProvider
   297  		valid    bool
   298  	}{
   299  		{
   300  			name: "otel normal",
   301  			provider: &meshconfig.MeshConfig_ExtensionProvider_EnvoyOpenTelemetryLogProvider{
   302  				Service: "otel.istio-syste.svc",
   303  				Port:    4000,
   304  			},
   305  			valid: true,
   306  		},
   307  		{
   308  			name: "otel service with namespace",
   309  			provider: &meshconfig.MeshConfig_ExtensionProvider_EnvoyOpenTelemetryLogProvider{
   310  				Service: "namespace/otel.istio-syste.svc",
   311  				Port:    4000,
   312  			},
   313  			valid: true,
   314  		},
   315  		{
   316  			name: "otel service with invalid namespace",
   317  			provider: &meshconfig.MeshConfig_ExtensionProvider_EnvoyOpenTelemetryLogProvider{
   318  				Service: "name/space/otel.istio-syste.svc",
   319  				Port:    4000,
   320  			},
   321  			valid: false,
   322  		},
   323  		{
   324  			name: "otel service with port",
   325  			provider: &meshconfig.MeshConfig_ExtensionProvider_EnvoyOpenTelemetryLogProvider{
   326  				Service: "otel.istio-syste.svc:4000",
   327  				Port:    4000,
   328  			},
   329  			valid: false,
   330  		},
   331  		{
   332  			name: "otel missing port",
   333  			provider: &meshconfig.MeshConfig_ExtensionProvider_EnvoyOpenTelemetryLogProvider{
   334  				Service: "otel.istio-syste.svc",
   335  			},
   336  			valid: false,
   337  		},
   338  	}
   339  	for _, c := range cases {
   340  		t.Run(c.name, func(t *testing.T) {
   341  			err := ValidateExtensionProviderEnvoyOtelAls(c.provider)
   342  			valid := err == nil
   343  			if valid != c.valid {
   344  				t.Errorf("Expected valid=%v, got valid=%v for %v", c.valid, valid, c.provider)
   345  			}
   346  		})
   347  	}
   348  }
   349  
   350  func TestValidateExtensionProviderEnvoyHTTPAls(t *testing.T) {
   351  	cases := []struct {
   352  		name     string
   353  		provider *meshconfig.MeshConfig_ExtensionProvider_EnvoyHttpGrpcV3LogProvider
   354  		valid    bool
   355  	}{
   356  		{
   357  			name: "normal",
   358  			provider: &meshconfig.MeshConfig_ExtensionProvider_EnvoyHttpGrpcV3LogProvider{
   359  				Service: "grpc-als.istio-syste.svc",
   360  				Port:    4000,
   361  			},
   362  			valid: true,
   363  		},
   364  		{
   365  			name: "service with namespace",
   366  			provider: &meshconfig.MeshConfig_ExtensionProvider_EnvoyHttpGrpcV3LogProvider{
   367  				Service: "namespace/grpc-als.istio-syste.svc",
   368  				Port:    4000,
   369  			},
   370  			valid: true,
   371  		},
   372  		{
   373  			name: "service with invalid namespace",
   374  			provider: &meshconfig.MeshConfig_ExtensionProvider_EnvoyHttpGrpcV3LogProvider{
   375  				Service: "name/space/grpc-als.istio-syste.svc",
   376  				Port:    4000,
   377  			},
   378  			valid: false,
   379  		},
   380  		{
   381  			name: "service with port",
   382  			provider: &meshconfig.MeshConfig_ExtensionProvider_EnvoyHttpGrpcV3LogProvider{
   383  				Service: "grpc-als.istio-syste.svc:4000",
   384  				Port:    4000,
   385  			},
   386  			valid: false,
   387  		},
   388  		{
   389  			name: "missing port",
   390  			provider: &meshconfig.MeshConfig_ExtensionProvider_EnvoyHttpGrpcV3LogProvider{
   391  				Service: "grpc-als.istio-syste.svc",
   392  			},
   393  			valid: false,
   394  		},
   395  	}
   396  	for _, c := range cases {
   397  		t.Run(c.name, func(t *testing.T) {
   398  			err := ValidateExtensionProviderEnvoyHTTPAls(c.provider)
   399  			valid := err == nil
   400  			if valid != c.valid {
   401  				t.Errorf("Expected valid=%v, got valid=%v for %v", c.valid, valid, c.provider)
   402  			}
   403  		})
   404  	}
   405  }
   406  
   407  func TestValidateExtensionProviderEnvoyTCPAls(t *testing.T) {
   408  	cases := []struct {
   409  		name     string
   410  		provider *meshconfig.MeshConfig_ExtensionProvider_EnvoyTcpGrpcV3LogProvider
   411  		valid    bool
   412  	}{
   413  		{
   414  			name: "normal",
   415  			provider: &meshconfig.MeshConfig_ExtensionProvider_EnvoyTcpGrpcV3LogProvider{
   416  				Service: "grpc-als.istio-syste.svc",
   417  				Port:    4000,
   418  			},
   419  			valid: true,
   420  		},
   421  		{
   422  			name: "service with namespace",
   423  			provider: &meshconfig.MeshConfig_ExtensionProvider_EnvoyTcpGrpcV3LogProvider{
   424  				Service: "namespace/grpc-als.istio-syste.svc",
   425  				Port:    4000,
   426  			},
   427  			valid: true,
   428  		},
   429  		{
   430  			name: "service with invalid namespace",
   431  			provider: &meshconfig.MeshConfig_ExtensionProvider_EnvoyTcpGrpcV3LogProvider{
   432  				Service: "name/space/grpc-als.istio-syste.svc",
   433  				Port:    4000,
   434  			},
   435  			valid: false,
   436  		},
   437  		{
   438  			name: "service with port",
   439  			provider: &meshconfig.MeshConfig_ExtensionProvider_EnvoyTcpGrpcV3LogProvider{
   440  				Service: "grpc-als.istio-syste.svc:4000",
   441  				Port:    4000,
   442  			},
   443  			valid: false,
   444  		},
   445  		{
   446  			name: "missing port",
   447  			provider: &meshconfig.MeshConfig_ExtensionProvider_EnvoyTcpGrpcV3LogProvider{
   448  				Service: "grpc-als.istio-syste.svc",
   449  			},
   450  			valid: false,
   451  		},
   452  	}
   453  	for _, c := range cases {
   454  		t.Run(c.name, func(t *testing.T) {
   455  			err := ValidateExtensionProviderEnvoyTCPAls(c.provider)
   456  			valid := err == nil
   457  			if valid != c.valid {
   458  				t.Errorf("Expected valid=%v, got valid=%v for %v", c.valid, valid, c.provider)
   459  			}
   460  		})
   461  	}
   462  }
   463  
   464  func TestValidateExtensionProviderTracingOpentelemetry(t *testing.T) {
   465  	cases := []struct {
   466  		name     string
   467  		provider *meshconfig.MeshConfig_ExtensionProvider_OpenTelemetryTracingProvider
   468  		valid    bool
   469  	}{
   470  		{
   471  			name: "normal",
   472  			provider: &meshconfig.MeshConfig_ExtensionProvider_OpenTelemetryTracingProvider{
   473  				Service: "collector.namespace.svc",
   474  				Port:    4317,
   475  			},
   476  			valid: true,
   477  		},
   478  		{
   479  			name: "service with namespace",
   480  			provider: &meshconfig.MeshConfig_ExtensionProvider_OpenTelemetryTracingProvider{
   481  				Service: "namespace/collector.namespace.svc",
   482  				Port:    4317,
   483  			},
   484  			valid: true,
   485  		},
   486  		{
   487  			name: "service with invalid namespace",
   488  			provider: &meshconfig.MeshConfig_ExtensionProvider_OpenTelemetryTracingProvider{
   489  				Service: "name/space/collector.namespace.svc",
   490  				Port:    4317,
   491  			},
   492  			valid: false,
   493  		},
   494  		{
   495  			name: "service with port",
   496  			provider: &meshconfig.MeshConfig_ExtensionProvider_OpenTelemetryTracingProvider{
   497  				Service: "collector.namespace.svc:4000",
   498  				Port:    4317,
   499  			},
   500  			valid: false,
   501  		},
   502  		{
   503  			name: "missing port",
   504  			provider: &meshconfig.MeshConfig_ExtensionProvider_OpenTelemetryTracingProvider{
   505  				Service: "collector.namespace.svc",
   506  			},
   507  			valid: false,
   508  		},
   509  	}
   510  	for _, c := range cases {
   511  		t.Run(c.name, func(t *testing.T) {
   512  			err := ValidateExtensionProviderTracingOpentelemetry(c.provider)
   513  			valid := err == nil
   514  			if valid != c.valid {
   515  				t.Errorf("Expected valid=%v, got valid=%v for %v", c.valid, valid, c.provider)
   516  			}
   517  		})
   518  	}
   519  }