Skip to content

Commit 690ed36

Browse files
authored
Merge branch 'main' into fix-tippy-tooltip
2 parents ba8ad89 + 43809e6 commit 690ed36

File tree

415 files changed

+1294
-660
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

415 files changed

+1294
-660
lines changed

CHANGELOG.md

+350
Large diffs are not rendered by default.

MAINTAINERS

-1
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,6 @@ Kees de Vries <[email protected]> (@Bwko)
55
Kim Carlbäcker <[email protected]> (@bkcsoft)
66
LefsFlare <[email protected]> (@LefsFlarey)
77
Lunny Xiao <[email protected]> (@lunny)
8-
Matthias Loibl <[email protected]> (@metalmatze)
98
Rachid Zarouali <[email protected]> (@xinity)
109
Rémy Boulanouar <[email protected]> (@DblK)
1110
Sandro Santilli <[email protected]> (@strk)

build/generate-svg.js

+10-2
Original file line numberDiff line numberDiff line change
@@ -25,14 +25,22 @@ async function processFile(file, {prefix, fullName} = {}) {
2525
if (prefix === 'octicon') name = name.replace(/-[0-9]+$/, ''); // chop of '-16' on octicons
2626
}
2727

28+
// Set the `xmlns` attribute so that the files are displayable in standalone documents
29+
// The svg backend module will strip the attribute during startup for inline display
2830
const {data} = optimize(await readFile(file, 'utf8'), {
2931
plugins: [
3032
{name: 'preset-default'},
31-
{name: 'removeXMLNS'},
3233
{name: 'removeDimensions'},
3334
{name: 'prefixIds', params: {prefix: () => name}},
3435
{name: 'addClassesToSVGElement', params: {classNames: ['svg', name]}},
35-
{name: 'addAttributesToSVGElement', params: {attributes: [{'width': '16'}, {'height': '16'}, {'aria-hidden': 'true'}]}},
36+
{
37+
name: 'addAttributesToSVGElement', params: {
38+
attributes: [
39+
{'xmlns': 'http://www.w3.org/2000/svg'},
40+
{'width': '16'}, {'height': '16'}, {'aria-hidden': 'true'},
41+
]
42+
}
43+
},
3644
],
3745
});
3846

custom/conf/app.example.ini

+1-1
Original file line numberDiff line numberDiff line change
@@ -1848,7 +1848,7 @@ ROUTER = console
18481848
;ENABLED = true
18491849
;;
18501850
;; Comma-separated list of allowed file extensions (`.zip`), mime types (`text/plain`) or wildcard type (`image/*`, `audio/*`, `video/*`). Empty value or `*/*` allows all types.
1851-
;ALLOWED_TYPES = .csv,.docx,.fodg,.fodp,.fods,.fodt,.gif,.gz,.jpeg,.jpg,.log,.md,.mov,.mp4,.odf,.odg,.odp,.ods,.odt,.pdf,.png,.pptx,.svg,.tgz,.txt,.webm,.xls,.xlsx,.zip
1851+
;ALLOWED_TYPES = .csv,.docx,.fodg,.fodp,.fods,.fodt,.gif,.gz,.jpeg,.jpg,.log,.md,.mov,.mp4,.odf,.odg,.odp,.ods,.odt,.patch,.pdf,.png,.pptx,.svg,.tgz,.txt,.webm,.xls,.xlsx,.zip
18521852
;;
18531853
;; Max size of each file. Defaults to 4MB
18541854
;MAX_SIZE = 4

docs/content/doc/advanced/config-cheat-sheet.en-us.md

+1-1
Original file line numberDiff line numberDiff line change
@@ -841,7 +841,7 @@ Default templates for project boards:
841841
## Issue and pull request attachments (`attachment`)
842842

843843
- `ENABLED`: **true**: Whether issue and pull request attachments are enabled.
844-
- `ALLOWED_TYPES`: **.csv,.docx,.fodg,.fodp,.fods,.fodt,.gif,.gz,.jpeg,.jpg,.log,.md,.mov,.mp4,.odf,.odg,.odp,.ods,.odt,.pdf,.png,.pptx,.svg,.tgz,.txt,.webm,.xls,.xlsx,.zip**: Comma-separated list of allowed file extensions (`.zip`), mime types (`text/plain`) or wildcard type (`image/*`, `audio/*`, `video/*`). Empty value or `*/*` allows all types.
844+
- `ALLOWED_TYPES`: **.csv,.docx,.fodg,.fodp,.fods,.fodt,.gif,.gz,.jpeg,.jpg,.log,.md,.mov,.mp4,.odf,.odg,.odp,.ods,.odt,.patch,.pdf,.png,.pptx,.svg,.tgz,.txt,.webm,.xls,.xlsx,.zip**: Comma-separated list of allowed file extensions (`.zip`), mime types (`text/plain`) or wildcard type (`image/*`, `audio/*`, `video/*`). Empty value or `*/*` allows all types.
845845
- `MAX_SIZE`: **4**: Maximum size (MB).
846846
- `MAX_FILES`: **5**: Maximum number of attachments that can be uploaded at once.
847847
- `STORAGE_TYPE`: **local**: Storage type for attachments, `local` for local disk or `minio` for s3 compatible object storage service, default is `local` or other name defined with `[storage.xxx]`

