first pass at strict_dns support for cf apps from registry
@@ -31,6 +31,7 @@ import (
"github.com/amalgam8/amalgam8/pkg/api"
"github.com/amalgam8/amalgam8/sidecar/config"
"github.com/amalgam8/amalgam8/sidecar/identity"
+ "github.com/amalgam8/amalgam8/sidecar/util"
)
// Envoy config related files
@@ -330,6 +331,17 @@ func BuildClusters(instances []*api.ServiceInstance, rules []api.Rule, tlsConfig
rules = AddDefaultRouteRules(rules, instances)
backends := make(map[string]*api.Backend)
+ staticClusters := make(map[string]*api.Backend)
+ instanceByClusterMap := make(map[string][]*api.ServiceInstance)
+ for _, inst := range instances {
+ clusterName := BuildServiceKey(inst.ServiceName, inst.Tags)
+ if _, _, err := util.SplitHostPort(inst.Endpoint); err != nil {
+ staticClusters[clusterName] = nil
+ }
+ instanceByClusterMap[clusterName] = append(instanceByClusterMap[clusterName], inst)
+ }
+
+ clusterMap := make(map[string]*api.Backend)
for _, rule := range rules {
if rule.Route != nil {
for _, backend := range rule.Route.Backends {
@@ -337,15 +349,53 @@ func BuildClusters(instances []*api.ServiceInstance, rules []api.Rule, tlsConfig
// TODO if two backends map to the same key, it will overwrite
// and will lose resilience field options in this case
backends[key] = &backend
+
+ if _, exists := staticClusters[key]; !exists {
+ clusterMap[key] = &backend
+ } else {
+ staticClusters[key] = &backend
+ }
+ }
+ }
+ }
+
+ clusters := make([]Cluster, 0, len(clusterMap))
+ for clusterName, backend := range clusterMap {
+
+ cluster := buildCluster(clusterName, backend, tlsConfig)
+
+ clusters = append(clusters, cluster)
+ }
+
+ for clusterName, backend := range staticClusters {
+ cluster := buildCluster(clusterName, backend, tlsConfig)
+ cluster.Type = "strict_dns"
+ hosts := make([]Host, 0, len(instanceByClusterMap[clusterName]))
+ for _, inst := range instanceByClusterMap[clusterName] {
+ host := Host{
+ URL: fmt.Sprintf("tcp://%v", inst.Endpoint.Value),
+ }
+ hosts = append(hosts, host)
+ }
+ cluster.Hosts = hosts
+ clusters = append(clusters, cluster)
+
}
+
+ sort.Sort(ClustersByName(clusters))
+
+ return clusters
}
+
+// BuildWeightKey builds filesystem key for Route Runtime weight keys
+func BuildWeightKey(service string, tags []string) string {
+ return fmt.Sprintf("%v.%v", service, BuildServiceKey("_", tags))
}
- clusters := make([]Cluster, 0, len(backends))
- for name, backend := range backends {
+func buildCluster(clusterName string, backend *api.Backend, tlsConfig *SSLContext) Cluster {
cluster := Cluster{
- Name: name,
- ServiceName: name,
+ Name: clusterName,
+ ServiceName: clusterName,
Type: "sds",
LbType: "round_robin",
ConnectTimeoutMs: 1000,
@@ -389,18 +439,7 @@ func BuildClusters(instances []*api.ServiceInstance, rules []api.Rule, tlsConfig
}
}
- clusters = append(clusters, cluster)
-
- }
-
- sort.Sort(ClustersByName(clusters))
-
- return clusters
-}
-
-// BuildWeightKey builds filesystem key for Route Runtime weight keys
-func BuildWeightKey(service string, tags []string) string {
- return fmt.Sprintf("%v.%v", service, BuildServiceKey("_", tags))
+ return cluster
}
// BuildRoutes builds routes based on rules. Assumes at least one route for each service
