2023-06-26 09:33:18 +03:00
// Copyright 2023 The Gitea Authors. All rights reserved.
// SPDX-License-Identifier: MIT
package integration
import (
2023-11-18 14:37:08 +03:00
"fmt"
2023-06-26 09:33:18 +03:00
"net/url"
2023-07-18 21:14:47 +03:00
"strings"
2023-06-26 09:33:18 +03:00
"testing"
"time"
actions_model "code.gitea.io/gitea/models/actions"
2024-07-29 05:21:22 +03:00
auth_model "code.gitea.io/gitea/models/auth"
2023-06-26 09:33:18 +03:00
"code.gitea.io/gitea/models/db"
2024-03-19 10:23:40 +03:00
git_model "code.gitea.io/gitea/models/git"
2023-06-26 09:33:18 +03:00
issues_model "code.gitea.io/gitea/models/issues"
2024-07-29 05:21:22 +03:00
"code.gitea.io/gitea/models/perm"
2023-06-26 09:33:18 +03:00
repo_model "code.gitea.io/gitea/models/repo"
unit_model "code.gitea.io/gitea/models/unit"
"code.gitea.io/gitea/models/unittest"
user_model "code.gitea.io/gitea/models/user"
actions_module "code.gitea.io/gitea/modules/actions"
"code.gitea.io/gitea/modules/git"
2024-03-19 10:23:40 +03:00
"code.gitea.io/gitea/modules/gitrepo"
2023-11-18 14:37:08 +03:00
"code.gitea.io/gitea/modules/setting"
2024-03-14 06:18:04 +03:00
"code.gitea.io/gitea/modules/test"
2023-06-26 09:33:18 +03:00
pull_service "code.gitea.io/gitea/services/pull"
2024-03-19 10:23:40 +03:00
release_service "code.gitea.io/gitea/services/release"
2023-06-26 09:33:18 +03:00
repo_service "code.gitea.io/gitea/services/repository"
files_service "code.gitea.io/gitea/services/repository/files"
"github.com/stretchr/testify/assert"
)
func TestPullRequestTargetEvent ( t * testing . T ) {
onGiteaRun ( t , func ( t * testing . T , u * url . URL ) {
user2 := unittest . AssertExistsAndLoadBean ( t , & user_model . User { ID : 2 } ) // owner of the base repo
2024-07-29 05:21:22 +03:00
user4 := unittest . AssertExistsAndLoadBean ( t , & user_model . User { ID : 4 } ) // owner of the forked repo
2023-06-26 09:33:18 +03:00
// create the base repo
2023-09-06 15:08:51 +03:00
baseRepo , err := repo_service . CreateRepository ( db . DefaultContext , user2 , user2 , repo_service . CreateRepoOptions {
2023-06-26 09:33:18 +03:00
Name : "repo-pull-request-target" ,
Description : "test pull-request-target event" ,
AutoInit : true ,
Gitignores : "Go" ,
License : "MIT" ,
Readme : "Default" ,
DefaultBranch : "main" ,
IsPrivate : false ,
} )
assert . NoError ( t , err )
assert . NotEmpty ( t , baseRepo )
// enable actions
2024-01-13 00:50:38 +03:00
err = repo_service . UpdateRepositoryUnits ( db . DefaultContext , baseRepo , [ ] repo_model . RepoUnit { {
2023-06-26 09:33:18 +03:00
RepoID : baseRepo . ID ,
Type : unit_model . TypeActions ,
} } , nil )
assert . NoError ( t , err )
2024-07-29 05:21:22 +03:00
// add user4 as the collaborator
ctx := NewAPITestContext ( t , baseRepo . OwnerName , baseRepo . Name , auth_model . AccessTokenScopeWriteRepository )
t . Run ( "AddUser4AsCollaboratorWithReadAccess" , doAPIAddCollaborator ( ctx , "user4" , perm . AccessModeRead ) )
2023-06-26 09:33:18 +03:00
// create the forked repo
2024-07-29 05:21:22 +03:00
forkedRepo , err := repo_service . ForkRepository ( git . DefaultContext , user2 , user4 , repo_service . ForkRepoOptions {
2023-06-26 09:33:18 +03:00
BaseRepo : baseRepo ,
Name : "forked-repo-pull-request-target" ,
Description : "test pull-request-target event" ,
} )
assert . NoError ( t , err )
assert . NotEmpty ( t , forkedRepo )
// add workflow file to the base repo
addWorkflowToBaseResp , err := files_service . ChangeRepoFiles ( git . DefaultContext , baseRepo , user2 , & files_service . ChangeRepoFilesOptions {
Files : [ ] * files_service . ChangeRepoFile {
{
2023-07-18 21:14:47 +03:00
Operation : "create" ,
TreePath : ".gitea/workflows/pr.yml" ,
2023-08-05 09:26:06 +03:00
ContentReader : strings . NewReader ( "name: test\non:\n pull_request_target:\n paths:\n - 'file_*.txt'\njobs:\n test:\n runs-on: ubuntu-latest\n steps:\n - run: echo helloworld\n" ) ,
2023-06-26 09:33:18 +03:00
} ,
} ,
Message : "add workflow" ,
OldBranch : "main" ,
NewBranch : "main" ,
Author : & files_service . IdentityOptions {
Name : user2 . Name ,
Email : user2 . Email ,
} ,
Committer : & files_service . IdentityOptions {
Name : user2 . Name ,
Email : user2 . Email ,
} ,
Dates : & files_service . CommitDateOptions {
Author : time . Now ( ) ,
Committer : time . Now ( ) ,
} ,
} )
assert . NoError ( t , err )
assert . NotEmpty ( t , addWorkflowToBaseResp )
// add a new file to the forked repo
2024-07-29 05:21:22 +03:00
addFileToForkedResp , err := files_service . ChangeRepoFiles ( git . DefaultContext , forkedRepo , user4 , & files_service . ChangeRepoFilesOptions {
2023-06-26 09:33:18 +03:00
Files : [ ] * files_service . ChangeRepoFile {
{
2023-07-18 21:14:47 +03:00
Operation : "create" ,
TreePath : "file_1.txt" ,
ContentReader : strings . NewReader ( "file1" ) ,
2023-06-26 09:33:18 +03:00
} ,
} ,
Message : "add file1" ,
OldBranch : "main" ,
NewBranch : "fork-branch-1" ,
Author : & files_service . IdentityOptions {
2024-07-29 05:21:22 +03:00
Name : user4 . Name ,
Email : user4 . Email ,
2023-06-26 09:33:18 +03:00
} ,
Committer : & files_service . IdentityOptions {
2024-07-29 05:21:22 +03:00
Name : user4 . Name ,
Email : user4 . Email ,
2023-06-26 09:33:18 +03:00
} ,
Dates : & files_service . CommitDateOptions {
Author : time . Now ( ) ,
Committer : time . Now ( ) ,
} ,
} )
assert . NoError ( t , err )
assert . NotEmpty ( t , addFileToForkedResp )
// create Pull
pullIssue := & issues_model . Issue {
RepoID : baseRepo . ID ,
Title : "Test pull-request-target-event" ,
2024-07-29 05:21:22 +03:00
PosterID : user4 . ID ,
Poster : user4 ,
2023-06-26 09:33:18 +03:00
IsPull : true ,
}
pullRequest := & issues_model . PullRequest {
HeadRepoID : forkedRepo . ID ,
BaseRepoID : baseRepo . ID ,
HeadBranch : "fork-branch-1" ,
BaseBranch : "main" ,
HeadRepo : forkedRepo ,
BaseRepo : baseRepo ,
Type : issues_model . PullRequestGitea ,
}
err = pull_service . NewPullRequest ( git . DefaultContext , baseRepo , pullIssue , nil , nil , pullRequest , nil )
assert . NoError ( t , err )
// load and compare ActionRun
2023-08-05 09:26:06 +03:00
assert . Equal ( t , 1 , unittest . GetCount ( t , & actions_model . ActionRun { RepoID : baseRepo . ID } ) )
2023-06-26 09:33:18 +03:00
actionRun := unittest . AssertExistsAndLoadBean ( t , & actions_model . ActionRun { RepoID : baseRepo . ID } )
2023-07-07 22:22:03 +03:00
assert . Equal ( t , addFileToForkedResp . Commit . SHA , actionRun . CommitSHA )
2023-06-26 09:33:18 +03:00
assert . Equal ( t , actions_module . GithubEventPullRequestTarget , actionRun . TriggerEvent )
2023-08-05 09:26:06 +03:00
// add another file whose name cannot match the specified path
2024-07-29 05:21:22 +03:00
addFileToForkedResp , err = files_service . ChangeRepoFiles ( git . DefaultContext , forkedRepo , user4 , & files_service . ChangeRepoFilesOptions {
2023-08-05 09:26:06 +03:00
Files : [ ] * files_service . ChangeRepoFile {
{
Operation : "create" ,
TreePath : "foo.txt" ,
ContentReader : strings . NewReader ( "foo" ) ,
} ,
} ,
Message : "add foo.txt" ,
OldBranch : "main" ,
NewBranch : "fork-branch-2" ,
Author : & files_service . IdentityOptions {
2024-07-29 05:21:22 +03:00
Name : user4 . Name ,
Email : user4 . Email ,
2023-08-05 09:26:06 +03:00
} ,
Committer : & files_service . IdentityOptions {
2024-07-29 05:21:22 +03:00
Name : user4 . Name ,
Email : user4 . Email ,
2023-08-05 09:26:06 +03:00
} ,
Dates : & files_service . CommitDateOptions {
Author : time . Now ( ) ,
Committer : time . Now ( ) ,
} ,
} )
assert . NoError ( t , err )
assert . NotEmpty ( t , addFileToForkedResp )
// create Pull
pullIssue = & issues_model . Issue {
RepoID : baseRepo . ID ,
Title : "A mismatched path cannot trigger pull-request-target-event" ,
2024-07-29 05:21:22 +03:00
PosterID : user4 . ID ,
Poster : user4 ,
2023-08-05 09:26:06 +03:00
IsPull : true ,
}
pullRequest = & issues_model . PullRequest {
HeadRepoID : forkedRepo . ID ,
BaseRepoID : baseRepo . ID ,
HeadBranch : "fork-branch-2" ,
BaseBranch : "main" ,
HeadRepo : forkedRepo ,
BaseRepo : baseRepo ,
Type : issues_model . PullRequestGitea ,
}
err = pull_service . NewPullRequest ( git . DefaultContext , baseRepo , pullIssue , nil , nil , pullRequest , nil )
assert . NoError ( t , err )
// the new pull request cannot trigger actions, so there is still only 1 record
assert . Equal ( t , 1 , unittest . GetCount ( t , & actions_model . ActionRun { RepoID : baseRepo . ID } ) )
2023-06-26 09:33:18 +03:00
} )
}
2023-11-18 14:37:08 +03:00
func TestSkipCI ( t * testing . T ) {
onGiteaRun ( t , func ( t * testing . T , u * url . URL ) {
2024-03-14 06:18:04 +03:00
session := loginUser ( t , "user2" )
2023-11-18 14:37:08 +03:00
user2 := unittest . AssertExistsAndLoadBean ( t , & user_model . User { ID : 2 } )
// create the repo
repo , err := repo_service . CreateRepository ( db . DefaultContext , user2 , user2 , repo_service . CreateRepoOptions {
Name : "skip-ci" ,
Description : "test skip ci functionality" ,
AutoInit : true ,
Gitignores : "Go" ,
License : "MIT" ,
Readme : "Default" ,
2024-03-14 06:18:04 +03:00
DefaultBranch : "master" ,
2023-11-18 14:37:08 +03:00
IsPrivate : false ,
} )
assert . NoError ( t , err )
assert . NotEmpty ( t , repo )
// enable actions
2024-01-13 00:50:38 +03:00
err = repo_service . UpdateRepositoryUnits ( db . DefaultContext , repo , [ ] repo_model . RepoUnit { {
2023-11-18 14:37:08 +03:00
RepoID : repo . ID ,
Type : unit_model . TypeActions ,
} } , nil )
assert . NoError ( t , err )
// add workflow file to the repo
addWorkflowToBaseResp , err := files_service . ChangeRepoFiles ( git . DefaultContext , repo , user2 , & files_service . ChangeRepoFilesOptions {
Files : [ ] * files_service . ChangeRepoFile {
{
Operation : "create" ,
TreePath : ".gitea/workflows/pr.yml" ,
2024-03-14 06:18:04 +03:00
ContentReader : strings . NewReader ( "name: test\non:\n push:\n branches: [master]\n pull_request:\njobs:\n test:\n runs-on: ubuntu-latest\n steps:\n - run: echo helloworld\n" ) ,
2023-11-18 14:37:08 +03:00
} ,
} ,
Message : "add workflow" ,
2024-03-14 06:18:04 +03:00
OldBranch : "master" ,
NewBranch : "master" ,
2023-11-18 14:37:08 +03:00
Author : & files_service . IdentityOptions {
Name : user2 . Name ,
Email : user2 . Email ,
} ,
Committer : & files_service . IdentityOptions {
Name : user2 . Name ,
Email : user2 . Email ,
} ,
Dates : & files_service . CommitDateOptions {
Author : time . Now ( ) ,
Committer : time . Now ( ) ,
} ,
} )
assert . NoError ( t , err )
assert . NotEmpty ( t , addWorkflowToBaseResp )
// a run has been created
assert . Equal ( t , 1 , unittest . GetCount ( t , & actions_model . ActionRun { RepoID : repo . ID } ) )
// add a file with a configured skip-ci string in commit message
addFileResp , err := files_service . ChangeRepoFiles ( git . DefaultContext , repo , user2 , & files_service . ChangeRepoFilesOptions {
Files : [ ] * files_service . ChangeRepoFile {
{
Operation : "create" ,
TreePath : "bar.txt" ,
ContentReader : strings . NewReader ( "bar" ) ,
} ,
} ,
Message : fmt . Sprintf ( "%s add bar" , setting . Actions . SkipWorkflowStrings [ 0 ] ) ,
2024-03-14 06:18:04 +03:00
OldBranch : "master" ,
NewBranch : "master" ,
2023-11-18 14:37:08 +03:00
Author : & files_service . IdentityOptions {
Name : user2 . Name ,
Email : user2 . Email ,
} ,
Committer : & files_service . IdentityOptions {
Name : user2 . Name ,
Email : user2 . Email ,
} ,
Dates : & files_service . CommitDateOptions {
Author : time . Now ( ) ,
Committer : time . Now ( ) ,
} ,
} )
assert . NoError ( t , err )
assert . NotEmpty ( t , addFileResp )
// the commit message contains a configured skip-ci string, so there is still only 1 record
assert . Equal ( t , 1 , unittest . GetCount ( t , & actions_model . ActionRun { RepoID : repo . ID } ) )
2024-03-14 06:18:04 +03:00
// add file to new branch
addFileToBranchResp , err := files_service . ChangeRepoFiles ( git . DefaultContext , repo , user2 , & files_service . ChangeRepoFilesOptions {
Files : [ ] * files_service . ChangeRepoFile {
{
Operation : "create" ,
TreePath : "test-skip-ci" ,
ContentReader : strings . NewReader ( "test-skip-ci" ) ,
} ,
} ,
Message : "add test file" ,
OldBranch : "master" ,
NewBranch : "test-skip-ci" ,
Author : & files_service . IdentityOptions {
Name : user2 . Name ,
Email : user2 . Email ,
} ,
Committer : & files_service . IdentityOptions {
Name : user2 . Name ,
Email : user2 . Email ,
} ,
Dates : & files_service . CommitDateOptions {
Author : time . Now ( ) ,
Committer : time . Now ( ) ,
} ,
} )
assert . NoError ( t , err )
assert . NotEmpty ( t , addFileToBranchResp )
resp := testPullCreate ( t , session , "user2" , "skip-ci" , true , "master" , "test-skip-ci" , "[skip ci] test-skip-ci" )
// check the redirected URL
url := test . RedirectURL ( resp )
assert . Regexp ( t , "^/user2/skip-ci/pulls/[0-9]*$" , url )
// the pr title contains a configured skip-ci string, so there is still only 1 record
assert . Equal ( t , 1 , unittest . GetCount ( t , & actions_model . ActionRun { RepoID : repo . ID } ) )
2023-11-18 14:37:08 +03:00
} )
}
2024-03-19 10:23:40 +03:00
func TestCreateDeleteRefEvent ( t * testing . T ) {
onGiteaRun ( t , func ( t * testing . T , u * url . URL ) {
user2 := unittest . AssertExistsAndLoadBean ( t , & user_model . User { ID : 2 } )
// create the repo
repo , err := repo_service . CreateRepository ( db . DefaultContext , user2 , user2 , repo_service . CreateRepoOptions {
Name : "create-delete-ref-event" ,
Description : "test create delete ref ci event" ,
AutoInit : true ,
Gitignores : "Go" ,
License : "MIT" ,
Readme : "Default" ,
DefaultBranch : "main" ,
IsPrivate : false ,
} )
assert . NoError ( t , err )
assert . NotEmpty ( t , repo )
// enable actions
err = repo_service . UpdateRepositoryUnits ( db . DefaultContext , repo , [ ] repo_model . RepoUnit { {
RepoID : repo . ID ,
Type : unit_model . TypeActions ,
} } , nil )
assert . NoError ( t , err )
// add workflow file to the repo
addWorkflowToBaseResp , err := files_service . ChangeRepoFiles ( git . DefaultContext , repo , user2 , & files_service . ChangeRepoFilesOptions {
Files : [ ] * files_service . ChangeRepoFile {
{
Operation : "create" ,
TreePath : ".gitea/workflows/createdelete.yml" ,
ContentReader : strings . NewReader ( "name: test\non:\n [create,delete]\njobs:\n test:\n runs-on: ubuntu-latest\n steps:\n - run: echo helloworld\n" ) ,
} ,
} ,
Message : "add workflow" ,
OldBranch : "main" ,
NewBranch : "main" ,
Author : & files_service . IdentityOptions {
Name : user2 . Name ,
Email : user2 . Email ,
} ,
Committer : & files_service . IdentityOptions {
Name : user2 . Name ,
Email : user2 . Email ,
} ,
Dates : & files_service . CommitDateOptions {
Author : time . Now ( ) ,
Committer : time . Now ( ) ,
} ,
} )
assert . NoError ( t , err )
assert . NotEmpty ( t , addWorkflowToBaseResp )
// Get the commit ID of the default branch
gitRepo , err := gitrepo . OpenRepository ( git . DefaultContext , repo )
assert . NoError ( t , err )
defer gitRepo . Close ( )
branch , err := git_model . GetBranch ( db . DefaultContext , repo . ID , repo . DefaultBranch )
assert . NoError ( t , err )
// create a branch
err = repo_service . CreateNewBranchFromCommit ( db . DefaultContext , user2 , repo , gitRepo , branch . CommitID , "test-create-branch" )
assert . NoError ( t , err )
run := unittest . AssertExistsAndLoadBean ( t , & actions_model . ActionRun {
Title : "add workflow" ,
RepoID : repo . ID ,
Event : "create" ,
Ref : "refs/heads/test-create-branch" ,
WorkflowID : "createdelete.yml" ,
CommitSHA : branch . CommitID ,
} )
assert . NotNil ( t , run )
// create a tag
err = release_service . CreateNewTag ( db . DefaultContext , user2 , repo , branch . CommitID , "test-create-tag" , "test create tag event" )
assert . NoError ( t , err )
run = unittest . AssertExistsAndLoadBean ( t , & actions_model . ActionRun {
Title : "add workflow" ,
RepoID : repo . ID ,
Event : "create" ,
Ref : "refs/tags/test-create-tag" ,
WorkflowID : "createdelete.yml" ,
CommitSHA : branch . CommitID ,
} )
assert . NotNil ( t , run )
// delete the branch
err = repo_service . DeleteBranch ( db . DefaultContext , user2 , repo , gitRepo , "test-create-branch" )
assert . NoError ( t , err )
run = unittest . AssertExistsAndLoadBean ( t , & actions_model . ActionRun {
Title : "add workflow" ,
RepoID : repo . ID ,
Event : "delete" ,
2024-08-19 19:25:41 +03:00
Ref : "refs/heads/main" ,
2024-03-19 10:23:40 +03:00
WorkflowID : "createdelete.yml" ,
CommitSHA : branch . CommitID ,
} )
assert . NotNil ( t , run )
// delete the tag
tag , err := repo_model . GetRelease ( db . DefaultContext , repo . ID , "test-create-tag" )
assert . NoError ( t , err )
err = release_service . DeleteReleaseByID ( db . DefaultContext , repo , tag , user2 , true )
assert . NoError ( t , err )
run = unittest . AssertExistsAndLoadBean ( t , & actions_model . ActionRun {
Title : "add workflow" ,
RepoID : repo . ID ,
Event : "delete" ,
2024-08-19 19:25:41 +03:00
Ref : "refs/heads/main" ,
2024-03-19 10:23:40 +03:00
WorkflowID : "createdelete.yml" ,
CommitSHA : branch . CommitID ,
} )
assert . NotNil ( t , run )
} )
}