loading up the forgejo repo on tangled to test page performance
0
fork

Configure Feed

Select the types of activity you want to include in your feed.

Merge pull request '[gitea] week 2024-46 cherry pick (gitea/main -> forgejo)' (#5988) from earl-warren/wcp/2024-46 into forgejo

Reviewed-on: https://codeberg.org/forgejo/forgejo/pulls/5988
Reviewed-by: Gusted <gusted@noreply.codeberg.org>

+88 -22
+16 -14
models/repo/user_repo.go
··· 75 75 return nil, err 76 76 } 77 77 78 - additionalUserIDs := make([]int64, 0, 10) 79 - if err = e.Table("team_user"). 80 - Join("INNER", "team_repo", "`team_repo`.team_id = `team_user`.team_id"). 81 - Join("INNER", "team_unit", "`team_unit`.team_id = `team_user`.team_id"). 82 - Where("`team_repo`.repo_id = ? AND (`team_unit`.access_mode >= ? OR (`team_unit`.access_mode = ? AND `team_unit`.`type` = ?))", 83 - repo.ID, perm.AccessModeWrite, perm.AccessModeRead, unit.TypePullRequests). 84 - Distinct("`team_user`.uid"). 85 - Select("`team_user`.uid"). 86 - Find(&additionalUserIDs); err != nil { 87 - return nil, err 88 - } 89 - 90 78 uniqueUserIDs := make(container.Set[int64]) 91 79 uniqueUserIDs.AddMultiple(userIDs...) 92 - uniqueUserIDs.AddMultiple(additionalUserIDs...) 80 + 81 + if repo.Owner.IsOrganization() { 82 + additionalUserIDs := make([]int64, 0, 10) 83 + if err = e.Table("team_user"). 84 + Join("INNER", "team_repo", "`team_repo`.team_id = `team_user`.team_id"). 85 + Join("INNER", "team_unit", "`team_unit`.team_id = `team_user`.team_id"). 86 + Where("`team_repo`.repo_id = ? AND (`team_unit`.access_mode >= ? OR (`team_unit`.access_mode = ? AND `team_unit`.`type` = ?))", 87 + repo.ID, perm.AccessModeWrite, perm.AccessModeRead, unit.TypePullRequests). 88 + Distinct("`team_user`.uid"). 89 + Select("`team_user`.uid"). 90 + Find(&additionalUserIDs); err != nil { 91 + return nil, err 92 + } 93 + uniqueUserIDs.AddMultiple(additionalUserIDs...) 94 + } 93 95 94 96 // Leave a seat for owner itself to append later, but if owner is an organization 95 97 // and just waste 1 unit is cheaper than re-allocate memory once. 96 98 users := make([]*user_model.User, 0, len(uniqueUserIDs)+1) 97 - if len(userIDs) > 0 { 99 + if len(uniqueUserIDs) > 0 { 98 100 if err = e.In("id", uniqueUserIDs.Values()). 99 101 Where(builder.Eq{"`user`.is_active": true}). 100 102 OrderBy(user_model.GetOrderByName()).
+1
release-notes/5988.md
··· 1 + fix: [commit](https://codeberg.org/forgejo/forgejo/commit/fc26becba4b08877a726f2e7e453992310245fe5) when a tag was removed and a release existed for that tag, it would be broken. The release is no longer broken the tag can be added again.
+12 -7
services/repository/push.go
··· 307 307 } 308 308 309 309 releases, err := db.Find[repo_model.Release](ctx, repo_model.FindReleasesOptions{ 310 - RepoID: repo.ID, 311 - TagNames: tags, 312 - IncludeTags: true, 310 + RepoID: repo.ID, 311 + TagNames: tags, 312 + IncludeDrafts: true, 313 + IncludeTags: true, 313 314 }) 314 315 if err != nil { 315 316 return fmt.Errorf("db.Find[repo_model.Release]: %w", err) ··· 394 395 } 395 396 newReleases = append(newReleases, rel) 396 397 } else { 397 - rel.Title = parts[0] 398 - rel.Note = note 399 398 rel.Sha1 = commit.ID.String() 400 399 rel.CreatedUnix = timeutil.TimeStamp(createdAt.Unix()) 401 400 rel.NumCommits = commitsCount 402 - if rel.IsTag && author != nil { 403 - rel.PublisherID = author.ID 401 + if rel.IsTag { 402 + rel.Title = parts[0] 403 + rel.Note = note 404 + if author != nil { 405 + rel.PublisherID = author.ID 406 + } 407 + } else { 408 + rel.IsDraft = false 404 409 } 405 410 if err = repo_model.UpdateRelease(ctx, rel); err != nil { 406 411 return fmt.Errorf("Update: %w", err)
+47
tests/integration/repo_tag_test.go
··· 5 5 package integration 6 6 7 7 import ( 8 + "fmt" 8 9 "net/http" 9 10 "net/url" 10 11 "strings" 11 12 "testing" 12 13 13 14 "code.gitea.io/gitea/models" 15 + auth_model "code.gitea.io/gitea/models/auth" 14 16 repo_model "code.gitea.io/gitea/models/repo" 15 17 "code.gitea.io/gitea/models/unittest" 16 18 user_model "code.gitea.io/gitea/models/user" 17 19 "code.gitea.io/gitea/modules/git" 18 20 repo_module "code.gitea.io/gitea/modules/repository" 21 + api "code.gitea.io/gitea/modules/structs" 19 22 "code.gitea.io/gitea/services/release" 20 23 "code.gitea.io/gitea/tests" 21 24 ··· 159 162 }) 160 163 }) 161 164 } 165 + 166 + func TestRepushTag(t *testing.T) { 167 + onGiteaRun(t, func(t *testing.T, u *url.URL) { 168 + repo := unittest.AssertExistsAndLoadBean(t, &repo_model.Repository{ID: 1}) 169 + owner := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: repo.OwnerID}) 170 + session := loginUser(t, owner.LowerName) 171 + token := getTokenForLoggedInUser(t, session, auth_model.AccessTokenScopeWriteRepository) 172 + 173 + httpContext := NewAPITestContext(t, owner.Name, repo.Name) 174 + 175 + dstPath := t.TempDir() 176 + 177 + u.Path = httpContext.GitPath() 178 + u.User = url.UserPassword(owner.Name, userPassword) 179 + 180 + doGitClone(dstPath, u)(t) 181 + 182 + // create and push a tag 183 + _, _, err := git.NewCommand(git.DefaultContext, "tag", "v2.0").RunStdString(&git.RunOpts{Dir: dstPath}) 184 + require.NoError(t, err) 185 + _, _, err = git.NewCommand(git.DefaultContext, "push", "origin", "--tags", "v2.0").RunStdString(&git.RunOpts{Dir: dstPath}) 186 + require.NoError(t, err) 187 + // create a release for the tag 188 + createdRelease := createNewReleaseUsingAPI(t, token, owner, repo, "v2.0", "", "Release of v2.0", "desc") 189 + assert.False(t, createdRelease.IsDraft) 190 + // delete the tag 191 + _, _, err = git.NewCommand(git.DefaultContext, "push", "origin", "--delete", "v2.0").RunStdString(&git.RunOpts{Dir: dstPath}) 192 + require.NoError(t, err) 193 + // query the release by API and it should be a draft 194 + req := NewRequest(t, "GET", fmt.Sprintf("/api/v1/repos/%s/%s/releases/tags/%s", owner.Name, repo.Name, "v2.0")) 195 + resp := MakeRequest(t, req, http.StatusOK) 196 + var respRelease *api.Release 197 + DecodeJSON(t, resp, &respRelease) 198 + assert.True(t, respRelease.IsDraft) 199 + // re-push the tag 200 + _, _, err = git.NewCommand(git.DefaultContext, "push", "origin", "--tags", "v2.0").RunStdString(&git.RunOpts{Dir: dstPath}) 201 + require.NoError(t, err) 202 + // query the release by API and it should not be a draft 203 + req = NewRequest(t, "GET", fmt.Sprintf("/api/v1/repos/%s/%s/releases/tags/%s", owner.Name, repo.Name, "v2.0")) 204 + resp = MakeRequest(t, req, http.StatusOK) 205 + DecodeJSON(t, resp, &respRelease) 206 + assert.False(t, respRelease.IsDraft) 207 + }) 208 + }
+12 -1
web_src/js/markup/mermaid.js
··· 56 56 btn.setAttribute('data-clipboard-text', source); 57 57 mermaidBlock.append(btn); 58 58 59 + const updateIframeHeight = () => { 60 + iframe.style.height = `${iframe.contentWindow.document.body.clientHeight}px`; 61 + }; 62 + 63 + // update height when element's visibility state changes, for example when the diagram is inside 64 + // a <details> + <summary> block and the <details> block becomes visible upon user interaction, it 65 + // would initially set a incorrect height and the correct height is set during this callback. 66 + (new IntersectionObserver(() => { 67 + updateIframeHeight(); 68 + }, {root: document.documentElement})).observe(iframe); 69 + 59 70 iframe.addEventListener('load', () => { 60 71 pre.replaceWith(mermaidBlock); 61 72 mermaidBlock.classList.remove('tw-hidden'); 62 - iframe.style.height = `${iframe.contentWindow.document.body.clientHeight}px`; 73 + updateIframeHeight(); 63 74 setTimeout(() => { // avoid flash of iframe background 64 75 mermaidBlock.classList.remove('is-loading'); 65 76 iframe.classList.remove('tw-invisible');