2014-04-02 20:43:31 +04:00
// Copyright 2014 The Gogs Authors. All rights reserved.
2018-11-28 14:26:14 +03:00
// Copyright 2018 The Gitea Authors. All rights reserved.
2022-11-27 21:20:29 +03:00
// SPDX-License-Identifier: MIT
2014-04-02 20:43:31 +04:00
package repo
import (
2016-03-06 22:44:22 +03:00
"fmt"
2021-04-05 18:30:52 +03:00
"net/http"
2021-03-22 19:09:51 +03:00
"strings"
2016-03-06 22:44:22 +03:00
2016-11-10 19:24:48 +03:00
"code.gitea.io/gitea/models"
2021-09-24 14:32:56 +03:00
"code.gitea.io/gitea/models/db"
2022-08-25 05:31:57 +03:00
repo_model "code.gitea.io/gitea/models/repo"
2021-11-09 22:57:58 +03:00
"code.gitea.io/gitea/models/unit"
2021-11-24 12:49:20 +03:00
user_model "code.gitea.io/gitea/models/user"
2016-11-10 19:24:48 +03:00
"code.gitea.io/gitea/modules/base"
"code.gitea.io/gitea/modules/context"
"code.gitea.io/gitea/modules/log"
2021-04-20 01:25:08 +03:00
"code.gitea.io/gitea/modules/markup"
2017-09-21 08:20:14 +03:00
"code.gitea.io/gitea/modules/markup/markdown"
2017-01-15 17:57:00 +03:00
"code.gitea.io/gitea/modules/setting"
2020-10-05 08:49:33 +03:00
"code.gitea.io/gitea/modules/upload"
2021-11-16 21:18:25 +03:00
"code.gitea.io/gitea/modules/util"
2021-01-26 18:36:53 +03:00
"code.gitea.io/gitea/modules/web"
2022-12-22 00:06:26 +03:00
"code.gitea.io/gitea/routers/web/feed"
2021-04-06 22:44:05 +03:00
"code.gitea.io/gitea/services/forms"
2019-09-15 18:28:25 +03:00
releaseservice "code.gitea.io/gitea/services/release"
2014-04-02 20:43:31 +04:00
)
2014-06-23 07:11:12 +04:00
const (
2016-11-24 10:04:31 +03:00
tplReleases base . TplName = "repo/release/list"
tplReleaseNew base . TplName = "repo/release/new"
2014-06-23 07:11:12 +04:00
)
2016-07-27 11:57:32 +03:00
// calReleaseNumCommitsBehind calculates given release has how many commits behind release target.
2022-08-25 05:31:57 +03:00
func calReleaseNumCommitsBehind ( repoCtx * context . Repository , release * repo_model . Release , countCache map [ string ] int64 ) error {
2016-03-06 22:44:22 +03:00
// Fast return if release target is same as default branch.
if repoCtx . BranchName == release . Target {
release . NumCommitsBehind = repoCtx . CommitsCount - release . NumCommits
return nil
}
// Get count if not exists
if _ , ok := countCache [ release . Target ] ; ! ok {
2016-07-27 11:57:32 +03:00
if repoCtx . GitRepo . IsBranchExist ( release . Target ) {
commit , err := repoCtx . GitRepo . GetBranchCommit ( release . Target )
if err != nil {
2022-10-24 22:29:17 +03:00
return fmt . Errorf ( "GetBranchCommit: %w" , err )
2016-07-27 11:57:32 +03:00
}
countCache [ release . Target ] , err = commit . CommitsCount ( )
if err != nil {
2022-10-24 22:29:17 +03:00
return fmt . Errorf ( "CommitsCount: %w" , err )
2016-07-27 11:57:32 +03:00
}
} else {
// Use NumCommits of the newest release on that target
countCache [ release . Target ] = release . NumCommits
2016-03-06 22:44:22 +03:00
}
}
2016-07-27 11:57:32 +03:00
release . NumCommitsBehind = countCache [ release . Target ] - release . NumCommits
2016-03-06 22:44:22 +03:00
return nil
}
2016-11-24 10:04:31 +03:00
// Releases render releases list page
2016-03-11 19:56:52 +03:00
func Releases ( ctx * context . Context ) {
2020-11-03 02:10:22 +03:00
releasesOrTags ( ctx , false )
}
// TagsList render tags list page
func TagsList ( ctx * context . Context ) {
releasesOrTags ( ctx , true )
}
func releasesOrTags ( ctx * context . Context , isTagList bool ) {
2015-11-16 19:16:52 +03:00
ctx . Data [ "PageIsReleaseList" ] = true
2020-10-22 03:55:25 +03:00
ctx . Data [ "DefaultBranch" ] = ctx . Repo . Repository . DefaultBranch
2021-05-03 20:27:48 +03:00
ctx . Data [ "IsViewBranch" ] = false
ctx . Data [ "IsViewTag" ] = true
// Disable the showCreateNewBranch form in the dropdown on this page.
ctx . Data [ "CanCreateBranch" ] = false
ctx . Data [ "HideBranchesInDropdown" ] = true
2014-11-07 06:06:41 +03:00
2020-11-03 02:10:22 +03:00
if isTagList {
ctx . Data [ "Title" ] = ctx . Tr ( "repo.release.tags" )
ctx . Data [ "PageIsTagList" ] = true
} else {
ctx . Data [ "Title" ] = ctx . Tr ( "repo.release.releases" )
ctx . Data [ "PageIsTagList" ] = false
}
2021-09-24 14:32:56 +03:00
listOptions := db . ListOptions {
2021-09-10 20:30:37 +03:00
Page : ctx . FormInt ( "page" ) ,
PageSize : ctx . FormInt ( "limit" ) ,
}
if listOptions . PageSize == 0 {
listOptions . PageSize = setting . Repository . Release . DefaultPagingNum
}
if listOptions . PageSize > setting . API . MaxResponseItems {
listOptions . PageSize = setting . API . MaxResponseItems
}
Fix various typos (#20338)
* Fix various typos
Found via `codespell -q 3 -S ./options/locale,./options/license,./public/vendor -L actived,allways,attachements,ba,befores,commiter,pullrequest,pullrequests,readby,splitted,te,unknwon`
Co-authored-by: zeripath <art27@cantab.net>
2022-07-13 00:32:37 +03:00
// TODO(20073) tags are used for compare feature which needs all tags
// filtering is done on the client-side atm
2022-06-21 20:42:19 +03:00
tagListStart , tagListEnd := 0 , 0
if isTagList {
tagListStart , tagListEnd = listOptions . GetStartEnd ( )
}
tags , err := ctx . Repo . GitRepo . GetTags ( tagListStart , tagListEnd )
2021-05-03 20:27:48 +03:00
if err != nil {
ctx . ServerError ( "GetTags" , err )
return
}
ctx . Data [ "Tags" ] = tags
2021-11-09 22:57:58 +03:00
writeAccess := ctx . Repo . CanWrite ( unit . TypeReleases )
2019-01-23 21:58:38 +03:00
ctx . Data [ "CanCreateRelease" ] = writeAccess && ! ctx . Repo . Repository . IsArchived
2018-11-28 14:26:14 +03:00
2022-08-25 05:31:57 +03:00
opts := repo_model . FindReleasesOptions {
2022-10-03 15:05:53 +03:00
ListOptions : listOptions ,
}
if isTagList {
// for the tags list page, show all releases with real tags (having real commit-id),
// the drafts should also be included because a real tag might be used as a draft.
opts . IncludeDrafts = true
opts . IncludeTags = true
opts . HasSha1 = util . OptionalBoolTrue
} else {
// only show draft releases for users who can write, read-only users shouldn't see draft releases.
opts . IncludeDrafts = writeAccess
2017-06-29 18:11:38 +03:00
}
2022-11-19 11:12:33 +03:00
releases , err := repo_model . GetReleasesByRepoID ( ctx , ctx . Repo . Repository . ID , opts )
2014-07-26 10:28:04 +04:00
if err != nil {
2018-01-11 00:34:17 +03:00
ctx . ServerError ( "GetReleasesByRepoID" , err )
2017-06-28 17:47:00 +03:00
return
}
2022-12-10 05:46:31 +03:00
count , err := repo_model . GetReleaseCountByRepoID ( ctx , ctx . Repo . Repository . ID , opts )
2017-06-28 17:47:00 +03:00
if err != nil {
2018-01-11 00:34:17 +03:00
ctx . ServerError ( "GetReleaseCountByRepoID" , err )
2014-11-07 06:06:41 +03:00
return
}
2022-08-25 05:31:57 +03:00
if err = repo_model . GetReleaseAttachments ( ctx , releases ... ) ; err != nil {
2018-01-11 00:34:17 +03:00
ctx . ServerError ( "GetReleaseAttachments" , err )
2017-01-15 17:57:00 +03:00
return
}
2017-06-03 06:46:56 +03:00
// Temporary cache commits count of used branches to speed up.
2015-12-10 04:46:05 +03:00
countCache := make ( map [ string ] int64 )
2021-11-24 12:49:20 +03:00
cacheUsers := make ( map [ int64 ] * user_model . User )
2022-03-22 10:03:22 +03:00
if ctx . Doer != nil {
cacheUsers [ ctx . Doer . ID ] = ctx . Doer
2017-06-18 06:38:24 +03:00
}
2016-12-29 16:21:19 +03:00
var ok bool
2016-03-06 22:44:22 +03:00
2017-06-03 06:46:56 +03:00
for _ , r := range releases {
if r . Publisher , ok = cacheUsers [ r . PublisherID ] ; ! ok {
2022-12-03 05:48:26 +03:00
r . Publisher , err = user_model . GetUserByID ( ctx , r . PublisherID )
2017-06-03 06:46:56 +03:00
if err != nil {
2021-11-24 12:49:20 +03:00
if user_model . IsErrUserNotExist ( err ) {
r . Publisher = user_model . NewGhostUser ( )
2017-06-03 06:46:56 +03:00
} else {
2018-01-11 00:34:17 +03:00
ctx . ServerError ( "GetUserByID" , err )
2016-03-06 22:44:22 +03:00
return
2014-07-26 10:28:04 +04:00
}
}
2017-06-03 06:46:56 +03:00
cacheUsers [ r . PublisherID ] = r . Publisher
2014-07-26 10:28:04 +04:00
}
2021-05-06 06:12:50 +03:00
2021-04-20 01:25:08 +03:00
r . Note , err = markdown . RenderString ( & markup . RenderContext {
URLPrefix : ctx . Repo . RepoLink ,
Metas : ctx . Repo . Repository . ComposeMetas ( ) ,
2021-06-21 01:39:12 +03:00
GitRepo : ctx . Repo . GitRepo ,
2021-08-28 23:15:56 +03:00
Ctx : ctx ,
2021-04-20 01:25:08 +03:00
} , r . Note )
if err != nil {
ctx . ServerError ( "RenderString" , err )
return
}
2021-05-06 06:12:50 +03:00
if r . IsDraft {
continue
}
if err := calReleaseNumCommitsBehind ( ctx . Repo , r , countCache ) ; err != nil {
ctx . ServerError ( "calReleaseNumCommitsBehind" , err )
return
}
2014-12-11 00:37:54 +03:00
}
2017-06-29 18:11:38 +03:00
ctx . Data [ "Releases" ] = releases
2020-11-03 02:10:22 +03:00
ctx . Data [ "ReleasesNum" ] = len ( releases )
2019-04-20 07:15:19 +03:00
2020-01-24 22:00:29 +03:00
pager := context . NewPagination ( int ( count ) , opts . PageSize , opts . Page , 5 )
2019-04-20 07:15:19 +03:00
pager . SetDefaultParams ( ctx )
ctx . Data [ "Page" ] = pager
2021-04-05 18:30:52 +03:00
ctx . HTML ( http . StatusOK , tplReleases )
2014-07-26 10:28:04 +04:00
}
2022-12-22 00:06:26 +03:00
// ReleasesFeedRSS get feeds for releases in RSS format
func ReleasesFeedRSS ( ctx * context . Context ) {
releasesOrTagsFeed ( ctx , true , "rss" )
}
// TagsListFeedRSS get feeds for tags in RSS format
func TagsListFeedRSS ( ctx * context . Context ) {
releasesOrTagsFeed ( ctx , false , "rss" )
}
// ReleasesFeedAtom get feeds for releases in Atom format
func ReleasesFeedAtom ( ctx * context . Context ) {
releasesOrTagsFeed ( ctx , true , "atom" )
}
// TagsListFeedAtom get feeds for tags in RSS format
func TagsListFeedAtom ( ctx * context . Context ) {
releasesOrTagsFeed ( ctx , false , "atom" )
}
func releasesOrTagsFeed ( ctx * context . Context , isReleasesOnly bool , formatType string ) {
feed . ShowReleaseFeed ( ctx , ctx . Repo . Repository , isReleasesOnly , formatType )
}
2020-04-18 17:47:15 +03:00
// SingleRelease renders a single release's page
func SingleRelease ( ctx * context . Context ) {
ctx . Data [ "PageIsReleaseList" ] = true
2023-03-27 16:41:33 +03:00
ctx . Data [ "DefaultBranch" ] = ctx . Repo . Repository . DefaultBranch
2020-04-18 17:47:15 +03:00
2021-11-09 22:57:58 +03:00
writeAccess := ctx . Repo . CanWrite ( unit . TypeReleases )
2020-04-18 17:47:15 +03:00
ctx . Data [ "CanCreateRelease" ] = writeAccess && ! ctx . Repo . Repository . IsArchived
2022-08-25 05:31:57 +03:00
release , err := repo_model . GetRelease ( ctx . Repo . Repository . ID , ctx . Params ( "*" ) )
2020-04-18 17:47:15 +03:00
if err != nil {
2022-08-25 05:31:57 +03:00
if repo_model . IsErrReleaseNotExist ( err ) {
2020-07-26 22:00:48 +03:00
ctx . NotFound ( "GetRelease" , err )
return
}
2020-04-18 17:47:15 +03:00
ctx . ServerError ( "GetReleasesByRepoID" , err )
return
}
2023-03-27 16:41:33 +03:00
ctx . Data [ "PageIsSingleTag" ] = release . IsTag
if release . IsTag {
ctx . Data [ "Title" ] = release . TagName
} else {
ctx . Data [ "Title" ] = release . Title
}
2020-04-18 17:47:15 +03:00
2022-08-25 05:31:57 +03:00
err = repo_model . GetReleaseAttachments ( ctx , release )
2020-04-18 17:47:15 +03:00
if err != nil {
ctx . ServerError ( "GetReleaseAttachments" , err )
return
}
2022-12-03 05:48:26 +03:00
release . Publisher , err = user_model . GetUserByID ( ctx , release . PublisherID )
2020-04-18 17:47:15 +03:00
if err != nil {
2021-11-24 12:49:20 +03:00
if user_model . IsErrUserNotExist ( err ) {
release . Publisher = user_model . NewGhostUser ( )
2020-04-18 17:47:15 +03:00
} else {
ctx . ServerError ( "GetUserByID" , err )
return
}
}
2021-05-06 06:12:50 +03:00
if ! release . IsDraft {
if err := calReleaseNumCommitsBehind ( ctx . Repo , release , make ( map [ string ] int64 ) ) ; err != nil {
ctx . ServerError ( "calReleaseNumCommitsBehind" , err )
return
}
2020-04-18 17:47:15 +03:00
}
2021-04-20 01:25:08 +03:00
release . Note , err = markdown . RenderString ( & markup . RenderContext {
URLPrefix : ctx . Repo . RepoLink ,
Metas : ctx . Repo . Repository . ComposeMetas ( ) ,
2021-06-21 01:39:12 +03:00
GitRepo : ctx . Repo . GitRepo ,
2021-08-28 23:15:56 +03:00
Ctx : ctx ,
2021-04-20 01:25:08 +03:00
} , release . Note )
if err != nil {
ctx . ServerError ( "RenderString" , err )
return
}
2020-04-18 17:47:15 +03:00
2022-08-25 05:31:57 +03:00
ctx . Data [ "Releases" ] = [ ] * repo_model . Release { release }
2021-04-05 18:30:52 +03:00
ctx . HTML ( http . StatusOK , tplReleases )
2020-04-18 17:47:15 +03:00
}
// LatestRelease redirects to the latest release
func LatestRelease ( ctx * context . Context ) {
2022-08-25 05:31:57 +03:00
release , err := repo_model . GetLatestReleaseByRepoID ( ctx . Repo . Repository . ID )
2020-04-18 17:47:15 +03:00
if err != nil {
2022-08-25 05:31:57 +03:00
if repo_model . IsErrReleaseNotExist ( err ) {
2020-04-18 17:47:15 +03:00
ctx . NotFound ( "LatestRelease" , err )
return
}
ctx . ServerError ( "GetLatestReleaseByRepoID" , err )
return
}
2022-11-19 11:12:33 +03:00
if err := release . LoadAttributes ( ctx ) ; err != nil {
2020-04-18 17:47:15 +03:00
ctx . ServerError ( "LoadAttributes" , err )
return
}
2023-02-11 09:34:11 +03:00
ctx . Redirect ( release . Link ( ) )
2020-04-18 17:47:15 +03:00
}
2021-03-22 19:09:51 +03:00
// NewRelease render creating or edit release page
2016-03-11 19:56:52 +03:00
func NewRelease ( ctx * context . Context ) {
2014-12-11 00:37:54 +03:00
ctx . Data [ "Title" ] = ctx . Tr ( "repo.release.new_release" )
2015-11-16 19:16:52 +03:00
ctx . Data [ "PageIsReleaseList" ] = true
2014-12-11 00:37:54 +03:00
ctx . Data [ "tag_target" ] = ctx . Repo . Repository . DefaultBranch
2021-08-11 03:31:13 +03:00
if tagName := ctx . FormString ( "tag" ) ; len ( tagName ) > 0 {
2022-08-25 05:31:57 +03:00
rel , err := repo_model . GetRelease ( ctx . Repo . Repository . ID , tagName )
if err != nil && ! repo_model . IsErrReleaseNotExist ( err ) {
2020-11-03 02:10:22 +03:00
ctx . ServerError ( "GetRelease" , err )
return
}
if rel != nil {
2021-03-22 19:09:51 +03:00
rel . Repo = ctx . Repo . Repository
2022-11-19 11:12:33 +03:00
if err := rel . LoadAttributes ( ctx ) ; err != nil {
2021-03-22 19:09:51 +03:00
ctx . ServerError ( "LoadAttributes" , err )
return
}
2020-11-03 02:10:22 +03:00
ctx . Data [ "tag_name" ] = rel . TagName
2022-05-10 15:41:37 +03:00
if rel . Target != "" {
ctx . Data [ "tag_target" ] = rel . Target
}
2020-11-03 02:10:22 +03:00
ctx . Data [ "title" ] = rel . Title
ctx . Data [ "content" ] = rel . Note
2021-03-22 19:09:51 +03:00
ctx . Data [ "attachments" ] = rel . Attachments
2020-11-03 02:10:22 +03:00
}
}
2020-10-05 08:49:33 +03:00
ctx . Data [ "IsAttachmentEnabled" ] = setting . Attachment . Enabled
2023-04-07 03:11:02 +03:00
assigneeUsers , err := repo_model . GetRepoAssignees ( ctx , ctx . Repo . Repository )
2023-02-01 22:14:40 +03:00
if err != nil {
2023-04-07 03:11:02 +03:00
ctx . ServerError ( "GetRepoAssignees" , err )
2023-02-01 22:14:40 +03:00
return
}
2023-04-07 03:11:02 +03:00
ctx . Data [ "Assignees" ] = makeSelfOnTop ( ctx , assigneeUsers )
2023-02-01 22:14:40 +03:00
2020-10-05 08:49:33 +03:00
upload . AddUploadContext ( ctx , "release" )
2021-04-05 18:30:52 +03:00
ctx . HTML ( http . StatusOK , tplReleaseNew )
2014-07-26 10:28:04 +04:00
}
2016-11-24 10:04:31 +03:00
// NewReleasePost response for creating a release
2021-01-26 18:36:53 +03:00
func NewReleasePost ( ctx * context . Context ) {
2021-04-06 22:44:05 +03:00
form := web . GetForm ( ctx ) . ( * forms . NewReleaseForm )
2014-12-11 00:37:54 +03:00
ctx . Data [ "Title" ] = ctx . Tr ( "repo.release.new_release" )
2015-11-16 19:16:52 +03:00
ctx . Data [ "PageIsReleaseList" ] = true
2014-07-26 10:28:04 +04:00
if ctx . HasError ( ) {
2021-04-05 18:30:52 +03:00
ctx . HTML ( http . StatusOK , tplReleaseNew )
2014-07-26 10:28:04 +04:00
return
}
2014-11-07 06:06:41 +03:00
if ! ctx . Repo . GitRepo . IsBranchExist ( form . Target ) {
2016-11-24 10:04:31 +03:00
ctx . RenderWithErr ( ctx . Tr ( "form.target_branch_not_exist" ) , tplReleaseNew , & form )
2014-11-07 06:06:41 +03:00
return
}
2017-09-20 08:26:49 +03:00
var attachmentUUIDs [ ] string
2020-08-18 07:23:45 +03:00
if setting . Attachment . Enabled {
2017-09-20 08:26:49 +03:00
attachmentUUIDs = form . Files
2016-08-06 20:02:15 +03:00
}
2022-08-25 05:31:57 +03:00
rel , err := repo_model . GetRelease ( ctx . Repo . Repository . ID , form . TagName )
2014-07-26 10:28:04 +04:00
if err != nil {
2022-08-25 05:31:57 +03:00
if ! repo_model . IsErrReleaseNotExist ( err ) {
2018-01-11 00:34:17 +03:00
ctx . ServerError ( "GetRelease" , err )
2017-09-20 08:26:49 +03:00
return
}
2014-07-26 10:28:04 +04:00
2021-02-28 22:57:45 +03:00
msg := ""
if len ( form . Title ) > 0 && form . AddTagMsg {
msg = form . Title + "\n\n" + form . Content
}
if len ( form . TagOnly ) > 0 {
2022-03-22 10:03:22 +03:00
if err = releaseservice . CreateNewTag ( ctx , ctx . Doer , ctx . Repo . Repository , form . Target , form . TagName , msg ) ; err != nil {
2021-02-28 22:57:45 +03:00
if models . IsErrTagAlreadyExists ( err ) {
e := err . ( models . ErrTagAlreadyExists )
ctx . Flash . Error ( ctx . Tr ( "repo.branch.tag_collision" , e . TagName ) )
ctx . Redirect ( ctx . Repo . RepoLink + "/src/" + ctx . Repo . BranchNameSubURL ( ) )
return
}
2021-06-25 17:28:55 +03:00
if models . IsErrInvalidTagName ( err ) {
ctx . Flash . Error ( ctx . Tr ( "repo.release.tag_name_invalid" ) )
ctx . Redirect ( ctx . Repo . RepoLink + "/src/" + ctx . Repo . BranchNameSubURL ( ) )
return
}
if models . IsErrProtectedTagName ( err ) {
ctx . Flash . Error ( ctx . Tr ( "repo.release.tag_name_protected" ) )
ctx . Redirect ( ctx . Repo . RepoLink + "/src/" + ctx . Repo . BranchNameSubURL ( ) )
return
}
2021-02-28 22:57:45 +03:00
ctx . ServerError ( "releaseservice.CreateNewTag" , err )
return
}
ctx . Flash . Success ( ctx . Tr ( "repo.tag.create_success" , form . TagName ) )
2021-11-16 21:18:25 +03:00
ctx . Redirect ( ctx . Repo . RepoLink + "/src/tag/" + util . PathEscapeSegments ( form . TagName ) )
2021-02-28 22:57:45 +03:00
return
}
2022-08-25 05:31:57 +03:00
rel = & repo_model . Release {
2017-09-20 08:26:49 +03:00
RepoID : ctx . Repo . Repository . ID ,
2021-06-25 17:28:55 +03:00
Repo : ctx . Repo . Repository ,
2022-03-22 10:03:22 +03:00
PublisherID : ctx . Doer . ID ,
Publisher : ctx . Doer ,
2017-09-20 08:26:49 +03:00
Title : form . Title ,
TagName : form . TagName ,
Target : form . Target ,
Note : form . Content ,
IsDraft : len ( form . Draft ) > 0 ,
IsPrerelease : form . Prerelease ,
IsTag : false ,
}
2014-07-26 10:28:04 +04:00
2021-02-28 22:57:45 +03:00
if err = releaseservice . CreateRelease ( ctx . Repo . GitRepo , rel , attachmentUUIDs , msg ) ; err != nil {
2017-09-20 08:26:49 +03:00
ctx . Data [ "Err_TagName" ] = true
switch {
2022-08-25 05:31:57 +03:00
case repo_model . IsErrReleaseAlreadyExist ( err ) :
2017-09-20 08:26:49 +03:00
ctx . RenderWithErr ( ctx . Tr ( "repo.release.tag_name_already_exist" ) , tplReleaseNew , & form )
case models . IsErrInvalidTagName ( err ) :
ctx . RenderWithErr ( ctx . Tr ( "repo.release.tag_name_invalid" ) , tplReleaseNew , & form )
2021-06-25 17:28:55 +03:00
case models . IsErrProtectedTagName ( err ) :
ctx . RenderWithErr ( ctx . Tr ( "repo.release.tag_name_protected" ) , tplReleaseNew , & form )
2017-09-20 08:26:49 +03:00
default :
2018-01-11 00:34:17 +03:00
ctx . ServerError ( "CreateRelease" , err )
2017-09-20 08:26:49 +03:00
}
return
}
} else {
if ! rel . IsTag {
ctx . Data [ "Err_TagName" ] = true
ctx . RenderWithErr ( ctx . Tr ( "repo.release.tag_name_already_exist" ) , tplReleaseNew , & form )
return
}
2014-07-26 10:28:04 +04:00
2017-09-20 08:26:49 +03:00
rel . Title = form . Title
rel . Note = form . Content
2017-12-08 08:22:02 +03:00
rel . Target = form . Target
2017-09-20 08:26:49 +03:00
rel . IsDraft = len ( form . Draft ) > 0
rel . IsPrerelease = form . Prerelease
2022-03-22 10:03:22 +03:00
rel . PublisherID = ctx . Doer . ID
2017-09-20 08:26:49 +03:00
rel . IsTag = false
2017-01-15 17:57:00 +03:00
2022-03-22 10:03:22 +03:00
if err = releaseservice . UpdateRelease ( ctx . Doer , ctx . Repo . GitRepo , rel , attachmentUUIDs , nil , nil ) ; err != nil {
2017-09-20 08:26:49 +03:00
ctx . Data [ "Err_TagName" ] = true
2021-03-22 19:09:51 +03:00
ctx . ServerError ( "UpdateRelease" , err )
2017-09-20 08:26:49 +03:00
return
2014-07-26 10:28:04 +04:00
}
}
2022-03-22 10:03:22 +03:00
log . Trace ( "Release created: %s/%s:%s" , ctx . Doer . LowerName , ctx . Repo . Repository . Name , form . TagName )
2014-07-26 10:28:04 +04:00
ctx . Redirect ( ctx . Repo . RepoLink + "/releases" )
}
2016-11-24 10:04:31 +03:00
// EditRelease render release edit page
2016-03-11 19:56:52 +03:00
func EditRelease ( ctx * context . Context ) {
2015-11-16 07:52:46 +03:00
ctx . Data [ "Title" ] = ctx . Tr ( "repo.release.edit_release" )
2015-11-16 19:16:52 +03:00
ctx . Data [ "PageIsReleaseList" ] = true
2015-11-16 07:52:46 +03:00
ctx . Data [ "PageIsEditRelease" ] = true
2020-10-05 08:49:33 +03:00
ctx . Data [ "IsAttachmentEnabled" ] = setting . Attachment . Enabled
upload . AddUploadContext ( ctx , "release" )
2014-07-26 10:28:04 +04:00
2016-08-11 23:45:42 +03:00
tagName := ctx . Params ( "*" )
2022-08-25 05:31:57 +03:00
rel , err := repo_model . GetRelease ( ctx . Repo . Repository . ID , tagName )
2014-07-26 10:28:04 +04:00
if err != nil {
2022-08-25 05:31:57 +03:00
if repo_model . IsErrReleaseNotExist ( err ) {
2018-01-11 00:34:17 +03:00
ctx . NotFound ( "GetRelease" , err )
2014-07-26 10:28:04 +04:00
} else {
2018-01-11 00:34:17 +03:00
ctx . ServerError ( "GetRelease" , err )
2014-07-26 10:28:04 +04:00
}
return
}
2015-11-20 10:38:41 +03:00
ctx . Data [ "ID" ] = rel . ID
2015-11-16 07:52:46 +03:00
ctx . Data [ "tag_name" ] = rel . TagName
ctx . Data [ "tag_target" ] = rel . Target
ctx . Data [ "title" ] = rel . Title
ctx . Data [ "content" ] = rel . Note
ctx . Data [ "prerelease" ] = rel . IsPrerelease
2016-11-14 19:30:22 +03:00
ctx . Data [ "IsDraft" ] = rel . IsDraft
2014-07-26 10:28:04 +04:00
2021-03-22 19:09:51 +03:00
rel . Repo = ctx . Repo . Repository
2022-11-19 11:12:33 +03:00
if err := rel . LoadAttributes ( ctx ) ; err != nil {
2021-03-22 19:09:51 +03:00
ctx . ServerError ( "LoadAttributes" , err )
return
}
ctx . Data [ "attachments" ] = rel . Attachments
2023-02-01 22:14:40 +03:00
// Get assignees.
2023-04-07 03:11:02 +03:00
assigneeUsers , err := repo_model . GetRepoAssignees ( ctx , rel . Repo )
2023-02-01 22:14:40 +03:00
if err != nil {
2023-04-07 03:11:02 +03:00
ctx . ServerError ( "GetRepoAssignees" , err )
2023-02-01 22:14:40 +03:00
return
}
2023-04-07 03:11:02 +03:00
ctx . Data [ "Assignees" ] = makeSelfOnTop ( ctx , assigneeUsers )
2023-02-01 22:14:40 +03:00
2021-04-05 18:30:52 +03:00
ctx . HTML ( http . StatusOK , tplReleaseNew )
2014-07-26 10:28:04 +04:00
}
2016-11-24 10:04:31 +03:00
// EditReleasePost response for edit release
2021-01-26 18:36:53 +03:00
func EditReleasePost ( ctx * context . Context ) {
2021-04-06 22:44:05 +03:00
form := web . GetForm ( ctx ) . ( * forms . EditReleaseForm )
2015-11-16 07:52:46 +03:00
ctx . Data [ "Title" ] = ctx . Tr ( "repo.release.edit_release" )
2015-11-16 19:16:52 +03:00
ctx . Data [ "PageIsReleaseList" ] = true
2015-11-16 07:52:46 +03:00
ctx . Data [ "PageIsEditRelease" ] = true
2014-07-26 10:28:04 +04:00
2016-08-11 23:45:42 +03:00
tagName := ctx . Params ( "*" )
2022-08-25 05:31:57 +03:00
rel , err := repo_model . GetRelease ( ctx . Repo . Repository . ID , tagName )
2014-07-26 10:28:04 +04:00
if err != nil {
2022-08-25 05:31:57 +03:00
if repo_model . IsErrReleaseNotExist ( err ) {
2018-01-11 00:34:17 +03:00
ctx . NotFound ( "GetRelease" , err )
2014-07-26 10:28:04 +04:00
} else {
2018-01-11 00:34:17 +03:00
ctx . ServerError ( "GetRelease" , err )
2014-07-26 10:28:04 +04:00
}
return
}
2017-09-20 08:26:49 +03:00
if rel . IsTag {
2018-01-11 00:34:17 +03:00
ctx . NotFound ( "GetRelease" , err )
2017-09-20 08:26:49 +03:00
return
}
2015-11-16 07:52:46 +03:00
ctx . Data [ "tag_name" ] = rel . TagName
ctx . Data [ "tag_target" ] = rel . Target
ctx . Data [ "title" ] = rel . Title
ctx . Data [ "content" ] = rel . Note
ctx . Data [ "prerelease" ] = rel . IsPrerelease
2014-07-26 10:28:04 +04:00
if ctx . HasError ( ) {
2021-04-05 18:30:52 +03:00
ctx . HTML ( http . StatusOK , tplReleaseNew )
2014-07-26 10:28:04 +04:00
return
}
2021-03-22 19:09:51 +03:00
const delPrefix = "attachment-del-"
const editPrefix = "attachment-edit-"
var addAttachmentUUIDs , delAttachmentUUIDs [ ] string
2022-01-20 20:46:10 +03:00
editAttachments := make ( map [ string ] string ) // uuid -> new name
2020-08-18 07:23:45 +03:00
if setting . Attachment . Enabled {
2021-03-22 19:09:51 +03:00
addAttachmentUUIDs = form . Files
for k , v := range ctx . Req . Form {
if strings . HasPrefix ( k , delPrefix ) && v [ 0 ] == "true" {
delAttachmentUUIDs = append ( delAttachmentUUIDs , k [ len ( delPrefix ) : ] )
} else if strings . HasPrefix ( k , editPrefix ) {
editAttachments [ k [ len ( editPrefix ) : ] ] = v [ 0 ]
}
}
2017-01-15 17:57:00 +03:00
}
2014-07-26 10:28:04 +04:00
rel . Title = form . Title
rel . Note = form . Content
rel . IsDraft = len ( form . Draft ) > 0
rel . IsPrerelease = form . Prerelease
2022-03-22 10:03:22 +03:00
if err = releaseservice . UpdateRelease ( ctx . Doer , ctx . Repo . GitRepo ,
2021-03-22 19:09:51 +03:00
rel , addAttachmentUUIDs , delAttachmentUUIDs , editAttachments ) ; err != nil {
2018-01-11 00:34:17 +03:00
ctx . ServerError ( "UpdateRelease" , err )
2014-07-26 10:28:04 +04:00
return
}
ctx . Redirect ( ctx . Repo . RepoLink + "/releases" )
}
2015-11-20 10:38:41 +03:00
Fix various typos (#20338)
* Fix various typos
Found via `codespell -q 3 -S ./options/locale,./options/license,./public/vendor -L actived,allways,attachements,ba,befores,commiter,pullrequest,pullrequests,readby,splitted,te,unknwon`
Co-authored-by: zeripath <art27@cantab.net>
2022-07-13 00:32:37 +03:00
// DeleteRelease deletes a release
2016-03-11 19:56:52 +03:00
func DeleteRelease ( ctx * context . Context ) {
2020-11-03 02:10:22 +03:00
deleteReleaseOrTag ( ctx , false )
}
Fix various typos (#20338)
* Fix various typos
Found via `codespell -q 3 -S ./options/locale,./options/license,./public/vendor -L actived,allways,attachements,ba,befores,commiter,pullrequest,pullrequests,readby,splitted,te,unknwon`
Co-authored-by: zeripath <art27@cantab.net>
2022-07-13 00:32:37 +03:00
// DeleteTag deletes a tag
2020-11-03 02:10:22 +03:00
func DeleteTag ( ctx * context . Context ) {
deleteReleaseOrTag ( ctx , true )
}
func deleteReleaseOrTag ( ctx * context . Context , isDelTag bool ) {
2022-03-22 10:03:22 +03:00
if err := releaseservice . DeleteReleaseByID ( ctx , ctx . FormInt64 ( "id" ) , ctx . Doer , isDelTag ) ; err != nil {
2022-06-16 23:03:03 +03:00
if models . IsErrProtectedTagName ( err ) {
ctx . Flash . Error ( ctx . Tr ( "repo.release.tag_name_protected" ) )
} else {
ctx . Flash . Error ( "DeleteReleaseByID: " + err . Error ( ) )
}
2015-11-20 10:38:41 +03:00
} else {
2020-11-03 02:10:22 +03:00
if isDelTag {
ctx . Flash . Success ( ctx . Tr ( "repo.release.deletion_tag_success" ) )
} else {
ctx . Flash . Success ( ctx . Tr ( "repo.release.deletion_success" ) )
}
}
if isDelTag {
2021-04-05 18:30:52 +03:00
ctx . JSON ( http . StatusOK , map [ string ] interface { } {
2020-11-03 02:10:22 +03:00
"redirect" : ctx . Repo . RepoLink + "/tags" ,
} )
return
2015-11-20 10:38:41 +03:00
}
2021-04-05 18:30:52 +03:00
ctx . JSON ( http . StatusOK , map [ string ] interface { } {
2015-11-20 10:38:41 +03:00
"redirect" : ctx . Repo . RepoLink + "/releases" ,
} )
}