docs/content/doc/usage/pull-request.en-us.md

+37-1
Original file line numberDiff line numberDiff line change
@@ -15,9 +15,45 @@ menu:
1515

1616
# Pull Request
1717

18+
A Pull Request (PR) is a way to propose changes to a repository.
19+
It is a request to merge one branch into another, accompanied by a description of the changes that were made.
20+
Pull Requests are commonly used as a way for contributors to propose changes and for maintainers to review and merge those changes.
21+
22+
## Creating a pull request
23+
24+
To create a PR, you'll need to follow these steps:
25+
26+
1. **Fork the repository** - If you don't have permission to make changes to the repository directly, you'll need to fork the repository to your own account.
27+
This creates a copy of the repository that you can make changes to.
28+
29+
2. **Create a branch (optional)** - Create a new branch on your forked repository that contains the changes you want to propose.
30+
Give the branch a descriptive name that indicates what the changes are for.
31+
32+
3. **Make your changes** - Make the changes you want, commit, and push them to your forked repository.
33+
34+
4. **Create the PR** - Go to the original repository and go to the "Pull Requests" tab. Click the "New Pull Request" button and select your new branch as the source branch.
35+
Enter a descriptive title and description for your Pull Request and click "Create Pull Request".
36+
37+
## Reviewing a pull request
38+
39+
When a PR is created, it triggers a review process. The maintainers of the repository are notified of the PR and can review the changes that were made.
40+
They can leave comments, request changes, or approve the changes.
41+
42+
If the maintainers request changes, you'll need to make those changes in your branch and push the changes to your forked repository.
43+
The PR will be updated automatically with the new changes.
44+
45+
If the maintainers approve the changes, they can merge the PR into the repository.
46+
47+
## Closing a pull request
48+
49+
If you decide that you no longer want to merge a PR, you can close it.
50+
To close a PR, go to the open PR and click the "Close Pull Request" button. This will close the PR without merging it.
51+
1852
## "Work In Progress" pull requests
1953

20-
Marking a pull request as being a work in progress will prevent that pull request from being accidentally merged. To mark a pull request as being a work in progress, you must prefix its title by `WIP:` or `[WIP]` (case insensitive). Those values are configurable in your `app.ini` file :
54+
Marking a pull request as being a work in progress will prevent that pull request from being accidentally merged.
55+
To mark a pull request as being a work in progress, you must prefix its title by `WIP:` or `[WIP]` (case insensitive).
56+
Those values are configurable in your `app.ini` file:
2157

