diff --git a/pkg/lint/rules/chartfile.go b/pkg/lint/rules/chartfile.go index 103c28374..99da01979 100644 --- a/pkg/lint/rules/chartfile.go +++ b/pkg/lint/rules/chartfile.go @@ -21,6 +21,7 @@ import ( "fmt" "os" "path/filepath" + "regexp" "github.com/Masterminds/semver/v3" "github.com/asaskevich/govalidator" @@ -118,11 +119,21 @@ func validateChartName(cf *chart.Metadata) error { } name := filepath.Base(cf.Name) if name != cf.Name { - return fmt.Errorf("chart name %q is invalid", cf.Name) + return fmt.Errorf("chart name %q is invalid: chart names must not include path components", cf.Name) } + if !validChartNameChecker(cf.Name) { + return fmt.Errorf("chart name %q is invalid: must be lowercase and may only contain letters, numbers, and dashes", cf.Name) + } + return nil } +// validChartNameChecker ensures that the chart name follows the defined pattern. +func validChartNameChecker(name string) bool { + re := regexp.MustCompile(`^[a-z0-9-]+$`) + return re.MatchString(name) +} + func validateChartAPIVersion(cf *chart.Metadata) error { if cf.APIVersion == "" { return errors.New("apiVersion is required. The value must be either \"v1\" or \"v2\"") diff --git a/pkg/lint/rules/chartfile_test.go b/pkg/lint/rules/chartfile_test.go index 1719a2011..4c344a8ca 100644 --- a/pkg/lint/rules/chartfile_test.go +++ b/pkg/lint/rules/chartfile_test.go @@ -67,14 +67,30 @@ func TestValidateChartYamlFormat(t *testing.T) { } func TestValidateChartName(t *testing.T) { - err := validateChartName(badChart) - if err == nil { - t.Errorf("validateChartName to return a linter error, got no error") + validChart := &chart.Chart{Metadata: &chart.Metadata{Name: "valid-chart"}} + + invalidChartNames := []struct { + name string + expected string + }{ + {"ValidChart", "chart name \"ValidChart\" is invalid: must be lowercase and may only contain letters, numbers and dashes"}, + {"chart.name", "chart name \"chart.name\" is invalid: must be lowercase and may only contain letters, numbers and dashes"}, + {"chart/name", "chart name \"chart/name\" is invalid: chart names must not include path components"}, + {"-bad-start", "chart name \"-bad-start\" is invalid: must be lowercase and may only contain letters, numbers and dashes"}, + {"/path/to/chart", "chart name \"/path/to/chart\" is invalid: chart names must not include path components"}, } - err = validateChartName(badChartName) - if err == nil { - t.Error("expected validateChartName to return a linter error for an invalid name, got no error") + err := validateChartName(validChart.Metadata) + if err != nil { + t.Errorf("expected validateChartName to return no error for a valid name, got %s", err) + } + + for _, chartName := range invalidChartNames { + badChart := &chart.Chart{Metadata: &chart.Metadata{Name: chartName.name}} + err := validateChartName(badChart.Metadata) + if err == nil || err.Error() != chartName.expected { + t.Errorf("validateChartName(%q) = %v, want error %q", chartName.name, err, chartName.expected) + } } }