From d8a267d3abf0d18cc34b6302d8dcf815474659f6 Mon Sep 17 00:00:00 2001 From: Gusted Date: Mon, 19 Feb 2024 14:32:37 +0100 Subject: [PATCH] [FEAT] Restrict file size of blame operation - Currently there exists a restriction to not render and show files that are larger than what's configured in `[UI].MAX_DISPLAY_FILE_SIZE`. - Apply the same restriction to the blame operation as well, as the blame operation can be seen as displaying a file. - Add integration test. - Ref: #2394 --- routers/web/repo/blame.go | 9 +++++ templates/repo/blame.tmpl | 10 ++++++ tests/integration/repo_test.go | 65 +++++++++++++++++++++++++++++----- 3 files changed, 75 insertions(+), 9 deletions(-) diff --git a/routers/web/repo/blame.go b/routers/web/repo/blame.go index d7c861c42b..c8bb6cca7b 100644 --- a/routers/web/repo/blame.go +++ b/routers/web/repo/blame.go @@ -16,6 +16,7 @@ import ( "code.gitea.io/gitea/modules/git" "code.gitea.io/gitea/modules/highlight" "code.gitea.io/gitea/modules/log" + "code.gitea.io/gitea/modules/setting" "code.gitea.io/gitea/modules/templates" "code.gitea.io/gitea/modules/timeutil" "code.gitea.io/gitea/modules/util" @@ -69,6 +70,14 @@ func RefBlame(ctx *context.Context) { ctx.Data["FileSize"] = blob.Size() ctx.Data["FileName"] = blob.Name() + // Do not display a blame view if the size of the file is + // larger than what is configured as the maximum. + if blob.Size() >= setting.UI.MaxDisplayFileSize { + ctx.Data["IsFileTooLarge"] = true + ctx.HTML(http.StatusOK, tplRepoHome) + return + } + ctx.Data["NumLinesSet"] = true ctx.Data["NumLines"], err = blob.GetBlobLineCount() if err != nil { diff --git a/templates/repo/blame.tmpl b/templates/repo/blame.tmpl index 31cd5b23f6..3bd5e36949 100644 --- a/templates/repo/blame.tmpl +++ b/templates/repo/blame.tmpl @@ -30,6 +30,15 @@
+ {{if .IsFileTooLarge}} + + + + + + +
{{ctx.Locale.Tr "repo.file_too_large"}}
+ {{else}} {{range $row := .BlameRows}} @@ -75,6 +84,7 @@ {{end}}
+ {{end}}
diff --git a/tests/integration/repo_test.go b/tests/integration/repo_test.go index 3f2755870e..b62297e0e9 100644 --- a/tests/integration/repo_test.go +++ b/tests/integration/repo_test.go @@ -15,13 +15,16 @@ import ( repo_model "code.gitea.io/gitea/models/repo" unit_model "code.gitea.io/gitea/models/unit" "code.gitea.io/gitea/models/unittest" + "code.gitea.io/gitea/modules/git" "code.gitea.io/gitea/modules/setting" "code.gitea.io/gitea/modules/test" + "code.gitea.io/gitea/modules/translation" repo_service "code.gitea.io/gitea/services/repository" "code.gitea.io/gitea/tests" "github.com/PuerkitoBio/goquery" "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" ) func TestViewRepo(t *testing.T) { @@ -447,17 +450,61 @@ func TestBlameFileInRepo(t *testing.T) { session := loginUser(t, "user2") - req := NewRequest(t, "GET", "/user2/repo1/blame/branch/master/README.md") - resp := session.MakeRequest(t, req, http.StatusOK) + t.Run("Assert", func(t *testing.T) { + defer tests.PrintCurrentTest(t)() - htmlDoc := NewHTMLParser(t, resp.Body) - description := htmlDoc.doc.Find("#repo-desc") - repoTopics := htmlDoc.doc.Find("#repo-topics") - repoSummary := htmlDoc.doc.Find(".repository-summary") + req := NewRequest(t, "GET", "/user2/repo1/blame/branch/master/README.md") + resp := session.MakeRequest(t, req, http.StatusOK) - assert.EqualValues(t, 0, description.Length()) - assert.EqualValues(t, 0, repoTopics.Length()) - assert.EqualValues(t, 0, repoSummary.Length()) + htmlDoc := NewHTMLParser(t, resp.Body) + description := htmlDoc.doc.Find("#repo-desc") + repoTopics := htmlDoc.doc.Find("#repo-topics") + repoSummary := htmlDoc.doc.Find(".repository-summary") + + assert.EqualValues(t, 0, description.Length()) + assert.EqualValues(t, 0, repoTopics.Length()) + assert.EqualValues(t, 0, repoSummary.Length()) + }) + + t.Run("File size", func(t *testing.T) { + defer tests.PrintCurrentTest(t)() + + repo := unittest.AssertExistsAndLoadBean(t, &repo_model.Repository{ID: 1}) + gitRepo, err := git.OpenRepository(git.DefaultContext, repo.RepoPath()) + require.NoError(t, err) + defer gitRepo.Close() + + commit, err := gitRepo.GetCommit("HEAD") + require.NoError(t, err) + + blob, err := commit.GetBlobByPath("README.md") + require.NoError(t, err) + + fileSize := blob.Size() + require.NotZero(t, fileSize) + + t.Run("Above maximum", func(t *testing.T) { + defer tests.PrintCurrentTest(t)() + defer test.MockVariableValue(&setting.UI.MaxDisplayFileSize, fileSize)() + + req := NewRequest(t, "GET", "/user2/repo1/blame/branch/master/README.md") + resp := session.MakeRequest(t, req, http.StatusOK) + + htmlDoc := NewHTMLParser(t, resp.Body) + assert.Contains(t, htmlDoc.Find(".code-view").Text(), translation.NewLocale("en-US").Tr("repo.file_too_large")) + }) + + t.Run("Under maximum", func(t *testing.T) { + defer tests.PrintCurrentTest(t)() + defer test.MockVariableValue(&setting.UI.MaxDisplayFileSize, fileSize+1)() + + req := NewRequest(t, "GET", "/user2/repo1/blame/branch/master/README.md") + resp := session.MakeRequest(t, req, http.StatusOK) + + htmlDoc := NewHTMLParser(t, resp.Body) + assert.NotContains(t, htmlDoc.Find(".code-view").Text(), translation.NewLocale("en-US").Tr("repo.file_too_large")) + }) + }) } // TestViewRepoDirectory repo description, topics and summary should not be displayed when within a directory