0
0
mirror of https://github.com/go-gitea/gitea.git synced 2026-05-08 18:53:51 +02:00

Add comment and integration test for RPM routing collision

Signed-off-by: Rohan Guliani <rohansguliani@google.com>
This commit is contained in:
Rohan Guliani 2026-04-02 19:59:34 +00:00
parent 86215d5212
commit 7d9a13241c
2 changed files with 27 additions and 0 deletions

View File

@ -473,6 +473,9 @@ func CommonRoutes() *web.Router {
g.MatchPath("GET", "/<group:*>/repodata/<filename>", rpm.GetRepositoryFile)
g.MatchPath("PUT", "/<group:*>/upload", reqPackageAccess(perm.AccessModeWrite), rpm.UploadPackageFile)
// this URL pattern is only used internally in the RPM index, it is generated by us, the filename part is not really used (can be anything)
// Order is important here: the more specific long route (with filename) must come first.
// If the short route is first, it can greedily match the filename as part of the architecture
// when the package name itself contains the string "package".
g.MatchPath("HEAD,GET", "/<group:*>/package/<name>/<version>/<architecture>/<filename>", rpm.DownloadPackageFile)
g.MatchPath("HEAD,GET", "/<group:*>/package/<name>/<version>/<architecture>", rpm.DownloadPackageFile)
g.MatchPath("DELETE", "/<group:*>/package/<name>/<version>/<architecture>", reqPackageAccess(perm.AccessModeWrite), rpm.DeletePackageFile)

View File

@ -15,6 +15,7 @@ import (
"strings"
"testing"
"code.gitea.io/gitea/models/db"
"code.gitea.io/gitea/models/packages"
"code.gitea.io/gitea/models/unittest"
user_model "code.gitea.io/gitea/models/user"
@ -164,6 +165,29 @@ gpgkey=%sapi/packages/%s/rpm/repository.key`,
req = NewRequest(t, "GET", fmt.Sprintf("%s/package/%s/%s/%s/any-file-name", groupURL, packageName, packageVersion, packageArchitecture))
resp = MakeRequest(t, req, http.StatusOK)
assert.Equal(t, content, resp.Body.Bytes())
// Test with "package" in the name (reproduces bug if fix not applied)
pvs, err := packages.GetVersionsByPackageType(t.Context(), user.ID, packages.TypeRpm)
assert.NoError(t, err)
require.NotEmpty(t, pvs)
// Rename package to "gitea-package" in DB to test collision
_, err = db.GetEngine(t.Context()).Exec("UPDATE package SET name = ?, lower_name = ? WHERE id = ?", "gitea-package", "gitea-package", pvs[0].PackageID)
assert.NoError(t, err)
// Rename package_file to match new name
_, err = db.GetEngine(t.Context()).Exec("UPDATE package_file SET name = ?, lower_name = ? WHERE version_id = ?", "gitea-package-1.0.2-1.x86_64.rpm", "gitea-package-1.0.2-1.x86_64.rpm", pvs[0].ID)
assert.NoError(t, err)
defer func() {
// Restore name
db.GetEngine(t.Context()).Exec("UPDATE package SET name = ?, lower_name = ? WHERE id = ?", packageName, strings.ToLower(packageName), pvs[0].PackageID)
db.GetEngine(t.Context()).Exec("UPDATE package_file SET name = ?, lower_name = ? WHERE version_id = ?", fmt.Sprintf("%s-%s.%s.rpm", packageName, packageVersion, packageArchitecture), strings.ToLower(fmt.Sprintf("%s-%s.%s.rpm", packageName, packageVersion, packageArchitecture)), pvs[0].ID)
}()
req = NewRequest(t, "GET", fmt.Sprintf("%s/package/%s/%s/%s/any-file-name", groupURL, "gitea-package", packageVersion, packageArchitecture))
resp = MakeRequest(t, req, http.StatusOK)
assert.Equal(t, content, resp.Body.Bytes())
})
t.Run("Repository", func(t *testing.T) {