2017-02-28 12:58:50 +03:00
// Copyright 2017 The Gitea Authors. All rights reserved.
2022-11-27 21:20:29 +03:00
// SPDX-License-Identifier: MIT
2017-02-28 12:58:50 +03:00
2022-06-06 11:01:49 +03:00
package repo_test
2017-02-28 12:58:50 +03:00
import (
2022-05-21 12:15:40 +03:00
"strings"
2017-02-28 12:58:50 +03:00
"testing"
2021-09-19 14:49:59 +03:00
"code.gitea.io/gitea/models/db"
2022-06-06 11:01:49 +03:00
repo_model "code.gitea.io/gitea/models/repo"
2021-11-12 17:36:47 +03:00
"code.gitea.io/gitea/models/unittest"
2024-02-29 21:52:49 +03:00
"code.gitea.io/gitea/modules/optional"
2017-10-27 00:16:13 +03:00
2017-02-28 12:58:50 +03:00
"github.com/stretchr/testify/assert"
)
2023-08-11 20:08:05 +03:00
func getTestCases ( ) [ ] struct {
name string
opts * repo_model . SearchRepoOptions
count int
} {
2017-10-10 04:23:29 +03:00
testCases := [ ] struct {
name string
2022-06-06 11:01:49 +03:00
opts * repo_model . SearchRepoOptions
2017-10-10 04:23:29 +03:00
count int
} {
2021-03-14 21:52:12 +03:00
{
name : "PublicRepositoriesByName" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { Keyword : "big_test_" , ListOptions : db . ListOptions { PageSize : 10 } , Collaborate : optional . Some ( false ) } ,
2021-03-14 21:52:12 +03:00
count : 7 ,
} ,
{
name : "PublicAndPrivateRepositoriesByName" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { Keyword : "big_test_" , ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , Private : true , Collaborate : optional . Some ( false ) } ,
2021-03-14 21:52:12 +03:00
count : 14 ,
} ,
{
name : "PublicAndPrivateRepositoriesByNameWithPagesizeLimitFirstPage" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { Keyword : "big_test_" , ListOptions : db . ListOptions { Page : 1 , PageSize : 5 } , Private : true , Collaborate : optional . Some ( false ) } ,
2021-03-14 21:52:12 +03:00
count : 14 ,
} ,
{
name : "PublicAndPrivateRepositoriesByNameWithPagesizeLimitSecondPage" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { Keyword : "big_test_" , ListOptions : db . ListOptions { Page : 2 , PageSize : 5 } , Private : true , Collaborate : optional . Some ( false ) } ,
2021-03-14 21:52:12 +03:00
count : 14 ,
} ,
{
name : "PublicAndPrivateRepositoriesByNameWithPagesizeLimitThirdPage" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { Keyword : "big_test_" , ListOptions : db . ListOptions { Page : 3 , PageSize : 5 } , Private : true , Collaborate : optional . Some ( false ) } ,
2021-03-14 21:52:12 +03:00
count : 14 ,
} ,
{
name : "PublicAndPrivateRepositoriesByNameWithPagesizeLimitFourthPage" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { Keyword : "big_test_" , ListOptions : db . ListOptions { Page : 3 , PageSize : 5 } , Private : true , Collaborate : optional . Some ( false ) } ,
2021-03-14 21:52:12 +03:00
count : 14 ,
} ,
{
name : "PublicRepositoriesOfUser" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 15 , Collaborate : optional . Some ( false ) } ,
2021-03-14 21:52:12 +03:00
count : 2 ,
} ,
{
name : "PublicRepositoriesOfUser2" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 18 , Collaborate : optional . Some ( false ) } ,
2021-03-14 21:52:12 +03:00
count : 0 ,
} ,
{
2023-09-14 05:59:53 +03:00
name : "PublicRepositoriesOfOrg3" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 20 , Collaborate : optional . Some ( false ) } ,
2021-03-14 21:52:12 +03:00
count : 2 ,
} ,
{
name : "PublicAndPrivateRepositoriesOfUser" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 15 , Private : true , Collaborate : optional . Some ( false ) } ,
2021-03-14 21:52:12 +03:00
count : 4 ,
} ,
{
name : "PublicAndPrivateRepositoriesOfUser2" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 18 , Private : true , Collaborate : optional . Some ( false ) } ,
2021-03-14 21:52:12 +03:00
count : 0 ,
} ,
{
2023-09-14 05:59:53 +03:00
name : "PublicAndPrivateRepositoriesOfOrg3" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 20 , Private : true , Collaborate : optional . Some ( false ) } ,
2021-03-14 21:52:12 +03:00
count : 4 ,
} ,
{
name : "PublicRepositoriesOfUserIncludingCollaborative" ,
2022-06-06 11:01:49 +03:00
opts : & repo_model . SearchRepoOptions { ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 15 } ,
2021-03-14 21:52:12 +03:00
count : 5 ,
} ,
{
name : "PublicRepositoriesOfUser2IncludingCollaborative" ,
2022-06-06 11:01:49 +03:00
opts : & repo_model . SearchRepoOptions { ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 18 } ,
2021-03-14 21:52:12 +03:00
count : 1 ,
} ,
{
2023-09-14 05:59:53 +03:00
name : "PublicRepositoriesOfOrg3IncludingCollaborative" ,
2022-06-06 11:01:49 +03:00
opts : & repo_model . SearchRepoOptions { ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 20 } ,
2021-03-14 21:52:12 +03:00
count : 3 ,
} ,
{
name : "PublicAndPrivateRepositoriesOfUserIncludingCollaborative" ,
2022-06-06 11:01:49 +03:00
opts : & repo_model . SearchRepoOptions { ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 15 , Private : true } ,
2021-03-14 21:52:12 +03:00
count : 9 ,
} ,
{
name : "PublicAndPrivateRepositoriesOfUser2IncludingCollaborative" ,
2022-06-06 11:01:49 +03:00
opts : & repo_model . SearchRepoOptions { ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 18 , Private : true } ,
2021-03-14 21:52:12 +03:00
count : 4 ,
} ,
{
2023-09-14 05:59:53 +03:00
name : "PublicAndPrivateRepositoriesOfOrg3IncludingCollaborative" ,
2022-06-06 11:01:49 +03:00
opts : & repo_model . SearchRepoOptions { ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 20 , Private : true } ,
2021-03-14 21:52:12 +03:00
count : 7 ,
} ,
{
name : "PublicRepositoriesOfOrganization" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 17 , Collaborate : optional . Some ( false ) } ,
2021-03-14 21:52:12 +03:00
count : 1 ,
} ,
{
name : "PublicAndPrivateRepositoriesOfOrganization" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 17 , Private : true , Collaborate : optional . Some ( false ) } ,
2021-03-14 21:52:12 +03:00
count : 2 ,
} ,
{
name : "AllPublic/PublicRepositoriesByName" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { Keyword : "big_test_" , ListOptions : db . ListOptions { PageSize : 10 } , AllPublic : true , Collaborate : optional . Some ( false ) } ,
2021-03-14 21:52:12 +03:00
count : 7 ,
} ,
{
name : "AllPublic/PublicAndPrivateRepositoriesByName" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { Keyword : "big_test_" , ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , Private : true , AllPublic : true , Collaborate : optional . Some ( false ) } ,
2021-03-14 21:52:12 +03:00
count : 14 ,
} ,
{
name : "AllPublic/PublicRepositoriesOfUserIncludingCollaborative" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 15 , AllPublic : true , Template : optional . Some ( false ) } ,
2024-10-12 02:35:04 +03:00
count : 34 ,
2021-03-14 21:52:12 +03:00
} ,
{
name : "AllPublic/PublicAndPrivateRepositoriesOfUserIncludingCollaborative" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 15 , Private : true , AllPublic : true , AllLimited : true , Template : optional . Some ( false ) } ,
2024-10-12 02:35:04 +03:00
count : 39 ,
2021-03-14 21:52:12 +03:00
} ,
{
name : "AllPublic/PublicAndPrivateRepositoriesOfUserIncludingCollaborativeByName" ,
2022-06-06 11:01:49 +03:00
opts : & repo_model . SearchRepoOptions { Keyword : "test" , ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 15 , Private : true , AllPublic : true } ,
2021-03-14 21:52:12 +03:00
count : 15 ,
} ,
{
name : "AllPublic/PublicAndPrivateRepositoriesOfUser2IncludingCollaborativeByName" ,
2022-06-06 11:01:49 +03:00
opts : & repo_model . SearchRepoOptions { Keyword : "test" , ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 18 , Private : true , AllPublic : true } ,
2021-03-14 21:52:12 +03:00
count : 13 ,
} ,
{
name : "AllPublic/PublicRepositoriesOfOrganization" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , OwnerID : 17 , AllPublic : true , Collaborate : optional . Some ( false ) , Template : optional . Some ( false ) } ,
2024-10-12 02:35:04 +03:00
count : 34 ,
2021-03-14 21:52:12 +03:00
} ,
{
name : "AllTemplates" ,
2024-02-29 21:52:49 +03:00
opts : & repo_model . SearchRepoOptions { ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , Template : optional . Some ( true ) } ,
2021-03-14 21:52:12 +03:00
count : 2 ,
} ,
2022-05-21 12:15:40 +03:00
{
name : "OwnerSlashRepoSearch" ,
2022-06-06 11:01:49 +03:00
opts : & repo_model . SearchRepoOptions { Keyword : "user/repo2" , ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , Private : true , OwnerID : 0 } ,
2023-09-14 05:59:53 +03:00
count : 2 ,
2022-05-21 12:15:40 +03:00
} ,
{
name : "OwnerSlashSearch" ,
2022-06-06 11:01:49 +03:00
opts : & repo_model . SearchRepoOptions { Keyword : "user20/" , ListOptions : db . ListOptions { Page : 1 , PageSize : 10 } , Private : true , OwnerID : 0 } ,
2022-05-21 12:15:40 +03:00
count : 4 ,
} ,
2017-10-10 04:23:29 +03:00
}
2023-08-11 20:08:05 +03:00
return testCases
}
func TestSearchRepository ( t * testing . T ) {
assert . NoError ( t , unittest . PrepareTestDatabase ( ) )
// test search public repository on explore page
repos , count , err := repo_model . SearchRepositoryByName ( db . DefaultContext , & repo_model . SearchRepoOptions {
ListOptions : db . ListOptions {
Page : 1 ,
PageSize : 10 ,
} ,
Keyword : "repo_12" ,
2024-02-29 21:52:49 +03:00
Collaborate : optional . Some ( false ) ,
2023-08-11 20:08:05 +03:00
} )
assert . NoError ( t , err )
if assert . Len ( t , repos , 1 ) {
assert . Equal ( t , "test_repo_12" , repos [ 0 ] . Name )
}
assert . Equal ( t , int64 ( 1 ) , count )
repos , count , err = repo_model . SearchRepositoryByName ( db . DefaultContext , & repo_model . SearchRepoOptions {
ListOptions : db . ListOptions {
Page : 1 ,
PageSize : 10 ,
} ,
Keyword : "test_repo" ,
2024-02-29 21:52:49 +03:00
Collaborate : optional . Some ( false ) ,
2023-08-11 20:08:05 +03:00
} )
assert . NoError ( t , err )
assert . Equal ( t , int64 ( 2 ) , count )
assert . Len ( t , repos , 2 )
// test search private repository on explore page
repos , count , err = repo_model . SearchRepositoryByName ( db . DefaultContext , & repo_model . SearchRepoOptions {
ListOptions : db . ListOptions {
Page : 1 ,
PageSize : 10 ,
} ,
Keyword : "repo_13" ,
Private : true ,
2024-02-29 21:52:49 +03:00
Collaborate : optional . Some ( false ) ,
2023-08-11 20:08:05 +03:00
} )
assert . NoError ( t , err )
if assert . Len ( t , repos , 1 ) {
assert . Equal ( t , "test_repo_13" , repos [ 0 ] . Name )
}
assert . Equal ( t , int64 ( 1 ) , count )
repos , count , err = repo_model . SearchRepositoryByName ( db . DefaultContext , & repo_model . SearchRepoOptions {
ListOptions : db . ListOptions {
Page : 1 ,
PageSize : 10 ,
} ,
Keyword : "test_repo" ,
Private : true ,
2024-02-29 21:52:49 +03:00
Collaborate : optional . Some ( false ) ,
2023-08-11 20:08:05 +03:00
} )
assert . NoError ( t , err )
assert . Equal ( t , int64 ( 3 ) , count )
assert . Len ( t , repos , 3 )
// Test non existing owner
repos , count , err = repo_model . SearchRepositoryByName ( db . DefaultContext , & repo_model . SearchRepoOptions { OwnerID : unittest . NonexistentID } )
assert . NoError ( t , err )
assert . Empty ( t , repos )
assert . Equal ( t , int64 ( 0 ) , count )
// Test search within description
repos , count , err = repo_model . SearchRepository ( db . DefaultContext , & repo_model . SearchRepoOptions {
ListOptions : db . ListOptions {
Page : 1 ,
PageSize : 10 ,
} ,
Keyword : "description_14" ,
2024-02-29 21:52:49 +03:00
Collaborate : optional . Some ( false ) ,
2023-08-11 20:08:05 +03:00
IncludeDescription : true ,
} )
assert . NoError ( t , err )
if assert . Len ( t , repos , 1 ) {
assert . Equal ( t , "test_repo_14" , repos [ 0 ] . Name )
}
assert . Equal ( t , int64 ( 1 ) , count )
// Test NOT search within description
repos , count , err = repo_model . SearchRepository ( db . DefaultContext , & repo_model . SearchRepoOptions {
ListOptions : db . ListOptions {
Page : 1 ,
PageSize : 10 ,
} ,
Keyword : "description_14" ,
2024-02-29 21:52:49 +03:00
Collaborate : optional . Some ( false ) ,
2023-08-11 20:08:05 +03:00
IncludeDescription : false ,
} )
assert . NoError ( t , err )
assert . Empty ( t , repos )
assert . Equal ( t , int64 ( 0 ) , count )
testCases := getTestCases ( )
2017-10-10 04:23:29 +03:00
for _ , testCase := range testCases {
t . Run ( testCase . name , func ( t * testing . T ) {
2022-11-19 11:12:33 +03:00
repos , count , err := repo_model . SearchRepositoryByName ( db . DefaultContext , testCase . opts )
2017-10-10 04:23:29 +03:00
assert . NoError ( t , err )
assert . Equal ( t , int64 ( testCase . count ) , count )
2017-10-27 00:16:13 +03:00
page := testCase . opts . Page
if page <= 0 {
page = 1
}
2021-03-14 21:52:12 +03:00
expectedLen := testCase . opts . PageSize
2017-10-27 00:16:13 +03:00
if testCase . opts . PageSize * page > testCase . count + testCase . opts . PageSize {
expectedLen = 0
} else if testCase . opts . PageSize * page > testCase . count {
2017-10-10 04:23:29 +03:00
expectedLen = testCase . count % testCase . opts . PageSize
}
2017-10-27 00:16:13 +03:00
if assert . Len ( t , repos , expectedLen ) {
for _ , repo := range repos {
assert . NotEmpty ( t , repo . Name )
if len ( testCase . opts . Keyword ) > 0 {
2022-05-21 12:15:40 +03:00
// Keyword match condition is different for search terms of form "owner/repo"
if strings . Count ( testCase . opts . Keyword , "/" ) == 1 {
// May still match as a whole...
wholeMatch := strings . Contains ( repo . Name , testCase . opts . Keyword )
pieces := strings . Split ( testCase . opts . Keyword , "/" )
ownerName := pieces [ 0 ]
repoName := pieces [ 1 ]
// ... or match in parts
splitMatch := strings . Contains ( repo . OwnerName , ownerName ) && strings . Contains ( repo . Name , repoName )
assert . True ( t , wholeMatch || splitMatch , "Keyword '%s' does not match repo '%s/%s'" , testCase . opts . Keyword , repo . Owner . Name , repo . Name )
} else {
assert . Contains ( t , repo . Name , testCase . opts . Keyword )
}
2017-10-27 00:16:13 +03:00
}
if ! testCase . opts . Private {
assert . False ( t , repo . IsPrivate )
}
2024-02-29 21:52:49 +03:00
if testCase . opts . Fork . Value ( ) && testCase . opts . Mirror . Value ( ) {
assert . True ( t , repo . IsFork && repo . IsMirror )
2017-10-27 00:16:13 +03:00
} else {
2024-02-29 21:52:49 +03:00
if testCase . opts . Fork . Has ( ) {
assert . Equal ( t , testCase . opts . Fork . Value ( ) , repo . IsFork )
2017-10-27 00:16:13 +03:00
}
2024-02-29 21:52:49 +03:00
if testCase . opts . Mirror . Has ( ) {
assert . Equal ( t , testCase . opts . Mirror . Value ( ) , repo . IsMirror )
2017-10-27 00:16:13 +03:00
}
}
if testCase . opts . OwnerID > 0 && ! testCase . opts . AllPublic {
2024-02-29 21:52:49 +03:00
if testCase . opts . Collaborate . Has ( ) {
if testCase . opts . Collaborate . Value ( ) {
assert . NotEqual ( t , testCase . opts . OwnerID , repo . Owner . ID )
} else {
assert . Equal ( t , testCase . opts . OwnerID , repo . Owner . ID )
}
2017-10-27 00:16:13 +03:00
}
}
2017-10-10 04:23:29 +03:00
}
}
} )
}
2017-02-28 12:58:50 +03:00
}
2018-09-13 05:33:48 +03:00
2023-08-11 20:08:05 +03:00
func TestCountRepository ( t * testing . T ) {
assert . NoError ( t , unittest . PrepareTestDatabase ( ) )
testCases := getTestCases ( )
for _ , testCase := range testCases {
t . Run ( testCase . name , func ( t * testing . T ) {
count , err := repo_model . CountRepository ( db . DefaultContext , testCase . opts )
assert . NoError ( t , err )
assert . Equal ( t , int64 ( testCase . count ) , count )
} )
}
}
2018-09-13 05:33:48 +03:00
func TestSearchRepositoryByTopicName ( t * testing . T ) {
2021-11-12 17:36:47 +03:00
assert . NoError ( t , unittest . PrepareTestDatabase ( ) )
2018-09-13 05:33:48 +03:00
testCases := [ ] struct {
name string
2022-06-06 11:01:49 +03:00
opts * repo_model . SearchRepoOptions
2018-09-13 05:33:48 +03:00
count int
} {
2021-03-14 21:52:12 +03:00
{
name : "AllPublic/SearchPublicRepositoriesFromTopicAndName" ,
2022-06-06 11:01:49 +03:00
opts : & repo_model . SearchRepoOptions { OwnerID : 21 , AllPublic : true , Keyword : "graphql" } ,
2021-03-14 21:52:12 +03:00
count : 2 ,
} ,
{
name : "AllPublic/OnlySearchPublicRepositoriesFromTopic" ,
2022-06-06 11:01:49 +03:00
opts : & repo_model . SearchRepoOptions { OwnerID : 21 , AllPublic : true , Keyword : "graphql" , TopicOnly : true } ,
2021-03-14 21:52:12 +03:00
count : 1 ,
} ,
{
name : "AllPublic/OnlySearchMultipleKeywordPublicRepositoriesFromTopic" ,
2022-06-06 11:01:49 +03:00
opts : & repo_model . SearchRepoOptions { OwnerID : 21 , AllPublic : true , Keyword : "graphql,golang" , TopicOnly : true } ,
2021-03-14 21:52:12 +03:00
count : 2 ,
} ,
2018-09-13 05:33:48 +03:00
}
for _ , testCase := range testCases {
t . Run ( testCase . name , func ( t * testing . T ) {
2022-11-19 11:12:33 +03:00
_ , count , err := repo_model . SearchRepositoryByName ( db . DefaultContext , testCase . opts )
2018-09-13 05:33:48 +03:00
assert . NoError ( t , err )
assert . Equal ( t , int64 ( testCase . count ) , count )
} )
}
}