mirror of
https://github.com/prometheus/prometheus.git
synced 2026-05-04 20:06:12 +02:00
* AWS SD: Elasticache This change adds Elasticache to the AWS SD. Co-authored-by: Ben Kochie <superq@gmail.com> Signed-off-by: Matt <small_minority@hotmail.com> --------- Signed-off-by: Matt <small_minority@hotmail.com> Co-authored-by: Ben Kochie <superq@gmail.com>
616 lines
24 KiB
Go
616 lines
24 KiB
Go
// Copyright The Prometheus Authors
|
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
|
// you may not use this file except in compliance with the License.
|
|
// You may obtain a copy of the License at
|
|
//
|
|
// http://www.apache.org/licenses/LICENSE-2.0
|
|
//
|
|
// Unless required by applicable law or agreed to in writing, software
|
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
// See the License for the specific language governing permissions and
|
|
// limitations under the License.
|
|
|
|
package aws
|
|
|
|
import (
|
|
"context"
|
|
"testing"
|
|
"time"
|
|
|
|
"github.com/aws/aws-sdk-go-v2/aws"
|
|
"github.com/aws/aws-sdk-go-v2/service/elasticache"
|
|
"github.com/aws/aws-sdk-go-v2/service/elasticache/types"
|
|
"github.com/prometheus/common/model"
|
|
"github.com/stretchr/testify/require"
|
|
|
|
"github.com/prometheus/prometheus/discovery/targetgroup"
|
|
)
|
|
|
|
// Struct for test data.
|
|
type elasticacheDataStore struct {
|
|
region string
|
|
serverlessCaches []types.ServerlessCache
|
|
cacheClusters []types.CacheCluster
|
|
tags map[string][]types.Tag // keyed by cache ARN
|
|
}
|
|
|
|
func TestElasticacheDiscoveryDescribeServerlessCaches(t *testing.T) {
|
|
ctx := context.Background()
|
|
|
|
for _, tt := range []struct {
|
|
name string
|
|
ecData *elasticacheDataStore
|
|
cacheNames []string
|
|
expectedCount int
|
|
}{
|
|
{
|
|
name: "MultipleCaches",
|
|
ecData: &elasticacheDataStore{
|
|
region: "us-west-2",
|
|
serverlessCaches: []types.ServerlessCache{
|
|
{
|
|
ServerlessCacheName: strptr("test-cache"),
|
|
ARN: strptr("arn:aws:elasticache:us-west-2:123456789012:serverlesscache:test-cache"),
|
|
Status: strptr("available"),
|
|
Engine: strptr("redis"),
|
|
FullEngineVersion: strptr("7.1"),
|
|
CreateTime: aws.Time(time.Now()),
|
|
Endpoint: &types.Endpoint{
|
|
Address: strptr("test-cache.serverless.use1.cache.amazonaws.com"),
|
|
Port: aws.Int32(6379),
|
|
},
|
|
},
|
|
{
|
|
ServerlessCacheName: strptr("prod-cache"),
|
|
ARN: strptr("arn:aws:elasticache:us-west-2:123456789012:serverlesscache:prod-cache"),
|
|
Status: strptr("available"),
|
|
Engine: strptr("valkey"),
|
|
FullEngineVersion: strptr("7.2"),
|
|
CreateTime: aws.Time(time.Now()),
|
|
Endpoint: &types.Endpoint{
|
|
Address: strptr("prod-cache.serverless.use1.cache.amazonaws.com"),
|
|
Port: aws.Int32(6379),
|
|
},
|
|
},
|
|
},
|
|
},
|
|
cacheNames: []string{},
|
|
expectedCount: 2,
|
|
},
|
|
{
|
|
name: "SingleCache",
|
|
ecData: &elasticacheDataStore{
|
|
region: "us-east-1",
|
|
serverlessCaches: []types.ServerlessCache{
|
|
{
|
|
ServerlessCacheName: strptr("single-cache"),
|
|
ARN: strptr("arn:aws:elasticache:us-east-1:123456789012:serverlesscache:single-cache"),
|
|
Status: strptr("available"),
|
|
Engine: strptr("redis"),
|
|
FullEngineVersion: strptr("7.1"),
|
|
CreateTime: aws.Time(time.Now()),
|
|
},
|
|
},
|
|
},
|
|
cacheNames: []string{"single-cache"},
|
|
expectedCount: 1,
|
|
},
|
|
{
|
|
name: "NoCaches",
|
|
ecData: &elasticacheDataStore{
|
|
region: "us-east-1",
|
|
serverlessCaches: []types.ServerlessCache{},
|
|
},
|
|
cacheNames: []string{},
|
|
expectedCount: 0,
|
|
},
|
|
} {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
client := newMockElasticacheClient(tt.ecData)
|
|
|
|
d := &ElasticacheDiscovery{
|
|
elasticacheClient: client,
|
|
cfg: &ElasticacheSDConfig{
|
|
Region: tt.ecData.region,
|
|
RequestConcurrency: 10,
|
|
},
|
|
}
|
|
|
|
caches, err := d.describeServerlessCaches(ctx, tt.cacheNames)
|
|
require.NoError(t, err)
|
|
require.Len(t, caches, tt.expectedCount)
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestElasticacheDiscoveryDescribeCacheClusters(t *testing.T) {
|
|
ctx := context.Background()
|
|
|
|
for _, tt := range []struct {
|
|
name string
|
|
ecData *elasticacheDataStore
|
|
clusterIDs []string
|
|
expectedCount int
|
|
skipTest bool
|
|
}{
|
|
{
|
|
name: "MockValidation",
|
|
ecData: &elasticacheDataStore{
|
|
region: "us-west-2",
|
|
cacheClusters: []types.CacheCluster{
|
|
{
|
|
CacheClusterId: strptr("test-cluster-001"),
|
|
ARN: strptr("arn:aws:elasticache:us-west-2:123456789012:cluster:test-cluster-001"),
|
|
CacheClusterStatus: strptr("available"),
|
|
Engine: strptr("redis"),
|
|
EngineVersion: strptr("7.1"),
|
|
CacheNodeType: strptr("cache.t3.micro"),
|
|
NumCacheNodes: aws.Int32(1),
|
|
ConfigurationEndpoint: &types.Endpoint{
|
|
Address: strptr("test-cluster.abc123.cfg.use1.cache.amazonaws.com"),
|
|
Port: aws.Int32(6379),
|
|
},
|
|
},
|
|
},
|
|
},
|
|
clusterIDs: []string{},
|
|
expectedCount: 1,
|
|
skipTest: false,
|
|
},
|
|
{
|
|
name: "NoClusters",
|
|
ecData: &elasticacheDataStore{
|
|
region: "us-east-1",
|
|
cacheClusters: []types.CacheCluster{},
|
|
},
|
|
clusterIDs: []string{},
|
|
expectedCount: 0,
|
|
skipTest: false,
|
|
},
|
|
} {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
if tt.skipTest {
|
|
t.Skip("Skipping complex test with concurrency")
|
|
}
|
|
client := newMockElasticacheClient(tt.ecData)
|
|
|
|
// Verify mock returns expected data
|
|
output, err := client.DescribeCacheClusters(ctx, &elasticache.DescribeCacheClustersInput{})
|
|
require.NoError(t, err)
|
|
require.Len(t, output.CacheClusters, tt.expectedCount)
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestAddServerlessCacheTargets(t *testing.T) {
|
|
testTime := time.Date(2024, 1, 1, 0, 0, 0, 0, time.UTC)
|
|
|
|
tests := []struct {
|
|
name string
|
|
cache *types.ServerlessCache
|
|
tags []types.Tag
|
|
expectedLabels model.LabelSet
|
|
}{
|
|
{
|
|
name: "ServerlessCacheWithEndpoint",
|
|
cache: &types.ServerlessCache{
|
|
ServerlessCacheName: strptr("my-cache"),
|
|
ARN: strptr("arn:aws:elasticache:us-east-1:123456789012:serverlesscache:my-cache"),
|
|
Status: strptr("available"),
|
|
Engine: strptr("redis"),
|
|
FullEngineVersion: strptr("7.1"),
|
|
MajorEngineVersion: strptr("7"),
|
|
CreateTime: aws.Time(testTime),
|
|
Endpoint: &types.Endpoint{
|
|
Address: strptr("my-cache.serverless.use1.cache.amazonaws.com"),
|
|
Port: aws.Int32(6379),
|
|
},
|
|
ReaderEndpoint: &types.Endpoint{
|
|
Address: strptr("my-cache-ro.serverless.use1.cache.amazonaws.com"),
|
|
Port: aws.Int32(6379),
|
|
},
|
|
SecurityGroupIds: []string{"sg-12345"},
|
|
SubnetIds: []string{"subnet-abcdef"},
|
|
CacheUsageLimits: &types.CacheUsageLimits{
|
|
DataStorage: &types.DataStorage{
|
|
Maximum: aws.Int32(10),
|
|
Minimum: aws.Int32(1),
|
|
Unit: types.DataStorageUnitGb,
|
|
},
|
|
ECPUPerSecond: &types.ECPUPerSecond{
|
|
Maximum: aws.Int32(5000),
|
|
Minimum: aws.Int32(1000),
|
|
},
|
|
},
|
|
},
|
|
tags: []types.Tag{
|
|
{Key: strptr("Environment"), Value: strptr("test")},
|
|
},
|
|
expectedLabels: model.LabelSet{
|
|
"__meta_elasticache_deployment_option": "serverless",
|
|
"__meta_elasticache_serverless_cache_arn": "arn:aws:elasticache:us-east-1:123456789012:serverlesscache:my-cache",
|
|
"__meta_elasticache_serverless_cache_name": "my-cache",
|
|
"__meta_elasticache_serverless_cache_status": "available",
|
|
"__meta_elasticache_serverless_cache_engine": "redis",
|
|
"__meta_elasticache_serverless_cache_full_engine_version": "7.1",
|
|
"__meta_elasticache_serverless_cache_major_engine_version": "7",
|
|
"__meta_elasticache_serverless_cache_create_time": "2024-01-01T00:00:00Z",
|
|
"__meta_elasticache_serverless_cache_endpoint_address": "my-cache.serverless.use1.cache.amazonaws.com",
|
|
"__meta_elasticache_serverless_cache_endpoint_port": "6379",
|
|
|
|
"__meta_elasticache_serverless_cache_security_group_id_0": "sg-12345",
|
|
"__meta_elasticache_serverless_cache_subnet_id_0": "subnet-abcdef",
|
|
|
|
"__address__": "my-cache.serverless.use1.cache.amazonaws.com:6379",
|
|
},
|
|
},
|
|
}
|
|
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
tg := &targetgroup.Group{
|
|
Source: "test",
|
|
}
|
|
|
|
addServerlessCacheTargets(tg, tt.cache, tt.tags)
|
|
|
|
require.Len(t, tg.Targets, 1)
|
|
labels := tg.Targets[0]
|
|
|
|
// Check that all expected labels are present with correct values
|
|
for k, v := range tt.expectedLabels {
|
|
actualValue, exists := labels[k]
|
|
require.True(t, exists, "label %s should exist", k)
|
|
require.Equal(t, v, actualValue, "label %s mismatch", k)
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestAddCacheClusterTargets(t *testing.T) {
|
|
testTime := time.Date(2024, 1, 1, 0, 0, 0, 0, time.UTC)
|
|
|
|
tests := []struct {
|
|
name string
|
|
cluster *types.CacheCluster
|
|
tags []types.Tag
|
|
expectedTargetCount int
|
|
expectedLabels []model.LabelSet // One per node
|
|
}{
|
|
{
|
|
name: "CacheClusterWithMultipleNodes",
|
|
cluster: &types.CacheCluster{
|
|
CacheClusterId: strptr("my-cluster-001"),
|
|
ARN: strptr("arn:aws:elasticache:us-east-1:123456789012:cluster:my-cluster-001"),
|
|
CacheClusterStatus: strptr("available"),
|
|
Engine: strptr("redis"),
|
|
EngineVersion: strptr("7.1"),
|
|
CacheNodeType: strptr("cache.t3.micro"),
|
|
NumCacheNodes: aws.Int32(2),
|
|
CacheClusterCreateTime: aws.Time(testTime),
|
|
ConfigurationEndpoint: &types.Endpoint{
|
|
Address: strptr("my-cluster.abc123.cfg.use1.cache.amazonaws.com"),
|
|
Port: aws.Int32(6379),
|
|
},
|
|
AtRestEncryptionEnabled: aws.Bool(true),
|
|
TransitEncryptionEnabled: aws.Bool(true),
|
|
AuthTokenEnabled: aws.Bool(true),
|
|
AutoMinorVersionUpgrade: aws.Bool(true),
|
|
CacheSubnetGroupName: strptr("my-subnet-group"),
|
|
PreferredAvailabilityZone: strptr("us-east-1a"),
|
|
SecurityGroups: []types.SecurityGroupMembership{
|
|
{
|
|
SecurityGroupId: strptr("sg-12345"),
|
|
Status: strptr("active"),
|
|
},
|
|
},
|
|
CacheNodes: []types.CacheNode{
|
|
{
|
|
CacheNodeId: strptr("0001"),
|
|
CacheNodeStatus: strptr("available"),
|
|
CacheNodeCreateTime: aws.Time(testTime),
|
|
CustomerAvailabilityZone: strptr("us-east-1a"),
|
|
Endpoint: &types.Endpoint{
|
|
Address: strptr("my-cluster-001.abc123.0001.use1.cache.amazonaws.com"),
|
|
Port: aws.Int32(6379),
|
|
},
|
|
},
|
|
{
|
|
CacheNodeId: strptr("0002"),
|
|
CacheNodeStatus: strptr("available"),
|
|
CacheNodeCreateTime: aws.Time(testTime),
|
|
CustomerAvailabilityZone: strptr("us-east-1b"),
|
|
Endpoint: &types.Endpoint{
|
|
Address: strptr("my-cluster-001.abc123.0002.use1.cache.amazonaws.com"),
|
|
Port: aws.Int32(6379),
|
|
},
|
|
},
|
|
},
|
|
},
|
|
tags: []types.Tag{
|
|
{Key: strptr("Environment"), Value: strptr("production")},
|
|
{Key: strptr("Application"), Value: strptr("web-app")},
|
|
},
|
|
expectedTargetCount: 2,
|
|
expectedLabels: []model.LabelSet{
|
|
{
|
|
"__meta_elasticache_deployment_option": "node",
|
|
"__meta_elasticache_cache_cluster_arn": "arn:aws:elasticache:us-east-1:123456789012:cluster:my-cluster-001",
|
|
"__meta_elasticache_cache_cluster_cache_cluster_id": "my-cluster-001",
|
|
"__meta_elasticache_cache_cluster_cache_cluster_status": "available",
|
|
"__meta_elasticache_cache_cluster_engine": "redis",
|
|
"__meta_elasticache_cache_cluster_engine_version": "7.1",
|
|
"__meta_elasticache_cache_cluster_cache_node_type": "cache.t3.micro",
|
|
"__meta_elasticache_cache_cluster_num_cache_nodes": "2",
|
|
"__meta_elasticache_cache_cluster_cache_cluster_create_time": "2024-01-01T00:00:00Z",
|
|
"__meta_elasticache_cache_cluster_configuration_endpoint_address": "my-cluster.abc123.cfg.use1.cache.amazonaws.com",
|
|
"__meta_elasticache_cache_cluster_configuration_endpoint_port": "6379",
|
|
"__meta_elasticache_cache_cluster_at_rest_encryption_enabled": "true",
|
|
"__meta_elasticache_cache_cluster_transit_encryption_enabled": "true",
|
|
"__meta_elasticache_cache_cluster_auth_token_enabled": "true",
|
|
"__meta_elasticache_cache_cluster_auto_minor_version_upgrade": "true",
|
|
"__meta_elasticache_cache_cluster_cache_subnet_group_name": "my-subnet-group",
|
|
"__meta_elasticache_cache_cluster_preferred_availability_zone": "us-east-1a",
|
|
"__meta_elasticache_cache_cluster_security_group_membership_id_0": "sg-12345",
|
|
"__meta_elasticache_cache_cluster_security_group_membership_status_0": "active",
|
|
"__meta_elasticache_cache_cluster_tag_Environment": "production",
|
|
"__meta_elasticache_cache_cluster_tag_Application": "web-app",
|
|
"__meta_elasticache_cache_cluster_node_id": "0001",
|
|
"__meta_elasticache_cache_cluster_node_status": "available",
|
|
"__meta_elasticache_cache_cluster_node_create_time": "2024-01-01T00:00:00Z",
|
|
"__meta_elasticache_cache_cluster_node_availability_zone": "us-east-1a",
|
|
"__meta_elasticache_cache_cluster_node_endpoint_address": "my-cluster-001.abc123.0001.use1.cache.amazonaws.com",
|
|
"__meta_elasticache_cache_cluster_node_endpoint_port": "6379",
|
|
"__address__": "my-cluster-001.abc123.0001.use1.cache.amazonaws.com:6379",
|
|
},
|
|
{
|
|
"__meta_elasticache_deployment_option": "node",
|
|
"__meta_elasticache_cache_cluster_arn": "arn:aws:elasticache:us-east-1:123456789012:cluster:my-cluster-001",
|
|
"__meta_elasticache_cache_cluster_cache_cluster_id": "my-cluster-001",
|
|
"__meta_elasticache_cache_cluster_cache_cluster_status": "available",
|
|
"__meta_elasticache_cache_cluster_engine": "redis",
|
|
"__meta_elasticache_cache_cluster_engine_version": "7.1",
|
|
"__meta_elasticache_cache_cluster_cache_node_type": "cache.t3.micro",
|
|
"__meta_elasticache_cache_cluster_num_cache_nodes": "2",
|
|
"__meta_elasticache_cache_cluster_cache_cluster_create_time": "2024-01-01T00:00:00Z",
|
|
"__meta_elasticache_cache_cluster_configuration_endpoint_address": "my-cluster.abc123.cfg.use1.cache.amazonaws.com",
|
|
"__meta_elasticache_cache_cluster_configuration_endpoint_port": "6379",
|
|
"__meta_elasticache_cache_cluster_at_rest_encryption_enabled": "true",
|
|
"__meta_elasticache_cache_cluster_transit_encryption_enabled": "true",
|
|
"__meta_elasticache_cache_cluster_auth_token_enabled": "true",
|
|
"__meta_elasticache_cache_cluster_auto_minor_version_upgrade": "true",
|
|
"__meta_elasticache_cache_cluster_cache_subnet_group_name": "my-subnet-group",
|
|
"__meta_elasticache_cache_cluster_preferred_availability_zone": "us-east-1a",
|
|
"__meta_elasticache_cache_cluster_security_group_membership_id_0": "sg-12345",
|
|
"__meta_elasticache_cache_cluster_security_group_membership_status_0": "active",
|
|
"__meta_elasticache_cache_cluster_tag_Environment": "production",
|
|
"__meta_elasticache_cache_cluster_tag_Application": "web-app",
|
|
"__meta_elasticache_cache_cluster_node_id": "0002",
|
|
"__meta_elasticache_cache_cluster_node_status": "available",
|
|
"__meta_elasticache_cache_cluster_node_create_time": "2024-01-01T00:00:00Z",
|
|
"__meta_elasticache_cache_cluster_node_availability_zone": "us-east-1b",
|
|
"__meta_elasticache_cache_cluster_node_endpoint_address": "my-cluster-001.abc123.0002.use1.cache.amazonaws.com",
|
|
"__meta_elasticache_cache_cluster_node_endpoint_port": "6379",
|
|
"__address__": "my-cluster-001.abc123.0002.use1.cache.amazonaws.com:6379",
|
|
},
|
|
},
|
|
},
|
|
{
|
|
name: "CacheClusterWithSingleNode",
|
|
cluster: &types.CacheCluster{
|
|
CacheClusterId: strptr("node-cluster-001"),
|
|
ARN: strptr("arn:aws:elasticache:us-east-1:123456789012:cluster:node-cluster-001"),
|
|
CacheClusterStatus: strptr("available"),
|
|
Engine: strptr("redis"),
|
|
EngineVersion: strptr("6.2"),
|
|
CacheNodeType: strptr("cache.r6g.large"),
|
|
NumCacheNodes: aws.Int32(1),
|
|
CacheNodes: []types.CacheNode{
|
|
{
|
|
CacheNodeId: strptr("0001"),
|
|
CacheNodeStatus: strptr("available"),
|
|
CacheNodeCreateTime: aws.Time(testTime),
|
|
CustomerAvailabilityZone: strptr("us-east-1a"),
|
|
Endpoint: &types.Endpoint{
|
|
Address: strptr("node-cluster-001.abc123.0001.use1.cache.amazonaws.com"),
|
|
Port: aws.Int32(6379),
|
|
},
|
|
},
|
|
},
|
|
},
|
|
tags: []types.Tag{},
|
|
expectedTargetCount: 1,
|
|
expectedLabels: []model.LabelSet{
|
|
{
|
|
"__meta_elasticache_deployment_option": "node",
|
|
"__meta_elasticache_cache_cluster_arn": "arn:aws:elasticache:us-east-1:123456789012:cluster:node-cluster-001",
|
|
"__meta_elasticache_cache_cluster_cache_cluster_id": "node-cluster-001",
|
|
"__meta_elasticache_cache_cluster_cache_cluster_status": "available",
|
|
"__meta_elasticache_cache_cluster_engine": "redis",
|
|
"__meta_elasticache_cache_cluster_engine_version": "6.2",
|
|
"__meta_elasticache_cache_cluster_cache_node_type": "cache.r6g.large",
|
|
"__meta_elasticache_cache_cluster_num_cache_nodes": "1",
|
|
"__meta_elasticache_cache_cluster_node_id": "0001",
|
|
"__meta_elasticache_cache_cluster_node_status": "available",
|
|
"__meta_elasticache_cache_cluster_node_create_time": "2024-01-01T00:00:00Z",
|
|
"__meta_elasticache_cache_cluster_node_availability_zone": "us-east-1a",
|
|
"__meta_elasticache_cache_cluster_node_endpoint_address": "node-cluster-001.abc123.0001.use1.cache.amazonaws.com",
|
|
"__meta_elasticache_cache_cluster_node_endpoint_port": "6379",
|
|
"__address__": "node-cluster-001.abc123.0001.use1.cache.amazonaws.com:6379",
|
|
},
|
|
},
|
|
},
|
|
}
|
|
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
tg := &targetgroup.Group{
|
|
Source: "test",
|
|
}
|
|
|
|
addCacheClusterTargets(tg, tt.cluster, tt.tags)
|
|
|
|
require.Len(t, tg.Targets, tt.expectedTargetCount)
|
|
|
|
// Check each target
|
|
for i, expectedLabels := range tt.expectedLabels {
|
|
labels := tg.Targets[i]
|
|
|
|
// Check that all expected labels are present with correct values
|
|
for k, v := range expectedLabels {
|
|
actualValue, exists := labels[k]
|
|
require.True(t, exists, "label %s should exist in target %d", k, i)
|
|
require.Equal(t, v, actualValue, "label %s mismatch in target %d", k, i)
|
|
}
|
|
}
|
|
})
|
|
}
|
|
}
|
|
|
|
// Mock Elasticache client.
|
|
type mockElasticacheClient struct {
|
|
data *elasticacheDataStore
|
|
}
|
|
|
|
func newMockElasticacheClient(data *elasticacheDataStore) *mockElasticacheClient {
|
|
return &mockElasticacheClient{data: data}
|
|
}
|
|
|
|
func (m *mockElasticacheClient) DescribeServerlessCaches(_ context.Context, input *elasticache.DescribeServerlessCachesInput, _ ...func(*elasticache.Options)) (*elasticache.DescribeServerlessCachesOutput, error) {
|
|
if input.ServerlessCacheName != nil {
|
|
// Filter by name
|
|
for _, cache := range m.data.serverlessCaches {
|
|
if cache.ServerlessCacheName != nil && *cache.ServerlessCacheName == *input.ServerlessCacheName {
|
|
return &elasticache.DescribeServerlessCachesOutput{
|
|
ServerlessCaches: []types.ServerlessCache{cache},
|
|
}, nil
|
|
}
|
|
}
|
|
return &elasticache.DescribeServerlessCachesOutput{
|
|
ServerlessCaches: []types.ServerlessCache{},
|
|
}, nil
|
|
}
|
|
|
|
return &elasticache.DescribeServerlessCachesOutput{
|
|
ServerlessCaches: m.data.serverlessCaches,
|
|
}, nil
|
|
}
|
|
|
|
func (m *mockElasticacheClient) DescribeCacheClusters(_ context.Context, input *elasticache.DescribeCacheClustersInput, _ ...func(*elasticache.Options)) (*elasticache.DescribeCacheClustersOutput, error) {
|
|
if input.CacheClusterId != nil {
|
|
// Single cluster lookup
|
|
for _, cluster := range m.data.cacheClusters {
|
|
if cluster.CacheClusterId != nil && *cluster.CacheClusterId == *input.CacheClusterId {
|
|
return &elasticache.DescribeCacheClustersOutput{
|
|
CacheClusters: []types.CacheCluster{cluster},
|
|
}, nil
|
|
}
|
|
}
|
|
return &elasticache.DescribeCacheClustersOutput{
|
|
CacheClusters: []types.CacheCluster{},
|
|
}, nil
|
|
}
|
|
|
|
return &elasticache.DescribeCacheClustersOutput{
|
|
CacheClusters: m.data.cacheClusters,
|
|
}, nil
|
|
}
|
|
|
|
func (m *mockElasticacheClient) ListTagsForResource(_ context.Context, input *elasticache.ListTagsForResourceInput, _ ...func(*elasticache.Options)) (*elasticache.ListTagsForResourceOutput, error) {
|
|
if input.ResourceName != nil {
|
|
if tags, ok := m.data.tags[*input.ResourceName]; ok {
|
|
return &elasticache.ListTagsForResourceOutput{
|
|
TagList: tags,
|
|
}, nil
|
|
}
|
|
}
|
|
|
|
return &elasticache.ListTagsForResourceOutput{
|
|
TagList: []types.Tag{},
|
|
}, nil
|
|
}
|
|
|
|
func TestSplitCacheDeploymentOptions(t *testing.T) {
|
|
tests := []struct {
|
|
name string
|
|
caches []string
|
|
expectedServerlessCacheIDs []string
|
|
expectedCacheClusterIDs []string
|
|
}{
|
|
{
|
|
name: "MixedARNs",
|
|
caches: []string{
|
|
"arn:aws:elasticache:us-east-1:123456789012:serverlesscache:my-serverless-cache",
|
|
"arn:aws:elasticache:us-east-1:123456789012:replicationgroup:my-replication-group",
|
|
"arn:aws:elasticache:us-west-2:123456789012:serverlesscache:prod-cache",
|
|
},
|
|
expectedServerlessCacheIDs: []string{"my-serverless-cache", "prod-cache"},
|
|
expectedCacheClusterIDs: []string{"my-replication-group"},
|
|
},
|
|
{
|
|
name: "OnlyServerlessCaches",
|
|
caches: []string{
|
|
"arn:aws:elasticache:us-east-1:123456789012:serverlesscache:cache-1",
|
|
"arn:aws:elasticache:us-east-1:123456789012:serverlesscache:cache-2",
|
|
},
|
|
expectedServerlessCacheIDs: []string{"cache-1", "cache-2"},
|
|
expectedCacheClusterIDs: nil,
|
|
},
|
|
{
|
|
name: "OnlyReplicationGroups",
|
|
caches: []string{
|
|
"arn:aws:elasticache:us-east-1:123456789012:replicationgroup:cluster-1",
|
|
"arn:aws:elasticache:us-east-1:123456789012:replicationgroup:cluster-2",
|
|
},
|
|
expectedServerlessCacheIDs: nil,
|
|
expectedCacheClusterIDs: []string{"cluster-1", "cluster-2"},
|
|
},
|
|
{
|
|
name: "EmptyInput",
|
|
caches: []string{},
|
|
expectedServerlessCacheIDs: nil,
|
|
expectedCacheClusterIDs: nil,
|
|
},
|
|
{
|
|
name: "InvalidARNs",
|
|
caches: []string{
|
|
"not-an-arn",
|
|
"arn:aws:elasticache:us-east-1",
|
|
"",
|
|
},
|
|
expectedServerlessCacheIDs: nil,
|
|
expectedCacheClusterIDs: nil,
|
|
},
|
|
{
|
|
name: "UnknownResourceType",
|
|
caches: []string{
|
|
"arn:aws:elasticache:us-east-1:123456789012:unknown:resource-id",
|
|
},
|
|
expectedServerlessCacheIDs: nil,
|
|
expectedCacheClusterIDs: nil,
|
|
},
|
|
{
|
|
name: "MixedWithInvalidARNs",
|
|
caches: []string{
|
|
"arn:aws:elasticache:us-east-1:123456789012:serverlesscache:valid-cache",
|
|
"invalid-arn",
|
|
"arn:aws:elasticache:us-east-1:123456789012:replicationgroup:valid-cluster",
|
|
"",
|
|
"arn:aws:elasticache:us-east-1:123456789012:unknown:ignored",
|
|
},
|
|
expectedServerlessCacheIDs: []string{"valid-cache"},
|
|
expectedCacheClusterIDs: []string{"valid-cluster"},
|
|
},
|
|
}
|
|
|
|
for _, tt := range tests {
|
|
t.Run(tt.name, func(t *testing.T) {
|
|
serverlessCacheIDs, cacheClusterIDs := splitCacheDeploymentOptions(tt.caches)
|
|
|
|
require.Equal(t, tt.expectedServerlessCacheIDs, serverlessCacheIDs, "serverless cache IDs mismatch")
|
|
require.Equal(t, tt.expectedCacheClusterIDs, cacheClusterIDs, "cache cluster IDs mismatch")
|
|
})
|
|
}
|
|
}
|