Allow changing global wiki editability via the API
The global wiki editability can be set via the web UI, this patch makes it possible to set the same thing via the API too. This is accomplished by adjusting the GET and PATCH handlers of the `/api/v1/repos/{owner}/{repo}` route. The first will include the property when checking the repo's settings, the second allows a repo admin to change the setting too. Signed-off-by: Gergely Nagy <forgejo@gergo.csillger.hu>
This commit is contained in:
parent
ada8bfa52f
commit
df8e58c5cb
5 changed files with 97 additions and 4 deletions
|
@ -89,6 +89,7 @@ type Repository struct {
|
||||||
HasWiki bool `json:"has_wiki"`
|
HasWiki bool `json:"has_wiki"`
|
||||||
ExternalWiki *ExternalWiki `json:"external_wiki,omitempty"`
|
ExternalWiki *ExternalWiki `json:"external_wiki,omitempty"`
|
||||||
WikiBranch string `json:"wiki_branch,omitempty"`
|
WikiBranch string `json:"wiki_branch,omitempty"`
|
||||||
|
GloballyEditableWiki bool `json:"globally_editable_wiki"`
|
||||||
HasPullRequests bool `json:"has_pull_requests"`
|
HasPullRequests bool `json:"has_pull_requests"`
|
||||||
HasProjects bool `json:"has_projects"`
|
HasProjects bool `json:"has_projects"`
|
||||||
HasReleases bool `json:"has_releases"`
|
HasReleases bool `json:"has_releases"`
|
||||||
|
@ -185,6 +186,8 @@ type EditRepoOption struct {
|
||||||
HasWiki *bool `json:"has_wiki,omitempty"`
|
HasWiki *bool `json:"has_wiki,omitempty"`
|
||||||
// set this structure to use external wiki instead of internal
|
// set this structure to use external wiki instead of internal
|
||||||
ExternalWiki *ExternalWiki `json:"external_wiki,omitempty"`
|
ExternalWiki *ExternalWiki `json:"external_wiki,omitempty"`
|
||||||
|
// set the globally editable state of the wiki
|
||||||
|
GloballyEditableWiki *bool `json:"globally_editable_wiki,omitempty"`
|
||||||
// sets the default branch for this repository.
|
// sets the default branch for this repository.
|
||||||
DefaultBranch *string `json:"default_branch,omitempty"`
|
DefaultBranch *string `json:"default_branch,omitempty"`
|
||||||
// sets the branch used for this repository's wiki.
|
// sets the branch used for this repository's wiki.
|
||||||
|
|
|
@ -845,6 +845,15 @@ func updateRepoUnits(ctx *context.APIContext, opts api.EditRepoOption) error {
|
||||||
newHasWiki = *opts.HasWiki
|
newHasWiki = *opts.HasWiki
|
||||||
}
|
}
|
||||||
if currHasWiki || newHasWiki {
|
if currHasWiki || newHasWiki {
|
||||||
|
wikiPermissions := repo.MustGetUnit(ctx, unit_model.TypeWiki).DefaultPermissions
|
||||||
|
if opts.GloballyEditableWiki != nil {
|
||||||
|
if *opts.GloballyEditableWiki {
|
||||||
|
wikiPermissions = repo_model.UnitAccessModeWrite
|
||||||
|
} else {
|
||||||
|
wikiPermissions = repo_model.UnitAccessModeRead
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if newHasWiki && opts.ExternalWiki != nil && !unit_model.TypeExternalWiki.UnitGlobalDisabled() {
|
if newHasWiki && opts.ExternalWiki != nil && !unit_model.TypeExternalWiki.UnitGlobalDisabled() {
|
||||||
// Check that values are valid
|
// Check that values are valid
|
||||||
if !validation.IsValidExternalURL(opts.ExternalWiki.ExternalWikiURL) {
|
if !validation.IsValidExternalURL(opts.ExternalWiki.ExternalWikiURL) {
|
||||||
|
@ -867,6 +876,7 @@ func updateRepoUnits(ctx *context.APIContext, opts api.EditRepoOption) error {
|
||||||
RepoID: repo.ID,
|
RepoID: repo.ID,
|
||||||
Type: unit_model.TypeWiki,
|
Type: unit_model.TypeWiki,
|
||||||
Config: config,
|
Config: config,
|
||||||
|
DefaultPermissions: wikiPermissions,
|
||||||
})
|
})
|
||||||
deleteUnitTypes = append(deleteUnitTypes, unit_model.TypeExternalWiki)
|
deleteUnitTypes = append(deleteUnitTypes, unit_model.TypeExternalWiki)
|
||||||
} else if !newHasWiki {
|
} else if !newHasWiki {
|
||||||
|
@ -876,6 +886,14 @@ func updateRepoUnits(ctx *context.APIContext, opts api.EditRepoOption) error {
|
||||||
if !unit_model.TypeWiki.UnitGlobalDisabled() {
|
if !unit_model.TypeWiki.UnitGlobalDisabled() {
|
||||||
deleteUnitTypes = append(deleteUnitTypes, unit_model.TypeWiki)
|
deleteUnitTypes = append(deleteUnitTypes, unit_model.TypeWiki)
|
||||||
}
|
}
|
||||||
|
} else if *opts.GloballyEditableWiki {
|
||||||
|
config := &repo_model.UnitConfig{}
|
||||||
|
units = append(units, repo_model.RepoUnit{
|
||||||
|
RepoID: repo.ID,
|
||||||
|
Type: unit_model.TypeWiki,
|
||||||
|
Config: config,
|
||||||
|
DefaultPermissions: wikiPermissions,
|
||||||
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -77,9 +77,13 @@ func innerToRepo(ctx context.Context, repo *repo_model.Repository, permissionInR
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
hasWiki := false
|
hasWiki := false
|
||||||
|
globallyEditableWiki := false
|
||||||
var externalWiki *api.ExternalWiki
|
var externalWiki *api.ExternalWiki
|
||||||
if _, err := repo.GetUnit(ctx, unit_model.TypeWiki); err == nil {
|
if wikiUnit, err := repo.GetUnit(ctx, unit_model.TypeWiki); err == nil {
|
||||||
hasWiki = true
|
hasWiki = true
|
||||||
|
if wikiUnit.DefaultPermissions == repo_model.UnitAccessModeWrite {
|
||||||
|
globallyEditableWiki = true
|
||||||
|
}
|
||||||
} else if unit, err := repo.GetUnit(ctx, unit_model.TypeExternalWiki); err == nil {
|
} else if unit, err := repo.GetUnit(ctx, unit_model.TypeExternalWiki); err == nil {
|
||||||
hasWiki = true
|
hasWiki = true
|
||||||
config := unit.ExternalWikiConfig()
|
config := unit.ExternalWikiConfig()
|
||||||
|
@ -211,6 +215,7 @@ func innerToRepo(ctx context.Context, repo *repo_model.Repository, permissionInR
|
||||||
InternalTracker: internalTracker,
|
InternalTracker: internalTracker,
|
||||||
HasWiki: hasWiki,
|
HasWiki: hasWiki,
|
||||||
WikiBranch: repo.WikiBranch,
|
WikiBranch: repo.WikiBranch,
|
||||||
|
GloballyEditableWiki: globallyEditableWiki,
|
||||||
HasProjects: hasProjects,
|
HasProjects: hasProjects,
|
||||||
HasReleases: hasReleases,
|
HasReleases: hasReleases,
|
||||||
HasPackages: hasPackages,
|
HasPackages: hasPackages,
|
||||||
|
|
9
templates/swagger/v1_json.tmpl
generated
9
templates/swagger/v1_json.tmpl
generated
|
@ -20835,6 +20835,11 @@
|
||||||
"external_wiki": {
|
"external_wiki": {
|
||||||
"$ref": "#/definitions/ExternalWiki"
|
"$ref": "#/definitions/ExternalWiki"
|
||||||
},
|
},
|
||||||
|
"globally_editable_wiki": {
|
||||||
|
"description": "set the globally editable state of the wiki",
|
||||||
|
"type": "boolean",
|
||||||
|
"x-go-name": "GloballyEditableWiki"
|
||||||
|
},
|
||||||
"has_actions": {
|
"has_actions": {
|
||||||
"description": "either `true` to enable actions unit, or `false` to disable them.",
|
"description": "either `true` to enable actions unit, or `false` to disable them.",
|
||||||
"type": "boolean",
|
"type": "boolean",
|
||||||
|
@ -23749,6 +23754,10 @@
|
||||||
"type": "string",
|
"type": "string",
|
||||||
"x-go-name": "FullName"
|
"x-go-name": "FullName"
|
||||||
},
|
},
|
||||||
|
"globally_editable_wiki": {
|
||||||
|
"type": "boolean",
|
||||||
|
"x-go-name": "GloballyEditableWiki"
|
||||||
|
},
|
||||||
"has_actions": {
|
"has_actions": {
|
||||||
"type": "boolean",
|
"type": "boolean",
|
||||||
"x-go-name": "HasActions"
|
"x-go-name": "HasActions"
|
||||||
|
|
|
@ -15,6 +15,7 @@ import (
|
||||||
repo_model "code.gitea.io/gitea/models/repo"
|
repo_model "code.gitea.io/gitea/models/repo"
|
||||||
unit_model "code.gitea.io/gitea/models/unit"
|
unit_model "code.gitea.io/gitea/models/unit"
|
||||||
"code.gitea.io/gitea/models/unittest"
|
"code.gitea.io/gitea/models/unittest"
|
||||||
|
user_model "code.gitea.io/gitea/models/user"
|
||||||
api "code.gitea.io/gitea/modules/structs"
|
api "code.gitea.io/gitea/modules/structs"
|
||||||
repo_service "code.gitea.io/gitea/services/repository"
|
repo_service "code.gitea.io/gitea/services/repository"
|
||||||
"code.gitea.io/gitea/tests"
|
"code.gitea.io/gitea/tests"
|
||||||
|
@ -286,6 +287,63 @@ func TestAPIEditOtherWikiPage(t *testing.T) {
|
||||||
testCreateWiki(http.StatusCreated)
|
testCreateWiki(http.StatusCreated)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestAPISetWikiGlobalEditability(t *testing.T) {
|
||||||
|
defer tests.PrepareTestEnv(t)()
|
||||||
|
user := unittest.AssertExistsAndLoadBean(t, &user_model.User{Name: "user2"})
|
||||||
|
session := loginUser(t, user.Name)
|
||||||
|
token := getTokenForLoggedInUser(t, session, auth_model.AccessTokenScopeWriteRepository)
|
||||||
|
|
||||||
|
// Create a new repository for testing purposes
|
||||||
|
repo, _, f := CreateDeclarativeRepo(t, user, "", []unit_model.Type{
|
||||||
|
unit_model.TypeCode,
|
||||||
|
unit_model.TypeWiki,
|
||||||
|
}, nil, nil)
|
||||||
|
defer f()
|
||||||
|
urlStr := fmt.Sprintf("/api/v1/repos/%s", repo.FullName())
|
||||||
|
|
||||||
|
assertGlobalEditability := func(t *testing.T, editability bool) {
|
||||||
|
t.Helper()
|
||||||
|
|
||||||
|
req := NewRequest(t, "GET", urlStr)
|
||||||
|
resp := MakeRequest(t, req, http.StatusOK)
|
||||||
|
|
||||||
|
var opts api.Repository
|
||||||
|
DecodeJSON(t, resp, &opts)
|
||||||
|
|
||||||
|
assert.Equal(t, opts.GloballyEditableWiki, editability)
|
||||||
|
}
|
||||||
|
|
||||||
|
t.Run("api includes GloballyEditableWiki", func(t *testing.T) {
|
||||||
|
defer tests.PrintCurrentTest(t)()
|
||||||
|
|
||||||
|
assertGlobalEditability(t, false)
|
||||||
|
})
|
||||||
|
|
||||||
|
t.Run("api can turn on GloballyEditableWiki", func(t *testing.T) {
|
||||||
|
defer tests.PrintCurrentTest(t)()
|
||||||
|
|
||||||
|
globallyEditable := true
|
||||||
|
req := NewRequestWithJSON(t, "PATCH", urlStr, &api.EditRepoOption{
|
||||||
|
GloballyEditableWiki: &globallyEditable,
|
||||||
|
}).AddTokenAuth(token)
|
||||||
|
MakeRequest(t, req, http.StatusOK)
|
||||||
|
|
||||||
|
assertGlobalEditability(t, true)
|
||||||
|
})
|
||||||
|
|
||||||
|
t.Run("disabling the wiki disables GloballyEditableWiki", func(t *testing.T) {
|
||||||
|
defer tests.PrintCurrentTest(t)()
|
||||||
|
|
||||||
|
hasWiki := false
|
||||||
|
req := NewRequestWithJSON(t, "PATCH", urlStr, &api.EditRepoOption{
|
||||||
|
HasWiki: &hasWiki,
|
||||||
|
}).AddTokenAuth(token)
|
||||||
|
MakeRequest(t, req, http.StatusOK)
|
||||||
|
|
||||||
|
assertGlobalEditability(t, false)
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
func TestAPIListPageRevisions(t *testing.T) {
|
func TestAPIListPageRevisions(t *testing.T) {
|
||||||
defer tests.PrepareTestEnv(t)()
|
defer tests.PrepareTestEnv(t)()
|
||||||
username := "user2"
|
username := "user2"
|
||||||
|
|
Loading…
Reference in a new issue