2258
```ini
2359
[repository.pull-request]

models/actions/runner.go

+1
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ type ActionRunner struct {
2525
ID int64
2626
UUID string `xorm:"CHAR(36) UNIQUE"`
2727
Name string `xorm:"VARCHAR(255)"`
28+
Version string `xorm:"VARCHAR(64)"`
2829
OwnerID int64 `xorm:"index"` // org level runner, 0 means system
2930
Owner *user_model.User `xorm:"-"`
3031
RepoID int64 `xorm:"index"` // repo level runner, if orgid also is zero, then it's a global

models/git/lfs_lock.go

+3-3
Original file line numberDiff line numberDiff line change
@@ -34,7 +34,7 @@ func init() {
3434

3535
// BeforeInsert is invoked from XORM before inserting an object of this type.
3636
func (l *LFSLock) BeforeInsert() {
37-
l.Path = util.CleanPath(l.Path)
37+
l.Path = util.PathJoinRel(l.Path)
3838
}
3939

4040
// CreateLFSLock creates a new lock.
@@ -49,7 +49,7 @@ func CreateLFSLock(ctx context.Context, repo *repo_model.Repository, lock *LFSLo
4949
return nil, err
5050
}
5151

52-
lock.Path = util.CleanPath(lock.Path)
52+
lock.Path = util.PathJoinRel(lock.Path)
5353
lock.RepoID = repo.ID
5454

5555
l, err := GetLFSLock(dbCtx, repo, lock.Path)
@@ -69,7 +69,7 @@ func CreateLFSLock(ctx context.Context, repo *repo_model.Repository, lock *LFSLo
6969

7070
// GetLFSLock returns release by given path.
7171
func GetLFSLock(ctx context.Context, repo *repo_model.Repository, path string) (*LFSLock, error) {
72-
path = util.CleanPath(path)
72+
path = util.PathJoinRel(path)
7373
rel := &LFSLock{RepoID: repo.ID}
7474
has, err := db.GetEngine(ctx).Where("lower(path) = ?", strings.ToLower(path)).Get(rel)
7575
if err != nil {

models/migrations/migrations.go

+2
Original file line numberDiff line numberDiff line change
@@ -473,6 +473,8 @@ var migrations = []Migration{
473473
NewMigration("Add missed column owner_id for project table", v1_20.AddNewColumnForProject),
474474
// v247 -> v248
475475
NewMigration("Fix incorrect project type", v1_20.FixIncorrectProjectType),
476+
// v248 -> v249
477+
NewMigration("Add version column to action_runner table", v1_20.AddVersionToActionRunner),
476478
}
477479

478480
// GetCurrentDBVersion returns the current db version

models/migrations/v1_20/v248.go

+14
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
// Copyright 2023 The Gitea Authors. All rights reserved.
2+
// SPDX-License-Identifier: MIT
3+
4+
package v1_20 //nolint
5+
6+
import "xorm.io/xorm"
7+
8+
func AddVersionToActionRunner(x *xorm.Engine) error {
9+
type ActionRunner struct {
10+
Version string `xorm:"VARCHAR(64)"` // the version of act_runner
11+
}
12+
13+
return x.Sync(new(ActionRunner))
14+
}

models/project/project.go

+11
Original file line numberDiff line numberDiff line change
@@ -144,10 +144,21 @@ func (p *Project) Link() string {
144144
return ""
145145
}
146146

147+
func (p *Project) IconName() string {
148+
if p.IsRepositoryProject() {
149+
return "octicon-project"
150+
}
151+
return "octicon-project-symlink"
152+
}
153+
147154
func (p *Project) IsOrganizationProject() bool {
148155
return p.Type == TypeOrganization
149156
}
150157

158+
func (p *Project) IsRepositoryProject() bool {
159+
return p.Type == TypeRepository
160+
}
161+
151162
func init() {
152163
db.RegisterModel(new(Project))
153164
}

modules/context/context.go

+32
Original file line numberDiff line numberDiff line change
@@ -16,8 +16,10 @@ import (
1616
"net/http"
1717
"net/url"
1818
"path"
19+
"regexp"
1920
"strconv"
2021
"strings"
22+
texttemplate "text/template"
2123
"time"
2224

2325
"code.gitea.io/gitea/models/db"
@@ -213,6 +215,8 @@ func (ctx *Context) RedirectToFirst(location ...string) {
213215
ctx.Redirect(setting.AppSubURL + "/")
214216
}
215217

218+
var templateExecutingErr = regexp.MustCompile(`^template: (.*):([1-9][0-9]*):([1-9][0-9]*): executing (?:"(.*)" at <(.*)>: )?`)
219+
216220
// HTML calls Context.HTML and renders the template to HTTP response
217221
func (ctx *Context) HTML(status int, name base.TplName) {
218222
log.Debug("Template: %s", name)
@@ -228,6 +232,34 @@ func (ctx *Context) HTML(status int, name base.TplName) {
228232
ctx.PlainText(http.StatusInternalServerError, "Unable to find status/500 template")
229233
return
230234
}
235+
if execErr, ok := err.(texttemplate.ExecError); ok {
236+
if groups := templateExecutingErr.FindStringSubmatch(err.Error()); len(groups) > 0 {
237+
errorTemplateName, lineStr, posStr := groups[1], groups[2], groups[3]
238+
target := ""
239+
if len(groups) == 6 {
240+
target = groups[5]
241+
}
242+
line, _ := strconv.Atoi(lineStr) // Cannot error out as groups[2] is [1-9][0-9]*
243+
pos, _ := strconv.Atoi(posStr) // Cannot error out as groups[3] is [1-9][0-9]*
244+
filename, filenameErr := templates.GetAssetFilename("templates/" + errorTemplateName + ".tmpl")
245+
if filenameErr != nil {
246+
filename = "(template) " + errorTemplateName
247+
}
248+
if errorTemplateName != string(name) {
249+
filename += " (subtemplate of " + string(name) + ")"
250+
}
251+
err = fmt.Errorf("%w\nin template file %s:\n%s", err, filename, templates.GetLineFromTemplate(errorTemplateName, line, target, pos))
252+
} else {
253+
filename, filenameErr := templates.GetAssetFilename("templates/" + execErr.Name + ".tmpl")
254+
if filenameErr != nil {
255+
filename = "(template) " + execErr.Name
256+
}
257+
if execErr.Name != string(name) {
258+
filename += " (subtemplate of " + string(name) + ")"
259+
}
260+
err = fmt.Errorf("%w\nin template file %s", err, filename)
261+
}
262+
}
231263
ctx.ServerError("Render failed", err)
232264
}
233265
}

modules/options/base.go

+53-14
Original file line numberDiff line numberDiff line change
@@ -7,36 +7,38 @@ import (
77
"fmt"
88
"io/fs"
99
"os"
10-
"path"
1110
"path/filepath"
1211

12+
"code.gitea.io/gitea/modules/log"
1313
"code.gitea.io/gitea/modules/setting"
1414
"code.gitea.io/gitea/modules/util"
1515
)
1616

17+
var directories = make(directorySet)
18+
1719
// Locale reads the content of a specific locale from static/bindata or custom path.
1820
func Locale(name string) ([]byte, error) {
19-
return fileFromDir(path.Join("locale", util.CleanPath(name)))
21+
return fileFromOptionsDir("locale", name)
2022
}
2123

2224
// Readme reads the content of a specific readme from static/bindata or custom path.
2325
func Readme(name string) ([]byte, error) {
24-
return fileFromDir(path.Join("readme", util.CleanPath(name)))
26+
return fileFromOptionsDir("readme", name)
2527
}
2628

2729
// Gitignore reads the content of a gitignore locale from static/bindata or custom path.
2830
func Gitignore(name string) ([]byte, error) {
29-
return fileFromDir(path.Join("gitignore", util.CleanPath(name)))
31+
return fileFromOptionsDir("gitignore", name)
3032
}
3133

3234
// License reads the content of a specific license from static/bindata or custom path.
3335
func License(name string) ([]byte, error) {
34-
return fileFromDir(path.Join("license", util.CleanPath(name)))
36+
return fileFromOptionsDir("license", name)
3537
}
3638

3739
// Labels reads the content of a specific labels from static/bindata or custom path.
3840
func Labels(name string) ([]byte, error) {
39-
return fileFromDir(path.Join("label", util.CleanPath(name)))
41+
return fileFromOptionsDir("label", name)
4042
}
4143

4244
// WalkLocales reads the content of a specific locale
@@ -79,17 +81,54 @@ func walkAssetDir(root string, callback func(path, name string, d fs.DirEntry, e
7981
return nil
8082
}
8183

82-
func statDirIfExist(dir string) ([]string, error) {
83-
isDir, err := util.IsDir(dir)
84+
// mustLocalPathAbs coverts a path to absolute path
85+
// FIXME: the old behavior (StaticRootPath might not be absolute), not ideal, just keep the same as before
86+
func mustLocalPathAbs(s string) string {
87+
abs, err := filepath.Abs(s)
8488
if err != nil {
85-
return nil, fmt.Errorf("unable to check if static directory %s is a directory. %w", dir, err)
89+
// This should never happen in a real system. If it happens, the user must have already been in trouble: the system is not able to resolve its own paths.
90+
log.Fatal("Unable to get absolute path for %q: %v", s, err)
8691
}
87-
if !isDir {
88-
return nil, nil
92+
return abs
93+
}
94+
95+
func joinLocalPaths(baseDirs []string, subDir string, elems ...string) (paths []string) {
96+
abs := make([]string, len(elems)+2)
97+
abs[1] = subDir
98+
copy(abs[2:], elems)
99+
for _, baseDir := range baseDirs {
100+
abs[0] = mustLocalPathAbs(baseDir)
101+
paths = append(paths, util.FilePathJoinAbs(abs...))
89102
}
90-
files, err := util.StatDir(dir, true)
91-
if err != nil {
92-
return nil, fmt.Errorf("unable to read directory %q. %w", dir, err)
103+
return paths
104+
}
105+
106+
func listLocalDirIfExist(baseDirs []string, subDir string, elems ...string) (files []string, err error) {
107+
for _, localPath := range joinLocalPaths(baseDirs, subDir, elems...) {
108+
isDir, err := util.IsDir(localPath)
109+
if err != nil {
110+
return nil, fmt.Errorf("unable to check if path %q is a directory. %w", localPath, err)
111+
} else if !isDir {
112+
continue
113+
}
114+
115+
dirFiles, err := util.StatDir(localPath, true)
116+
if err != nil {
117+
return nil, fmt.Errorf("unable to read directory %q. %w", localPath, err)
118+
}
119+
files = append(files, dirFiles...)
93120
}
94121
return files, nil
95122
}
123+
124+
func readLocalFile(baseDirs []string, subDir string, elems ...string) ([]byte, error) {
125+
for _, localPath := range joinLocalPaths(baseDirs, subDir, elems...) {
126+
data, err := os.ReadFile(localPath)
127+
if err == nil {
128+
return data, nil
129+
} else if !os.IsNotExist(err) {
130+
log.Error("Unable to read file %q. Error: %v", localPath, err)
131+
}
132+
}
133+
return nil, os.ErrNotExist
134+
}

0 commit comments

Comments
 (0)