gitforge/tests/integration/change_default_branch_test.go
Andreas Ahlenstorf b29e21a90c fix: use proper ${{ forgejo.ref }} in scheduled workflows (#13081)
Forgejo uses the plain branch name instead of a so-called fully-formed ref name (`refs/heads/<branch_name>`) when setting the `Ref` property of scheduled workflows, which is wrong.

Resolves https://codeberg.org/forgejo/forgejo/issues/13060.

## Checklist

The [contributor guide](https://forgejo.org/docs/next/contributor/) contains information that will be helpful to first time contributors. All work and communication must conform to Forgejo's [AI Agreement](https://codeberg.org/forgejo/governance/src/branch/main/AIAgreement.md). There also are a few [conditions for merging Pull Requests in Forgejo repositories](https://codeberg.org/forgejo/governance/src/branch/main/PullRequestsAgreement.md). You are also welcome to join the [Forgejo development chatroom](https://matrix.to/#/#forgejo-development:matrix.org).

### Tests for Go changes

(can be removed for JavaScript changes)

- I added test coverage for Go changes...
  - [ ] in their respective `*_test.go` for unit tests.
  - [x] in the `tests/integration` directory if it involves interactions with a live Forgejo server.
- I ran...
  - [x] `make pr-go` before pushing

### Tests for JavaScript changes

(can be removed for Go changes)

- I added test coverage for JavaScript changes...
  - [ ] in `web_src/js/*.test.js` if it can be unit tested.
  - [ ] in `tests/e2e/*.test.e2e.js` if it requires interactions with a live Forgejo server (see also the [developer guide for JavaScript testing](https://codeberg.org/forgejo/forgejo/src/branch/forgejo/tests/e2e/README.md#end-to-end-tests)).

### Documentation

- [ ] I created a pull request [to the documentation](https://codeberg.org/forgejo/docs) to explain to Forgejo users how to use this change.
- [ ] I did not document these changes and I do not expect someone else to do it.

### Release notes

- [x] This change will be noticed by a Forgejo user or admin (feature, bug fix, performance, etc.). I suggest to include a release note for this change.
- [ ] This change is not visible to a Forgejo user or admin (refactor, dependency upgrade, etc.). I think there is no need to add a release note for this change.

*The decision if the pull request will be shown in the release notes is up to the mergers / release team.*

The content of the `release-notes/<pull request number>.md` file will serve as the basis for the release notes. If the file does not exist, the title of the pull request will be used instead.

Reviewed-on: https://codeberg.org/forgejo/forgejo/pulls/13081
Reviewed-by: Mathieu Fenniak <mfenniak@noreply.codeberg.org>
2026-06-15 04:15:07 +02:00

178 lines
5 KiB
Go

// Copyright 2017 The Gitea Authors. All rights reserved.
// SPDX-License-Identifier: MIT
package integration
import (
"fmt"
"net/http"
"net/url"
"strings"
"testing"
actions_model "forgejo.org/models/actions"
"forgejo.org/models/db"
repo_model "forgejo.org/models/repo"
"forgejo.org/models/unittest"
user_model "forgejo.org/models/user"
"forgejo.org/modules/gitrepo"
"forgejo.org/modules/optional"
repo_service "forgejo.org/services/repository"
files_service "forgejo.org/services/repository/files"
"forgejo.org/tests"
"forgejo.org/tests/forgery"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
)
func TestChangeDefaultBranch(t *testing.T) {
defer tests.PrepareTestEnv(t)()
repo := unittest.AssertExistsAndLoadBean(t, &repo_model.Repository{ID: 1})
owner := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: repo.OwnerID})
session := loginUser(t, owner.Name)
branchesURL := fmt.Sprintf("/%s/%s/settings/branches", owner.Name, repo.Name)
req := NewRequestWithValues(t, "POST", branchesURL, map[string]string{
"action": "default_branch",
"branch": "DefaultBranch",
})
session.MakeRequest(t, req, http.StatusSeeOther)
req = NewRequestWithValues(t, "POST", branchesURL, map[string]string{
"action": "default_branch",
"branch": "does_not_exist",
})
session.MakeRequest(t, req, http.StatusNotFound)
}
func TestChangeDefaultBranchUpdatesSchedules(t *testing.T) {
type expectedSpec struct {
cron string
timeZone optional.Option[string]
}
expectedMainSpec := expectedSpec{
cron: "30 5,17 * * *",
timeZone: optional.None[string](),
}
expectedTestSpec := expectedSpec{
cron: "0 * * * *",
timeZone: optional.None[string](),
}
testWorkflow := struct {
name string
workflowID string
workflowDirectory string
workflowContent string
updatedWorkflowContent string
expectedWorkflowTitle string
}{
name: "Forgejo",
workflowID: "scheduled.yml",
workflowDirectory: ".forgejo/workflows",
workflowContent: `
on:
schedule:
- cron: "30 5,17 * * *"
jobs:
test:
steps:
- run: echo OK
`,
updatedWorkflowContent: `
on:
schedule:
- cron: "0 * * * *"
jobs:
test:
steps:
- run: echo updated
`,
expectedWorkflowTitle: ".forgejo/workflows/scheduled.yml",
}
onApplicationRun(t, func(t *testing.T, u *url.URL) {
user := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: 2})
// create repo
var sha string
repo := forgery.CreateRepository(t, user, &forgery.CreateRepositoryOptions{
Files: forgery.MapFS{
fmt.Sprintf("%s/%s", testWorkflow.workflowDirectory, testWorkflow.workflowID): forgery.MapFile(testWorkflow.workflowContent),
},
LatestSha: &sha,
})
gitRepo, err := gitrepo.OpenRepository(t.Context(), repo)
require.NoError(t, err)
defer gitRepo.Close()
// create new branch
err = repo_service.CreateNewBranch(t.Context(), user, repo, gitRepo, repo.DefaultBranch, "test")
require.NoError(t, err)
commit, err := gitRepo.GetBranchCommit("test")
require.NoError(t, err)
_, err = files_service.ChangeRepoFiles(
t.Context(),
repo,
user,
&files_service.ChangeRepoFilesOptions{
LastCommitID: commit.ID.String(),
OldBranch: "test",
NewBranch: "test",
Message: "update workflow",
Files: []*files_service.ChangeRepoFile{
{
Operation: "update",
TreePath: testWorkflow.expectedWorkflowTitle,
ContentReader: strings.NewReader(testWorkflow.updatedWorkflowContent),
},
},
},
)
require.NoError(t, err)
assertSchedule := func(t *testing.T, expectedRef, content string, spec expectedSpec) {
t.Helper()
schedules, err := db.Find[actions_model.ActionSchedule](t.Context(), actions_model.FindScheduleOptions{RepoID: repo.ID})
require.NoError(t, err)
require.Len(t, schedules, 1)
assert.Equal(t, expectedRef, schedules[0].Ref)
assert.Equal(t, testWorkflow.expectedWorkflowTitle, schedules[0].Title)
assert.Equal(t, repo.ID, schedules[0].RepoID)
assert.Equal(t, testWorkflow.workflowID, schedules[0].WorkflowID)
assert.Equal(t, testWorkflow.workflowDirectory, schedules[0].WorkflowDirectory)
assert.Equal(t, []byte(content), schedules[0].Content)
specs, total, err := actions_model.FindSpecs(t.Context(), actions_model.FindSpecOptions{RepoID: repo.ID})
require.NoError(t, err)
require.Equal(t, int64(1), total)
require.Len(t, specs, 1)
assert.Equal(t, schedules[0].ID, specs[0].ScheduleID)
assert.Equal(t, spec.cron, specs[0].Spec)
assert.Equal(t, spec.timeZone, specs[0].TimeZone)
}
// change default branch to test
err = repo_service.SetRepoDefaultBranch(t.Context(), repo, gitRepo, "test")
require.NoError(t, err)
assertSchedule(t, "refs/heads/test", testWorkflow.updatedWorkflowContent, expectedTestSpec)
// change default branch to main
err = repo_service.SetRepoDefaultBranch(t.Context(), repo, gitRepo, "main")
require.NoError(t, err)
assertSchedule(t, "refs/heads/main", testWorkflow.workflowContent, expectedMainSpec)
})
}