Skip to content

Commit

Permalink
eks*: improve container ECR checks
Browse files Browse the repository at this point in the history
Signed-off-by: Gyuho Lee <[email protected]>
  • Loading branch information
gyuho committed May 15, 2020
1 parent 0699037 commit cc418cc
Show file tree
Hide file tree
Showing 12 changed files with 112 additions and 38 deletions.
2 changes: 2 additions & 0 deletions eks/cluster-loader/remote/remote.go
Original file line number Diff line number Diff line change
Expand Up @@ -194,6 +194,7 @@ func (ts *tester) Delete() error {
func (ts *tester) checkECR() error {
ts.cfg.Logger.Info("describing ECR repositories")
out, err := ts.cfg.ECRAPI.DescribeRepositories(&ecr.DescribeRepositoriesInput{
RegistryId: aws.String(ts.cfg.EKSConfig.AddOnClusterLoaderRemote.RepositoryAccountID),
RepositoryNames: aws.StringSlice([]string{ts.cfg.EKSConfig.AddOnClusterLoaderRemote.RepositoryName}),
})
if err != nil {
Expand Down Expand Up @@ -222,6 +223,7 @@ func (ts *tester) checkECR() error {

ts.cfg.Logger.Info("describing images")
imgOut, err := ts.cfg.ECRAPI.DescribeImages(&ecr.DescribeImagesInput{
RegistryId: aws.String(ts.cfg.EKSConfig.AddOnClusterLoaderRemote.RepositoryAccountID),
RepositoryName: aws.String(ts.cfg.EKSConfig.AddOnClusterLoaderRemote.RepositoryName),
ImageIds: []*ecr.ImageIdentifier{
{
Expand Down
2 changes: 2 additions & 0 deletions eks/fargate/fargate.go
Original file line number Diff line number Diff line change
Expand Up @@ -160,6 +160,7 @@ func (ts *tester) Delete() error {
func (ts *tester) checkECR() error {
ts.cfg.Logger.Info("describing ECR repositories")
out, err := ts.cfg.ECRAPI.DescribeRepositories(&ecr.DescribeRepositoriesInput{
RegistryId: aws.String(ts.cfg.EKSConfig.AddOnFargate.RepositoryAccountID),
RepositoryNames: aws.StringSlice([]string{ts.cfg.EKSConfig.AddOnFargate.RepositoryName}),
})
if err != nil {
Expand Down Expand Up @@ -188,6 +189,7 @@ func (ts *tester) checkECR() error {

ts.cfg.Logger.Info("describing images")
imgOut, err := ts.cfg.ECRAPI.DescribeImages(&ecr.DescribeImagesInput{
RegistryId: aws.String(ts.cfg.EKSConfig.AddOnFargate.RepositoryAccountID),
RepositoryName: aws.String(ts.cfg.EKSConfig.AddOnFargate.RepositoryName),
ImageIds: []*ecr.ImageIdentifier{
{
Expand Down
2 changes: 2 additions & 0 deletions eks/hollow-nodes/remote/remote.go
Original file line number Diff line number Diff line change
Expand Up @@ -181,6 +181,7 @@ func (ts *tester) Delete() (err error) {
func (ts *tester) checkECR() error {
ts.cfg.Logger.Info("describing ECR repositories")
out, err := ts.cfg.ECRAPI.DescribeRepositories(&ecr.DescribeRepositoriesInput{
RegistryId: aws.String(ts.cfg.EKSConfig.AddOnHollowNodesRemote.RepositoryAccountID),
RepositoryNames: aws.StringSlice([]string{ts.cfg.EKSConfig.AddOnHollowNodesRemote.RepositoryName}),
})
if err != nil {
Expand Down Expand Up @@ -209,6 +210,7 @@ func (ts *tester) checkECR() error {

ts.cfg.Logger.Info("describing images")
imgOut, err := ts.cfg.ECRAPI.DescribeImages(&ecr.DescribeImagesInput{
RegistryId: aws.String(ts.cfg.EKSConfig.AddOnHollowNodesRemote.RepositoryAccountID),
RepositoryName: aws.String(ts.cfg.EKSConfig.AddOnHollowNodesRemote.RepositoryName),
ImageIds: []*ecr.ImageIdentifier{
{
Expand Down
2 changes: 2 additions & 0 deletions eks/irsa-fargate/irsa-fargate.go
Original file line number Diff line number Diff line change
Expand Up @@ -197,6 +197,7 @@ func (ts *tester) Delete() error {
func (ts *tester) checkECR() error {
ts.cfg.Logger.Info("describing ECR repositories")
out, err := ts.cfg.ECRAPI.DescribeRepositories(&ecr.DescribeRepositoriesInput{
RegistryId: aws.String(ts.cfg.EKSConfig.AddOnIRSAFargate.RepositoryAccountID),
RepositoryNames: aws.StringSlice([]string{ts.cfg.EKSConfig.AddOnIRSAFargate.RepositoryName}),
})
if err != nil {
Expand Down Expand Up @@ -225,6 +226,7 @@ func (ts *tester) checkECR() error {

ts.cfg.Logger.Info("describing images")
imgOut, err := ts.cfg.ECRAPI.DescribeImages(&ecr.DescribeImagesInput{
RegistryId: aws.String(ts.cfg.EKSConfig.AddOnIRSAFargate.RepositoryAccountID),
RepositoryName: aws.String(ts.cfg.EKSConfig.AddOnIRSAFargate.RepositoryName),
ImageIds: []*ecr.ImageIdentifier{
{
Expand Down
2 changes: 2 additions & 0 deletions eks/irsa/irsa.go
Original file line number Diff line number Diff line change
Expand Up @@ -198,6 +198,7 @@ func (ts *tester) Delete() error {
func (ts *tester) checkECR() error {
ts.cfg.Logger.Info("describing ECR repositories")
out, err := ts.cfg.ECRAPI.DescribeRepositories(&ecr.DescribeRepositoriesInput{
RegistryId: aws.String(ts.cfg.EKSConfig.AddOnIRSA.RepositoryAccountID),
RepositoryNames: aws.StringSlice([]string{ts.cfg.EKSConfig.AddOnIRSA.RepositoryName}),
})
if err != nil {
Expand Down Expand Up @@ -226,6 +227,7 @@ func (ts *tester) checkECR() error {

ts.cfg.Logger.Info("describing images")
imgOut, err := ts.cfg.ECRAPI.DescribeImages(&ecr.DescribeImagesInput{
RegistryId: aws.String(ts.cfg.EKSConfig.AddOnIRSA.RepositoryAccountID),
RepositoryName: aws.String(ts.cfg.EKSConfig.AddOnIRSA.RepositoryName),
ImageIds: []*ecr.ImageIdentifier{
{
Expand Down
45 changes: 25 additions & 20 deletions eksconfig/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -366,6 +366,7 @@ AWS_K8S_TESTER_EKS_ADD_ON_CONFORMANCE_ENABLE=true \
| AWS_K8S_TESTER_EKS_ADD_ON_FARGATE_ROLE_MANAGED_POLICY_ARNS | read-only "false" | *eksconfig.AddOnFargate.RoleManagedPolicyARNs | []string |
| AWS_K8S_TESTER_EKS_ADD_ON_FARGATE_ROLE_CFN_STACK_ID | read-only "true" | *eksconfig.AddOnFargate.RoleCFNStackID | string |
| AWS_K8S_TESTER_EKS_ADD_ON_FARGATE_PROFILE_NAME | read-only "false" | *eksconfig.AddOnFargate.ProfileName | string |
| AWS_K8S_TESTER_EKS_ADD_ON_FARGATE_REPOSITORY_ACCOUNT_ID | read-only "false" | *eksconfig.AddOnFargate.RepositoryAccountID | string |
| AWS_K8S_TESTER_EKS_ADD_ON_FARGATE_REPOSITORY_NAME | read-only "false" | *eksconfig.AddOnFargate.RepositoryName | string |
| AWS_K8S_TESTER_EKS_ADD_ON_FARGATE_REPOSITORY_URI | read-only "false" | *eksconfig.AddOnFargate.RepositoryURI | string |
| AWS_K8S_TESTER_EKS_ADD_ON_FARGATE_REPOSITORY_IMAGE_TAG | read-only "false" | *eksconfig.AddOnFargate.RepositoryImageTag | string |
Expand All @@ -388,6 +389,7 @@ AWS_K8S_TESTER_EKS_ADD_ON_CONFORMANCE_ENABLE=true \
| AWS_K8S_TESTER_EKS_ADD_ON_IRSA_ROLE_MANAGED_POLICY_ARNS | read-only "false" | *eksconfig.AddOnIRSA.RoleManagedPolicyARNs | []string |
| AWS_K8S_TESTER_EKS_ADD_ON_IRSA_ROLE_CFN_STACK_ID | read-only "true" | *eksconfig.AddOnIRSA.RoleCFNStackID | string |
| AWS_K8S_TESTER_EKS_ADD_ON_IRSA_S3_KEY | read-only "false" | *eksconfig.AddOnIRSA.S3Key | string |
| AWS_K8S_TESTER_EKS_ADD_ON_IRSA_REPOSITORY_ACCOUNT_ID | read-only "false" | *eksconfig.AddOnIRSA.RepositoryAccountID | string |
| AWS_K8S_TESTER_EKS_ADD_ON_IRSA_REPOSITORY_NAME | read-only "false" | *eksconfig.AddOnIRSA.RepositoryName | string |
| AWS_K8S_TESTER_EKS_ADD_ON_IRSA_REPOSITORY_URI | read-only "false" | *eksconfig.AddOnIRSA.RepositoryURI | string |
| AWS_K8S_TESTER_EKS_ADD_ON_IRSA_REPOSITORY_IMAGE_TAG | read-only "false" | *eksconfig.AddOnIRSA.RepositoryImageTag | string |
Expand Down Expand Up @@ -415,6 +417,7 @@ AWS_K8S_TESTER_EKS_ADD_ON_CONFORMANCE_ENABLE=true \
| AWS_K8S_TESTER_EKS_ADD_ON_IRSA_FARGATE_ROLE_CFN_STACK_ID | read-only "true" | *eksconfig.AddOnIRSAFargate.RoleCFNStackID | string |
| AWS_K8S_TESTER_EKS_ADD_ON_IRSA_FARGATE_S3_KEY | read-only "false" | *eksconfig.AddOnIRSAFargate.S3Key | string |
| AWS_K8S_TESTER_EKS_ADD_ON_IRSA_FARGATE_PROFILE_NAME | read-only "false" | *eksconfig.AddOnIRSAFargate.ProfileName | string |
| AWS_K8S_TESTER_EKS_ADD_ON_IRSA_FARGATE_REPOSITORY_ACCOUNT_ID | read-only "false" | *eksconfig.AddOnIRSAFargate.RepositoryAccountID | string |
| AWS_K8S_TESTER_EKS_ADD_ON_IRSA_FARGATE_REPOSITORY_NAME | read-only "false" | *eksconfig.AddOnIRSAFargate.RepositoryName | string |
| AWS_K8S_TESTER_EKS_ADD_ON_IRSA_FARGATE_REPOSITORY_URI | read-only "false" | *eksconfig.AddOnIRSAFargate.RepositoryURI | string |
| AWS_K8S_TESTER_EKS_ADD_ON_IRSA_FARGATE_REPOSITORY_IMAGE_TAG | read-only "false" | *eksconfig.AddOnIRSAFargate.RepositoryImageTag | string |
Expand Down Expand Up @@ -491,26 +494,27 @@ AWS_K8S_TESTER_EKS_ADD_ON_CONFORMANCE_ENABLE=true \
*-----------------------------------------------------------------*-------------------*---------------------------------------------------*-------------------*
*--------------------------------------------------------------------*-------------------*------------------------------------------------------*-------------------*
| ENVIRONMENTAL VARIABLE | READ ONLY | TYPE | GO TYPE |
*--------------------------------------------------------------------*-------------------*------------------------------------------------------*-------------------*
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_ENABLE | read-only "false" | *eksconfig.AddOnHollowNodesRemote.Enable | bool |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_CREATED | read-only "true" | *eksconfig.AddOnHollowNodesRemote.Created | bool |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_CREATE_TOOK | read-only "true" | *eksconfig.AddOnHollowNodesRemote.CreateTook | time.Duration |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_CREATE_TOOK_STRING | read-only "true" | *eksconfig.AddOnHollowNodesRemote.CreateTookString | string |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_DELETE_TOOK | read-only "true" | *eksconfig.AddOnHollowNodesRemote.DeleteTook | time.Duration |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_DELETE_TOOK_STRING | read-only "true" | *eksconfig.AddOnHollowNodesRemote.DeleteTookString | string |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_NAMESPACE | read-only "false" | *eksconfig.AddOnHollowNodesRemote.Namespace | string |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_NODE_LABEL_PREFIX | read-only "false" | *eksconfig.AddOnHollowNodesRemote.NodeLabelPrefix | string |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_NODE_LABELS | read-only "true" | *eksconfig.AddOnHollowNodesRemote.NodeLabels | map[string]string |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_NODES | read-only "false" | *eksconfig.AddOnHollowNodesRemote.Nodes | int |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_DEPLOYMENT_REPLICAS | read-only "false" | *eksconfig.AddOnHollowNodesRemote.DeploymentReplicas | int32 |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_MAX_OPEN_FILES | read-only "false" | *eksconfig.AddOnHollowNodesRemote.MaxOpenFiles | int64 |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_REPOSITORY_NAME | read-only "false" | *eksconfig.AddOnHollowNodesRemote.RepositoryName | string |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_REPOSITORY_URI | read-only "false" | *eksconfig.AddOnHollowNodesRemote.RepositoryURI | string |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_REPOSITORY_IMAGE_TAG | read-only "false" | *eksconfig.AddOnHollowNodesRemote.RepositoryImageTag | string |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_CREATED_NODE_NAMES | read-only "true" | *eksconfig.AddOnHollowNodesRemote.CreatedNodeNames | []string |
*--------------------------------------------------------------------*-------------------*------------------------------------------------------*-------------------*
*---------------------------------------------------------------------*-------------------*-------------------------------------------------------*-------------------*
| ENVIRONMENTAL VARIABLE | READ ONLY | TYPE | GO TYPE |
*---------------------------------------------------------------------*-------------------*-------------------------------------------------------*-------------------*
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_ENABLE | read-only "false" | *eksconfig.AddOnHollowNodesRemote.Enable | bool |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_CREATED | read-only "true" | *eksconfig.AddOnHollowNodesRemote.Created | bool |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_CREATE_TOOK | read-only "true" | *eksconfig.AddOnHollowNodesRemote.CreateTook | time.Duration |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_CREATE_TOOK_STRING | read-only "true" | *eksconfig.AddOnHollowNodesRemote.CreateTookString | string |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_DELETE_TOOK | read-only "true" | *eksconfig.AddOnHollowNodesRemote.DeleteTook | time.Duration |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_DELETE_TOOK_STRING | read-only "true" | *eksconfig.AddOnHollowNodesRemote.DeleteTookString | string |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_NAMESPACE | read-only "false" | *eksconfig.AddOnHollowNodesRemote.Namespace | string |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_NODE_LABEL_PREFIX | read-only "false" | *eksconfig.AddOnHollowNodesRemote.NodeLabelPrefix | string |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_NODE_LABELS | read-only "true" | *eksconfig.AddOnHollowNodesRemote.NodeLabels | map[string]string |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_NODES | read-only "false" | *eksconfig.AddOnHollowNodesRemote.Nodes | int |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_DEPLOYMENT_REPLICAS | read-only "false" | *eksconfig.AddOnHollowNodesRemote.DeploymentReplicas | int32 |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_MAX_OPEN_FILES | read-only "false" | *eksconfig.AddOnHollowNodesRemote.MaxOpenFiles | int64 |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_REPOSITORY_ACCOUNT_ID | read-only "false" | *eksconfig.AddOnHollowNodesRemote.RepositoryAccountID | string |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_REPOSITORY_NAME | read-only "false" | *eksconfig.AddOnHollowNodesRemote.RepositoryName | string |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_REPOSITORY_URI | read-only "false" | *eksconfig.AddOnHollowNodesRemote.RepositoryURI | string |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_REPOSITORY_IMAGE_TAG | read-only "false" | *eksconfig.AddOnHollowNodesRemote.RepositoryImageTag | string |
| AWS_K8S_TESTER_EKS_ADD_ON_HOLLOW_NODES_REMOTE_CREATED_NODE_NAMES | read-only "true" | *eksconfig.AddOnHollowNodesRemote.CreatedNodeNames | []string |
*---------------------------------------------------------------------*-------------------*-------------------------------------------------------*-------------------*
*---------------------------------------------------------------------------------*-------------------*-----------------------------------------------------------------*---------------------------*
Expand Down Expand Up @@ -543,6 +547,7 @@ AWS_K8S_TESTER_EKS_ADD_ON_CONFORMANCE_ENABLE=true \
| AWS_K8S_TESTER_EKS_ADD_ON_CLUSTER_LOADER_REMOTE_DEPLOYMENT_REPLICAS | read-only "false" | *eksconfig.AddOnClusterLoaderRemote.DeploymentReplicas | int32 |
| AWS_K8S_TESTER_EKS_ADD_ON_CLUSTER_LOADER_REMOTE_DURATION | read-only "false" | *eksconfig.AddOnClusterLoaderRemote.Duration | time.Duration |
| AWS_K8S_TESTER_EKS_ADD_ON_CLUSTER_LOADER_REMOTE_DURATION_STRING | read-only "true" | *eksconfig.AddOnClusterLoaderRemote.DurationString | string |
| AWS_K8S_TESTER_EKS_ADD_ON_CLUSTER_LOADER_REMOTE_REPOSITORY_ACCOUNT_ID | read-only "false" | *eksconfig.AddOnClusterLoaderRemote.RepositoryAccountID | string |
| AWS_K8S_TESTER_EKS_ADD_ON_CLUSTER_LOADER_REMOTE_REPOSITORY_NAME | read-only "false" | *eksconfig.AddOnClusterLoaderRemote.RepositoryName | string |
| AWS_K8S_TESTER_EKS_ADD_ON_CLUSTER_LOADER_REMOTE_REPOSITORY_URI | read-only "false" | *eksconfig.AddOnClusterLoaderRemote.RepositoryURI | string |
| AWS_K8S_TESTER_EKS_ADD_ON_CLUSTER_LOADER_REMOTE_REPOSITORY_IMAGE_TAG | read-only "false" | *eksconfig.AddOnClusterLoaderRemote.RepositoryImageTag | string |
Expand Down
17 changes: 14 additions & 3 deletions eksconfig/add-on-cluster-loader-remote.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,9 @@ package eksconfig

import (
"errors"
"fmt"
"path/filepath"
"strings"
"time"

"github.com/aws/aws-k8s-tester/pkg/randutil"
Expand Down Expand Up @@ -38,13 +40,16 @@ type AddOnClusterLoaderRemote struct {
Duration time.Duration `json:"duration,omitempty"`
DurationString string `json:"duration-string,omitempty" read-only:"true"`

// RepositoryName is the repositoryName for tester.
// RepositoryAccountID is the account ID for tester ECR image.
// e.g. "aws/aws-k8s-tester" for "[ACCOUNT_ID].dkr.ecr.us-west-2.amazonaws.com/aws/aws-k8s-tester"
RepositoryAccountID string `json:"repository-account-id,omitempty"`
// RepositoryName is the repositoryName for tester ECR image.
// e.g. "aws/aws-k8s-tester" for "[ACCOUNT_ID].dkr.ecr.us-west-2.amazonaws.com/aws/aws-k8s-tester"
RepositoryName string `json:"repository-name,omitempty"`
// RepositoryURI is the repositoryUri for tester.
// RepositoryURI is the repositoryUri for tester ECR image.
// e.g. "[ACCOUNT_ID].dkr.ecr.us-west-2.amazonaws.com/aws/aws-k8s-tester"
RepositoryURI string `json:"repository-uri,omitempty"`
// RepositoryImageTag is the image tag for tester.
// RepositoryImageTag is the image tag for tester ECR image.
// e.g. "latest" for image URI "[ACCOUNT_ID].dkr.ecr.us-west-2.amazonaws.com/aws/aws-k8s-tester:latest"
RepositoryImageTag string `json:"repository-image-tag,omitempty"`

Expand Down Expand Up @@ -101,12 +106,18 @@ func (cfg *Config) validateAddOnClusterLoaderRemote() error {
}
cfg.AddOnClusterLoaderRemote.DurationString = cfg.AddOnClusterLoaderRemote.Duration.String()

if cfg.AddOnClusterLoaderRemote.RepositoryAccountID == "" {
return errors.New("AddOnClusterLoaderRemote.RepositoryAccountID empty")
}
if cfg.AddOnClusterLoaderRemote.RepositoryName == "" {
return errors.New("AddOnClusterLoaderRemote.RepositoryName empty")
}
if cfg.AddOnClusterLoaderRemote.RepositoryURI == "" {
return errors.New("AddOnClusterLoaderRemote.RepositoryURI empty")
}
if strings.Contains(cfg.AddOnClusterLoaderRemote.RepositoryURI, cfg.AddOnClusterLoaderRemote.RepositoryAccountID) {
return fmt.Errorf("AddOnClusterLoaderRemote.RepositoryURI %q does not have AddOnClusterLoaderRemote.RepositoryAccountID %q", cfg.AddOnClusterLoaderRemote.RepositoryURI, cfg.AddOnClusterLoaderRemote.RepositoryAccountID)
}
if cfg.AddOnClusterLoaderRemote.RepositoryImageTag == "" {
return errors.New("AddOnClusterLoaderRemote.RepositoryImageTag empty")
}
Expand Down
Loading

0 comments on commit cc418cc

Please sign in to comment.