diff --git a/internal/blueprint/repository_customizations.go b/internal/blueprint/repository_customizations.go index 652aca82d..43d61abc5 100644 --- a/internal/blueprint/repository_customizations.go +++ b/internal/blueprint/repository_customizations.go @@ -3,6 +3,7 @@ package blueprint import ( "fmt" "net/url" + "regexp" "strings" "github.com/osbuild/osbuild-composer/internal/fsnode" @@ -24,11 +25,18 @@ type RepositoryCustomization struct { Filename string `json:"filename,omitempty" toml:"filename,omitempty"` } +const repoFilenameRegex = "^[\\w.-]{1,250}\\.repo$" + func validateCustomRepository(repo *RepositoryCustomization) error { if repo.Id == "" { return fmt.Errorf("Repository ID is required") } + filenameRegex := regexp.MustCompile(repoFilenameRegex) + if !filenameRegex.MatchString(repo.getFilename()) { + return fmt.Errorf("Repository filename %q is invalid", repo.getFilename()) + } + if len(repo.BaseURLs) == 0 && repo.Mirrorlist == "" && repo.Metalink == "" { return fmt.Errorf("Repository base URL, mirrorlist or metalink is required") } @@ -60,6 +68,9 @@ func (rc *RepositoryCustomization) getFilename() string { if rc.Filename == "" { return fmt.Sprintf("%s.repo", rc.Id) } + if !strings.HasSuffix(rc.Filename, ".repo") { + return fmt.Sprintf("%s.repo", rc.Filename) + } return rc.Filename } diff --git a/internal/blueprint/repository_customizations_test.go b/internal/blueprint/repository_customizations_test.go index 1c59f8c6e..acd3c634c 100644 --- a/internal/blueprint/repository_customizations_test.go +++ b/internal/blueprint/repository_customizations_test.go @@ -79,6 +79,19 @@ func TestGetCustomRepositories(t *testing.T) { }, wantErr: fmt.Errorf("Repository gpg key is not a valid URL or a valid gpg key"), }, + { + name: "Test invalid repository filename error", + expectedCustomizations: Customizations{ + Repositories: []RepositoryCustomization{ + { + Id: "example-1", + BaseURLs: []string{"http://example-1.com"}, + Filename: "!nval!d", + }, + }, + }, + wantErr: fmt.Errorf("Repository filename %q is invalid", "!nval!d.repo"), + }, } for _, tt := range testCases { @@ -126,6 +139,15 @@ func TestCustomRepoFilename(t *testing.T) { }, WantFilename: "test.repo", }, + { + Name: "Test custom filename without extension", + Repo: RepositoryCustomization{ + Id: "example-1", + BaseURLs: []string{"http://example-1.com"}, + Filename: "test", + }, + WantFilename: "test.repo", + }, } for _, tt := range testCases {