Merge branch 'main' into pacman-packages

This commit is contained in:
Danila Fominykh 2023-10-11 23:38:46 -03:00 committed by GitHub
commit 99f856a4db
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
262 changed files with 1998 additions and 1613 deletions

View File

@ -1,428 +0,0 @@
---
kind: pipeline
name: release-version
platform:
os: linux
arch: amd64
workspace:
base: /source
path: /
trigger:
event:
- tag
volumes:
- name: deps
temp: {}
steps:
- name: fetch-tags
image: docker:git
pull: always
commands:
- git fetch --tags --force
- name: deps-frontend
image: node:20
pull: always
commands:
- make deps-frontend
- name: deps-backend
image: gitea/test_env:linux-1.20-amd64
pull: always
commands:
- make deps-backend
volumes:
- name: deps
path: /go
- name: static
image: techknowlogick/xgo:go-1.21.x
pull: always
commands:
- apt-get update && apt-get -qqy install ca-certificates curl gnupg
- mkdir -p /etc/apt/keyrings && curl -fsSL https://deb.nodesource.com/gpgkey/nodesource-repo.gpg.key | gpg --dearmor -o /etc/apt/keyrings/nodesource.gpg
- echo "deb [signed-by=/etc/apt/keyrings/nodesource.gpg] https://deb.nodesource.com/node_20.x nodistro main" > /etc/apt/sources.list.d/nodesource.list
- apt-get update && apt-get -qqy install nodejs
- export PATH=$PATH:$GOPATH/bin
- make release
environment:
GOPROXY: https://goproxy.io # proxy.golang.org is blocked in China, this proxy is not
TAGS: bindata sqlite sqlite_unlock_notify
DEBIAN_FRONTEND: noninteractive
depends_on: [fetch-tags]
volumes:
- name: deps
path: /go
- name: gpg-sign
image: plugins/gpgsign:1
pull: always
settings:
detach_sign: true
excludes:
- "dist/release/*.sha256"
files:
- "dist/release/*"
environment:
GPGSIGN_KEY:
from_secret: gpgsign_key
GPGSIGN_PASSPHRASE:
from_secret: gpgsign_passphrase
depends_on: [static]
- name: release-tag
image: woodpeckerci/plugin-s3:latest
pull: always
settings:
acl:
from_secret: aws_s3_acl
region:
from_secret: aws_s3_region
bucket:
from_secret: aws_s3_bucket
endpoint:
from_secret: aws_s3_endpoint
path_style:
from_secret: aws_s3_path_style
source: "dist/release/*"
strip_prefix: dist/release/
target: "/gitea/${DRONE_TAG##v}"
environment:
AWS_ACCESS_KEY_ID:
from_secret: aws_access_key_id
AWS_SECRET_ACCESS_KEY:
from_secret: aws_secret_access_key
depends_on: [gpg-sign]
- name: github
image: plugins/github-release:latest
pull: always
settings:
files:
- "dist/release/*"
file_exists: overwrite
environment:
GITHUB_TOKEN:
from_secret: github_token
depends_on: [gpg-sign]
---
kind: pipeline
type: docker
name: docker-linux-amd64-release-version
platform:
os: linux
arch: amd64
trigger:
ref:
include:
- "refs/tags/**"
exclude:
- "refs/tags/**-rc*"
paths:
exclude:
- "docs/**"
steps:
- name: fetch-tags
image: docker:git
pull: always
commands:
- git fetch --tags --force
- name: publish
image: plugins/docker:latest
pull: always
settings:
auto_tag: true
auto_tag_suffix: linux-amd64
repo: gitea/gitea
build_args:
- GOPROXY=https://goproxy.io
password:
from_secret: docker_password
username:
from_secret: docker_username
environment:
PLUGIN_MIRROR:
from_secret: plugin_mirror
DOCKER_BUILDKIT: 1
when:
event:
exclude:
- pull_request
- name: publish-rootless
image: plugins/docker:latest
settings:
dockerfile: Dockerfile.rootless
auto_tag: true
auto_tag_suffix: linux-amd64-rootless
repo: gitea/gitea
build_args:
- GOPROXY=https://goproxy.io
password:
from_secret: docker_password
username:
from_secret: docker_username
environment:
PLUGIN_MIRROR:
from_secret: plugin_mirror
DOCKER_BUILDKIT: 1
when:
event:
exclude:
- pull_request
---
kind: pipeline
type: docker
name: docker-linux-amd64-release-candidate-version
platform:
os: linux
arch: amd64
trigger:
ref:
- "refs/tags/**-rc*"
paths:
exclude:
- "docs/**"
steps:
- name: fetch-tags
image: docker:git
pull: always
commands:
- git fetch --tags --force
- name: publish
image: plugins/docker:latest
pull: always
settings:
tags: ${DRONE_TAG##v}-linux-amd64
repo: gitea/gitea
build_args:
- GOPROXY=https://goproxy.io
password:
from_secret: docker_password
username:
from_secret: docker_username
environment:
PLUGIN_MIRROR:
from_secret: plugin_mirror
DOCKER_BUILDKIT: 1
when:
event:
exclude:
- pull_request
- name: publish-rootless
image: plugins/docker:latest
settings:
dockerfile: Dockerfile.rootless
tags: ${DRONE_TAG##v}-linux-amd64-rootless
repo: gitea/gitea
build_args:
- GOPROXY=https://goproxy.io
password:
from_secret: docker_password
username:
from_secret: docker_username
environment:
PLUGIN_MIRROR:
from_secret: plugin_mirror
DOCKER_BUILDKIT: 1
when:
event:
exclude:
- pull_request
---
kind: pipeline
type: docker
name: docker-linux-arm64-release-version
platform:
os: linux
arch: arm64
trigger:
ref:
include:
- "refs/tags/**"
exclude:
- "refs/tags/**-rc*"
paths:
exclude:
- "docs/**"
steps:
- name: fetch-tags
image: docker:git
pull: always
commands:
- git fetch --tags --force
- name: publish
image: plugins/docker:latest
pull: always
settings:
auto_tag: true
auto_tag_suffix: linux-arm64
repo: gitea/gitea
build_args:
- GOPROXY=https://goproxy.io
password:
from_secret: docker_password
username:
from_secret: docker_username
environment:
PLUGIN_MIRROR:
from_secret: plugin_mirror
DOCKER_BUILDKIT: 1
when:
event:
exclude:
- pull_request
- name: publish-rootless
image: plugins/docker:latest
settings:
dockerfile: Dockerfile.rootless
auto_tag: true
auto_tag_suffix: linux-arm64-rootless
repo: gitea/gitea
build_args:
- GOPROXY=https://goproxy.io
password:
from_secret: docker_password
username:
from_secret: docker_username
environment:
PLUGIN_MIRROR:
from_secret: plugin_mirror
DOCKER_BUILDKIT: 1
when:
event:
exclude:
- pull_request
---
kind: pipeline
type: docker
name: docker-linux-arm64-release-candidate-version
platform:
os: linux
arch: arm64
trigger:
ref:
- "refs/tags/**-rc*"
paths:
exclude:
- "docs/**"
steps:
- name: fetch-tags
image: docker:git
pull: always
commands:
- git fetch --tags --force
- name: publish
image: plugins/docker:latest
pull: always
settings:
tags: ${DRONE_TAG##v}-linux-arm64
repo: gitea/gitea
build_args:
- GOPROXY=https://goproxy.io
password:
from_secret: docker_password
username:
from_secret: docker_username
environment:
PLUGIN_MIRROR:
from_secret: plugin_mirror
DOCKER_BUILDKIT: 1
when:
event:
exclude:
- pull_request
- name: publish-rootless
image: plugins/docker:latest
settings:
dockerfile: Dockerfile.rootless
tags: ${DRONE_TAG##v}-linux-arm64-rootless
repo: gitea/gitea
build_args:
- GOPROXY=https://goproxy.io
password:
from_secret: docker_password
username:
from_secret: docker_username
environment:
PLUGIN_MIRROR:
from_secret: plugin_mirror
DOCKER_BUILDKIT: 1
when:
event:
exclude:
- pull_request
---
kind: pipeline
type: docker
name: docker-manifest-version
platform:
os: linux
arch: amd64
steps:
- name: manifest-rootless
image: plugins/manifest
pull: always
settings:
auto_tag: true
ignore_missing: true
spec: docker/manifest.rootless.tmpl
password:
from_secret: docker_password
username:
from_secret: docker_username
- name: manifest
image: plugins/manifest
settings:
auto_tag: true
ignore_missing: true
spec: docker/manifest.tmpl
password:
from_secret: docker_password
username:
from_secret: docker_username
trigger:
ref:
- "refs/tags/**"
paths:
exclude:
- "docs/**"
depends_on:
- docker-linux-amd64-release-version
- docker-linux-amd64-release-candidate-version
- docker-linux-arm64-release-version
- docker-linux-arm64-release-candidate-version

View File

@ -476,7 +476,7 @@ rules:
prefer-exponentiation-operator: [2]
prefer-named-capture-group: [0]
prefer-numeric-literals: [2]
prefer-object-has-own: [0]
prefer-object-has-own: [2]
prefer-object-spread: [2]
prefer-promise-reject-errors: [2, {allowEmptyReject: false}]
prefer-regex-literals: [2]

View File

@ -1,6 +1,6 @@
name: Bug Report
description: Found something you weren't expecting? Report it here!
labels: ["kind/bug"]
labels: ["type/bug"]
body:
- type: markdown
attributes:

View File

@ -1,6 +1,6 @@
name: Feature Request
description: Got an idea for a feature that Gitea doesn't have currently? Submit your idea here!
labels: ["kind/proposal"]
labels: ["type/proposal"]
body:
- type: markdown
attributes:

View File

@ -1,6 +1,6 @@
name: Web Interface Bug Report
description: Something doesn't look quite as it should? Report it here!
labels: ["kind/bug", "kind/ui"]
labels: ["type/bug", "topic/ui"]
body:
- type: markdown
attributes:

View File

@ -2,3 +2,4 @@ self-hosted-runner:
labels:
- actuated-4cpu-8gb
- actuated-4cpu-16gb
- nscloud

33
.github/labeler.yml vendored
View File

@ -1,35 +1,36 @@
kind/docs:
modifies/docs:
- "**/*.md"
- "docs/**"
kind/ui:
modifies/frontend:
- "web_src/**/*"
modifies/templates:
- all: ["templates/**", "!templates/swagger/v1_json.tmpl"]
kind/api:
- "templates/swagger/v1_json.tmpl"
modifies/api:
- "routers/api/**"
- "templates/swagger/v1_json.tmpl"
kind/build:
modifies/cli:
- "cmd/**"
modifies/translation:
- "options/locale/*.ini"
modifies/migrations:
- "models/migrations/**/*"
modifies/internal:
- "Makefile"
- "Dockerfile"
- "Dockerfile.rootless"
- "docker/**"
- "webpack.config.js"
theme/package-registry:
- "modules/packages/**"
- "services/packages/**"
- "routers/api/packages/**"
- "routers/web/shared/packages/**"
kind/cli:
- "cmd/**"
kind/lint:
- ".eslintrc.yaml"
- ".golangci.yml"
- ".markdownlint.yaml"
- ".spectral.yaml"
- ".stylelintrc.yaml"
- ".yamllint.yaml"
- ".github/**"

View File

@ -18,4 +18,3 @@ jobs:
- uses: actions/labeler@v4
with:
dot: true
sync-labels: true

View File

@ -1,4 +1,4 @@
name: release-nightly-assets
name: release-nightly
on:
push:
@ -48,15 +48,15 @@ jobs:
REF_NAME=$(echo "${{ github.ref }}" | sed -e 's/refs\/heads\///' -e 's/refs\/tags\///' -e 's/release\/v//')
echo "Cleaned name is ${REF_NAME}"
echo "branch=${REF_NAME}" >> "$GITHUB_OUTPUT"
- name: configure aws
uses: aws-actions/configure-aws-credentials@v4
with:
aws-region: ${{ secrets.AWS_REGION }}
aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY_ID }}
aws-secret-access-key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
- name: upload binaries to s3
uses: jakejarvis/s3-sync-action@master
env:
AWS_S3_BUCKET: ${{ secrets.AWS_S3_BUCKET }}
AWS_ACCESS_KEY_ID: ${{ secrets.AWS_ACCESS_KEY_ID }}
AWS_SECRET_ACCESS_KEY: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
AWS_REGION: ${{ secrets.AWS_REGION }}
SOURCE_DIR: dist/release
DEST_DIR: gitea/${{ steps.clean_name.outputs.branch }}
run: |
aws s3 sync dist/release s3://${{ secrets.AWS_S3_BUCKET }}/gitea/${{ steps.clean_name.outputs.branch }} --no-progress
nightly-docker-rootful:
runs-on: ubuntu-latest
steps:

125
.github/workflows/release-tag-rc.yml vendored Normal file
View File

@ -0,0 +1,125 @@
name: release-tag-rc
on:
push:
tags:
- 'v1*-rc*'
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: false
jobs:
binary:
runs-on: nscloud
steps:
- uses: actions/checkout@v4
# fetch all commits instead of only the last as some branches are long lived and could have many between versions
# fetch all tags to ensure that "git describe" reports expected Gitea version, eg. v1.21.0-dev-1-g1234567
- run: git fetch --unshallow --quiet --tags --force
- uses: actions/setup-go@v4
with:
go-version: "~1.21"
check-latest: true
- uses: actions/setup-node@v3
with:
node-version: 20
- run: make deps-frontend deps-backend
# xgo build
- run: make release
env:
TAGS: bindata sqlite sqlite_unlock_notify
- name: import gpg key
id: import_gpg
uses: crazy-max/ghaction-import-gpg@v5
with:
gpg_private_key: ${{ secrets.GPGSIGN_KEY }}
passphrase: ${{ secrets.GPGSIGN_PASSPHRASE }}
- name: sign binaries
run: |
for f in dist/release/*; do
echo '${{ secrets.GPGSIGN_PASSPHRASE }}' | gpg --pinentry-mode loopback --passphrase-fd 0 --batch --yes --detach-sign -u ${{ steps.import_gpg.outputs.fingerprint }} --output "$f.asc" "$f"
done
# clean branch name to get the folder name in S3
- name: Get cleaned branch name
id: clean_name
run: |
REF_NAME=$(echo "${{ github.ref }}" | sed -e 's/refs\/heads\///' -e 's/refs\/tags\///' -e 's/release\/v//')
echo "Cleaned name is ${REF_NAME}"
echo "branch=${REF_NAME}" >> "$GITHUB_OUTPUT"
- name: configure aws
uses: aws-actions/configure-aws-credentials@v4
with:
aws-region: ${{ secrets.AWS_REGION }}
aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY_ID }}
aws-secret-access-key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
- name: upload binaries to s3
run: |
aws s3 sync dist/release s3://${{ secrets.AWS_S3_BUCKET }}/gitea/${{ steps.clean_name.outputs.branch }} --no-progress
- name: create github release
run: |
gh release create ${{ github.ref_name }} --title ${{ github.ref_name }} --draft --notes-from-tag dist/release/*
env:
GITHUB_TOKEN: ${{ secrets.RELEASE_TOKEN }}
docker-rootful:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
# fetch all commits instead of only the last as some branches are long lived and could have many between versions
# fetch all tags to ensure that "git describe" reports expected Gitea version, eg. v1.21.0-dev-1-g1234567
- run: git fetch --unshallow --quiet --tags --force
- uses: docker/setup-qemu-action@v2
- uses: docker/setup-buildx-action@v2
- uses: docker/metadata-action@v5
id: meta
with:
images: gitea/gitea
# 1.2.3-rc0
tags: |
type=semver,pattern={{version}}
- name: Login to Docker Hub
uses: docker/login-action@v2
with:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
- name: build rootful docker image
uses: docker/build-push-action@v4
with:
context: .
platforms: linux/amd64,linux/arm64
push: true
tags: ${{ steps.meta.outputs.tags }}
labels: ${{ steps.meta.outputs.labels }}
docker-rootless:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
# fetch all commits instead of only the last as some branches are long lived and could have many between versions
# fetch all tags to ensure that "git describe" reports expected Gitea version, eg. v1.21.0-dev-1-g1234567
- run: git fetch --unshallow --quiet --tags --force
- uses: docker/setup-qemu-action@v2
- uses: docker/setup-buildx-action@v2
- uses: docker/metadata-action@v5
id: meta
with:
images: gitea/gitea
# each tag below will have the suffix of -rootless
flavor: |
suffix=-rootless
# 1.2.3-rc0
tags: |
type=semver,pattern={{version}}
- name: Login to Docker Hub
uses: docker/login-action@v2
with:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
- name: build rootless docker image
uses: docker/build-push-action@v4
with:
context: .
platforms: linux/amd64,linux/arm64
push: true
file: Dockerfile.rootless
tags: ${{ steps.meta.outputs.tags }}
labels: ${{ steps.meta.outputs.labels }}

View File

@ -0,0 +1,141 @@
name: release-tag-version
on:
push:
tags:
- 'v1.*'
- '!v1*-rc*'
- '!v1*-dev'
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: false
jobs:
binary:
runs-on: nscloud
steps:
- uses: actions/checkout@v4
# fetch all commits instead of only the last as some branches are long lived and could have many between versions
# fetch all tags to ensure that "git describe" reports expected Gitea version, eg. v1.21.0-dev-1-g1234567
- run: git fetch --unshallow --quiet --tags --force
- uses: actions/setup-go@v4
with:
go-version: "~1.21"
check-latest: true
- uses: actions/setup-node@v3
with:
node-version: 20
- run: make deps-frontend deps-backend
# xgo build
- run: make release
env:
TAGS: bindata sqlite sqlite_unlock_notify
- name: import gpg key
id: import_gpg
uses: crazy-max/ghaction-import-gpg@v5
with:
gpg_private_key: ${{ secrets.GPGSIGN_KEY }}
passphrase: ${{ secrets.GPGSIGN_PASSPHRASE }}
- name: sign binaries
run: |
for f in dist/release/*; do
echo '${{ secrets.GPGSIGN_PASSPHRASE }}' | gpg --pinentry-mode loopback --passphrase-fd 0 --batch --yes --detach-sign -u ${{ steps.import_gpg.outputs.fingerprint }} --output "$f.asc" "$f"
done
# clean branch name to get the folder name in S3
- name: Get cleaned branch name
id: clean_name
run: |
REF_NAME=$(echo "${{ github.ref }}" | sed -e 's/refs\/heads\///' -e 's/refs\/tags\///' -e 's/release\/v//')
echo "Cleaned name is ${REF_NAME}"
echo "branch=${REF_NAME}" >> "$GITHUB_OUTPUT"
- name: configure aws
uses: aws-actions/configure-aws-credentials@v4
with:
aws-region: ${{ secrets.AWS_REGION }}
aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY_ID }}
aws-secret-access-key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
- name: upload binaries to s3
run: |
aws s3 sync dist/release s3://${{ secrets.AWS_S3_BUCKET }}/gitea/${{ steps.clean_name.outputs.branch }} --no-progress
- name: create github release
run: |
gh release create ${{ github.ref_name }} --title ${{ github.ref_name }} --draft --notes-from-tag dist/release/*
env:
GITHUB_TOKEN: ${{ secrets.RELEASE_TOKEN }}
docker-rootful:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
# fetch all commits instead of only the last as some branches are long lived and could have many between versions
# fetch all tags to ensure that "git describe" reports expected Gitea version, eg. v1.21.0-dev-1-g1234567
- run: git fetch --unshallow --quiet --tags --force
- uses: docker/setup-qemu-action@v2
- uses: docker/setup-buildx-action@v2
- uses: docker/metadata-action@v5
id: meta
with:
images: gitea/gitea
# this will generate tags in the following format:
# latest
# 1
# 1.2
# 1.2.3
tags: |
type=raw,value=latest
type=semver,pattern={{major}}
type=semver,pattern={{major}}.{{minor}}
type=semver,pattern={{version}}
- name: Login to Docker Hub
uses: docker/login-action@v2
with:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
- name: build rootful docker image
uses: docker/build-push-action@v4
with:
context: .
platforms: linux/amd64,linux/arm64
push: true
tags: ${{ steps.meta.outputs.tags }}
labels: ${{ steps.meta.outputs.labels }}
docker-rootless:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
# fetch all commits instead of only the last as some branches are long lived and could have many between versions
# fetch all tags to ensure that "git describe" reports expected Gitea version, eg. v1.21.0-dev-1-g1234567
- run: git fetch --unshallow --quiet --tags --force
- uses: docker/setup-qemu-action@v2
- uses: docker/setup-buildx-action@v2
- uses: docker/metadata-action@v5
id: meta
with:
images: gitea/gitea
# each tag below will have the suffix of -rootless
flavor: |
suffix=-rootless
# this will generate tags in the following format (with -rootless suffix added):
# latest
# 1
# 1.2
# 1.2.3
tags: |
type=raw,value=latest
type=semver,pattern={{major}}
type=semver,pattern={{major}}.{{minor}}
type=semver,pattern={{version}}
- name: Login to Docker Hub
uses: docker/login-action@v2
with:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
- name: build rootless docker image
uses: docker/build-push-action@v4
with:
context: .
platforms: linux/amd64,linux/arm64
push: true
file: Dockerfile.rootless
tags: ${{ steps.meta.outputs.tags }}
labels: ${{ steps.meta.outputs.labels }}

View File

@ -24,8 +24,6 @@ rules:
document-start:
level: error
present: false
ignore: |
/.drone.yml
document-end:
present: false

View File

@ -225,17 +225,20 @@ PRs without a milestone may not be merged.
### Labels
Every PR should be labeled correctly with every label that applies. \
This includes especially the distinction between `bug` (fixing existing functionality), `feature` (new functionality), `enhancement` (upgrades for existing functionality), and `refactoring` (improving the internal code structure without changing the output (much)). \
Furthermore,
Almost all labels used inside Gitea can be classified as one of the following:
- `modifies/…`: Determines which parts of the codebase are affected. These labels will be set through the CI.
- `topic/…`: Determines the conceptual component of Gitea that is affected, i.e. issues, projects, or authentication. At best, PRs should only target one component but there might be overlap. Must be set manually.
- `type/…`: Determines the type of an issue or PR (feature, refactoring, docs, bug, …). If GitHub supported scoped labels, these labels would be exclusive, so you should set **exactly** one, not more or less (every PR should fall into one of the provided categories, and only one).
- `issue/…` / `pr/…`: Labels that are specific to issues or PRs respectively and that are only necessary in a given context, i.e. `issue/not-a-bug` or `pr/need-2-approvals`
Every PR should be labeled correctly with every label that applies.
There are also some labels that will be managed automatically.\
In particular, these are
- the amount of pending required approvals
- whether this PR is `blocked`, a `backport` or `breaking`
- if it targets the `ui` or `api`
- if it increases the application `speed`
- reduces `memory usage`
are oftentimes notable labels.
- has all `backport`s or needs a manual backport
### Breaking PRs

View File

@ -58,3 +58,4 @@ CaiCandong <1290147055@qq.com> (@caicandong)
Rui Chen <rui@chenrui.dev> (@chenrui333)
Nanguan Lin <nanguanlin6@gmail.com> (@lng2020)
kerwin612 <kerwin612@qq.com> (@kerwin612)
Gary Wang <git@blumia.net> (@BLumia)

View File

@ -62,7 +62,7 @@ func runListAuth(c *cli.Context) error {
return err
}
authSources, err := auth_model.Sources()
authSources, err := auth_model.Sources(ctx)
if err != nil {
return err
}
@ -100,7 +100,7 @@ func runDeleteAuth(c *cli.Context) error {
return err
}
source, err := auth_model.GetSourceByID(c.Int64("id"))
source, err := auth_model.GetSourceByID(ctx, c.Int64("id"))
if err != nil {
return err
}

View File

@ -17,9 +17,9 @@ import (
type (
authService struct {
initDB func(ctx context.Context) error
createAuthSource func(*auth.Source) error
updateAuthSource func(*auth.Source) error
getAuthSourceByID func(id int64) (*auth.Source, error)
createAuthSource func(context.Context, *auth.Source) error
updateAuthSource func(context.Context, *auth.Source) error
getAuthSourceByID func(ctx context.Context, id int64) (*auth.Source, error)
}
)
@ -289,12 +289,12 @@ func findLdapSecurityProtocolByName(name string) (ldap.SecurityProtocol, bool) {
// getAuthSource gets the login source by its id defined in the command line flags.
// It returns an error if the id is not set, does not match any source or if the source is not of expected type.
func (a *authService) getAuthSource(c *cli.Context, authType auth.Type) (*auth.Source, error) {
func (a *authService) getAuthSource(ctx context.Context, c *cli.Context, authType auth.Type) (*auth.Source, error) {
if err := argsSet(c, "id"); err != nil {
return nil, err
}
authSource, err := a.getAuthSourceByID(c.Int64("id"))
authSource, err := a.getAuthSourceByID(ctx, c.Int64("id"))
if err != nil {
return nil, err
}
@ -332,7 +332,7 @@ func (a *authService) addLdapBindDn(c *cli.Context) error {
return err
}
return a.createAuthSource(authSource)
return a.createAuthSource(ctx, authSource)
}
// updateLdapBindDn updates a new LDAP via Bind DN authentication source.
@ -344,7 +344,7 @@ func (a *authService) updateLdapBindDn(c *cli.Context) error {
return err
}
authSource, err := a.getAuthSource(c, auth.LDAP)
authSource, err := a.getAuthSource(ctx, c, auth.LDAP)
if err != nil {
return err
}
@ -354,7 +354,7 @@ func (a *authService) updateLdapBindDn(c *cli.Context) error {
return err
}
return a.updateAuthSource(authSource)
return a.updateAuthSource(ctx, authSource)
}
// addLdapSimpleAuth adds a new LDAP (simple auth) authentication source.
@ -383,7 +383,7 @@ func (a *authService) addLdapSimpleAuth(c *cli.Context) error {
return err
}
return a.createAuthSource(authSource)
return a.createAuthSource(ctx, authSource)
}
// updateLdapBindDn updates a new LDAP (simple auth) authentication source.
@ -395,7 +395,7 @@ func (a *authService) updateLdapSimpleAuth(c *cli.Context) error {
return err
}
authSource, err := a.getAuthSource(c, auth.DLDAP)
authSource, err := a.getAuthSource(ctx, c, auth.DLDAP)
if err != nil {
return err
}
@ -405,5 +405,5 @@ func (a *authService) updateLdapSimpleAuth(c *cli.Context) error {
return err
}
return a.updateAuthSource(authSource)
return a.updateAuthSource(ctx, authSource)
}

View File

@ -210,15 +210,15 @@ func TestAddLdapBindDn(t *testing.T) {
initDB: func(context.Context) error {
return nil
},
createAuthSource: func(authSource *auth.Source) error {
createAuthSource: func(ctx context.Context, authSource *auth.Source) error {
createdAuthSource = authSource
return nil
},
updateAuthSource: func(authSource *auth.Source) error {
updateAuthSource: func(ctx context.Context, authSource *auth.Source) error {
assert.FailNow(t, "case %d: should not call updateAuthSource", n)
return nil
},
getAuthSourceByID: func(id int64) (*auth.Source, error) {
getAuthSourceByID: func(ctx context.Context, id int64) (*auth.Source, error) {
assert.FailNow(t, "case %d: should not call getAuthSourceByID", n)
return nil, nil
},
@ -441,15 +441,15 @@ func TestAddLdapSimpleAuth(t *testing.T) {
initDB: func(context.Context) error {
return nil
},
createAuthSource: func(authSource *auth.Source) error {
createAuthSource: func(ctx context.Context, authSource *auth.Source) error {
createdAuthSource = authSource
return nil
},
updateAuthSource: func(authSource *auth.Source) error {
updateAuthSource: func(ctx context.Context, authSource *auth.Source) error {
assert.FailNow(t, "case %d: should not call updateAuthSource", n)
return nil
},
getAuthSourceByID: func(id int64) (*auth.Source, error) {
getAuthSourceByID: func(ctx context.Context, id int64) (*auth.Source, error) {
assert.FailNow(t, "case %d: should not call getAuthSourceByID", n)
return nil, nil
},
@ -896,15 +896,15 @@ func TestUpdateLdapBindDn(t *testing.T) {
initDB: func(context.Context) error {
return nil
},
createAuthSource: func(authSource *auth.Source) error {
createAuthSource: func(ctx context.Context, authSource *auth.Source) error {
assert.FailNow(t, "case %d: should not call createAuthSource", n)
return nil
},
updateAuthSource: func(authSource *auth.Source) error {
updateAuthSource: func(ctx context.Context, authSource *auth.Source) error {
updatedAuthSource = authSource
return nil
},
getAuthSourceByID: func(id int64) (*auth.Source, error) {
getAuthSourceByID: func(ctx context.Context, id int64) (*auth.Source, error) {
if c.id != 0 {
assert.Equal(t, c.id, id, "case %d: wrong id", n)
}
@ -1286,15 +1286,15 @@ func TestUpdateLdapSimpleAuth(t *testing.T) {
initDB: func(context.Context) error {
return nil
},
createAuthSource: func(authSource *auth.Source) error {
createAuthSource: func(ctx context.Context, authSource *auth.Source) error {
assert.FailNow(t, "case %d: should not call createAuthSource", n)
return nil
},
updateAuthSource: func(authSource *auth.Source) error {
updateAuthSource: func(ctx context.Context, authSource *auth.Source) error {
updatedAuthSource = authSource
return nil
},
getAuthSourceByID: func(id int64) (*auth.Source, error) {
getAuthSourceByID: func(ctx context.Context, id int64) (*auth.Source, error) {
if c.id != 0 {
assert.Equal(t, c.id, id, "case %d: wrong id", n)
}

View File

@ -183,7 +183,7 @@ func runAddOauth(c *cli.Context) error {
}
}
return auth_model.CreateSource(&auth_model.Source{
return auth_model.CreateSource(ctx, &auth_model.Source{
Type: auth_model.OAuth2,
Name: c.String("name"),
IsActive: true,
@ -203,7 +203,7 @@ func runUpdateOauth(c *cli.Context) error {
return err
}
source, err := auth_model.GetSourceByID(c.Int64("id"))
source, err := auth_model.GetSourceByID(ctx, c.Int64("id"))
if err != nil {
return err
}
@ -294,5 +294,5 @@ func runUpdateOauth(c *cli.Context) error {
oAuth2Config.CustomURLMapping = customURLMapping
source.Cfg = oAuth2Config
return auth_model.UpdateSource(source)
return auth_model.UpdateSource(ctx, source)
}

View File

@ -156,7 +156,7 @@ func runAddSMTP(c *cli.Context) error {
smtpConfig.Auth = "PLAIN"
}
return auth_model.CreateSource(&auth_model.Source{
return auth_model.CreateSource(ctx, &auth_model.Source{
Type: auth_model.SMTP,
Name: c.String("name"),
IsActive: active,
@ -176,7 +176,7 @@ func runUpdateSMTP(c *cli.Context) error {
return err
}
source, err := auth_model.GetSourceByID(c.Int64("id"))
source, err := auth_model.GetSourceByID(ctx, c.Int64("id"))
if err != nil {
return err
}
@ -197,5 +197,5 @@ func runUpdateSMTP(c *cli.Context) error {
source.Cfg = smtpConfig
return auth_model.UpdateSource(source)
return auth_model.UpdateSource(ctx, source)
}

View File

@ -548,7 +548,8 @@ ENABLE = true
;; Pre-register OAuth2 applications for some universally useful services
;; * https://github.com/hickford/git-credential-oauth
;; * https://github.com/git-ecosystem/git-credential-manager
;DEFAULT_APPLICATIONS = git-credential-oauth, git-credential-manager
;; * https://gitea.com/gitea/tea
;DEFAULT_APPLICATIONS = git-credential-oauth, git-credential-manager, tea
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
@ -950,7 +951,7 @@ LEVEL = Info
;; Note: Code and Releases can currently not be deactivated. If you specify default repo units you should still list them for future compatibility.
;; External wiki and issue tracker can't be enabled by default as it requires additional settings.
;; Disabled repo units will not be added to new repositories regardless if it is in the default list.
;DEFAULT_REPO_UNITS = repo.code,repo.releases,repo.issues,repo.pulls,repo.wiki,repo.projects,repo.packages
;DEFAULT_REPO_UNITS = repo.code,repo.releases,repo.issues,repo.pulls,repo.wiki,repo.projects,repo.packages,repo.actions
;;
;; Comma separated list of default forked repo units.
;; The set of allowed values and rules are the same as DEFAULT_REPO_UNITS.
@ -1420,7 +1421,7 @@ LEVEL = Info
;DATADIR = queues/ ; Relative paths will be made absolute against `%(APP_DATA_PATH)s`.
;;
;; Default queue length before a channel queue will block
;LENGTH = 100
;LENGTH = 100000
;;
;; Batch size to send for batched queues
;BATCH_LENGTH = 20

View File

@ -102,7 +102,7 @@ In addition, there is _`StaticRootPath`_ which can be set as a built-in at build
- `ENABLE_PUSH_CREATE_USER`: **false**: Allow users to push local repositories to Gitea and have them automatically created for a user.
- `ENABLE_PUSH_CREATE_ORG`: **false**: Allow users to push local repositories to Gitea and have them automatically created for an org.
- `DISABLED_REPO_UNITS`: **_empty_**: Comma separated list of globally disabled repo units. Allowed values: \[repo.issues, repo.ext_issues, repo.pulls, repo.wiki, repo.ext_wiki, repo.projects, repo.packages, repo.actions\]
- `DEFAULT_REPO_UNITS`: **repo.code,repo.releases,repo.issues,repo.pulls,repo.wiki,repo.projects,repo.packages**: Comma separated list of default new repo units. Allowed values: \[repo.code, repo.releases, repo.issues, repo.pulls, repo.wiki, repo.projects, repo.packages, repo.actions\]. Note: Code and Releases can currently not be deactivated. If you specify default repo units you should still list them for future compatibility. External wiki and issue tracker can't be enabled by default as it requires additional settings. Disabled repo units will not be added to new repositories regardless if it is in the default list.
- `DEFAULT_REPO_UNITS`: **repo.code,repo.releases,repo.issues,repo.pulls,repo.wiki,repo.projects,repo.packages,repo.actions**: Comma separated list of default new repo units. Allowed values: \[repo.code, repo.releases, repo.issues, repo.pulls, repo.wiki, repo.projects, repo.packages, repo.actions\]. Note: Code and Releases can currently not be deactivated. If you specify default repo units you should still list them for future compatibility. External wiki and issue tracker can't be enabled by default as it requires additional settings. Disabled repo units will not be added to new repositories regardless if it is in the default list.
- `DEFAULT_FORK_REPO_UNITS`: **repo.code,repo.pulls**: Comma separated list of default forked repo units. The set of allowed values and rules is the same as `DEFAULT_REPO_UNITS`.
- `PREFIX_ARCHIVE_FILES`: **true**: Prefix archive files by placing them in a directory named after the repository.
- `DISABLE_MIGRATIONS`: **false**: Disable migrating feature.
@ -483,7 +483,7 @@ Configuration at `[queue]` will set defaults for queues with overrides for indiv
- `TYPE`: **level**: General queue type, currently support: `level` (uses a LevelDB internally), `channel`, `redis`, `dummy`. Invalid types are treated as `level`.
- `DATADIR`: **queues/common**: Base DataDir for storing level queues. `DATADIR` for individual queues can be set in `queue.name` sections. Relative paths will be made absolute against `%(APP_DATA_PATH)s`.
- `LENGTH`: **100**: Maximal queue size before channel queues block
- `LENGTH`: **100000**: Maximal queue size before channel queues block
- `BATCH_LENGTH`: **20**: Batch data before passing to the handler
- `CONN_STR`: **redis://127.0.0.1:6379/0**: Connection string for the redis queue type. For `redis-cluster` use `redis+cluster://127.0.0.1:6379/0`. Options can be set using query params. Similarly, LevelDB options can also be set using: **leveldb://relative/path?option=value** or **leveldb:///absolute/path?option=value**, and will override `DATADIR`
- `QUEUE_NAME`: **_queue**: The suffix for default redis and disk queue name. Individual queues will default to **`name`**`QUEUE_NAME` but can be overridden in the specific `queue.name` section.
@ -1107,7 +1107,7 @@ This section only does "set" config, a removed config key from this section won'
- `JWT_SECRET_URI`: **_empty_**: Instead of defining JWT_SECRET in the configuration, this configuration option can be used to give Gitea a path to a file that contains the secret (example value: `file:/etc/gitea/oauth2_jwt_secret`)
- `JWT_SIGNING_PRIVATE_KEY_FILE`: **jwt/private.pem**: Private key file path used to sign OAuth2 tokens. The path is relative to `APP_DATA_PATH`. This setting is only needed if `JWT_SIGNING_ALGORITHM` is set to `RS256`, `RS384`, `RS512`, `ES256`, `ES384` or `ES512`. The file must contain a RSA or ECDSA private key in the PKCS8 format. If no key exists a 4096 bit key will be created for you.
- `MAX_TOKEN_LENGTH`: **32767**: Maximum length of token/cookie to accept from OAuth2 provider
- `DEFAULT_APPLICATIONS`: **git-credential-oauth, git-credential-manager**: Pre-register OAuth applications for some services on startup. See the [OAuth2 documentation](/development/oauth2-provider.md) for the list of available options.
- `DEFAULT_APPLICATIONS`: **git-credential-oauth, git-credential-manager, tea**: Pre-register OAuth applications for some services on startup. See the [OAuth2 documentation](/development/oauth2-provider.md) for the list of available options.
## i18n (`i18n`)

View File

@ -102,7 +102,7 @@ menu:
- `ENABLE_PUSH_CREATE_USER`: **false**: 允许用户将本地存储库推送到Gitea并为用户自动创建它们。
- `ENABLE_PUSH_CREATE_ORG`: **false**: 允许用户将本地存储库推送到Gitea并为组织自动创建它们。
- `DISABLED_REPO_UNITS`: **_empty_**: 逗号分隔的全局禁用的仓库单元列表。允许的值是:: \[repo.issues, repo.ext_issues, repo.pulls, repo.wiki, repo.ext_wiki, repo.projects, repo.packages, repo.actions\]
- `DEFAULT_REPO_UNITS`: **repo.code,repo.releases,repo.issues,repo.pulls,repo.wiki,repo.projects,repo.packages**: 逗号分隔的默认新仓库单元列表。允许的值是:: \[repo.code, repo.releases, repo.issues, repo.pulls, repo.wiki, repo.projects, repo.packages, repo.actions\]. 注意目前无法停用代码和发布。如果您指定了默认的仓库单元您仍应将它们列出以保持未来的兼容性。外部wiki和问题跟踪器不能默认启用因为它需要额外的设置。禁用的仓库单元将不会添加到新的仓库中无论它是否在默认列表中。
- `DEFAULT_REPO_UNITS`: **repo.code,repo.releases,repo.issues,repo.pulls,repo.wiki,repo.projects,repo.packages,repo.actions**: 逗号分隔的默认新仓库单元列表。允许的值是:: \[repo.code, repo.releases, repo.issues, repo.pulls, repo.wiki, repo.projects, repo.packages, repo.actions\]. 注意目前无法停用代码和发布。如果您指定了默认的仓库单元您仍应将它们列出以保持未来的兼容性。外部wiki和问题跟踪器不能默认启用因为它需要额外的设置。禁用的仓库单元将不会添加到新的仓库中无论它是否在默认列表中。
- `DEFAULT_FORK_REPO_UNITS`: **repo.code,repo.pulls**: 逗号分隔的默认分叉仓库单元列表。允许的值和规则与`DEFAULT_REPO_UNITS`相同。
- `PREFIX_ARCHIVE_FILES`: **true**: 通过将存档文件放置在以仓库命名的目录中来添加前缀。
- `DISABLE_MIGRATIONS`: **false**: 禁用迁移功能。
@ -472,7 +472,7 @@ menu:
- `TYPE`**level**:通用队列类型,当前支持:`level`(在内部使用 LevelDB、`channel`、`redis`、`dummy`。无效的类型将视为 `level`
- `DATADIR`**queues/common**:用于存储 level 队列的基本 DataDir。单独的队列的 `DATADIR` 可以在 `queue.name` 部分进行设置。相对路径将根据 `%(APP_DATA_PATH)s` 变为绝对路径。
- `LENGTH`**100**:通道队列阻塞之前的最大队列大小
- `LENGTH`**100000**:通道队列阻塞之前的最大队列大小
- `BATCH_LENGTH`**20**:在传递给处理程序之前批处理数据
- `CONN_STR`**redis://127.0.0.1:6379/0**redis 队列类型的连接字符串。对于 `redis-cluster`,使用 `redis+cluster://127.0.0.1:6379/0`。可以使用查询参数来设置选项。类似地LevelDB 选项也可以使用:**leveldb://relative/path?option=value** 或 **leveldb:///absolute/path?option=value** 进行设置,并将覆盖 `DATADIR`
- `QUEUE_NAME`**_queue**:默认的 redis 和磁盘队列名称的后缀。单独的队列将默认为 **`name`**`QUEUE_NAME`,但可以在特定的 `queue.name` 部分中进行覆盖。
@ -1056,7 +1056,7 @@ Gitea 创建以下非唯一队列:
- `JWT_SECRET_URI`**_empty_**:可以使用此配置选项,而不是在配置中定义`JWT_SECRET`以向Gitea提供包含密钥的文件的路径示例值`file:/etc/gitea/oauth2_jwt_secret`)。
- `JWT_SIGNING_PRIVATE_KEY_FILE`**jwt/private.pem**用于签署OAuth2令牌的私钥文件路径。路径相对于`APP_DATA_PATH`。仅当`JWT_SIGNING_ALGORITHM`设置为`RS256``RS384``RS512``ES256``ES384`或`ES512`时才需要此设置。文件必须包含PKCS8格式的RSA或ECDSA私钥。如果不存在密钥则将为您创建一个4096位密钥。
- `MAX_TOKEN_LENGTH`**32767**从OAuth2提供者接受的令牌/cookie的最大长度。
- `DEFAULT_APPLICATIONS`**git-credential-oauthgit-credential-manager**在启动时预注册用于某些服务的OAuth应用程序。有关可用选项列表请参阅[OAuth2文档](/development/oauth2-provider.md)。
- `DEFAULT_APPLICATIONS`**git-credential-oauthgit-credential-manager, tea**在启动时预注册用于某些服务的OAuth应用程序。有关可用选项列表请参阅[OAuth2文档](/development/oauth2-provider.md)。
## i18n (`i18n`)

View File

@ -381,3 +381,9 @@ If you really need to do so, to make Gitea works with sub-path (eg: `http://exam
1. Set `[server] ROOT_URL = http://example.com/gitea/` in your `app.ini` file.
2. Make the reverse-proxy pass `http://example.com/gitea/foo` to `http://gitea-server:3000/foo`.
3. Make sure the reverse-proxy not decode the URI, the request `http://example.com/gitea/a%2Fb` should be passed as `http://gitea-server:3000/a%2Fb`.
## Docker / Container Registry
The container registry uses a fixed sub-path `/v2` which can't be changed.
Even if you deploy Gitea with a different sub-path, `/v2` will be used by the `docker` client.
Therefore you may need to add an additional route to your reverse proxy configuration.

View File

@ -23,7 +23,7 @@ If you don't want your repository to be visible for search engines read further.
## Block search engines indexation using robots.txt
To make Gitea serve a custom `robots.txt` (default: empty 404) for top level installations,
create a file called `robots.txt` in the [`custom` folder or `CustomPath`](administration/customizing-gitea.md)
create a file with path `public/robots.txt` in the [`custom` folder or `CustomPath`](administration/customizing-gitea.md)
Examples on how to configure the `robots.txt` can be found at [https://moz.com/learn/seo/robotstxt](https://moz.com/learn/seo/robotstxt).

View File

@ -22,7 +22,7 @@ menu:
## 使用 robots.txt 阻止搜索引擎索引
为了使 Gitea 为顶级安装提供自定义的`robots.txt`(默认为空的 404请在[`custom`文件夹或`CustomPath`]administration/customizing-gitea.md中创建一个名为 `robots.txt` 的文件。
为了使 Gitea 为顶级安装提供自定义的`robots.txt`(默认为空的 404请在 [`custom`文件夹或`CustomPath`]administration/customizing-gitea.md中创建一个名为 `public/robots.txt` 的文件。
有关如何配置 `robots.txt` 的示例,请参考 [https://moz.com/learn/seo/robotstxt](https://moz.com/learn/seo/robotstxt)。

View File

@ -86,6 +86,7 @@ Gitea creates OAuth applications for the following services by default on startu
|-----------|-----------|---------|
|[git-credential-oauth](https://github.com/hickford/git-credential-oauth)|Git credential helper|`a4792ccc-144e-407e-86c9-5e7d8d9c3269`|
|[Git Credential Manager](https://github.com/git-ecosystem/git-credential-manager)|Git credential helper|`e90ee53c-94e2-48ac-9358-a874fb9e0662`|
|[tea](https://gitea.com/gitea/tea)|tea|`d57cb8c4-630c-4168-8324-ec79935e18d4`|
To prevent unexpected behavior, they are being displayed as locked in the UI and their creation can instead be controlled by the `DEFAULT_APPLICATIONS` parameter in `app.ini`.

View File

@ -1,6 +1,6 @@
---
date: "2017-07-21T12:00:00+02:00"
title: "Run as service in Linux"
title: "Run as a Linux service"
slug: "linux-service"
sidebar_position: 40
toc: false
@ -15,11 +15,11 @@ menu:
identifier: "linux-service"
---
### Run Gitea as Linux service
# Run as a Linux service
You can run Gitea as service, using either systemd or supervisor. The steps below tested on Ubuntu 16.04, but those should work on any Linux distributions (with little modification).
You can run Gitea as a Linux service, using either systemd or supervisor. The steps below tested on Ubuntu 16.04, but those should work on any Linux distributions (with little modification).
#### Using systemd
## Using systemd
Copy the sample [gitea.service](https://github.com/go-gitea/gitea/blob/main/contrib/systemd/gitea.service) to `/etc/systemd/system/gitea.service`, then edit the file with your favorite editor.
@ -41,7 +41,7 @@ If you have systemd version 220 or later, you can enable and immediately start G
sudo systemctl enable gitea --now
```
#### Using supervisor
## Using supervisor
Install supervisor by running below command in terminal:

View File

@ -1,6 +1,6 @@
---
date: "2016-12-21T15:00:00-02:00"
title: "Register as a Windows Service"
title: "Register as a Windows service"
slug: "windows-service"
sidebar_position: 50
toc: false
@ -14,8 +14,9 @@ menu:
sidebar_position: 50
identifier: "windows-service"
---
# Register as a Windows service
# Prerequisites
## Prerequisites
The following changes are made in C:\gitea\custom\conf\app.ini:
@ -27,7 +28,7 @@ Sets Gitea to run as the local system user.
COMPUTERNAME is whatever the response is from `echo %COMPUTERNAME%` on the command line. If the response is `USER-PC` then `RUN_USER = USER-PC$`
## Use absolute paths
### Use absolute paths
If you use SQLite3, change the `PATH` to include the full path:
@ -36,7 +37,7 @@ If you use SQLite3, change the `PATH` to include the full path:
PATH = c:/gitea/data/gitea.db
```
# Register as a Windows Service
## Register Gitea
To register Gitea as a Windows service, open a command prompt (cmd) as an Administrator,
then run the following command:
@ -51,7 +52,7 @@ Open "Windows Services", search for the service named "gitea", right-click it an
"Run". If everything is OK, Gitea will be reachable on `http://localhost:3000` (or the port
that was configured).
## Service startup type
### Service startup type
It was observed that on loaded systems during boot Gitea service may fail to start with timeout records in Windows Event Log.
In that case change startup type to `Automatic-Delayed`. This can be done during service creation, or by running config command
@ -60,7 +61,7 @@ In that case change startup type to `Automatic-Delayed`. This can be done during
sc.exe config gitea start= delayed-auto
```
## Adding startup dependencies
### Adding startup dependencies
To add a startup dependency to the Gitea Windows service (eg Mysql, Mariadb), as an Administrator, then run the following command:
@ -70,9 +71,9 @@ sc.exe config gitea depend= mariadb
This will ensure that when the Windows machine restarts, the automatic starting of Gitea is postponed until the database is ready and thus mitigate failed startups.
## Unregister as a service
## Unregister Gitea
To unregister Gitea as a service, open a command prompt (cmd) as an Administrator and run:
To unregister Gitea as a Windows service, open a command prompt (cmd) as an Administrator and run:
```
sc.exe delete gitea

View File

@ -77,6 +77,7 @@ curl --user your_username:your_password_or_token \
```
If you are using 2FA or OAuth use a [personal access token](development/api-usage.md#authentication) instead of the password.
You cannot publish a file with the same name twice to a package. You must delete the existing package file first.
The server responds with the following HTTP Status codes.

View File

@ -25,6 +25,7 @@ To work with the Composer package registry, you can use [Composer](https://getco
To publish a Composer package perform a HTTP PUT operation with the package content in the request body.
The package content must be the zipped PHP project with the `composer.json` file.
You cannot publish a package if a package of the same name and version already exists. You must delete the existing package first.
```
@ -64,7 +65,8 @@ The server responds with the following HTTP Status codes.
| HTTP Status Code | Meaning |
| ----------------- | ------- |
| `201 Created` | The package has been published. |
| `400 Bad Request` | The package name and/or version are invalid or a package with the same name and version already exist. |
| `400 Bad Request` | The package is invalid. |
| `409 Conflict` | A package file with the same combination of parameters exists already. |
## Configuring the package registry

View File

@ -63,6 +63,8 @@ For example:
conan upload --remote=gitea ConanPackage/1.2@gitea/final
```
You cannot publish a file with the same name twice to a package. You must delete the existing package or file first.
The Gitea Conan package registry has full [revision](https://docs.conan.io/en/latest/versioning/revisions.html) support.
## Install a package

View File

@ -63,8 +63,18 @@ curl --user your_username:your_password_or_token \
https://gitea.example.com/api/packages/testuser/conda/package-1.0.conda
```
If you are using 2FA or OAuth use a [personal access token](development/api-usage.md#authentication) instead of the password.
You cannot publish a package if a package of the same name and version already exists. You must delete the existing package first.
The server responds with the following HTTP Status codes.
| HTTP Status Code | Meaning |
| ----------------- | ------- |
| `201 Created` | The package has been published. |
| `400 Bad Request` | The package is invalid. |
| `409 Conflict` | A package file with the same combination of parameters exists already. |
## Install a package
To install a package from the package registry, execute one of the following commands:

View File

@ -68,8 +68,18 @@ curl --user your_username:your_password_or_token \
https://gitea.example.com/api/packages/testuser/cran/bin?platform=windows&rversion=4.2
```
If you are using 2FA or OAuth use a [personal access token](development/api-usage.md#authentication) instead of the password.
You cannot publish a package if a package of the same name and version already exists. You must delete the existing package first.
The server responds with the following HTTP Status codes.
| HTTP Status Code | Meaning |
| ----------------- | ------- |
| `201 Created` | The package has been published. |
| `400 Bad Request` | The package is invalid. |
| `409 Conflict` | A package file with the same combination of parameters exists already. |
## Install a package
To install a R package from the package registry, execute the following command:

View File

@ -77,14 +77,15 @@ curl --user your_username:your_password_or_token \
```
If you are using 2FA or OAuth use a [personal access token](development/api-usage.md#authentication) instead of the password.
You cannot publish a file with the same name twice to a package. You must delete the existing package version first.
You cannot publish a package if a package of the same name, version, distribution, component and architecture already exists. You must delete the existing package first.
The server responds with the following HTTP Status codes.
| HTTP Status Code | Meaning |
| ----------------- | ------- |
| `201 Created` | The package has been published. |
| `400 Bad Request` | The package name, version, distribution, component or architecture are invalid. |
| `400 Bad Request` | The package is invalid. |
| `409 Conflict` | A package file with the same combination of parameters exists already. |
## Delete a package

View File

@ -41,6 +41,8 @@ curl --user your_username:your_password_or_token \
If you are using 2FA or OAuth use a [personal access token](development/api-usage.md#authentication) instead of the password.
You cannot publish a package if a package of the same name and version already exists. You must delete the existing package first.
The server responds with the following HTTP Status codes.
| HTTP Status Code | Meaning |

View File

@ -67,6 +67,14 @@ curl -X PUT --user {username}:{password} \
You cannot publish a package if a package of the same name and version already exists. You must delete the existing package first.
The server responds with the following HTTP Status codes.
| HTTP Status Code | Meaning |
| ----------------- | ------- |
| `201 Created` | The package has been published. |
| `400 Bad Request` | The package is invalid. |
| `409 Conflict` | A package file with the same combination of parameters exists already. |
## Install a package
To install a Swift package from the package registry, add it in the `Package.swift` file dependencies list:

View File

@ -44,8 +44,18 @@ curl --user your_username:your_password_or_token \
https://gitea.example.com/api/packages/testuser/vagrant/test_system/1.0.0/hyperv.box
```
If you are using 2FA or OAuth use a [personal access token](development/api-usage.md#authentication) instead of the password.
You cannot publish a box if a box of the same name, version and provider already exists. You must delete the existing package first.
The server responds with the following HTTP Status codes.
| HTTP Status Code | Meaning |
| ----------------- | ------- |
| `201 Created` | The package has been published. |
| `400 Bad Request` | The package is invalid. |
| `409 Conflict` | A package with the same combination of parameters exists already. |
## Install a package
To install a box from the package registry, execute the following command:

2
go.mod
View File

@ -41,7 +41,7 @@ require (
github.com/go-ap/jsonld v0.0.0-20221030091449-f2a191312c73
github.com/go-chi/chi/v5 v5.0.10
github.com/go-chi/cors v1.2.1
github.com/go-co-op/gocron v1.35.0
github.com/go-co-op/gocron v1.31.1
github.com/go-enry/go-enry/v2 v2.8.6
github.com/go-fed/httpsig v1.1.1-0.20201223112313-55836744818e
github.com/go-git/go-billy/v5 v5.5.0

4
go.sum
View File

@ -345,8 +345,8 @@ github.com/go-chi/chi/v5 v5.0.10 h1:rLz5avzKpjqxrYwXNfmjkrYYXOyLJd37pz53UFHC6vk=
github.com/go-chi/chi/v5 v5.0.10/go.mod h1:DslCQbL2OYiznFReuXYUmQ2hGd1aDpCnlMNITLSKoi8=
github.com/go-chi/cors v1.2.1 h1:xEC8UT3Rlp2QuWNEr4Fs/c2EAGVKBwy/1vHx3bppil4=
github.com/go-chi/cors v1.2.1/go.mod h1:sSbTewc+6wYHBBCW7ytsFSn836hqM7JxpglAy2Vzc58=
github.com/go-co-op/gocron v1.35.0 h1:niC91OHiSEimXgPPay02AI1gLGL4JGBgDzmWtgZ8n5A=
github.com/go-co-op/gocron v1.35.0/go.mod h1:NLi+bkm4rRSy1F8U7iacZOz0xPseMoIOnvabGoSe/no=
github.com/go-co-op/gocron v1.31.1 h1:LZAuBlU0t3SPGUMJGhrJ6VuCc3CsrYzkzicygvVWlfA=
github.com/go-co-op/gocron v1.31.1/go.mod h1:39f6KNSGVOU1LO/ZOoZfcSxwlsJDQOKSu8erN0SH48Y=
github.com/go-enry/go-enry/v2 v2.8.6 h1:T6ljs5+qNiUTDqpfK5GUD5EvLNdDbf804u8iC30vw7U=
github.com/go-enry/go-enry/v2 v2.8.6/go.mod h1:9yrj4ES1YrbNb1Wb7/PWYr2bpaCXUGRt0uafN0ISyG8=
github.com/go-enry/go-oniguruma v1.2.1 h1:k8aAMuJfMrqm/56SG2lV9Cfti6tC4x8673aHCcBk+eo=

View File

@ -42,7 +42,7 @@ func (jobs ActionJobList) LoadRuns(ctx context.Context, withRepo bool) error {
for _, r := range runs {
runsList = append(runsList, r)
}
return runsList.LoadRepos()
return runsList.LoadRepos(ctx)
}
return nil
}

View File

@ -52,9 +52,9 @@ func (runs RunList) LoadTriggerUser(ctx context.Context) error {
return nil
}
func (runs RunList) LoadRepos() error {
func (runs RunList) LoadRepos(ctx context.Context) error {
repoIDs := runs.GetRepoIDs()
repos, err := repo_model.GetRepositoriesMapByIDs(repoIDs)
repos, err := repo_model.GetRepositoriesMapByIDs(ctx, repoIDs)
if err != nil {
return err
}

View File

@ -49,9 +49,9 @@ func (schedules ScheduleList) LoadTriggerUser(ctx context.Context) error {
return nil
}
func (schedules ScheduleList) LoadRepos() error {
func (schedules ScheduleList) LoadRepos(ctx context.Context) error {
repoIDs := schedules.GetRepoIDs()
repos, err := repo_model.GetRepositoriesMapByIDs(repoIDs)
repos, err := repo_model.GetRepositoriesMapByIDs(ctx, repoIDs)
if err != nil {
return err
}

View File

@ -53,9 +53,9 @@ func (specs SpecList) GetRepoIDs() []int64 {
return ids.Values()
}
func (specs SpecList) LoadRepos() error {
func (specs SpecList) LoadRepos(ctx context.Context) error {
repoIDs := specs.GetRepoIDs()
repos, err := repo_model.GetRepositoriesMapByIDs(repoIDs)
repos, err := repo_model.GetRepositoriesMapByIDs(ctx, repoIDs)
if err != nil {
return err
}

View File

@ -102,7 +102,7 @@ func GetStatistic(ctx context.Context) (stats Statistic) {
stats.Counter.Follow, _ = e.Count(new(user_model.Follow))
stats.Counter.Mirror, _ = e.Count(new(repo_model.Mirror))
stats.Counter.Release, _ = e.Count(new(repo_model.Release))
stats.Counter.AuthSource = auth.CountSources()
stats.Counter.AuthSource = auth.CountSources(ctx)
stats.Counter.Webhook, _ = e.Count(new(webhook.Webhook))
stats.Counter.Milestone, _ = e.Count(new(issues_model.Milestone))
stats.Counter.Label, _ = e.Count(new(issues_model.Label))

View File

@ -91,7 +91,7 @@ func addKey(ctx context.Context, key *PublicKey) (err error) {
}
// AddPublicKey adds new public key to database and authorized_keys file.
func AddPublicKey(ownerID int64, name, content string, authSourceID int64) (*PublicKey, error) {
func AddPublicKey(ctx context.Context, ownerID int64, name, content string, authSourceID int64) (*PublicKey, error) {
log.Trace(content)
fingerprint, err := CalcFingerprint(content)
@ -99,7 +99,7 @@ func AddPublicKey(ownerID int64, name, content string, authSourceID int64) (*Pub
return nil, err
}
ctx, committer, err := db.TxContext(db.DefaultContext)
ctx, committer, err := db.TxContext(ctx)
if err != nil {
return nil, err
}
@ -136,9 +136,9 @@ func AddPublicKey(ownerID int64, name, content string, authSourceID int64) (*Pub
}
// GetPublicKeyByID returns public key by given ID.
func GetPublicKeyByID(keyID int64) (*PublicKey, error) {
func GetPublicKeyByID(ctx context.Context, keyID int64) (*PublicKey, error) {
key := new(PublicKey)
has, err := db.GetEngine(db.DefaultContext).
has, err := db.GetEngine(ctx).
ID(keyID).
Get(key)
if err != nil {
@ -180,7 +180,7 @@ func SearchPublicKeyByContentExact(ctx context.Context, content string) (*Public
}
// SearchPublicKey returns a list of public keys matching the provided arguments.
func SearchPublicKey(uid int64, fingerprint string) ([]*PublicKey, error) {
func SearchPublicKey(ctx context.Context, uid int64, fingerprint string) ([]*PublicKey, error) {
keys := make([]*PublicKey, 0, 5)
cond := builder.NewCond()
if uid != 0 {
@ -189,12 +189,12 @@ func SearchPublicKey(uid int64, fingerprint string) ([]*PublicKey, error) {
if fingerprint != "" {
cond = cond.And(builder.Eq{"fingerprint": fingerprint})
}
return keys, db.GetEngine(db.DefaultContext).Where(cond).Find(&keys)
return keys, db.GetEngine(ctx).Where(cond).Find(&keys)
}
// ListPublicKeys returns a list of public keys belongs to given user.
func ListPublicKeys(uid int64, listOptions db.ListOptions) ([]*PublicKey, error) {
sess := db.GetEngine(db.DefaultContext).Where("owner_id = ? AND type != ?", uid, KeyTypePrincipal)
func ListPublicKeys(ctx context.Context, uid int64, listOptions db.ListOptions) ([]*PublicKey, error) {
sess := db.GetEngine(ctx).Where("owner_id = ? AND type != ?", uid, KeyTypePrincipal)
if listOptions.Page != 0 {
sess = db.SetSessionPagination(sess, &listOptions)
@ -207,30 +207,30 @@ func ListPublicKeys(uid int64, listOptions db.ListOptions) ([]*PublicKey, error)
}
// CountPublicKeys count public keys a user has
func CountPublicKeys(userID int64) (int64, error) {
sess := db.GetEngine(db.DefaultContext).Where("owner_id = ? AND type != ?", userID, KeyTypePrincipal)
func CountPublicKeys(ctx context.Context, userID int64) (int64, error) {
sess := db.GetEngine(ctx).Where("owner_id = ? AND type != ?", userID, KeyTypePrincipal)
return sess.Count(&PublicKey{})
}
// ListPublicKeysBySource returns a list of synchronized public keys for a given user and login source.
func ListPublicKeysBySource(uid, authSourceID int64) ([]*PublicKey, error) {
func ListPublicKeysBySource(ctx context.Context, uid, authSourceID int64) ([]*PublicKey, error) {
keys := make([]*PublicKey, 0, 5)
return keys, db.GetEngine(db.DefaultContext).
return keys, db.GetEngine(ctx).
Where("owner_id = ? AND login_source_id = ?", uid, authSourceID).
Find(&keys)
}
// UpdatePublicKeyUpdated updates public key use time.
func UpdatePublicKeyUpdated(id int64) error {
func UpdatePublicKeyUpdated(ctx context.Context, id int64) error {
// Check if key exists before update as affected rows count is unreliable
// and will return 0 affected rows if two updates are made at the same time
if cnt, err := db.GetEngine(db.DefaultContext).ID(id).Count(&PublicKey{}); err != nil {
if cnt, err := db.GetEngine(ctx).ID(id).Count(&PublicKey{}); err != nil {
return err
} else if cnt != 1 {
return ErrKeyNotExist{id}
}
_, err := db.GetEngine(db.DefaultContext).ID(id).Cols("updated_unix").Update(&PublicKey{
_, err := db.GetEngine(ctx).ID(id).Cols("updated_unix").Update(&PublicKey{
UpdatedUnix: timeutil.TimeStampNow(),
})
if err != nil {
@ -250,7 +250,7 @@ func DeletePublicKeys(ctx context.Context, keyIDs ...int64) error {
}
// PublicKeysAreExternallyManaged returns whether the provided KeyID represents an externally managed Key
func PublicKeysAreExternallyManaged(keys []*PublicKey) ([]bool, error) {
func PublicKeysAreExternallyManaged(ctx context.Context, keys []*PublicKey) ([]bool, error) {
sources := make([]*auth.Source, 0, 5)
externals := make([]bool, len(keys))
keyloop:
@ -272,7 +272,7 @@ keyloop:
if source == nil {
var err error
source, err = auth.GetSourceByID(key.LoginSourceID)
source, err = auth.GetSourceByID(ctx, key.LoginSourceID)
if err != nil {
if auth.IsErrSourceNotExist(err) {
externals[i] = false
@ -295,15 +295,15 @@ keyloop:
}
// PublicKeyIsExternallyManaged returns whether the provided KeyID represents an externally managed Key
func PublicKeyIsExternallyManaged(id int64) (bool, error) {
key, err := GetPublicKeyByID(id)
func PublicKeyIsExternallyManaged(ctx context.Context, id int64) (bool, error) {
key, err := GetPublicKeyByID(ctx, id)
if err != nil {
return false, err
}
if key.LoginSourceID == 0 {
return false, nil
}
source, err := auth.GetSourceByID(key.LoginSourceID)
source, err := auth.GetSourceByID(ctx, key.LoginSourceID)
if err != nil {
if auth.IsErrSourceNotExist(err) {
return false, nil
@ -318,9 +318,9 @@ func PublicKeyIsExternallyManaged(id int64) (bool, error) {
}
// deleteKeysMarkedForDeletion returns true if ssh keys needs update
func deleteKeysMarkedForDeletion(keys []string) (bool, error) {
func deleteKeysMarkedForDeletion(ctx context.Context, keys []string) (bool, error) {
// Start session
ctx, committer, err := db.TxContext(db.DefaultContext)
ctx, committer, err := db.TxContext(ctx)
if err != nil {
return false, err
}
@ -349,7 +349,7 @@ func deleteKeysMarkedForDeletion(keys []string) (bool, error) {
}
// AddPublicKeysBySource add a users public keys. Returns true if there are changes.
func AddPublicKeysBySource(usr *user_model.User, s *auth.Source, sshPublicKeys []string) bool {
func AddPublicKeysBySource(ctx context.Context, usr *user_model.User, s *auth.Source, sshPublicKeys []string) bool {
var sshKeysNeedUpdate bool
for _, sshKey := range sshPublicKeys {
var err error
@ -368,7 +368,7 @@ func AddPublicKeysBySource(usr *user_model.User, s *auth.Source, sshPublicKeys [
marshalled = marshalled[:len(marshalled)-1]
sshKeyName := fmt.Sprintf("%s-%s", s.Name, ssh.FingerprintSHA256(out))
if _, err := AddPublicKey(usr.ID, sshKeyName, marshalled, s.ID); err != nil {
if _, err := AddPublicKey(ctx, usr.ID, sshKeyName, marshalled, s.ID); err != nil {
if IsErrKeyAlreadyExist(err) {
log.Trace("AddPublicKeysBySource[%s]: Public SSH Key %s already exists for user", sshKeyName, usr.Name)
} else {
@ -387,14 +387,14 @@ func AddPublicKeysBySource(usr *user_model.User, s *auth.Source, sshPublicKeys [
}
// SynchronizePublicKeys updates a users public keys. Returns true if there are changes.
func SynchronizePublicKeys(usr *user_model.User, s *auth.Source, sshPublicKeys []string) bool {
func SynchronizePublicKeys(ctx context.Context, usr *user_model.User, s *auth.Source, sshPublicKeys []string) bool {
var sshKeysNeedUpdate bool
log.Trace("synchronizePublicKeys[%s]: Handling Public SSH Key synchronization for user %s", s.Name, usr.Name)
// Get Public Keys from DB with current LDAP source
var giteaKeys []string
keys, err := ListPublicKeysBySource(usr.ID, s.ID)
keys, err := ListPublicKeysBySource(ctx, usr.ID, s.ID)
if err != nil {
log.Error("synchronizePublicKeys[%s]: Error listing Public SSH Keys for user %s: %v", s.Name, usr.Name, err)
}
@ -429,7 +429,7 @@ func SynchronizePublicKeys(usr *user_model.User, s *auth.Source, sshPublicKeys [
newKeys = append(newKeys, key)
}
}
if AddPublicKeysBySource(usr, s, newKeys) {
if AddPublicKeysBySource(ctx, usr, s, newKeys) {
sshKeysNeedUpdate = true
}
@ -443,7 +443,7 @@ func SynchronizePublicKeys(usr *user_model.User, s *auth.Source, sshPublicKeys [
}
// Delete keys from DB that no longer exist in the source
needUpd, err := deleteKeysMarkedForDeletion(giteaKeysToDelete)
needUpd, err := deleteKeysMarkedForDeletion(ctx, giteaKeysToDelete)
if err != nil {
log.Error("synchronizePublicKeys[%s]: Error deleting Public Keys marked for deletion for user %s: %v", s.Name, usr.Name, err)
}

View File

@ -21,7 +21,7 @@ import (
func ParseCommitWithSSHSignature(ctx context.Context, c *git.Commit, committer *user_model.User) *CommitVerification {
// Now try to associate the signature with the committer, if present
if committer.ID != 0 {
keys, err := ListPublicKeys(committer.ID, db.ListOptions{})
keys, err := ListPublicKeys(ctx, committer.ID, db.ListOptions{})
if err != nil { // Skipping failed to get ssh keys of user
log.Error("ListPublicKeys: %v", err)
return &CommitVerification{

View File

@ -48,8 +48,8 @@ func (key *DeployKey) AfterLoad() {
}
// GetContent gets associated public key content.
func (key *DeployKey) GetContent() error {
pkey, err := GetPublicKeyByID(key.KeyID)
func (key *DeployKey) GetContent(ctx context.Context) error {
pkey, err := GetPublicKeyByID(ctx, key.KeyID)
if err != nil {
return err
}

View File

@ -81,7 +81,7 @@ func CalcFingerprint(publicKeyContent string) (string, error) {
fnName, fp string
err error
)
if setting.SSH.StartBuiltinServer {
if len(setting.SSH.KeygenPath) == 0 {
fnName = "calcFingerprintNative"
fp, err = calcFingerprintNative(publicKeyContent)
} else {

View File

@ -51,7 +51,7 @@ func Test_SSHParsePublicKey(t *testing.T) {
if err != nil {
// Some servers do not support ecdsa format.
if !strings.Contains(err.Error(), "line 1 too long:") {
assert.Fail(t, "%v", err)
assert.FailNow(t, "%v", err)
}
}
assert.Equal(t, tc.keyType, keyTypeK)
@ -60,7 +60,7 @@ func Test_SSHParsePublicKey(t *testing.T) {
t.Run("SSHParseKeyNative", func(t *testing.T) {
keyTypeK, lengthK, err := SSHNativeParsePublicKey(tc.content)
if err != nil {
assert.Fail(t, "%v", err)
assert.FailNow(t, "%v", err)
}
assert.Equal(t, tc.keyType, keyTypeK)
assert.EqualValues(t, tc.length, lengthK)

View File

@ -66,6 +66,11 @@ func BuiltinApplications() map[string]*BuiltinOAuth2Application {
DisplayName: "Git Credential Manager",
RedirectURIs: []string{"http://127.0.0.1", "https://127.0.0.1"},
}
m["d57cb8c4-630c-4168-8324-ec79935e18d4"] = &BuiltinOAuth2Application{
ConfigName: "tea",
DisplayName: "tea",
RedirectURIs: []string{"http://127.0.0.1", "https://127.0.0.1"},
}
return m
}

View File

@ -5,6 +5,7 @@
package auth
import (
"context"
"fmt"
"reflect"
@ -199,8 +200,8 @@ func (source *Source) SkipVerify() bool {
// CreateSource inserts a AuthSource in the DB if not already
// existing with the given name.
func CreateSource(source *Source) error {
has, err := db.GetEngine(db.DefaultContext).Where("name=?", source.Name).Exist(new(Source))
func CreateSource(ctx context.Context, source *Source) error {
has, err := db.GetEngine(ctx).Where("name=?", source.Name).Exist(new(Source))
if err != nil {
return err
} else if has {
@ -211,7 +212,7 @@ func CreateSource(source *Source) error {
source.IsSyncEnabled = false
}
_, err = db.GetEngine(db.DefaultContext).Insert(source)
_, err = db.GetEngine(ctx).Insert(source)
if err != nil {
return err
}
@ -232,7 +233,7 @@ func CreateSource(source *Source) error {
err = registerableSource.RegisterSource()
if err != nil {
// remove the AuthSource in case of errors while registering configuration
if _, err := db.GetEngine(db.DefaultContext).Delete(source); err != nil {
if _, err := db.GetEngine(ctx).Delete(source); err != nil {
log.Error("CreateSource: Error while wrapOpenIDConnectInitializeError: %v", err)
}
}
@ -240,33 +241,33 @@ func CreateSource(source *Source) error {
}
// Sources returns a slice of all login sources found in DB.
func Sources() ([]*Source, error) {
func Sources(ctx context.Context) ([]*Source, error) {
auths := make([]*Source, 0, 6)
return auths, db.GetEngine(db.DefaultContext).Find(&auths)
return auths, db.GetEngine(ctx).Find(&auths)
}
// SourcesByType returns all sources of the specified type
func SourcesByType(loginType Type) ([]*Source, error) {
func SourcesByType(ctx context.Context, loginType Type) ([]*Source, error) {
sources := make([]*Source, 0, 1)
if err := db.GetEngine(db.DefaultContext).Where("type = ?", loginType).Find(&sources); err != nil {
if err := db.GetEngine(ctx).Where("type = ?", loginType).Find(&sources); err != nil {
return nil, err
}
return sources, nil
}
// AllActiveSources returns all active sources
func AllActiveSources() ([]*Source, error) {
func AllActiveSources(ctx context.Context) ([]*Source, error) {
sources := make([]*Source, 0, 5)
if err := db.GetEngine(db.DefaultContext).Where("is_active = ?", true).Find(&sources); err != nil {
if err := db.GetEngine(ctx).Where("is_active = ?", true).Find(&sources); err != nil {
return nil, err
}
return sources, nil
}
// ActiveSources returns all active sources of the specified type
func ActiveSources(tp Type) ([]*Source, error) {
func ActiveSources(ctx context.Context, tp Type) ([]*Source, error) {
sources := make([]*Source, 0, 1)
if err := db.GetEngine(db.DefaultContext).Where("is_active = ? and type = ?", true, tp).Find(&sources); err != nil {
if err := db.GetEngine(ctx).Where("is_active = ? and type = ?", true, tp).Find(&sources); err != nil {
return nil, err
}
return sources, nil
@ -274,11 +275,11 @@ func ActiveSources(tp Type) ([]*Source, error) {
// IsSSPIEnabled returns true if there is at least one activated login
// source of type LoginSSPI
func IsSSPIEnabled() bool {
func IsSSPIEnabled(ctx context.Context) bool {
if !db.HasEngine {
return false
}
sources, err := ActiveSources(SSPI)
sources, err := ActiveSources(ctx, SSPI)
if err != nil {
log.Error("ActiveSources: %v", err)
return false
@ -287,7 +288,7 @@ func IsSSPIEnabled() bool {
}
// GetSourceByID returns login source by given ID.
func GetSourceByID(id int64) (*Source, error) {
func GetSourceByID(ctx context.Context, id int64) (*Source, error) {
source := new(Source)
if id == 0 {
source.Cfg = registeredConfigs[NoType]()
@ -297,7 +298,7 @@ func GetSourceByID(id int64) (*Source, error) {
return source, nil
}
has, err := db.GetEngine(db.DefaultContext).ID(id).Get(source)
has, err := db.GetEngine(ctx).ID(id).Get(source)
if err != nil {
return nil, err
} else if !has {
@ -307,24 +308,24 @@ func GetSourceByID(id int64) (*Source, error) {
}
// UpdateSource updates a Source record in DB.
func UpdateSource(source *Source) error {
func UpdateSource(ctx context.Context, source *Source) error {
var originalSource *Source
if source.IsOAuth2() {
// keep track of the original values so we can restore in case of errors while registering OAuth2 providers
var err error
if originalSource, err = GetSourceByID(source.ID); err != nil {
if originalSource, err = GetSourceByID(ctx, source.ID); err != nil {
return err
}
}
has, err := db.GetEngine(db.DefaultContext).Where("name=? AND id!=?", source.Name, source.ID).Exist(new(Source))
has, err := db.GetEngine(ctx).Where("name=? AND id!=?", source.Name, source.ID).Exist(new(Source))
if err != nil {
return err
} else if has {
return ErrSourceAlreadyExist{source.Name}
}
_, err = db.GetEngine(db.DefaultContext).ID(source.ID).AllCols().Update(source)
_, err = db.GetEngine(ctx).ID(source.ID).AllCols().Update(source)
if err != nil {
return err
}
@ -345,7 +346,7 @@ func UpdateSource(source *Source) error {
err = registerableSource.RegisterSource()
if err != nil {
// restore original values since we cannot update the provider it self
if _, err := db.GetEngine(db.DefaultContext).ID(source.ID).AllCols().Update(originalSource); err != nil {
if _, err := db.GetEngine(ctx).ID(source.ID).AllCols().Update(originalSource); err != nil {
log.Error("UpdateSource: Error while wrapOpenIDConnectInitializeError: %v", err)
}
}
@ -353,8 +354,8 @@ func UpdateSource(source *Source) error {
}
// CountSources returns number of login sources.
func CountSources() int64 {
count, _ := db.GetEngine(db.DefaultContext).Count(new(Source))
func CountSources(ctx context.Context) int64 {
count, _ := db.GetEngine(ctx).Count(new(Source))
return count
}

View File

@ -42,7 +42,7 @@ func TestDumpAuthSource(t *testing.T) {
auth_model.RegisterTypeConfig(auth_model.OAuth2, new(TestSource))
auth_model.CreateSource(&auth_model.Source{
auth_model.CreateSource(db.DefaultContext, &auth_model.Source{
Type: auth_model.OAuth2,
Name: "TestSource",
IsActive: false,

View File

@ -31,6 +31,10 @@ func TestGetCommitStatuses(t *testing.T) {
assert.Equal(t, structs.CommitStatusPending, statuses[0].State)
assert.Equal(t, "https://try.gitea.io/api/v1/repos/user2/repo1/statuses/1234123412341234123412341234123412341234", statuses[0].APIURL(db.DefaultContext))
assert.Equal(t, "cov/awesomeness", statuses[1].Context)
assert.Equal(t, structs.CommitStatusWarning, statuses[1].State)
assert.Equal(t, "https://try.gitea.io/api/v1/repos/user2/repo1/statuses/1234123412341234123412341234123412341234", statuses[1].APIURL(db.DefaultContext))
assert.Equal(t, "cov/awesomeness", statuses[2].Context)
assert.Equal(t, structs.CommitStatusSuccess, statuses[2].State)
assert.Equal(t, "https://try.gitea.io/api/v1/repos/user2/repo1/statuses/1234123412341234123412341234123412341234", statuses[2].APIURL(db.DefaultContext))

View File

@ -111,7 +111,7 @@ func findCodeComments(ctx context.Context, opts FindCommentsOptions, issue *Issu
if comment.RenderedContent, err = markdown.RenderString(&markup.RenderContext{
Ctx: ctx,
URLPrefix: issue.Repo.Link(),
Metas: issue.Repo.ComposeMetas(),
Metas: issue.Repo.ComposeMetas(ctx),
}, comment.Content); err != nil {
return nil, err
}

View File

@ -127,8 +127,8 @@ const (
)
// CreateIssueDependency creates a new dependency for an issue
func CreateIssueDependency(user *user_model.User, issue, dep *Issue) error {
ctx, committer, err := db.TxContext(db.DefaultContext)
func CreateIssueDependency(ctx context.Context, user *user_model.User, issue, dep *Issue) error {
ctx, committer, err := db.TxContext(ctx)
if err != nil {
return err
}
@ -168,8 +168,8 @@ func CreateIssueDependency(user *user_model.User, issue, dep *Issue) error {
}
// RemoveIssueDependency removes a dependency from an issue
func RemoveIssueDependency(user *user_model.User, issue, dep *Issue, depType DependencyType) (err error) {
ctx, committer, err := db.TxContext(db.DefaultContext)
func RemoveIssueDependency(ctx context.Context, user *user_model.User, issue, dep *Issue, depType DependencyType) (err error) {
ctx, committer, err := db.TxContext(ctx)
if err != nil {
return err
}

View File

@ -28,16 +28,16 @@ func TestCreateIssueDependency(t *testing.T) {
assert.NoError(t, err)
// Create a dependency and check if it was successful
err = issues_model.CreateIssueDependency(user1, issue1, issue2)
err = issues_model.CreateIssueDependency(db.DefaultContext, user1, issue1, issue2)
assert.NoError(t, err)
// Do it again to see if it will check if the dependency already exists
err = issues_model.CreateIssueDependency(user1, issue1, issue2)
err = issues_model.CreateIssueDependency(db.DefaultContext, user1, issue1, issue2)
assert.Error(t, err)
assert.True(t, issues_model.IsErrDependencyExists(err))
// Check for circular dependencies
err = issues_model.CreateIssueDependency(user1, issue2, issue1)
err = issues_model.CreateIssueDependency(db.DefaultContext, user1, issue2, issue1)
assert.Error(t, err)
assert.True(t, issues_model.IsErrCircularDependency(err))
@ -57,6 +57,6 @@ func TestCreateIssueDependency(t *testing.T) {
assert.True(t, left)
// Test removing the dependency
err = issues_model.RemoveIssueDependency(user1, issue1, issue2, issues_model.DependencyTypeBlockedBy)
err = issues_model.RemoveIssueDependency(db.DefaultContext, user1, issue1, issue2, issues_model.DependencyTypeBlockedBy)
assert.NoError(t, err)
}

View File

@ -83,12 +83,12 @@ func RemoveDuplicateExclusiveIssueLabels(ctx context.Context, issue *Issue, labe
}
// NewIssueLabel creates a new issue-label relation.
func NewIssueLabel(issue *Issue, label *Label, doer *user_model.User) (err error) {
if HasIssueLabel(db.DefaultContext, issue.ID, label.ID) {
func NewIssueLabel(ctx context.Context, issue *Issue, label *Label, doer *user_model.User) (err error) {
if HasIssueLabel(ctx, issue.ID, label.ID) {
return nil
}
ctx, committer, err := db.TxContext(db.DefaultContext)
ctx, committer, err := db.TxContext(ctx)
if err != nil {
return err
}
@ -149,8 +149,8 @@ func newIssueLabels(ctx context.Context, issue *Issue, labels []*Label, doer *us
}
// NewIssueLabels creates a list of issue-label relations.
func NewIssueLabels(issue *Issue, labels []*Label, doer *user_model.User) (err error) {
ctx, committer, err := db.TxContext(db.DefaultContext)
func NewIssueLabels(ctx context.Context, issue *Issue, labels []*Label, doer *user_model.User) (err error) {
ctx, committer, err := db.TxContext(ctx)
if err != nil {
return err
}
@ -359,8 +359,8 @@ func clearIssueLabels(ctx context.Context, issue *Issue, doer *user_model.User)
// ClearIssueLabels removes all issue labels as the given user.
// Triggers appropriate WebHooks, if any.
func ClearIssueLabels(issue *Issue, doer *user_model.User) (err error) {
ctx, committer, err := db.TxContext(db.DefaultContext)
func ClearIssueLabels(ctx context.Context, issue *Issue, doer *user_model.User) (err error) {
ctx, committer, err := db.TxContext(ctx)
if err != nil {
return err
}
@ -432,8 +432,8 @@ func RemoveDuplicateExclusiveLabels(labels []*Label) []*Label {
// ReplaceIssueLabels removes all current labels and add new labels to the issue.
// Triggers appropriate WebHooks, if any.
func ReplaceIssueLabels(issue *Issue, labels []*Label, doer *user_model.User) (err error) {
ctx, committer, err := db.TxContext(db.DefaultContext)
func ReplaceIssueLabels(ctx context.Context, issue *Issue, labels []*Label, doer *user_model.User) (err error) {
ctx, committer, err := db.TxContext(ctx)
if err != nil {
return err
}

View File

@ -6,6 +6,7 @@ package issues_test
import (
"testing"
"code.gitea.io/gitea/models/db"
issues_model "code.gitea.io/gitea/models/issues"
"code.gitea.io/gitea/models/unittest"
user_model "code.gitea.io/gitea/models/user"
@ -21,7 +22,7 @@ func TestNewIssueLabelsScope(t *testing.T) {
label2 := unittest.AssertExistsAndLoadBean(t, &issues_model.Label{ID: 8})
doer := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: 2})
assert.NoError(t, issues_model.NewIssueLabels(issue, []*issues_model.Label{label1, label2}, doer))
assert.NoError(t, issues_model.NewIssueLabels(db.DefaultContext, issue, []*issues_model.Label{label1, label2}, doer))
assert.Len(t, issue.Labels, 1)
assert.Equal(t, label2.ID, issue.Labels[0].ID)

View File

@ -4,6 +4,8 @@
package issues
import (
"context"
"code.gitea.io/gitea/models/db"
user_model "code.gitea.io/gitea/models/user"
)
@ -17,16 +19,16 @@ type IssueLockOptions struct {
// LockIssue locks an issue. This would limit commenting abilities to
// users with write access to the repo
func LockIssue(opts *IssueLockOptions) error {
return updateIssueLock(opts, true)
func LockIssue(ctx context.Context, opts *IssueLockOptions) error {
return updateIssueLock(ctx, opts, true)
}
// UnlockIssue unlocks a previously locked issue.
func UnlockIssue(opts *IssueLockOptions) error {
return updateIssueLock(opts, false)
func UnlockIssue(ctx context.Context, opts *IssueLockOptions) error {
return updateIssueLock(ctx, opts, false)
}
func updateIssueLock(opts *IssueLockOptions, lock bool) error {
func updateIssueLock(ctx context.Context, opts *IssueLockOptions, lock bool) error {
if opts.Issue.IsLocked == lock {
return nil
}
@ -39,7 +41,7 @@ func updateIssueLock(opts *IssueLockOptions, lock bool) error {
commentType = CommentTypeUnlock
}
ctx, committer, err := db.TxContext(db.DefaultContext)
ctx, committer, err := db.TxContext(ctx)
if err != nil {
return err
}

View File

@ -38,11 +38,7 @@ func (issue *Issue) projectID(ctx context.Context) int64 {
}
// ProjectBoardID return project board id if issue was assigned to one
func (issue *Issue) ProjectBoardID() int64 {
return issue.projectBoardID(db.DefaultContext)
}
func (issue *Issue) projectBoardID(ctx context.Context) int64 {
func (issue *Issue) ProjectBoardID(ctx context.Context) int64 {
var ip project_model.ProjectIssue
has, err := db.GetEngine(ctx).Where("issue_id=?", issue.ID).Get(&ip)
if err != nil || !has {
@ -100,8 +96,8 @@ func LoadIssuesFromBoardList(ctx context.Context, bs project_model.BoardList) (m
}
// ChangeProjectAssign changes the project associated with an issue
func ChangeProjectAssign(issue *Issue, doer *user_model.User, newProjectID int64) error {
ctx, committer, err := db.TxContext(db.DefaultContext)
func ChangeProjectAssign(ctx context.Context, issue *Issue, doer *user_model.User, newProjectID int64) error {
ctx, committer, err := db.TxContext(ctx)
if err != nil {
return err
}
@ -156,8 +152,8 @@ func addUpdateIssueProject(ctx context.Context, issue *Issue, doer *user_model.U
}
// MoveIssueAcrossProjectBoards move a card from one board to another
func MoveIssueAcrossProjectBoards(issue *Issue, board *project_model.Board) error {
ctx, committer, err := db.TxContext(db.DefaultContext)
func MoveIssueAcrossProjectBoards(ctx context.Context, issue *Issue, board *project_model.Board) error {
ctx, committer, err := db.TxContext(ctx)
if err != nil {
return err
}

View File

@ -444,9 +444,9 @@ func applySubscribedCondition(sess *xorm.Session, subscriberID int64) *xorm.Sess
}
// GetRepoIDsForIssuesOptions find all repo ids for the given options
func GetRepoIDsForIssuesOptions(opts *IssuesOptions, user *user_model.User) ([]int64, error) {
func GetRepoIDsForIssuesOptions(ctx context.Context, opts *IssuesOptions, user *user_model.User) ([]int64, error) {
repoIDs := make([]int64, 0, 5)
e := db.GetEngine(db.DefaultContext)
e := db.GetEngine(ctx)
sess := e.Join("INNER", "repository", "`issue`.repo_id = `repository`.id")

View File

@ -34,7 +34,7 @@ func TestIssue_ReplaceLabels(t *testing.T) {
for i, labelID := range labelIDs {
labels[i] = unittest.AssertExistsAndLoadBean(t, &issues_model.Label{ID: labelID, RepoID: repo.ID})
}
assert.NoError(t, issues_model.ReplaceIssueLabels(issue, labels, doer))
assert.NoError(t, issues_model.ReplaceIssueLabels(db.DefaultContext, issue, labels, doer))
unittest.AssertCount(t, &issues_model.IssueLabel{IssueID: issueID}, len(expectedLabelIDs))
for _, labelID := range expectedLabelIDs {
unittest.AssertExistsAndLoadBean(t, &issues_model.IssueLabel{IssueID: issueID, LabelID: labelID})
@ -122,7 +122,7 @@ func TestIssue_ClearLabels(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
issue := unittest.AssertExistsAndLoadBean(t, &issues_model.Issue{ID: test.issueID})
doer := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: test.doerID})
assert.NoError(t, issues_model.ClearIssueLabels(issue, doer))
assert.NoError(t, issues_model.ClearIssueLabels(db.DefaultContext, issue, doer))
unittest.AssertNotExistsBean(t, &issues_model.IssueLabel{IssueID: test.issueID})
}
}
@ -230,7 +230,7 @@ func TestGetRepoIDsForIssuesOptions(t *testing.T) {
[]int64{1, 2},
},
} {
repoIDs, err := issues_model.GetRepoIDsForIssuesOptions(&test.Opts, user)
repoIDs, err := issues_model.GetRepoIDsForIssuesOptions(db.DefaultContext, &test.Opts, user)
assert.NoError(t, err)
if assert.Len(t, repoIDs, len(test.ExpectedRepoIDs)) {
for i, repoID := range repoIDs {

View File

@ -307,7 +307,7 @@ func TestNewIssueLabel(t *testing.T) {
// add new IssueLabel
prevNumIssues := label.NumIssues
assert.NoError(t, issues_model.NewIssueLabel(issue, label, doer))
assert.NoError(t, issues_model.NewIssueLabel(db.DefaultContext, issue, label, doer))
unittest.AssertExistsAndLoadBean(t, &issues_model.IssueLabel{IssueID: issue.ID, LabelID: label.ID})
unittest.AssertExistsAndLoadBean(t, &issues_model.Comment{
Type: issues_model.CommentTypeLabel,
@ -320,7 +320,7 @@ func TestNewIssueLabel(t *testing.T) {
assert.EqualValues(t, prevNumIssues+1, label.NumIssues)
// re-add existing IssueLabel
assert.NoError(t, issues_model.NewIssueLabel(issue, label, doer))
assert.NoError(t, issues_model.NewIssueLabel(db.DefaultContext, issue, label, doer))
unittest.CheckConsistencyFor(t, &issues_model.Issue{}, &issues_model.Label{})
}
@ -334,19 +334,19 @@ func TestNewIssueExclusiveLabel(t *testing.T) {
exclusiveLabelB := unittest.AssertExistsAndLoadBean(t, &issues_model.Label{ID: 8})
// coexisting regular and exclusive label
assert.NoError(t, issues_model.NewIssueLabel(issue, otherLabel, doer))
assert.NoError(t, issues_model.NewIssueLabel(issue, exclusiveLabelA, doer))
assert.NoError(t, issues_model.NewIssueLabel(db.DefaultContext, issue, otherLabel, doer))
assert.NoError(t, issues_model.NewIssueLabel(db.DefaultContext, issue, exclusiveLabelA, doer))
unittest.AssertExistsAndLoadBean(t, &issues_model.IssueLabel{IssueID: issue.ID, LabelID: otherLabel.ID})
unittest.AssertExistsAndLoadBean(t, &issues_model.IssueLabel{IssueID: issue.ID, LabelID: exclusiveLabelA.ID})
// exclusive label replaces existing one
assert.NoError(t, issues_model.NewIssueLabel(issue, exclusiveLabelB, doer))
assert.NoError(t, issues_model.NewIssueLabel(db.DefaultContext, issue, exclusiveLabelB, doer))
unittest.AssertExistsAndLoadBean(t, &issues_model.IssueLabel{IssueID: issue.ID, LabelID: otherLabel.ID})
unittest.AssertExistsAndLoadBean(t, &issues_model.IssueLabel{IssueID: issue.ID, LabelID: exclusiveLabelB.ID})
unittest.AssertNotExistsBean(t, &issues_model.IssueLabel{IssueID: issue.ID, LabelID: exclusiveLabelA.ID})
// exclusive label replaces existing one again
assert.NoError(t, issues_model.NewIssueLabel(issue, exclusiveLabelA, doer))
assert.NoError(t, issues_model.NewIssueLabel(db.DefaultContext, issue, exclusiveLabelA, doer))
unittest.AssertExistsAndLoadBean(t, &issues_model.IssueLabel{IssueID: issue.ID, LabelID: otherLabel.ID})
unittest.AssertExistsAndLoadBean(t, &issues_model.IssueLabel{IssueID: issue.ID, LabelID: exclusiveLabelA.ID})
unittest.AssertNotExistsBean(t, &issues_model.IssueLabel{IssueID: issue.ID, LabelID: exclusiveLabelB.ID})
@ -359,7 +359,7 @@ func TestNewIssueLabels(t *testing.T) {
issue := unittest.AssertExistsAndLoadBean(t, &issues_model.Issue{ID: 5})
doer := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: 2})
assert.NoError(t, issues_model.NewIssueLabels(issue, []*issues_model.Label{label1, label2}, doer))
assert.NoError(t, issues_model.NewIssueLabels(db.DefaultContext, issue, []*issues_model.Label{label1, label2}, doer))
unittest.AssertExistsAndLoadBean(t, &issues_model.IssueLabel{IssueID: issue.ID, LabelID: label1.ID})
unittest.AssertExistsAndLoadBean(t, &issues_model.Comment{
Type: issues_model.CommentTypeLabel,
@ -377,7 +377,7 @@ func TestNewIssueLabels(t *testing.T) {
assert.EqualValues(t, 1, label2.NumClosedIssues)
// corner case: test empty slice
assert.NoError(t, issues_model.NewIssueLabels(issue, []*issues_model.Label{}, doer))
assert.NoError(t, issues_model.NewIssueLabels(db.DefaultContext, issue, []*issues_model.Label{}, doer))
unittest.CheckConsistencyFor(t, &issues_model.Issue{}, &issues_model.Label{})
}

View File

@ -58,8 +58,8 @@ func (opts GetMilestonesOption) toCond() builder.Cond {
}
// GetMilestones returns milestones filtered by GetMilestonesOption's
func GetMilestones(opts GetMilestonesOption) (MilestoneList, int64, error) {
sess := db.GetEngine(db.DefaultContext).Where(opts.toCond())
func GetMilestones(ctx context.Context, opts GetMilestonesOption) (MilestoneList, int64, error) {
sess := db.GetEngine(ctx).Where(opts.toCond())
if opts.Page != 0 {
sess = db.SetSessionPagination(sess, &opts)

View File

@ -40,7 +40,7 @@ func TestGetMilestonesByRepoID(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
test := func(repoID int64, state api.StateType) {
repo := unittest.AssertExistsAndLoadBean(t, &repo_model.Repository{ID: repoID})
milestones, _, err := issues_model.GetMilestones(issues_model.GetMilestonesOption{
milestones, _, err := issues_model.GetMilestones(db.DefaultContext, issues_model.GetMilestonesOption{
RepoID: repo.ID,
State: state,
})
@ -77,7 +77,7 @@ func TestGetMilestonesByRepoID(t *testing.T) {
test(3, api.StateClosed)
test(3, api.StateAll)
milestones, _, err := issues_model.GetMilestones(issues_model.GetMilestonesOption{
milestones, _, err := issues_model.GetMilestones(db.DefaultContext, issues_model.GetMilestonesOption{
RepoID: unittest.NonexistentID,
State: api.StateOpen,
})
@ -90,7 +90,7 @@ func TestGetMilestones(t *testing.T) {
repo := unittest.AssertExistsAndLoadBean(t, &repo_model.Repository{ID: 1})
test := func(sortType string, sortCond func(*issues_model.Milestone) int) {
for _, page := range []int{0, 1} {
milestones, _, err := issues_model.GetMilestones(issues_model.GetMilestonesOption{
milestones, _, err := issues_model.GetMilestones(db.DefaultContext, issues_model.GetMilestonesOption{
ListOptions: db.ListOptions{
Page: page,
PageSize: setting.UI.IssuePagingNum,
@ -107,7 +107,7 @@ func TestGetMilestones(t *testing.T) {
}
assert.True(t, sort.IntsAreSorted(values))
milestones, _, err = issues_model.GetMilestones(issues_model.GetMilestonesOption{
milestones, _, err = issues_model.GetMilestones(db.DefaultContext, issues_model.GetMilestonesOption{
ListOptions: db.ListOptions{
Page: page,
PageSize: setting.UI.IssuePagingNum,

View File

@ -378,9 +378,9 @@ func (pr *PullRequest) GetApprovalCounts(ctx context.Context) ([]*ReviewCount, e
}
// GetApprovers returns the approvers of the pull request
func (pr *PullRequest) GetApprovers() string {
func (pr *PullRequest) GetApprovers(ctx context.Context) string {
stringBuilder := strings.Builder{}
if err := pr.getReviewedByLines(&stringBuilder); err != nil {
if err := pr.getReviewedByLines(ctx, &stringBuilder); err != nil {
log.Error("Unable to getReviewedByLines: Error: %v", err)
return ""
}
@ -388,14 +388,14 @@ func (pr *PullRequest) GetApprovers() string {
return stringBuilder.String()
}
func (pr *PullRequest) getReviewedByLines(writer io.Writer) error {
func (pr *PullRequest) getReviewedByLines(ctx context.Context, writer io.Writer) error {
maxReviewers := setting.Repository.PullRequest.DefaultMergeMessageMaxApprovers
if maxReviewers == 0 {
return nil
}
ctx, committer, err := db.TxContext(db.DefaultContext)
ctx, committer, err := db.TxContext(ctx)
if err != nil {
return err
}
@ -594,9 +594,9 @@ func GetUnmergedPullRequest(ctx context.Context, headRepoID, baseRepoID int64, h
// GetLatestPullRequestByHeadInfo returns the latest pull request (regardless of its status)
// by given head information (repo and branch).
func GetLatestPullRequestByHeadInfo(repoID int64, branch string) (*PullRequest, error) {
func GetLatestPullRequestByHeadInfo(ctx context.Context, repoID int64, branch string) (*PullRequest, error) {
pr := new(PullRequest)
has, err := db.GetEngine(db.DefaultContext).
has, err := db.GetEngine(ctx).
Where("head_repo_id = ? AND head_branch = ? AND flow = ?", repoID, branch, PullRequestFlowGithub).
OrderBy("id DESC").
Get(pr)
@ -646,9 +646,9 @@ func GetPullRequestByID(ctx context.Context, id int64) (*PullRequest, error) {
}
// GetPullRequestByIssueIDWithNoAttributes returns pull request with no attributes loaded by given issue ID.
func GetPullRequestByIssueIDWithNoAttributes(issueID int64) (*PullRequest, error) {
func GetPullRequestByIssueIDWithNoAttributes(ctx context.Context, issueID int64) (*PullRequest, error) {
var pr PullRequest
has, err := db.GetEngine(db.DefaultContext).Where("issue_id = ?", issueID).Get(&pr)
has, err := db.GetEngine(ctx).Where("issue_id = ?", issueID).Get(&pr)
if err != nil {
return nil, err
}
@ -687,14 +687,14 @@ func GetAllUnmergedAgitPullRequestByPoster(ctx context.Context, uid int64) ([]*P
}
// Update updates all fields of pull request.
func (pr *PullRequest) Update() error {
_, err := db.GetEngine(db.DefaultContext).ID(pr.ID).AllCols().Update(pr)
func (pr *PullRequest) Update(ctx context.Context) error {
_, err := db.GetEngine(ctx).ID(pr.ID).AllCols().Update(pr)
return err
}
// UpdateCols updates specific fields of pull request.
func (pr *PullRequest) UpdateCols(cols ...string) error {
_, err := db.GetEngine(db.DefaultContext).ID(pr.ID).Cols(cols...).Update(pr)
func (pr *PullRequest) UpdateCols(ctx context.Context, cols ...string) error {
_, err := db.GetEngine(ctx).ID(pr.ID).Cols(cols...).Update(pr)
return err
}
@ -706,8 +706,8 @@ func (pr *PullRequest) UpdateColsIfNotMerged(ctx context.Context, cols ...string
// IsWorkInProgress determine if the Pull Request is a Work In Progress by its title
// Issue must be set before this method can be called.
func (pr *PullRequest) IsWorkInProgress() bool {
if err := pr.LoadIssue(db.DefaultContext); err != nil {
func (pr *PullRequest) IsWorkInProgress(ctx context.Context) bool {
if err := pr.LoadIssue(ctx); err != nil {
log.Error("LoadIssue: %v", err)
return false
}
@ -774,8 +774,8 @@ func GetPullRequestsByHeadBranch(ctx context.Context, headBranch string, headRep
}
// GetBaseBranchLink returns the relative URL of the base branch
func (pr *PullRequest) GetBaseBranchLink() string {
if err := pr.LoadBaseRepo(db.DefaultContext); err != nil {
func (pr *PullRequest) GetBaseBranchLink(ctx context.Context) string {
if err := pr.LoadBaseRepo(ctx); err != nil {
log.Error("LoadBaseRepo: %v", err)
return ""
}
@ -786,12 +786,12 @@ func (pr *PullRequest) GetBaseBranchLink() string {
}
// GetHeadBranchLink returns the relative URL of the head branch
func (pr *PullRequest) GetHeadBranchLink() string {
func (pr *PullRequest) GetHeadBranchLink(ctx context.Context) string {
if pr.Flow == PullRequestFlowAGit {
return ""
}
if err := pr.LoadHeadRepo(db.DefaultContext); err != nil {
if err := pr.LoadHeadRepo(ctx); err != nil {
log.Error("LoadHeadRepo: %v", err)
return ""
}
@ -810,14 +810,14 @@ func UpdateAllowEdits(ctx context.Context, pr *PullRequest) error {
}
// Mergeable returns if the pullrequest is mergeable.
func (pr *PullRequest) Mergeable() bool {
func (pr *PullRequest) Mergeable(ctx context.Context) bool {
// If a pull request isn't mergable if it's:
// - Being conflict checked.
// - Has a conflict.
// - Received a error while being conflict checked.
// - Is a work-in-progress pull request.
return pr.Status != PullRequestStatusChecking && pr.Status != PullRequestStatusConflict &&
pr.Status != PullRequestStatusError && !pr.IsWorkInProgress()
pr.Status != PullRequestStatusError && !pr.IsWorkInProgress(ctx)
}
// HasEnoughApprovals returns true if pr has enough granted approvals.
@ -890,7 +890,7 @@ func MergeBlockedByOutdatedBranch(protectBranch *git_model.ProtectedBranch, pr *
func PullRequestCodeOwnersReview(ctx context.Context, pull *Issue, pr *PullRequest) error {
files := []string{"CODEOWNERS", "docs/CODEOWNERS", ".gitea/CODEOWNERS"}
if pr.IsWorkInProgress() {
if pr.IsWorkInProgress(ctx) {
return nil
}

View File

@ -213,7 +213,7 @@ func TestPullRequest_Update(t *testing.T) {
pr := unittest.AssertExistsAndLoadBean(t, &issues_model.PullRequest{ID: 1})
pr.BaseBranch = "baseBranch"
pr.HeadBranch = "headBranch"
pr.Update()
pr.Update(db.DefaultContext)
pr = unittest.AssertExistsAndLoadBean(t, &issues_model.PullRequest{ID: pr.ID})
assert.Equal(t, "baseBranch", pr.BaseBranch)
@ -228,7 +228,7 @@ func TestPullRequest_UpdateCols(t *testing.T) {
BaseBranch: "baseBranch",
HeadBranch: "headBranch",
}
assert.NoError(t, pr.UpdateCols("head_branch"))
assert.NoError(t, pr.UpdateCols(db.DefaultContext, "head_branch"))
pr = unittest.AssertExistsAndLoadBean(t, &issues_model.PullRequest{ID: 1})
assert.Equal(t, "master", pr.BaseBranch)
@ -260,13 +260,13 @@ func TestPullRequest_IsWorkInProgress(t *testing.T) {
pr := unittest.AssertExistsAndLoadBean(t, &issues_model.PullRequest{ID: 2})
pr.LoadIssue(db.DefaultContext)
assert.False(t, pr.IsWorkInProgress())
assert.False(t, pr.IsWorkInProgress(db.DefaultContext))
pr.Issue.Title = "WIP: " + pr.Issue.Title
assert.True(t, pr.IsWorkInProgress())
assert.True(t, pr.IsWorkInProgress(db.DefaultContext))
pr.Issue.Title = "[wip]: " + pr.Issue.Title
assert.True(t, pr.IsWorkInProgress())
assert.True(t, pr.IsWorkInProgress(db.DefaultContext))
}
func TestPullRequest_GetWorkInProgressPrefixWorkInProgress(t *testing.T) {
@ -334,7 +334,7 @@ func TestGetApprovers(t *testing.T) {
// Official reviews are already deduplicated. Allow unofficial reviews
// to assert that there are no duplicated approvers.
setting.Repository.PullRequest.DefaultMergeMessageOfficialApproversOnly = false
approvers := pr.GetApprovers()
approvers := pr.GetApprovers(db.DefaultContext)
expected := "Reviewed-by: User Five <user5@example.com>\nReviewed-by: Org Six <org6@example.com>\n"
assert.EqualValues(t, expected, approvers)
}

View File

@ -18,9 +18,6 @@ func ReduceCommitStatus(x *xorm.Engine) error {
if _, err := sess.Exec(`UPDATE commit_status SET state='pending' WHERE state='running'`); err != nil {
return err
}
if _, err := sess.Exec(`UPDATE commit_status SET state='failure' WHERE state='warning'`); err != nil {
return err
}
return sess.Commit()
}

View File

@ -277,8 +277,8 @@ func UpdateRepoStats(ctx context.Context, id int64) error {
return nil
}
func updateUserStarNumbers(users []user_model.User) error {
ctx, committer, err := db.TxContext(db.DefaultContext)
func updateUserStarNumbers(ctx context.Context, users []user_model.User) error {
ctx, committer, err := db.TxContext(ctx)
if err != nil {
return err
}
@ -294,19 +294,19 @@ func updateUserStarNumbers(users []user_model.User) error {
}
// DoctorUserStarNum recalculate Stars number for all user
func DoctorUserStarNum() (err error) {
func DoctorUserStarNum(ctx context.Context) (err error) {
const batchSize = 100
for start := 0; ; start += batchSize {
users := make([]user_model.User, 0, batchSize)
if err = db.GetEngine(db.DefaultContext).Limit(batchSize, start).Where("type = ?", 0).Cols("id").Find(&users); err != nil {
if err = db.GetEngine(ctx).Limit(batchSize, start).Where("type = ?", 0).Cols("id").Find(&users); err != nil {
return err
}
if len(users) == 0 {
break
}
if err = updateUserStarNumbers(users); err != nil {
if err = updateUserStarNumbers(ctx, users); err != nil {
return err
}
}

View File

@ -31,8 +31,8 @@ func ExistsWithAvatarAtStoragePath(ctx context.Context, storagePath string) (boo
}
// RelAvatarLink returns a relative link to the repository's avatar.
func (repo *Repository) RelAvatarLink() string {
return repo.relAvatarLink(db.DefaultContext)
func (repo *Repository) RelAvatarLink(ctx context.Context) string {
return repo.relAvatarLink(ctx)
}
// generateRandomAvatar generates a random avatar for repository.

View File

@ -108,8 +108,8 @@ func GetLanguageStats(ctx context.Context, repo *Repository) (LanguageStatList,
}
// GetTopLanguageStats returns the top language statistics for a repository
func GetTopLanguageStats(repo *Repository, limit int) (LanguageStatList, error) {
stats, err := GetLanguageStats(db.DefaultContext, repo)
func GetTopLanguageStats(ctx context.Context, repo *Repository, limit int) (LanguageStatList, error) {
stats, err := GetLanguageStats(ctx, repo)
if err != nil {
return nil, err
}
@ -140,8 +140,8 @@ func GetTopLanguageStats(repo *Repository, limit int) (LanguageStatList, error)
}
// UpdateLanguageStats updates the language statistics for repository
func UpdateLanguageStats(repo *Repository, commitID string, stats map[string]int64) error {
ctx, committer, err := db.TxContext(db.DefaultContext)
func UpdateLanguageStats(ctx context.Context, repo *Repository, commitID string, stats map[string]int64) error {
ctx, committer, err := db.TxContext(ctx)
if err != nil {
return err
}
@ -212,8 +212,8 @@ func UpdateLanguageStats(repo *Repository, commitID string, stats map[string]int
}
// CopyLanguageStat Copy originalRepo language stat information to destRepo (use for forked repo)
func CopyLanguageStat(originalRepo, destRepo *Repository) error {
ctx, committer, err := db.TxContext(db.DefaultContext)
func CopyLanguageStat(ctx context.Context, originalRepo, destRepo *Repository) error {
ctx, committer, err := db.TxContext(ctx)
if err != nil {
return err
}

View File

@ -447,7 +447,7 @@ func (repo *Repository) MustOwner(ctx context.Context) *user_model.User {
}
// ComposeMetas composes a map of metas for properly rendering issue links and external issue trackers.
func (repo *Repository) ComposeMetas() map[string]string {
func (repo *Repository) ComposeMetas(ctx context.Context) map[string]string {
if len(repo.RenderingMetas) == 0 {
metas := map[string]string{
"user": repo.OwnerName,
@ -456,7 +456,7 @@ func (repo *Repository) ComposeMetas() map[string]string {
"mode": "comment",
}
unit, err := repo.GetUnit(db.DefaultContext, unit.TypeExternalTracker)
unit, err := repo.GetUnit(ctx, unit.TypeExternalTracker)
if err == nil {
metas["format"] = unit.ExternalTrackerConfig().ExternalTrackerFormat
switch unit.ExternalTrackerConfig().ExternalTrackerStyle {
@ -470,10 +470,10 @@ func (repo *Repository) ComposeMetas() map[string]string {
}
}
repo.MustOwner(db.DefaultContext)
repo.MustOwner(ctx)
if repo.Owner.IsOrganization() {
teams := make([]string, 0, 5)
_ = db.GetEngine(db.DefaultContext).Table("team_repo").
_ = db.GetEngine(ctx).Table("team_repo").
Join("INNER", "team", "team.id = team_repo.team_id").
Where("team_repo.repo_id = ?", repo.ID).
Select("team.lower_name").
@ -489,10 +489,10 @@ func (repo *Repository) ComposeMetas() map[string]string {
}
// ComposeDocumentMetas composes a map of metas for properly rendering documents
func (repo *Repository) ComposeDocumentMetas() map[string]string {
func (repo *Repository) ComposeDocumentMetas(ctx context.Context) map[string]string {
if len(repo.DocumentRenderingMetas) == 0 {
metas := map[string]string{}
for k, v := range repo.ComposeMetas() {
for k, v := range repo.ComposeMetas(ctx) {
metas[k] = v
}
metas["mode"] = "document"
@ -566,8 +566,8 @@ func (repo *Repository) CanEnablePulls() bool {
}
// AllowsPulls returns true if repository meets the requirements of accepting pulls and has them enabled.
func (repo *Repository) AllowsPulls() bool {
return repo.CanEnablePulls() && repo.UnitEnabled(db.DefaultContext, unit.TypePullRequests)
func (repo *Repository) AllowsPulls(ctx context.Context) bool {
return repo.CanEnablePulls() && repo.UnitEnabled(ctx, unit.TypePullRequests)
}
// CanEnableEditor returns true if repository meets the requirements of web editor.
@ -718,12 +718,12 @@ func GetRepositoryByOwnerAndName(ctx context.Context, ownerName, repoName string
}
// GetRepositoryByName returns the repository by given name under user if exists.
func GetRepositoryByName(ownerID int64, name string) (*Repository, error) {
func GetRepositoryByName(ctx context.Context, ownerID int64, name string) (*Repository, error) {
repo := &Repository{
OwnerID: ownerID,
LowerName: strings.ToLower(name),
}
has, err := db.GetEngine(db.DefaultContext).Get(repo)
has, err := db.GetEngine(ctx).Get(repo)
if err != nil {
return nil, err
} else if !has {
@ -788,9 +788,9 @@ func GetRepositoryByID(ctx context.Context, id int64) (*Repository, error) {
}
// GetRepositoriesMapByIDs returns the repositories by given id slice.
func GetRepositoriesMapByIDs(ids []int64) (map[int64]*Repository, error) {
func GetRepositoriesMapByIDs(ctx context.Context, ids []int64) (map[int64]*Repository, error) {
repos := make(map[int64]*Repository, len(ids))
return repos, db.GetEngine(db.DefaultContext).In("id", ids).Find(&repos)
return repos, db.GetEngine(ctx).In("id", ids).Find(&repos)
}
// IsRepositoryModelOrDirExist returns true if the repository with given name under user has already existed.
@ -822,8 +822,8 @@ func GetTemplateRepo(ctx context.Context, repo *Repository) (*Repository, error)
}
// TemplateRepo returns the repository, which is template of this repository
func (repo *Repository) TemplateRepo() *Repository {
repo, err := GetTemplateRepo(db.DefaultContext, repo)
func (repo *Repository) TemplateRepo(ctx context.Context) *Repository {
repo, err := GetTemplateRepo(ctx, repo)
if err != nil {
log.Error("TemplateRepo: %v", err)
return nil

View File

@ -36,14 +36,14 @@ func init() {
}
// GetUnindexedRepos returns repos which do not have an indexer status
func GetUnindexedRepos(indexerType RepoIndexerType, maxRepoID int64, page, pageSize int) ([]int64, error) {
func GetUnindexedRepos(ctx context.Context, indexerType RepoIndexerType, maxRepoID int64, page, pageSize int) ([]int64, error) {
ids := make([]int64, 0, 50)
cond := builder.Cond(builder.IsNull{
"repo_indexer_status.id",
}).And(builder.Eq{
"repository.is_empty": false,
})
sess := db.GetEngine(db.DefaultContext).Table("repository").Join("LEFT OUTER", "repo_indexer_status", "repository.id = repo_indexer_status.repo_id AND repo_indexer_status.indexer_type = ?", indexerType)
sess := db.GetEngine(ctx).Table("repository").Join("LEFT OUTER", "repo_indexer_status", "repository.id = repo_indexer_status.repo_id AND repo_indexer_status.indexer_type = ?", indexerType)
if maxRepoID > 0 {
cond = builder.And(cond, builder.Lte{
"repository.id": maxRepoID,

View File

@ -21,8 +21,8 @@ import (
)
// FindReposMapByIDs find repos as map
func FindReposMapByIDs(repoIDs []int64, res map[int64]*Repository) error {
return db.GetEngine(db.DefaultContext).In("id", repoIDs).Find(&res)
func FindReposMapByIDs(ctx context.Context, repoIDs []int64, res map[int64]*Repository) error {
return db.GetEngine(ctx).In("id", repoIDs).Find(&res)
}
// RepositoryListDefaultPageSize is the default number of repositories
@ -672,12 +672,12 @@ func SearchRepositoryByName(ctx context.Context, opts *SearchRepoOptions) (Repos
// SearchRepositoryIDs takes keyword and part of repository name to search,
// it returns results in given range and number of total results.
func SearchRepositoryIDs(opts *SearchRepoOptions) ([]int64, int64, error) {
func SearchRepositoryIDs(ctx context.Context, opts *SearchRepoOptions) ([]int64, int64, error) {
opts.IncludeDescription = false
cond := SearchRepositoryCondition(opts)
sess, count, err := searchRepositoryByCondition(db.DefaultContext, opts, cond)
sess, count, err := searchRepositoryByCondition(ctx, opts, cond)
if err != nil {
return nil, 0, err
}

View File

@ -83,7 +83,7 @@ func TestMetas(t *testing.T) {
repo.Units = nil
metas := repo.ComposeMetas()
metas := repo.ComposeMetas(db.DefaultContext)
assert.Equal(t, "testRepo", metas["repo"])
assert.Equal(t, "testOwner", metas["user"])
@ -97,7 +97,7 @@ func TestMetas(t *testing.T) {
testSuccess := func(expectedStyle string) {
repo.Units = []*repo_model.RepoUnit{&externalTracker}
repo.RenderingMetas = nil
metas := repo.ComposeMetas()
metas := repo.ComposeMetas(db.DefaultContext)
assert.Equal(t, expectedStyle, metas["style"])
assert.Equal(t, "testRepo", metas["repo"])
assert.Equal(t, "testOwner", metas["user"])
@ -118,7 +118,7 @@ func TestMetas(t *testing.T) {
repo, err := repo_model.GetRepositoryByID(db.DefaultContext, 3)
assert.NoError(t, err)
metas = repo.ComposeMetas()
metas = repo.ComposeMetas(db.DefaultContext)
assert.Contains(t, metas, "org")
assert.Contains(t, metas, "teams")
assert.Equal(t, "org3", metas["org"])

View File

@ -20,5 +20,5 @@ func TestCheckRepoStats(t *testing.T) {
func TestDoctorUserStarNum(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
assert.NoError(t, DoctorUserStarNum())
assert.NoError(t, DoctorUserStarNum(db.DefaultContext))
}

View File

@ -91,6 +91,7 @@ var (
TypeWiki,
TypeProjects,
TypePackages,
TypeActions,
}
// ForkRepoUnits contains the default unit types for forks

View File

@ -89,7 +89,7 @@ func TestLoadUnitConfig(t *testing.T) {
setting.Repository.DefaultForkRepoUnits = []string{"repo.releases", "repo.releases"}
assert.NoError(t, LoadUnitConfig())
assert.Equal(t, []Type{TypeIssues}, DisabledRepoUnits)
assert.ElementsMatch(t, []Type{TypeCode, TypePullRequests, TypeReleases, TypeWiki, TypePackages, TypeProjects}, DefaultRepoUnits)
assert.ElementsMatch(t, []Type{TypeCode, TypePullRequests, TypeReleases, TypeWiki, TypePackages, TypeProjects, TypeActions}, DefaultRepoUnits)
assert.Equal(t, []Type{TypeReleases}, DefaultForkRepoUnits)
})
}

View File

@ -47,8 +47,7 @@ func checkForConsistency(t assert.TestingT, bean any) {
assert.NoError(t, err)
f := consistencyCheckMap[tb.Name]
if f == nil {
assert.Fail(t, "unknown bean type: %#v", bean)
return
assert.FailNow(t, "unknown bean type: %#v", bean)
}
f(t, bean)
}

View File

@ -495,7 +495,7 @@ func RepoAssignment(ctx *Context) context.CancelFunc {
}
// Get repository.
repo, err := repo_model.GetRepositoryByName(owner.ID, repoName)
repo, err := repo_model.GetRepositoryByName(ctx, owner.ID, repoName)
if err != nil {
if repo_model.IsErrRepoNotExist(err) {
redirectRepoID, err := repo_model.LookupRedirect(owner.ID, repoName)
@ -711,13 +711,13 @@ func RepoAssignment(ctx *Context) context.CancelFunc {
// Pull request is allowed if this is a fork repository
// and base repository accepts pull requests.
if repo.BaseRepo != nil && repo.BaseRepo.AllowsPulls() {
if repo.BaseRepo != nil && repo.BaseRepo.AllowsPulls(ctx) {
canCompare = true
ctx.Data["BaseRepo"] = repo.BaseRepo
ctx.Repo.PullRequest.BaseRepo = repo.BaseRepo
ctx.Repo.PullRequest.Allowed = canPush
ctx.Repo.PullRequest.HeadInfoSubURL = url.PathEscape(ctx.Repo.Owner.Name) + ":" + util.PathEscapeSegments(ctx.Repo.BranchName)
} else if repo.AllowsPulls() {
} else if repo.AllowsPulls(ctx) {
// Or, this is repository accepts pull requests between branches.
canCompare = true
ctx.Data["BaseRepo"] = repo

View File

@ -83,8 +83,7 @@ func LoadRepo(t *testing.T, ctx gocontext.Context, repoID int64) {
ctx.Repo = repo
doer = ctx.Doer
default:
assert.Fail(t, "context is not *context.Context or *context.APIContext")
return
assert.FailNow(t, "context is not *context.Context or *context.APIContext")
}
repo.Repository = unittest.AssertExistsAndLoadBean(t, &repo_model.Repository{ID: repoID})
@ -105,8 +104,7 @@ func LoadRepoCommit(t *testing.T, ctx gocontext.Context) {
case *context.APIContext:
repo = ctx.Repo
default:
assert.Fail(t, "context is not *context.Context or *context.APIContext")
return
assert.FailNow(t, "context is not *context.Context or *context.APIContext")
}
gitRepo, err := git.OpenRepository(ctx, repo.Repository.RepoPath())
@ -130,8 +128,7 @@ func LoadUser(t *testing.T, ctx gocontext.Context, userID int64) {
case *context.APIContext:
ctx.Doer = doer
default:
assert.Fail(t, "context is not *context.Context or *context.APIContext")
return
assert.FailNow(t, "context is not *context.Context or *context.APIContext")
}
}

View File

@ -74,7 +74,7 @@ func checkPRMergeBase(ctx context.Context, logger log.Logger, autofix bool) erro
pr.MergeBase = strings.TrimSpace(pr.MergeBase)
if pr.MergeBase != oldMergeBase {
if autofix {
if err := pr.UpdateCols("merge_base"); err != nil {
if err := pr.UpdateCols(ctx, "merge_base"); err != nil {
logger.Critical("Failed to update merge_base. ERROR: %v", err)
return fmt.Errorf("Failed to update merge_base. ERROR: %w", err)
}

View File

@ -74,7 +74,7 @@ func checkHooks(ctx context.Context, logger log.Logger, autofix bool) error {
func checkUserStarNum(ctx context.Context, logger log.Logger, autofix bool) error {
if autofix {
if err := models.DoctorUserStarNum(); err != nil {
if err := models.DoctorUserStarNum(ctx); err != nil {
logger.Critical("Unable update User Stars numbers")
return err
}

View File

@ -27,7 +27,7 @@ func Test_nulSeparatedAttributeWriter_ReadAttribute(t *testing.T) {
assert.Equal(t, "linguist-vendored", attr.Attribute)
assert.Equal(t, "unspecified", attr.Value)
case <-time.After(100 * time.Millisecond):
assert.Fail(t, "took too long to read an attribute from the list")
assert.FailNow(t, "took too long to read an attribute from the list")
}
// Write a second attribute again
n, err = wr.Write([]byte(testStr))
@ -41,7 +41,7 @@ func Test_nulSeparatedAttributeWriter_ReadAttribute(t *testing.T) {
assert.Equal(t, "linguist-vendored", attr.Attribute)
assert.Equal(t, "unspecified", attr.Value)
case <-time.After(100 * time.Millisecond):
assert.Fail(t, "took too long to read an attribute from the list")
assert.FailNow(t, "took too long to read an attribute from the list")
}
// Write a partial attribute
@ -52,14 +52,14 @@ func Test_nulSeparatedAttributeWriter_ReadAttribute(t *testing.T) {
select {
case <-wr.ReadAttribute():
assert.Fail(t, "There should not be an attribute ready to read")
assert.FailNow(t, "There should not be an attribute ready to read")
case <-time.After(100 * time.Millisecond):
}
_, err = wr.Write([]byte("attribute\x00"))
assert.NoError(t, err)
select {
case <-wr.ReadAttribute():
assert.Fail(t, "There should not be an attribute ready to read")
assert.FailNow(t, "There should not be an attribute ready to read")
case <-time.After(100 * time.Millisecond):
}

View File

@ -71,7 +71,6 @@ func TestRepository_GetTag(t *testing.T) {
if lTag == nil {
assert.NotNil(t, lTag)
assert.FailNow(t, "nil lTag: %s", lTagName)
return
}
assert.EqualValues(t, lTagName, lTag.Name)
assert.EqualValues(t, lTagCommitID, lTag.ID.String())
@ -105,7 +104,6 @@ func TestRepository_GetTag(t *testing.T) {
if aTag == nil {
assert.NotNil(t, aTag)
assert.FailNow(t, "nil aTag: %s", aTagName)
return
}
assert.EqualValues(t, aTagName, aTag.Name)
assert.EqualValues(t, aTagID, aTag.ID.String())

View File

@ -288,7 +288,7 @@ func populateRepoIndexer(ctx context.Context) {
return
default:
}
ids, err := repo_model.GetUnindexedRepos(repo_model.RepoIndexerTypeCode, maxRepoID, 0, 50)
ids, err := repo_model.GetUnindexedRepos(ctx, repo_model.RepoIndexerTypeCode, maxRepoID, 0, 50)
if err != nil {
log.Error("populateRepoIndexer: %v", err)
return

View File

@ -96,11 +96,10 @@ func TestBleveIndexAndSearch(t *testing.T) {
idx := bleve.NewIndexer(dir)
_, err := idx.Init(context.Background())
if err != nil {
assert.Fail(t, "Unable to create bleve indexer Error: %v", err)
if idx != nil {
idx.Close()
}
return
assert.FailNow(t, "Unable to create bleve indexer Error: %v", err)
}
defer idx.Close()
@ -118,11 +117,10 @@ func TestESIndexAndSearch(t *testing.T) {
indexer := elasticsearch.NewIndexer(u, "gitea_codes")
if _, err := indexer.Init(context.Background()); err != nil {
assert.Fail(t, "Unable to init ES indexer Error: %v", err)
if indexer != nil {
indexer.Close()
}
return
assert.FailNow(t, "Unable to init ES indexer Error: %v", err)
}
defer indexer.Close()

View File

@ -107,7 +107,7 @@ func getIssueIndexerData(ctx context.Context, issueID int64) (*internal.IndexerD
NoLabel: len(labels) == 0,
MilestoneID: issue.MilestoneID,
ProjectID: projectID,
ProjectBoardID: issue.ProjectBoardID(),
ProjectBoardID: issue.ProjectBoardID(ctx),
PosterID: issue.PosterID,
AssigneeID: issue.AssigneeID,
MentionIDs: mentionIDs,

View File

@ -68,7 +68,7 @@ func (db *DBIndexer) Index(id int64) error {
}
return err
}
err = repo_model.UpdateLanguageStats(repo, commitID, stats)
err = repo_model.UpdateLanguageStats(ctx, repo, commitID, stats)
if err != nil {
log.Error("Unable to update language stats for ID %s for default branch %s in %s. Error: %v", commitID, repo.DefaultBranch, repo.RepoPath(), err)
return err

View File

@ -4,6 +4,8 @@
package stats
import (
"context"
"code.gitea.io/gitea/models/db"
repo_model "code.gitea.io/gitea/models/repo"
"code.gitea.io/gitea/modules/graceful"
@ -28,14 +30,14 @@ func Init() error {
return err
}
go populateRepoIndexer()
go populateRepoIndexer(db.DefaultContext)
return nil
}
// populateRepoIndexer populate the repo indexer with pre-existing data. This
// should only be run when the indexer is created for the first time.
func populateRepoIndexer() {
func populateRepoIndexer(ctx context.Context) {
log.Info("Populating the repo stats indexer with existing repositories")
isShutdown := graceful.GetManager().IsShutdown()
@ -62,7 +64,7 @@ func populateRepoIndexer() {
return
default:
}
ids, err := repo_model.GetUnindexedRepos(repo_model.RepoIndexerTypeStats, maxRepoID, 0, 50)
ids, err := repo_model.GetUnindexedRepos(ctx, repo_model.RepoIndexerTypeStats, maxRepoID, 0, 50)
if err != nil {
log.Error("populateRepoIndexer: %v", err)
return

View File

@ -45,7 +45,7 @@ func TestRepoStatsIndex(t *testing.T) {
status, err := repo_model.GetIndexerStatus(db.DefaultContext, repo, repo_model.RepoIndexerTypeStats)
assert.NoError(t, err)
assert.Equal(t, "65f1bf27bc3bf70f64657658635e66094edbcb4d", status.CommitSha)
langs, err := repo_model.GetTopLanguageStats(repo, 5)
langs, err := repo_model.GetTopLanguageStats(db.DefaultContext, repo, 5)
assert.NoError(t, err)
assert.Empty(t, langs)
}

View File

@ -50,7 +50,7 @@ func TestManager_Cancel(t *testing.T) {
select {
case <-ctx.Done():
default:
assert.Fail(t, "Cancel should cancel the provided context")
assert.FailNow(t, "Cancel should cancel the provided context")
}
finished()
@ -62,7 +62,7 @@ func TestManager_Cancel(t *testing.T) {
select {
case <-ctx.Done():
default:
assert.Fail(t, "Cancel should cancel the provided context")
assert.FailNow(t, "Cancel should cancel the provided context")
}
finished()
}

View File

@ -46,7 +46,7 @@ CONN_STR = redis://
assert.Equal(t, "default", q.GetName())
assert.Equal(t, "level", q.GetType())
assert.Equal(t, filepath.Join(setting.AppDataPath, "queues/common"), q.baseConfig.DataFullDir)
assert.Equal(t, 100, q.baseConfig.Length)
assert.Equal(t, 100000, q.baseConfig.Length)
assert.Equal(t, 20, q.batchLength)
assert.Equal(t, "", q.baseConfig.ConnStr)
assert.Equal(t, "default_queue", q.baseConfig.QueueFullName)

View File

@ -149,8 +149,9 @@ func EnvironmentToConfig(cfg ConfigProvider, envs []string) (changed bool) {
continue
}
}
key := section.Key(keyName)
key := ConfigSectionKey(section, keyName)
if key == nil {
changed = true
key, err = section.NewKey(keyName, keyValue)
if err != nil {
log.Error("Error creating key: %s in section: %s with value: %s : %v", keyName, sectionName, keyValue, err)

View File

@ -115,3 +115,29 @@ key = old
EnvironmentToConfig(cfg, []string{"GITEA__sec__key__FILE=" + tmpFile})
assert.Equal(t, "value-from-file\n", cfg.Section("sec").Key("key").String())
}
func TestEnvironmentToConfigSubSecKey(t *testing.T) {
// the INI package has a quirk: by default, the keys are inherited.
// when maintaining the keys, the newly added sub key should not be affected by the parent key.
cfg, err := NewConfigProviderFromData(`
[sec]
key = some
`)
assert.NoError(t, err)
changed := EnvironmentToConfig(cfg, []string{"GITEA__sec_0X2E_sub__key=some"})
assert.True(t, changed)
tmpFile := t.TempDir() + "/test-sub-sec-key.ini"
defer os.Remove(tmpFile)
err = cfg.SaveTo(tmpFile)
assert.NoError(t, err)
bs, err := os.ReadFile(tmpFile)
assert.NoError(t, err)
assert.Equal(t, `[sec]
key = some
[sec.sub]
key = some
`, string(bs))
}

View File

@ -110,7 +110,7 @@ var OAuth2 = struct {
JWTSigningAlgorithm: "RS256",
JWTSigningPrivateKeyFile: "jwt/private.pem",
MaxTokenLength: math.MaxInt16,
DefaultApplications: []string{"git-credential-oauth", "git-credential-manager"},
DefaultApplications: []string{"git-credential-oauth", "git-credential-manager", "tea"},
}
func loadOAuth2From(rootCfg ConfigProvider) {

View File

@ -30,7 +30,7 @@ func GetQueueSettings(rootCfg ConfigProvider, name string) (QueueSettings, error
queueSettingsDefault := QueueSettings{
Type: "level", // dummy, channel, level, redis
Datadir: "queues/common", // relative to AppDataPath
Length: 100, // queue length before a channel queue will block
Length: 100000, // queue length before a channel queue will block
QueueName: "_queue",
SetName: "_unique",

View File

@ -16,13 +16,16 @@ const (
CommitStatusError CommitStatusState = "error"
// CommitStatusFailure is for when the CommitStatus is Failure
CommitStatusFailure CommitStatusState = "failure"
// CommitStatusWarning is for when the CommitStatus is Warning
CommitStatusWarning CommitStatusState = "warning"
)
var commitStatusPriorities = map[CommitStatusState]int{
CommitStatusError: 0,
CommitStatusFailure: 1,
CommitStatusPending: 2,
CommitStatusSuccess: 3,
CommitStatusWarning: 2,
CommitStatusPending: 3,
CommitStatusSuccess: 4,
}
func (css CommitStatusState) String() string {
@ -32,7 +35,7 @@ func (css CommitStatusState) String() string {
// NoBetterThan returns true if this State is no better than the given State
// This function only handles the states defined in CommitStatusPriorities
func (css CommitStatusState) NoBetterThan(css2 CommitStatusState) bool {
// NoBetterThan only handles the 4 states above
// NoBetterThan only handles the 5 states above
if _, exist := commitStatusPriorities[css]; !exist {
return false
}
@ -63,3 +66,8 @@ func (css CommitStatusState) IsError() bool {
func (css CommitStatusState) IsFailure() bool {
return css == CommitStatusFailure
}
// IsWarning represents if commit status state is warning
func (css CommitStatusState) IsWarning() bool {
return css == CommitStatusWarning
}

View File

@ -74,27 +74,31 @@ func ActionIcon(opType activities_model.ActionType) string {
switch opType {
case activities_model.ActionCreateRepo, activities_model.ActionTransferRepo, activities_model.ActionRenameRepo:
return "repo"
case activities_model.ActionCommitRepo, activities_model.ActionPushTag, activities_model.ActionDeleteTag, activities_model.ActionDeleteBranch:
case activities_model.ActionCommitRepo:
return "git-commit"
case activities_model.ActionCreateIssue:
return "issue-opened"
case activities_model.ActionCreatePullRequest:
return "git-pull-request"
case activities_model.ActionCommentIssue, activities_model.ActionCommentPull:
return "comment-discussion"
case activities_model.ActionDeleteBranch:
return "git-branch"
case activities_model.ActionMergePullRequest, activities_model.ActionAutoMergePullRequest:
return "git-merge"
case activities_model.ActionCloseIssue, activities_model.ActionClosePullRequest:
case activities_model.ActionCreatePullRequest:
return "git-pull-request"
case activities_model.ActionClosePullRequest:
return "git-pull-request-closed"
case activities_model.ActionCreateIssue:
return "issue-opened"
case activities_model.ActionCloseIssue:
return "issue-closed"
case activities_model.ActionReopenIssue, activities_model.ActionReopenPullRequest:
return "issue-reopened"
case activities_model.ActionCommentIssue, activities_model.ActionCommentPull:
return "comment-discussion"
case activities_model.ActionMirrorSyncPush, activities_model.ActionMirrorSyncCreate, activities_model.ActionMirrorSyncDelete:
return "mirror"
case activities_model.ActionApprovePullRequest:
return "check"
case activities_model.ActionRejectPullRequest:
return "diff"
case activities_model.ActionPublishRelease:
return "file-diff"
case activities_model.ActionPublishRelease, activities_model.ActionPushTag, activities_model.ActionDeleteTag:
return "tag"
case activities_model.ActionPullReviewDismissed:
return "x"

View File

@ -97,6 +97,7 @@ locked=Gesperrt
copy=Kopieren
copy_url=URL kopieren
copy_hash=Hash kopieren
copy_content=Inhalt kopieren
copy_branch=Branchenname kopieren
copy_success=Kopiert!
@ -112,6 +113,7 @@ step2=Schritt 2:
error=Fehler
error404=Die Seite, die Du versuchst aufzurufen, <strong>existiert nicht</strong> oder <strong>Du bist nicht berechtigt</strong>, diese anzusehen.
go_back=Zurück
never=Niemals
unknown=Unbekannt
@ -183,6 +185,7 @@ network_error=Netzwerkfehler
[startpage]
app_desc=Ein einfacher, selbst gehosteter Git-Service
install=Einfach zu installieren
install_desc=Starte einfach <a target="_blank" rel="noopener noreferrer" href="https://docs.gitea.com/installation/install-from-binary">die Anwendung</a> für deine Plattform oder nutze <a target="_blank" rel="noopener noreferrer" href="https://github.com/go-gitea/gitea/tree/master/docker">Docker</a>. Es existieren auch <a target="_blank" rel="noopener noreferrer" href="https://docs.gitea.com/installation/install-from-package">paketierte Versionen</a>.
platform=Plattformübergreifend
platform_desc=Gitea läuft überall, wo <a target="_blank" rel="noopener noreferrer" href="http://golang.org/">Go</a> kompiliert: Windows, macOS, Linux, ARM, etc. Wähle das System, das dir am meisten gefällt!
lightweight=Leichtgewicht
@ -371,6 +374,7 @@ reset_password_mail_sent_prompt=Eine Bestätigungs-E-Mail wurde an <b>%s</b> ges
active_your_account=Aktiviere dein Konto
account_activated=Konto wurde aktiviert
prohibit_login=Anmelden verboten
prohibit_login_desc=Die Anmeldung mit diesem Konto ist nicht gestattet. Bitte kontaktiere den Administrator.
resent_limit_prompt=Du hast bereits eine Aktivierungs-E-Mail angefordert. Bitte warte 3 Minuten und probiere es dann nochmal.
has_unconfirmed_mail=Hallo %s, du hast eine unbestätigte E-Mail-Adresse (<b>%s</b>). Wenn du keine Bestätigungs-E-Mail erhalten hast oder eine neue senden möchtest, klicke bitte auf den folgenden Button.
resend_mail=Aktivierungs-E-Mail erneut verschicken
@ -378,8 +382,10 @@ email_not_associate=Diese E-Mail-Adresse ist mit keinem Konto verknüpft.
send_reset_mail=Wiederherstellungs-E-Mail senden
reset_password=Kontowiederherstellung
invalid_code=Dein Bestätigungs-Code ist ungültig oder abgelaufen.
invalid_code_forgot_password=Dein Bestätigungscode ist ungültig oder abgelaufen. Klicke <a href="%s">hier</a>, um eine neue Sitzung zu starten.
invalid_password=Ihr Passwort stimmt nicht mit dem Passwort überein, das zur Erstellung des Kontos verwendet wurde.
reset_password_helper=Konto wiederherstellen
reset_password_wrong_user=Du bist angemeldet als %s, aber der Link zur Kontowiederherstellung ist für %s
password_too_short=Das Passwort muss mindestens %d Zeichen lang sein.
non_local_account=Benutzer, die nicht von Gitea verwaltet werden können ihre Passwörter nicht über das Web Interface ändern.
verify=Verifizieren
@ -404,6 +410,7 @@ openid_connect_title=Mit bestehendem Konto verbinden
openid_connect_desc=Die gewählte OpenID-URI ist unbekannt. Ordne sie hier einem neuen Account zu.
openid_register_title=Neues Konto einrichten
openid_register_desc=Die gewählte OpenID-URI ist unbekannt. Ordne sie hier einem neuen Account zu.
openid_signin_desc=Gib deine OpenID-URI ein, zum Beispiel alice.openid.example.org oder https://openid.example.org/alice.
disable_forgot_password_mail=Die Kontowiederherstellung ist deaktiviert, da keine E-Mail eingerichtet ist. Bitte kontaktiere den zuständigen Administrator.
disable_forgot_password_mail_admin=Die Kontowiederherstellung ist nur verfügbar, wenn eine E-Mail eingerichtet wurde. Bitte richte eine E-Mail Adresse ein, um die Kontowiederherstellung freizuschalten.
email_domain_blacklisted=Du kannst dich nicht mit deiner E-Mail-Adresse registrieren.
@ -413,7 +420,9 @@ authorize_application_created_by=Diese Anwendung wurde von %s erstellt.
authorize_application_description=Wenn du diese Anwendung autorisierst, wird sie die Berechtigung erhalten, alle Informationen zu deinem Account zu bearbeiten oder zu lesen. Dies beinhaltet auch private Repositories und Organisationen.
authorize_title=`"%s" den Zugriff auf deinen Account gestatten?`
authorization_failed=Autorisierung fehlgeschlagen
authorization_failed_desc=Die Autorisierung ist fehlgeschlagen, da wir eine ungültige Anfrage erkannt haben. Bitte kontaktiere den Betreuer der App, die du zu autorisieren versucht hast.
sspi_auth_failed=SSPI-Authentifizierung fehlgeschlagen
password_pwned=Das von dir gewählte Passwort befindet sich auf einer <a target="_blank" rel="noopener noreferrer" href="https://haveibeenpwned.com/Passwords">List gestohlener Passwörter</a>, die öffentlich verfügbar sind. Bitte versuche es erneut mit einem anderen Passwort und ziehe in Erwägung, auch anderswo deine Passwörter zu ändern.
password_pwned_err=Anfrage an HaveIBeenPwned konnte nicht abgeschlossen werden
[mail]
@ -428,6 +437,7 @@ activate_account.text_1=Hallo <b>%[1]s</b>, danke für deine Registrierung bei %
activate_account.text_2=Bitte klicke innerhalb von <b>%s</b> auf folgenden Link, um dein Konto zu aktivieren:
activate_email=Bestätige deine E-Mail-Adresse
activate_email.title=%s, bitte verifiziere deine E-Mail-Adresse
activate_email.text=Bitte klicke innerhalb von <b>%s</b> auf folgenden Link, um dein Konto zu aktivieren:
register_notify=Willkommen bei Gitea
@ -597,6 +607,7 @@ user_bio=Biografie
disabled_public_activity=Dieser Benutzer hat die öffentliche Sichtbarkeit der Aktivität deaktiviert.
email_visibility.limited=Ihre E-Mail-Adresse ist für alle authentifizierten Benutzer sichtbar
email_visibility.private=Deine E-Mail-Adresse ist nur für Dich und Administratoren sichtbar
show_on_map=Diesen Ort auf einer Karte anzeigen
settings=Benutzereinstellungen
form.name_reserved=Der Benutzername "%s" ist reserviert.
@ -619,9 +630,13 @@ delete=Konto löschen
twofa=Zwei-Faktor-Authentifizierung
account_link=Verknüpfte Benutzerkonten
organization=Organisationen
uid=UID
webauthn=Hardware-Sicherheitsschlüssel
public_profile=Öffentliches Profil
biography_placeholder=Erzähle uns ein wenig über Dich selbst! (Du kannst Markdown verwenden)
location_placeholder=Teile Deinen ungefähren Standort mit anderen
profile_desc=Lege fest, wie dein Profil anderen Benutzern angezeigt wird. Deine primäre E-Mail-Adresse wird für Benachrichtigungen, Passwort-Wiederherstellung und webbasierte Git-Operationen verwendet.
password_username_disabled=Benutzer, die nicht von Gitea verwaltet werden können ihren Benutzernamen nicht ändern. Bitte kontaktiere deinen Administrator für mehr Details.
full_name=Vollständiger Name
website=Webseite
@ -633,6 +648,8 @@ update_language_not_found=Sprache "%s" ist nicht verfügbar.
update_language_success=Sprache wurde aktualisiert.
update_profile_success=Dein Profil wurde aktualisiert.
change_username=Dein Benutzername wurde geändert.
change_username_prompt=Hinweis: Das Ändern deines Benutzernamen ändert auch deine Account-URL.
change_username_redirect_prompt=Der alte Benutzername wird auf den neuen Benutzernamen weiterleiten, bis er erneut als Benutzername verwendet wird.
continue=Weiter
cancel=Abbrechen
language=Sprache
@ -657,6 +674,7 @@ comment_type_group_project=Projekt
comment_type_group_issue_ref=Issue-Referenz
saved_successfully=Die Einstellungen wurden erfolgreich gespeichert.
privacy=Datenschutz
keep_activity_private=Aktivität auf der Profilseite ausblenden
keep_activity_private_popup=Macht die Aktivität nur für dich und die Administratoren sichtbar
lookup_avatar_by_mail=Profilbild anhand der E-Mail-Addresse suchen
@ -666,6 +684,7 @@ choose_new_avatar=Neues Profilbild auswählen
update_avatar=Profilbild aktualisieren
delete_current_avatar=Aktuelles Profilbild löschen
uploaded_avatar_not_a_image=Die hochgeladene Datei ist kein Bild.
uploaded_avatar_is_too_big=Die hochgeladene Dateigröße (%d KiB) überschreitet die maximale Größe (%d KiB).
update_avatar_success=Dein Profilbild wurde geändert.
update_user_avatar_success=Der Avatar des Benutzers wurde aktualisiert.
@ -681,6 +700,7 @@ emails=E-Mail-Adressen
manage_emails=E-Mail-Adressen verwalten
manage_themes=Standard-Theme auswählen
manage_openid=OpenID-Adressen verwalten
email_desc=Deine primäre E-Mail-Adresse wird für Benachrichtigungen, Passwort-Wiederherstellung und, sofern sie nicht versteckt ist, web-basierte Git-Operationen verwendet.
theme_desc=Dies wird dein Standard-Theme auf der Seite sein.
primary=Primär
activated=Aktiviert
@ -688,6 +708,7 @@ requires_activation=Erfordert Aktivierung
primary_email=Als primäre E-Mail-Adresse verwenden
activate_email=Aktivierung senden
activations_pending=Aktivierung ausstehend
can_not_add_email_activations_pending=Es gibt eine ausstehende Aktivierung, versuche es in ein paar Minuten erneut, wenn du eine neue E-Mail hinzufügen möchtest.
delete_email=Löschen
email_deletion=E-Mail-Adresse löschen
email_deletion_desc=Die E-Mail-Adresse und die damit verbundenen Informationen werden von deinem Konto entfernt. Git-Commits von dieser E-Mail-Addresse bleiben unverändert. Fortfahren?
@ -706,6 +727,7 @@ add_email_success=Die neue E-Mail-Addresse wurde hinzugefügt.
email_preference_set_success=E-Mail-Einstellungen wurden erfolgreich aktualisiert.
add_openid_success=Die neue OpenID-Adresse wurde hinzugefügt.
keep_email_private=E-Mail-Adresse verbergen
keep_email_private_popup=Dies wird Deine E-Mail-Adresse nicht nur in Deinem Profil ausblenden, sondern auch, wenn Du einen Pull Request erstellst oder eine Datei über das Web-Interface bearbeitest. Gepushte Commits werden nicht geändert.
openid_desc=Mit OpenID kannst du dich über einen Drittanbieter authentifizieren.
manage_ssh_keys=SSH-Schlüssel verwalten
@ -784,7 +806,9 @@ ssh_disabled=SSH ist deaktiviert
ssh_signonly=SSH ist derzeit deaktiviert, sodass diese Schlüssel nur zur Commit-Signaturverifizierung verwendet werden.
ssh_externally_managed=Dieser SSH-Schlüssel wird extern für diesen Benutzer verwaltet
manage_social=Verknüpfte soziale Konten verwalten
social_desc=Diese sozialen Konten können verwendet werden, um sich bei deinem Konto anzumelden. Stelle sicher, dass du sie alle zuordnen kannst.
unbind=Trennen
unbind_success=Das soziale Konto wurde erfolgreich entfernt.
manage_access_token=Zugriffstokens verwalten
generate_new_token=Neuen Token erzeugen
@ -805,6 +829,8 @@ permissions_access_all=Alle (öffentlich, privat und begrenzt)
select_permissions=Berechtigungen auswählen
permission_no_access=Kein Zugriff
permission_read=Gelesen
permission_write=Lesen und Schreiben
access_token_desc=Ausgewählte Token-Berechtigungen beschränken die Authentifizierung auf die entsprechenden <a %s>API</a>-Routen. Lies die <a %s>Dokumentation</a> für mehr Informationen.
at_least_one_permission=Du musst mindestens eine Berechtigung auswählen, um ein Token zu erstellen
permissions_list=Berechtigungen:
@ -816,6 +842,8 @@ remove_oauth2_application_desc=Das Entfernen einer OAuth2-Anwendung wird den Zug
remove_oauth2_application_success=Die Anwendung wurde gelöscht.
create_oauth2_application=Neue OAuth2 Anwendung erstellen
create_oauth2_application_button=Anwendung erstellen
create_oauth2_application_success=Du hast erfolgreich eine neue OAuth2-Anwendung erstellt.
update_oauth2_application_success=Du hast die OAuth2-Anwendung erfolgreich aktualisiert.
oauth2_application_name=Name der Anwendung
oauth2_confidential_client=Vertraulicher Client. Für Anwendungen aktivieren, die das Geheimnis sicher speichern, z. B. Webanwendungen. Wähle diese Option nicht für native Anwendungen für PCs und Mobilgeräte.
oauth2_redirect_uris=URIs für die Weiterleitung. Bitte verwende eine neue Zeile für jede URI.
@ -824,19 +852,25 @@ oauth2_client_id=Client-ID
oauth2_client_secret=Client-Secret
oauth2_regenerate_secret=Secret neu generieren
oauth2_regenerate_secret_hint=Secret verloren?
oauth2_client_secret_hint=Das Secret wird nach dem Verlassen oder Aktualisieren dieser Seite nicht mehr angezeigt. Bitte stelle sicher, dass du es gespeichert hast.
oauth2_application_edit=Bearbeiten
oauth2_application_create_description=OAuth2 Anwendungen geben deiner Drittanwendung Zugriff auf Benutzeraccounts dieser Gitea-Instanz.
oauth2_application_remove_description=Das Entfernen einer OAuth2-Anwendung hat zur Folge, dass diese nicht mehr auf autorisierte Benutzeraccounts auf dieser Instanz zugreifen kann. Möchtest Du fortfahren?
oauth2_application_locked=Wenn es in der Konfiguration aktiviert ist, registriert Gitea einige OAuth2-Anwendungen beim Starten vor. Um unerwartetes Verhalten zu verhindern, können diese weder bearbeitet noch entfernt werden. Weitere Informationen findest Du in der OAuth2-Dokumentation.
authorized_oauth2_applications=Autorisierte OAuth2-Anwendungen
authorized_oauth2_applications_description=Den folgenden Drittanbieter-Apps hast Du Zugriff auf Deinen persönlichen Gitea-Account gewährt. Bitte widerrufe die Autorisierung für Apps, die Du nicht mehr nutzt.
revoke_key=Widerrufen
revoke_oauth2_grant=Autorisierung widerrufen
revoke_oauth2_grant_description=Wenn du die Autorisierung widerrufst, kann die Anwendung nicht mehr auf deine Daten zugreifen. Bist du dir sicher?
revoke_oauth2_grant_success=Zugriff erfolgreich widerrufen.
twofa_desc=Zwei-Faktor-Authentifizierung trägt zu einer höheren Accountsicherheit bei.
twofa_is_enrolled=Für dein Konto ist die Zwei-Faktor-Authentifizierung <strong>eingeschaltet</strong>.
twofa_not_enrolled=Für dein Konto ist die Zwei-Faktor-Authentifizierung momentan nicht eingeschaltet.
twofa_disable=Zwei-Faktor-Authentifizierung deaktivieren
twofa_scratch_token_regenerate=Neues Einmalpasswort erstellen
twofa_scratch_token_regenerated=Dein temporärer Token ist jetzt %s. Speichere ihn an einem sicheren Ort, er wird nie wieder angezeigt.
twofa_enroll=Zwei-Faktor-Authentifizierung aktivieren
twofa_disable_note=Du kannst die Zwei-Faktor-Authentifizierung auch wieder deaktivieren.
twofa_disable_desc=Wenn du die Zwei-Faktor-Authentifizierung deaktivierst, wird die Sicherheit deines Kontos verringert. Fortfahren?
@ -863,8 +897,10 @@ remove_account_link=Verknüpften Account entfernen
remove_account_link_desc=Wenn du den verknüpften Account entfernst, wirst du darüber nicht mehr auf deinen Gitea-Account zugreifen können. Fortfahren?
remove_account_link_success=Der verknüpfte Account wurde entfernt.
hooks.desc=Webhooks hinzufügen, die für <strong>alle Repositories</strong>, die dir gehören, ausgelöst werden.
orgs_none=Du bist kein Mitglied in einer Organisation.
repos_none=Du besitzt keine Repositories.
delete_account=Konto löschen
delete_prompt=Wenn du fortfährst, wird dein Account permanent gelöscht. Dies <strong>KANN NICHT</strong> rückgängig gemacht werden.
@ -883,9 +919,12 @@ visibility=Nutzer Sichtbarkeit
visibility.public=Öffentlich
visibility.public_tooltip=Für alle sichtbar
visibility.limited=Begrenzt
visibility.limited_tooltip=Nur für authentifizierte Benutzer sichtbar
visibility.private=Privat
visibility.private_tooltip=Sichtbar nur für Mitglieder von Organisationen, denen du beigetreten bist
[repo]
new_repo_helper=Ein Repository enthält alle Projektdateien, einschließlich des Änderungsverlaufs. Schon woanders vorhanden? <a href="%s">Migriere das Repository.</a>
owner=Besitzer
owner_helper=Einige Organisationen könnten in der Dropdown-Liste nicht angezeigt werden, da die Anzahl an Repositories begrenzt ist.
repo_name=Repository-Name
@ -897,6 +936,7 @@ template_helper=Repository zu einem Template machen
template_description=Template-Repositories erlauben es Benutzern, neue Repositories mit den gleichen Verzeichnisstrukturen, Dateien und optionalen Einstellungen zu erstellen.
visibility=Sichtbarkeit
visibility_description=Nur der Besitzer oder Organisationsmitglieder mit entsprechender Berechtigung, werden in der Lage sein, es zu sehen.
visibility_helper=In privates Repository umwandeln
visibility_helper_forced=Auf dieser Gitea-Instanz können nur private Repositories angelegt werden.
visibility_fork_helper=(Eine Änderung dieses Wertes wirkt sich auf alle Forks aus)
clone_helper=Benötigst du Hilfe beim Klonen? Öffne die <a target="_blank" rel="noopener noreferrer" href="%s">Hilfe</a>.
@ -905,6 +945,9 @@ fork_from=Fork von
already_forked=Du hast bereits einen Fork von %s erstellt
fork_to_different_account=Fork in ein anderes Konto erstellen
fork_visibility_helper=Die Sichtbarkeit eines geforkten Repositories kann nicht geändert werden.
fork_branch=Branch, der zum Fork geklont werden soll
all_branches=Alle Branches
fork_no_valid_owners=Dieses Repository kann nicht geforkt werden, da keine gültigen Besitzer vorhanden sind.
use_template=Dieses Template verwenden
clone_in_vsc=In VS Code klonen
download_zip=ZIP herunterladen
@ -933,6 +976,7 @@ trust_model_helper_collaborator_committer=Mitarbeiter+Committer: Vertraue Signat
trust_model_helper_default=Standard: Verwende das Standardvertrauensmodell für diese Installation
create_repo=Repository erstellen
default_branch=Standardbranch
default_branch_label=Standard
default_branch_helper=Der default Branch ist der Basisbranch für Pull-Requests und Commits.
mirror_prune=Entfernen
mirror_prune_desc=Entferne veraltete remote-tracking Referenzen
@ -941,6 +985,8 @@ mirror_interval_invalid=Das Spiegel-Intervall ist ungültig.
mirror_sync_on_commit=Synchronisieren, wenn Commits gepusht wurden
mirror_address=Klonen via URL
mirror_address_desc=Gib alle erforderlichen Anmeldedaten im Abschnitt "Authentifizierung" ein.
mirror_address_url_invalid=Die angegebene URL ist ungültig. Achte darauf, alle URL-Komponenten korrekt zu maskieren.
mirror_address_protocol_invalid=Die angegebene URL ist ungültig. Nur URLs beginnend mit http(s):// oder git:// sind möglich.
mirror_lfs=Großdatei-Speicher (LFS)
mirror_lfs_desc=Mirroring von LFS-Dateien aktivieren.
mirror_lfs_endpoint=LFS-Endpunkt
@ -966,13 +1012,20 @@ delete_preexisting=Vorhandene Dateien löschen
delete_preexisting_content=Dateien in %s löschen
delete_preexisting_success=Nicht übernommene Dateien in %s gelöscht
blame_prior=Blame vor dieser Änderung anzeigen
blame.ignore_revs=Revisionen in <a href="%s">.git-blame-ignore-revs</a> werden ignoriert. Klicke <a href="%s">hier, um das zu umgehen</a> und die normale Blame-Ansicht zu sehen.
blame.ignore_revs.failed=Fehler beim Ignorieren der Revisionen in <a href="%s">.git-blame-ignore-revs</a>.
author_search_tooltip=Zeigt maximal 30 Benutzer
tree_path_not_found_commit=Pfad %[1]s existiert nicht in Commit%[2]s
tree_path_not_found_branch=Pfad %[1]s existiert nicht in Branch %[2]s
tree_path_not_found_tag=Pfad %[1]s existiert nicht in Tag %[2]s
transfer.accept=Übertragung Akzeptieren
transfer.accept_desc=`Übertragung nach "%s"`
transfer.reject=Übertragung Ablehnen
transfer.reject_desc=Übertragung nach "%s " abbrechen
transfer.no_permission_to_accept=Du hast keine Berechtigung, diesen Transfer anzunehmen.
transfer.no_permission_to_reject=Du hast keine Berechtigung, diesen Transfer abzulehnen.
desc.private=Privat
desc.public=Öffentlich
@ -993,6 +1046,8 @@ template.issue_labels=Issue Label
template.one_item=Es muss mindestens ein Template ausgewählt werden
template.invalid=Es muss ein Template-Repository ausgewählt werden
archive.title=Dieses Repository ist archiviert. Du kannst Dateien ansehen und es klonen, kannst aber nicht pushen oder Issues/Pull-Requests öffnen.
archive.title_date=Dieses Repository wurde am %s archiviert. Du kannst Dateien ansehen und es klonen, aber nicht pushen oder Issues/Pull-Requests öffnen.
archive.issue.nocomment=Dieses Repo ist archiviert. Du kannst Issues nicht kommentieren.
archive.pull.nocomment=Dieses Repo ist archiviert. Du kannst Pull-Requests nicht kommentieren.
@ -1009,6 +1064,7 @@ migrate_options_lfs=LFS-Dateien migrieren
migrate_options_lfs_endpoint.label=LFS-Endpunkt
migrate_options_lfs_endpoint.description=Migration wird versuchen, über den entfernten Git-Server <a target="_blank" rel="noopener noreferrer" href="%s">den LFS-Server zu bestimmen</a>. Du kannst auch einen eigenen Endpunkt angeben, wenn die LFS-Dateien woanders gespeichert werden.
migrate_options_lfs_endpoint.description.local=Ein lokaler Serverpfad wird ebenfalls unterstützt.
migrate_options_lfs_endpoint.placeholder=Wenn leer gelassen, wird der Endpunkt von der Clone-URL abgeleitet
migrate_items=Migrationselemente
migrate_items_wiki=Wiki
migrate_items_milestones=Meilensteine
@ -1111,6 +1167,10 @@ file_view_rendered=Ansicht rendern
file_view_raw=Originalformat anzeigen
file_permalink=Permalink
file_too_large=Die Datei ist zu groß zum Anzeigen.
invisible_runes_header=`Diese Datei enthält unsichtbare Unicode-Zeichen`
invisible_runes_description=`Diese Datei enthält unsichtbare Unicode-Zeichen, die für Menschen nicht unterscheidbar sind, aber von einem Computer unterschiedlich verarbeitet werden können. Wenn du glaubst, dass das absichtlich so ist, kannst du diese Warnung ignorieren. Benutze den „Escape“-Button, um versteckte Zeichen anzuzeigen.`
ambiguous_runes_header=`Diese Datei enthält mehrdeutige Unicode-Zeichen`
ambiguous_runes_description=`Diese Datei enthält Unicode-Zeichen, die mit anderen Zeichen verwechselt werden können. Wenn du glaubst, dass das absichtlich so ist, kannst du diese Warnung ignorieren. Benutze den „Escape“-Button, um versteckte Zeichen anzuzeigen.`
invisible_runes_line=`Diese Zeile enthält unsichtbare Unicode-Zeichen`
ambiguous_runes_line=`Diese Zeile enthält mehrdeutige Unicode-Zeichen`
ambiguous_character=`%[1]c [U+%04[1]X] kann mit %[2]c [U+%04[2]X] verwechselt werden`
@ -1123,11 +1183,15 @@ video_not_supported_in_browser=Dein Browser unterstützt das HTML5 'video'-Tag n
audio_not_supported_in_browser=Dein Browser unterstützt den HTML5 'audio'-Tag nicht.
stored_lfs=Gespeichert mit Git LFS
symbolic_link=Softlink
executable_file=Ausführbare Datei
commit_graph=Commit graph
commit_graph.select=Branches auswählen
commit_graph.hide_pr_refs=Pull-Requests ausblenden
commit_graph.monochrome=Monochrom
commit_graph.color=Farbe
commit.contained_in=Dieser Commit ist enthalten in:
commit.contained_in_default_branch=Dieser Commit ist im Standard-Branch enthalten
commit.load_referencing_branches_and_tags=Lade Branches und Tags, die diesen Commit referenzieren
blame=Blame
download_file=Datei herunterladen
normal_view=Normale Ansicht
@ -1220,6 +1284,7 @@ commits.signed_by_untrusted_user=Signiert von nicht vertrauenswürdigen Benutzer
commits.signed_by_untrusted_user_unmatched=Signiert von nicht vertrauenswürdigen Benutzern, der nicht mit dem Committer übereinstimmt
commits.gpg_key_id=GPG-Schlüssel-ID
commits.ssh_key_fingerprint=SSH-Key-Fingerabdruck
commits.view_path=An diesem Punkt im Verlauf anzeigen
commit.operations=Operationen
commit.revert=Zurücksetzen
@ -1381,6 +1446,7 @@ issues.filter_sort.moststars=Meiste Favoriten
issues.filter_sort.feweststars=Wenigste Favoriten
issues.filter_sort.mostforks=Meiste Forks
issues.filter_sort.fewestforks=Wenigste Forks
issues.keyword_search_unavailable=Zurzeit ist die Stichwort-Suche nicht verfügbar. Bitte wende dich an den Website-Administrator.
issues.action_open=Öffnen
issues.action_close=Schließen
issues.action_label=Label
@ -1429,8 +1495,17 @@ issues.ref_closed_from=`<a href="%[3]s">hat dieses Issue %[4]s geschlossen</a> <
issues.ref_reopened_from=`<a href="%[3]s">hat dieses Issue %[4]s</a> <a id="%[1]s" href="#%[1]s">%[2]s</a> wieder geöffnet`
issues.ref_from=`von %[1]s`
issues.author=Autor
issues.author_helper=Dieser Benutzer ist der Autor.
issues.role.owner=Besitzer
issues.role.owner_helper=Dieser Benutzer ist der Besitzer dieses Repositorys.
issues.role.member=Mitglied
issues.role.member_helper=Dieser Benutzer ist Mitglied der Organisation, die dieses Repository besitzt.
issues.role.collaborator=Mitarbeiter
issues.role.collaborator_helper=Dieser Benutzer wurde zur Zusammenarbeit am Repository eingeladen.
issues.role.first_time_contributor=Erstmaliger Mitwirkender
issues.role.first_time_contributor_helper=Dies ist der erste Beitrag dieses Benutzers zum Repository.
issues.role.contributor=Mitwirkender
issues.role.contributor_helper=Dieser Benutzer hat schon zuvor zu dem Repository beigetragen.
issues.re_request_review=Review erneut anfordern
issues.is_stale=Seit diesem Review gab es Änderungen an diesem PR
issues.remove_request_review=Review-Anfrage entfernen
@ -1445,6 +1520,9 @@ issues.label_title=Labelname
issues.label_description=Labelbeschreibung
issues.label_color=Labelfarbe
issues.label_exclusive=Exklusiv
issues.label_archive=Label archivieren
issues.label_archived_filter=Archivierte Labels anzeigen
issues.label_archive_tooltip=Archivierte Labels werden bei der Suche nach Label standardmäßig von den Vorschlägen ausgeschlossen.
issues.label_exclusive_desc=Nenne das Label <code>Bereich/Element</code> um es gegenseitig ausschließend mit anderen <code>Bereich/</code> Labels zu machen.
issues.label_exclusive_warning=Alle im Konflikt stehenden Labels werden beim Bearbeiten der Labels eines Issues oder eines Pull-Requests entfernt.
issues.label_count=%d Label
@ -1499,6 +1577,7 @@ issues.tracking_already_started=`Du hast die Zeiterfassung bereits in <a href="%
issues.stop_tracking=Zeiterfassung stoppen
issues.stop_tracking_history=hat die Zeiterfassung %s angehalten
issues.cancel_tracking=Verwerfen
issues.cancel_tracking_history=`hat die Zeiterfassung %s abgebrochen`
issues.add_time=Zeit manuell hinzufügen
issues.del_time=Diese Zeiterfassung löschen
issues.add_time_short=Zeit hinzufügen
@ -1522,6 +1601,7 @@ issues.due_date_form=JJJJ-MM-TT
issues.due_date_form_add=Fälligkeitsdatum hinzufügen
issues.due_date_form_edit=Bearbeiten
issues.due_date_form_remove=Entfernen
issues.due_date_not_writer=Du musst Schreibrechte für dieses Repository haben, um das Fälligkeitsdatum zu ändern.
issues.due_date_not_set=Kein Fälligkeitsdatum gesetzt.
issues.due_date_added=hat %[2]s das Fälligkeitsdatum %[1]s hinzugefügt
issues.due_date_modified=ändert das Abgabedatum von %[2]s auf %[1]s %[3]s s
@ -1577,6 +1657,7 @@ issues.review.pending.tooltip=Dieser Kommentar ist derzeit nicht für andere Ben
issues.review.review=Review
issues.review.reviewers=Reviewer
issues.review.outdated=Veraltet
issues.review.outdated_description=Der Inhalt hat sich geändert, seit dieser Kommentar abgegeben wurde
issues.review.option.show_outdated_comments=Veraltete Kommentare anzeigen
issues.review.option.hide_outdated_comments=Veraltete Kommentare ausblenden
issues.review.show_outdated=Veraltete anzeigen
@ -1618,6 +1699,13 @@ pulls.switch_comparison_type=Vergleichstyp wechseln
pulls.switch_head_and_base=Head und Base vertauschen
pulls.filter_branch=Branch filtern
pulls.no_results=Keine Ergebnisse verfügbar.
pulls.show_all_commits=Alle Commits anzeigen
pulls.show_changes_since_your_last_review=Zeige Änderungen seit deinem letzten Review
pulls.showing_only_single_commit=Nur Änderungen aus Commit %[1]s werden angezeigt
pulls.showing_specified_commit_range=Zeige nur die Änderungen zwischen %[1]s..%[2]s
pulls.select_commit_hold_shift_for_range=Commit auswählen. Halte Shift + klicke, um eine Reihe auszuwählen
pulls.review_only_possible_for_full_diff=Ein Review ist nur möglich, wenn das vollständige Diff angezeigt wird
pulls.filter_changes_by_commit=Nach Commit filtern
pulls.nothing_to_compare=Diese Branches sind identisch. Es muss kein Pull-Request erstellt werden.
pulls.nothing_to_compare_and_allow_empty_pr=Diese Branches sind gleich. Der Pull-Request wird leer sein.
pulls.has_pull_request=`Es existiert bereits ein Pull-Request zwischen diesen beiden Branches: <a href="%[1]s">%[2]s#%[3]d</a>`
@ -1649,6 +1737,12 @@ pulls.is_empty=Die Änderungen an diesem Branch sind bereits auf dem Zielbranch.
pulls.required_status_check_failed=Einige erforderliche Prüfungen waren nicht erfolgreich.
pulls.required_status_check_missing=Einige erforderliche Prüfungen fehlen.
pulls.required_status_check_administrator=Als Administrator kannst du diesen Pull-Request weiterhin mergen.
pulls.blocked_by_approvals=Dieser Pull-Request hat noch nicht genügend Zustimmungen. %d von %d Zustimmungen erteilt.
pulls.blocked_by_rejection=Dieser Pull-Request hat Änderungen, die von einem offiziellen Reviewer angefragt wurden.
pulls.blocked_by_official_review_requests=Dieser Pull Request hat offizielle Review-Anfragen.
pulls.blocked_by_outdated_branch=Dieser Pull Request ist blockiert, da er veraltet ist.
pulls.blocked_by_changed_protected_files_1=Dieser Pull Request ist blockiert, weil er eine geschützte Datei ändert:
pulls.blocked_by_changed_protected_files_n=Dieser Pull Request ist blockiert, weil er geschützte Dateien ändert:
pulls.can_auto_merge_desc=Dieser Pull-Request kann automatisch gemergt werden.
pulls.cannot_auto_merge_desc=Dieser Pull-Request kann nicht automatisch gemergt werden, da es Konflikte gibt.
pulls.cannot_auto_merge_helper=Bitte manuell mergen, um die Konflikte zu beheben.
@ -1683,6 +1777,7 @@ pulls.rebase_conflict_summary=Fehlermeldung
pulls.unrelated_histories=Merge fehlgeschlagen: Der Head des Merges und die Basis haben keinen gemeinsamen Verlauf. Hinweis: Versuche eine andere Strategie
pulls.merge_out_of_date=Merge fehlgeschlagen: Während des Mergens wurde die Basis aktualisiert. Hinweis: Versuche es erneut.
pulls.head_out_of_date=Mergen fehlgeschlagen: Der Head wurde aktualisiert während der Merge erstellt wurde. Tipp: Versuche es erneut.
pulls.has_merged=Fehler: Der Pull-Request wurde gemerged, du kannst den Zielbranch nicht wieder mergen oder ändern.
pulls.push_rejected=Mergen fehlgeschlagen: Der Push wurde abgelehnt. Überprüfe die Git Hooks für dieses Repository.
pulls.push_rejected_summary=Vollständige Ablehnungsmeldung
pulls.push_rejected_no_message=Mergen fehlgeschlagen: Der Push wurde abgelehnt, aber es gab keine Fehlermeldung.<br>Überprüfe die Git Hooks für dieses Repository
@ -1723,6 +1818,7 @@ pulls.auto_merge_canceled_schedule_comment=`hat den Automerge für diesen Pull-R
pulls.delete.title=Diesen Pull-Request löschen?
pulls.delete.text=Willst du diesen Pull-Request wirklich löschen? (Dies wird den Inhalt unwiderruflich löschen. Überlege, ob du ihn nicht lieber schließen willst, um ihn zu archivieren)
pulls.recently_pushed_new_branches=Du hast auf den Branch <strong>%[1]s</strong> %[2]s gepusht
pull.deleted_branch=(gelöscht):%s
@ -1732,6 +1828,7 @@ milestones.update_ago=%s aktualisiert
milestones.no_due_date=Kein Fälligkeitsdatum
milestones.open=Öffnen
milestones.close=Schließen
milestones.new_subheader=Benutze Meilensteine, um Issues zu organisieren und den Fortschritt darzustellen.
milestones.completeness=%d%% abgeschlossen
milestones.create=Meilenstein erstellen
milestones.title=Titel
@ -1748,11 +1845,26 @@ milestones.edit_success=Meilenstein "%s" wurde aktualisiert.
milestones.deletion=Meilenstein löschen
milestones.deletion_desc=Das Löschen des Meilensteins entfernt ihn von allen Issues. Fortfahren?
milestones.deletion_success=Der Meilenstein wurde gelöscht.
milestones.filter_sort.earliest_due_data=Frühestes Fälligkeitsdatum
milestones.filter_sort.latest_due_date=Spätestes Fälligkeitsdatum
milestones.filter_sort.least_complete=Am wenigsten vollständig
milestones.filter_sort.most_complete=Vollständigste
milestones.filter_sort.most_issues=Meiste Issues
milestones.filter_sort.least_issues=Wenigste Issues
signing.will_sign=Dieser Commit wird mit dem Key "%s" signiert werden.
signing.wont_sign.error=Es gab einen Fehler bei der Prüfung, ob der Commit signiert werden kann.
signing.wont_sign.nokey=Es ist kein Schlüssel zum Signieren dieses Commits verfügbar.
signing.wont_sign.never=Commits werden nie signiert.
signing.wont_sign.always=Commits werden immer signiert.
signing.wont_sign.pubkey=Der Commit wird nicht signiert, da du keinen öffentlichen Schlüssel mit deinem Account verknüpft hast.
signing.wont_sign.twofa=Du musst Zwei-Faktor-Authentifizierung aktivieren, damit Commits signiert werden.
signing.wont_sign.parentsigned=Der Commit wird nicht signiert werden, da der vorherige Commit nicht signiert ist.
signing.wont_sign.basesigned=Der Merge Commit wird nicht signiert werden, da der Basis-Commit nicht signiert ist.
signing.wont_sign.headsigned=Der Merge Commit wird nicht signiert werden, da der Head-Commit nicht signiert ist.
signing.wont_sign.commitssigned=Der Merge Commit wird nicht signiert werden, da alle zugehörigen Commits nicht signiert sind.
signing.wont_sign.approved=Der Merge Commit wird nicht signiert werden, da der Pull Request nicht genehmigt wurde.
signing.wont_sign.not_signed_in=Du bist nicht eingeloggt.
ext_wiki=Zugriff auf externes Wiki
ext_wiki.desc=Verweis auf externes Wiki.
@ -1882,7 +1994,9 @@ settings.mirror_settings.docs.disabled_push_mirror.info=Push-Mirrors wurden von
settings.mirror_settings.docs.no_new_mirrors=Dein Repository spiegelt Änderungen von oder zu einem anderen Repository. Bitte beachte, dass du gerade keine neuen Mirror anlegen kannst.
settings.mirror_settings.docs.can_still_use=Obwohl du existierende Mirrors gerade nicht bearbeiten oder neu anlegen kannst, sind bestehende Mirrors weiterhin nutzbar.
settings.mirror_settings.docs.pull_mirror_instructions=Um einen Pull-Mirror einzurichten, konsultiere bitte:
settings.mirror_settings.docs.more_information_if_disabled=Hier kannst du mehr über Push- und Pull-Mirrors erfahren:
settings.mirror_settings.docs.doc_link_title=Wie spiegele ich Repositories?
settings.mirror_settings.docs.doc_link_pull_section=den Abschnitt "Von einem entfernten Repository pullen" in der Dokumentation.
settings.mirror_settings.docs.pulling_remote_title=Aus einem Remote-Repository pullen
settings.mirror_settings.mirrored_repository=Gespiegeltes Repository
settings.mirror_settings.direction=Richtung
@ -1892,8 +2006,11 @@ settings.mirror_settings.last_update=Letzte Aktualisierung
settings.mirror_settings.push_mirror.none=Keine Push-Mirrors konfiguriert
settings.mirror_settings.push_mirror.remote_url=URL zum Git-Remote-Repository
settings.mirror_settings.push_mirror.add=Push-Mirror hinzufügen
settings.mirror_settings.push_mirror.edit_sync_time=Mirror-Sync-Intervall anpassen
settings.sync_mirror=Jetzt synchronisieren
settings.pull_mirror_sync_in_progress=Aktuell werden Änderungen von %s gepullt.
settings.push_mirror_sync_in_progress=Aktuell werden Änderungen auf %s gepusht.
settings.site=Webseite
settings.update_settings=Einstellungen speichern
settings.update_mirror_settings=Mirror-Einstellungen aktualisieren
@ -1960,6 +2077,7 @@ settings.transfer.rejected=Repository-Übertragung wurde abgelehnt.
settings.transfer.success=Repository-Übertragung war erfolgreich.
settings.transfer_abort=Übertragung abbrechen
settings.transfer_abort_invalid=Du kannst nur eingeleitete Repository-Übertragung abbrechen.
settings.transfer_abort_success=Die Repository-Übertragung zu %s wurde abgebrochen.
settings.transfer_desc=Übertrage dieses Repository auf einen anderen Benutzer oder eine Organisation, in der du Admin-Rechte hast.
settings.transfer_form_title=Gib den Repository-Namen zur Bestätigung ein:
settings.transfer_in_progress=Es gibt derzeit eine laufende Übertragung. Bitte brich diese ab, wenn du dieses Repository an einen anderen Benutzer übertragen möchtest.
@ -2026,12 +2144,14 @@ settings.webhook_deletion_desc=Das Entfernen eines Webhooks löscht seine Einste
settings.webhook_deletion_success=Webhook wurde entfernt.
settings.webhook.test_delivery=Senden testen
settings.webhook.test_delivery_desc=Teste diesen Webhook mit einem Fake-Event.
settings.webhook.test_delivery_desc_disabled=Um diesen Webhook mit einem Fake-Event zu testen, aktiviere ihn.
settings.webhook.request=Anfrage
settings.webhook.response=Antwort
settings.webhook.headers=Kopfzeilen
settings.webhook.payload=Inhalt
settings.webhook.body=Inhalt
settings.webhook.replay.description=Diesen Webhook wiederholen.
settings.webhook.replay.description_disabled=Um diesen Webhook wiederzugeben, aktiviere ihn.
settings.webhook.delivery.success=Ein Event wurde zur Sendungs-Warteschlange hinzugefügt. Es kann ein paar Sekunden dauern, bevor es im Verlauf erscheint.
settings.githooks_desc=Git-Hooks werden von Git selbst bereitgestellt. Du kannst die Dateien der unterstützten Hooks in der Liste unten bearbeiten, um eigene Operationen einzubinden.
settings.githook_edit_desc=Wenn ein Hook nicht aktiv ist, wird der Standardinhalt benutzt. Lasse den Inhalt leer, um den Hook zu deaktivieren.
@ -2191,6 +2311,7 @@ settings.dismiss_stale_approvals_desc=Wenn neue Commits gepusht werden, die den
settings.require_signed_commits=Signierte Commits erforderlich
settings.require_signed_commits_desc=Pushes auf diesen Branch ablehnen, wenn Commits nicht signiert oder nicht überprüfbar sind.
settings.protect_branch_name_pattern=Muster für geschützte Branchnamen
settings.protect_branch_name_pattern_desc=Geschützte Branch-Namensmuster. Lies <a href="github.com/gobwas/glob">die Dokumentation</a> für die Muster-Syntax. Beispiele: main, release/**
settings.protect_patterns=Muster
settings.protect_protected_file_patterns=Geschützte Dateimuster (durch Semikolon ';' getrennt):
settings.protect_protected_file_patterns_desc=Geschützte Dateien dürfen nicht direkt geändert werden, auch wenn der Benutzer Rechte hat, Dateien in diesem Branch hinzuzufügen, zu bearbeiten oder zu löschen. Mehrere Muster können mit Semikolon (';') getrennt werden. Siehe <a href='https://pkg.go.dev/github.com/gobwas/glob#Compile'>github.com/gobwas/glob</a> Dokumentation zur Mustersyntax. Beispiele: <code>.drone.yml</code>, <code>/docs/**/*.txt</code>.
@ -2227,18 +2348,26 @@ settings.tags.protection.allowed.teams=Erlaubte Teams
settings.tags.protection.allowed.noone=Niemand
settings.tags.protection.create=Tag schützen
settings.tags.protection.none=Es gibt keine geschützten Tags.
settings.tags.protection.pattern.description=Du kannst einen einzigen Namen oder ein globales Schema oder einen regulären Ausdruck verwenden, um mehrere Tags zu schützen. Mehr dazu im <a target="_blank" rel="noopener" href="https://docs.gitea.com/usage/protected-tags">Guide für geschützte Tags (Englisch)</a>.
settings.bot_token=Bot-Token
settings.chat_id=Chat-ID
settings.thread_id=Thread-ID
settings.matrix.homeserver_url=Homeserver-URL
settings.matrix.room_id=Raum-ID
settings.matrix.message_type=Nachrichtentyp
settings.archive.button=Repo archivieren
settings.archive.header=Dieses Repo archivieren
settings.archive.text=Durch das Archivieren wird ein Repo vollständig schreibgeschützt. Es wird vom Dashboard versteckt. Niemand (nicht einmal du!) wird in der Lage sein, neue Commits zu erstellen oder Issues oder Pull-Requests zu öffnen.
settings.archive.success=Das Repo wurde erfolgreich archiviert.
settings.archive.error=Beim Versuch, das Repository zu archivieren, ist ein Fehler aufgetreten. Weitere Details finden sich im Log.
settings.archive.error_ismirror=Du kannst keinen Repo-Mirror archivieren.
settings.archive.branchsettings_unavailable=Branch-Einstellungen sind nicht verfügbar wenn das Repo archiviert ist.
settings.archive.tagsettings_unavailable=Tag Einstellungen sind nicht verfügbar, wenn das Repo archiviert wurde.
settings.unarchive.button=Archivieren rückgängig machen
settings.unarchive.header=Archivieren dieses Repositories rückgängig machen
settings.unarchive.text=Durch das Aufheben der Archivierung kann das Repo wieder Commits und Pushes sowie neue Issues und Pull-Requests empfangen.
settings.unarchive.success=Die Archivierung des Repos wurde erfolgreich wieder rückgängig gemacht.
settings.unarchive.error=Beim Versuch, die Archivierung des Repos aufzuheben, ist ein Fehler aufgetreten. Weitere Details finden sich im Log.
settings.update_avatar_success=Der Repository-Avatar wurde aktualisiert.
settings.lfs=LFS
settings.lfs_filelist=LFS-Dateien, die in diesem Repository gespeichert sind
@ -2305,6 +2434,7 @@ diff.show_more=Mehr anzeigen
diff.load=Diff laden
diff.generated=generiert
diff.vendored=vendored
diff.comment.add_line_comment=Einzelnen Kommentar hinzufügen
diff.comment.placeholder=Kommentieren...
diff.comment.markdown_info=Styling mit Markdown wird unterstützt.
diff.comment.add_single_comment=Einzelnen Kommentar hinzufügen
@ -2361,6 +2491,7 @@ release.edit_release=Release aktualisieren
release.delete_release=Release löschen
release.delete_tag=Tag löschen
release.deletion=Release löschen
release.deletion_desc=Beim Entfernen wird ein Release nur von Gitea gelöscht. Es betrifft weder den Git-Tag, noch den Inhalt des Repos oder seinen Änderungsverlauf. Fortfahren?
release.deletion_success=Das Release wurde gelöscht.
release.deletion_tag_desc=Löscht dieses Tag aus dem Projektarchiv. Repository-Inhalt und Verlauf bleiben unverändert. Fortfahren?
release.deletion_tag_success=Der Tag wurde gelöscht.
@ -2376,10 +2507,12 @@ release.releases_for=Releases für %s
release.tags_for=Tags für %s
branch.name=Branchname
branch.search=Branch suchen
branch.already_exists=Ein Branch mit dem Namen "%s" existiert bereits.
branch.delete_head=Löschen
branch.delete=Branch "%s" löschen
branch.delete_html=Branch löschen
branch.delete_desc=Das Löschen eines Branches ist permanent. Obwohl der Branch für eine kurze Zeit weiter existieren könnte, kann diese Aktion in den meisten Fällen NICHT rückgängig gemacht werden. Fortfahren?
branch.deletion_success=Branch "%s" wurde gelöscht.
branch.deletion_failed=Branch "%s" konnte nicht gelöscht werden.
branch.delete_branch_has_new_commits=Der Branch "%s" kann nicht gelöscht werden, da seit dem letzten Merge neue Commits hinzugefügt wurden.
@ -2419,6 +2552,7 @@ tag.create_success=Tag "%s" wurde erstellt.
topic.manage_topics=Themen verwalten
topic.done=Fertig
topic.count_prompt=Du kannst nicht mehr als 25 Themen auswählen
topic.format_prompt=Themen müssen entweder mit einem Buchstaben oder einer Ziffer beginnen. Sie können Bindestriche („-“) und Punkte ('.') enthalten und bis zu 35 Zeichen lang sein. Nur Kleinbuchstaben sind zulässig.
find_file.go_to_file=Datei suchen
find_file.no_matching=Keine passende Datei gefunden
@ -2457,6 +2591,7 @@ form.create_org_not_allowed=Du bist nicht berechtigt, eine Organisation zu erste
settings=Einstellungen
settings.options=Organisation
settings.full_name=Vollständiger Name
settings.email=Kontakt-E-Mail-Adresse
settings.website=Webseite
settings.location=Standort
settings.permission=Berechtigungen
@ -2470,6 +2605,7 @@ settings.visibility.private_shortname=Privat
settings.update_settings=Einstellungen speichern
settings.update_setting_success=Organisationseinstellungen wurden aktualisiert.
settings.change_orgname_prompt=Hinweis: Das Ändern des Organisationsnamens wird auch die URL deiner Organisation ändern und den alten Namen freigeben.
settings.change_orgname_redirect_prompt=Der alte Name wird weiterleiten, bis er wieder beansprucht wird.
settings.update_avatar_success=Der Organisationsavatar wurde aktualisiert.
settings.delete=Organisation löschen
@ -2545,15 +2681,19 @@ teams.all_repositories_helper=Team hat Zugriff auf alle Repositories. Wenn dies
teams.all_repositories_read_permission_desc=Dieses Team gewährt <strong>Lese</strong>-Zugriff auf <strong>Repositories</strong>: Mitglieder können Repositories ansehen und klonen.
teams.all_repositories_write_permission_desc=Dieses Team gewährt <strong>Schreib</strong>-Zugriff auf <strong>alle Repositories</strong>: Mitglieder können Repositories lesen und auf sie pushen.
teams.all_repositories_admin_permission_desc=Dieses Team gewährt <strong>Administrator</strong>-Zugriff auf <strong>alle Repositories</strong>: Mitglieder können Repositories lesen, auf sie pushen und Mitwirkende zu Repositorys hinzufügen.
teams.invite.title=Du wurdest eingeladen, dem Team <strong>%s</strong> in der Organisation <strong>%s</strong> beizutreten.
teams.invite.by=Von %s eingeladen
teams.invite.description=Bitte klicke auf die folgende Schaltfläche, um dem Team beizutreten.
[admin]
dashboard=Dashboard
identity_access=Identität & Zugriff
users=Benutzerkonten
organizations=Organisationen
assets=Code-Assets
repositories=Repositories
hooks=Webhooks
integrations=Integrationen
authentication=Authentifizierungsquellen
emails=Benutzer E-Mails
config=Konfiguration
@ -2562,6 +2702,7 @@ monitor=Monitoring
first_page=Erste
last_page=Letzte
total=Gesamt: %d
settings=Administratoreinstellungen
dashboard.new_version_hint=Gitea %s ist jetzt verfügbar, deine derzeitige Version ist %s. Weitere Details findest du im <a target="_blank" rel="noreferrer" href="https://blog.gitea.io">Blog</a>.
dashboard.statistic=Übersicht
@ -2574,11 +2715,13 @@ dashboard.clean_unbind_oauth=Nicht verbundene OAuth-Verbindungen löschen
dashboard.clean_unbind_oauth_success=Alle unverbundene OAuth-Verbindungen wurden gelöscht.
dashboard.task.started=Aufgabe gestartet: %[1]s
dashboard.task.process=Aufgabe: %[1]s
dashboard.task.cancelled=Aufgabe: %[1]s abgebrochen: %[3]s
dashboard.task.error=Fehler in Aufgabe: %[1]s: %[3]s
dashboard.task.finished=Aufgabe: %[1]s, gestartet von %[2]s, wurde beendet
dashboard.task.unknown=Unbekannte Aufgabe: %[1]s
dashboard.cron.started=Cron gestartet: %[1]s
dashboard.cron.process=Cron: %[1]s
dashboard.cron.cancelled=Cron: %[1]s abgebrochen: %[3]s
dashboard.cron.error=Fehler in Cron: %s: %[3]s
dashboard.cron.finished=Cron: %[1]s ist beendet
dashboard.delete_inactive_accounts=Alle nicht aktivierten Konten löschen
@ -2588,6 +2731,7 @@ dashboard.delete_repo_archives.started=Löschen aller Repository-Archive gestart
dashboard.delete_missing_repos=Alle Repository-Datensätze mit verloren gegangenen Git-Dateien löschen
dashboard.delete_missing_repos.started=Alle Repositories löschen, die den Git-File-Task nicht gestartet haben.
dashboard.delete_generated_repository_avatars=Generierte Repository-Avatare löschen
dashboard.sync_repo_branches=Fehlende Branches aus den Git-Daten in die Datenbank synchronisieren
dashboard.update_mirrors=Mirrors aktualisieren
dashboard.repo_health_check=Healthchecks für alle Repositories ausführen
dashboard.check_repo_stats=Überprüfe alle Repository-Statistiken
@ -2604,6 +2748,7 @@ dashboard.reinit_missing_repos=Alle Git-Repositories neu einlesen, für die Eint
dashboard.sync_external_users=Externe Benutzerdaten synchronisieren
dashboard.cleanup_hook_task_table=Hook-Task-Tabelle bereinigen
dashboard.cleanup_packages=Veraltete Pakete löschen
dashboard.cleanup_actions=Abgelaufene Logs und Artefakte von Actions bereinigen
dashboard.server_uptime=Server-Uptime
dashboard.current_goroutine=Aktuelle Goroutinen
dashboard.current_memory_usage=Aktuelle Speichernutzung
@ -2641,6 +2786,9 @@ dashboard.gc_lfs=Garbage-Collection für LFS Meta-Objekte ausführen
dashboard.stop_zombie_tasks=Zombie-Aufgaben stoppen
dashboard.stop_endless_tasks=Endlose Aufgaben stoppen
dashboard.cancel_abandoned_jobs=Aufgegebene Jobs abbrechen
dashboard.start_schedule_tasks=Terminierte Aufgaben starten
dashboard.sync_branch.started=Synchronisierung der Branches gestartet
dashboard.rebuild_issue_indexer=Issue-Indexer neu bauen
users.user_manage_panel=Benutzerkontenverwaltung
users.new_account=Benutzerkonto erstellen
@ -2649,6 +2797,9 @@ users.full_name=Vollständiger Name
users.activated=Aktiviert
users.admin=Administrator
users.restricted=Eingeschränkt
users.reserved=Reserviert
users.bot=Bot
users.remote=Remote
users.2fa=2FA
users.repos=Repos
users.created=Registriert am
@ -2695,6 +2846,7 @@ users.list_status_filter.is_prohibit_login=Login verbieten
users.list_status_filter.not_prohibit_login=Login erlaubt
users.list_status_filter.is_2fa_enabled=2FA aktiviert
users.list_status_filter.not_2fa_enabled=2FA deaktiviert
users.details=Benutzerdetails
emails.email_manage_panel=Benutzer-E-Mail-Verwaltung
emails.primary=Primär
@ -2726,10 +2878,12 @@ repos.stars=Favoriten
repos.forks=Forks
repos.issues=Issues
repos.size=Größe
repos.lfs_size=LFS-Größe
packages.package_manage_panel=Paketverwaltung
packages.total_size=Gesamtgröße: %s
packages.unreferenced_size=Nicht referenzierte Größe: %s
packages.cleanup=Veraltete Daten löschen
packages.owner=Besitzer
packages.creator=Ersteller
packages.name=Name
@ -2740,10 +2894,12 @@ packages.size=Größe
packages.published=Veröffentlicht
defaulthooks=Standard-Webhooks
defaulthooks.desc=Webhooks senden automatisch eine HTTP-POST-Anfrage an einen Server, wenn bestimmte Gitea-Events ausgelöst werden. Hier definierte Webhooks sind die Standardwerte, die in alle neuen Repositories kopiert werden. Mehr Infos findest du in der <a target="_blank" rel="noopener" href="https://docs.gitea.com/usage/webhooks">Webhooks-Anleitung</a> (auf Englisch).
defaulthooks.add_webhook=Standard-Webhook hinzufügen
defaulthooks.update_webhook=Standard-Webhook aktualisieren
systemhooks=System-Webhooks
systemhooks.desc=Webhooks senden automatisch HTTP-POST-Anfragen an einen Server, wenn bestimmte Gitea-Events ausgelöst werden. Hier definierte Webhooks werden auf alle Repositories des Systems übertragen, beachte daher mögliche Performance-Einbrüche. Mehr Infos findest du in der <a target="_blank" rel="noopener" href="https://docs.gitea.com/usage/webhooks">Webhooks-Anleitung</a> (auf Englisch).
systemhooks.add_webhook=System-Webhook hinzufügen
systemhooks.update_webhook=System-Webhook aktualisieren
@ -2836,6 +2992,7 @@ auths.sspi_default_language=Standardsprache für Benutzer
auths.sspi_default_language_helper=Standardsprache für Benutzer, die automatisch mit der SSPI Authentifizierungsmethode erstellt wurden. Leer lassen, wenn du es bevorzugst, dass eine Sprache automatisch erkannt wird.
auths.tips=Tipps
auths.tips.oauth2.general=OAuth2-Authentifizierung
auths.tips.oauth2.general.tip=Beim Registrieren einer OAuth2-Anwendung sollte die Callback-URL folgendermaßen lauten:
auths.tip.oauth2_provider=OAuth2-Anbieter
auths.tip.bitbucket=Registriere einen neuen OAuth-Consumer unter https://bitbucket.org/account/user/<dein-benutzername>/oauth-consumers/new und füge die Berechtigung „Account“ „Read“ hinzu.
auths.tip.nextcloud=Registriere über das "Settings -> Security -> OAuth 2.0 client"-Menü einen neuen "OAuth consumer" auf der Nextcloud-Instanz
@ -2847,6 +3004,7 @@ auths.tip.google_plus=Du erhältst die OAuth2-Client-Zugangsdaten in der Google-
auths.tip.openid_connect=Benutze die OpenID-Connect-Discovery-URL (<server>/.well-known/openid-configuration), um die Endpunkte zu spezifizieren
auths.tip.twitter=Gehe auf https://dev.twitter.com/apps, erstelle eine Anwendung und stelle sicher, dass die Option „Allow this application to be used to Sign in with Twitter“ aktiviert ist
auths.tip.discord=Erstelle unter https://discordapp.com/developers/applications/me eine neue Anwendung.
auths.tip.gitea=Registriere eine neue OAuth2-Anwendung. Eine Anleitung findest du unter https://docs.gitea.com/development/oauth2-provider/
auths.tip.yandex=`Erstelle eine neue Anwendung auf https://oauth.yandex.com/client/new. Wähle folgende Berechtigungen aus dem "Yandex.Passport API" Bereich: "Zugriff auf E-Mail-Adresse", "Zugriff auf Benutzeravatar" und "Zugriff auf Benutzername, Vor- und Nachname, Geschlecht"`
auths.tip.mastodon=Gebe eine benutzerdefinierte URL für die Mastodon-Instanz ein, mit der du dich authentifizieren möchtest (oder benutze die standardmäßige)
auths.edit=Authentifikationsquelle bearbeiten
@ -2876,6 +3034,7 @@ config.disable_router_log=Router-Log deaktivieren
config.run_user=Ausführen als
config.run_mode=Laufzeit-Modus
config.git_version=Git-Version
config.app_data_path=App-Datenpfad
config.repo_root_path=Repository-Wurzelpfad
config.lfs_root_path=LFS-Wurzelpfad
config.log_file_root_path=Logdateipfad
@ -3027,8 +3186,10 @@ monitor.queue.name=Name
monitor.queue.type=Typ
monitor.queue.exemplar=Beispieltyp
monitor.queue.numberworkers=Anzahl der Worker
monitor.queue.activeworkers=Aktive Worker
monitor.queue.maxnumberworkers=Maximale Anzahl der Worker
monitor.queue.numberinqueue=Nummer in der Warteschlange
monitor.queue.review_add=Worker hinzufügen / prüfen
monitor.queue.settings.title=Pool-Einstellungen
monitor.queue.settings.desc=Pools wachsen dynamisch basierend auf der Blockierung der Arbeitswarteschlange.
monitor.queue.settings.maxnumberworkers=Maximale Anzahl an Workern
@ -3149,6 +3310,7 @@ desc=Repository-Pakete verwalten.
empty=Noch keine Pakete vorhanden.
empty.documentation=Weitere Informationen zur Paket-Registry findest Du in der <a target="_blank" rel="noopener noreferrer" href="%s">Dokumentation</a>.
empty.repo=Hast du ein Paket hochgeladen, das hier nicht angezeigt wird? Gehe zu den <a href="%[1]s">Paketeinstellungen</a> und verlinke es mit diesem Repo.
registry.documentation=Für weitere Informationen zur %s-Registry, schaue in der <a target="_blank" rel="noopener noreferrer" href="%s">Dokumentation</a> nach.
filter.type=Typ
filter.type.all=Alle
filter.no_result=Keine Ergebnisse mit diesen Kriterien gefunden.
@ -3238,6 +3400,8 @@ pub.install=Um das Paket mit Dart zu installieren, führe den folgenden Befehl a
pypi.requires=Erfordert Python
pypi.install=Nutze folgenden Befehl, um das Paket mit pip zu installieren:
rpm.registry=Diese Registry über die Kommandozeile einrichten:
rpm.distros.redhat=auf RedHat-basierten Distributionen
rpm.distros.suse=auf SUSE-basierten Distributionen
rpm.install=Nutze folgenden Befehl, um das Paket zu installieren:
rubygems.install=Um das Paket mit gem zu installieren, führe den folgenden Befehl aus:
rubygems.install2=oder füg es zum Gemfile hinzu:
@ -3262,14 +3426,17 @@ settings.delete.success=Das Paket wurde gelöscht.
settings.delete.error=Löschen des Pakets fehlgeschlagen.
owner.settings.cargo.title=Cargo-Registry-Index
owner.settings.cargo.initialize=Index initialisieren
owner.settings.cargo.initialize.description=Ein spezielles Index-Repository wird benötigt, um die Cargo-Registry zu nutzen. Diese Option wird dieses Repository (neu) erstellen und automatisch konfigurieren.
owner.settings.cargo.initialize.error=Cargo-Index konnte nicht initialisiert werden: %v
owner.settings.cargo.initialize.success=Der Cargo-Index wurde erfolgreich erstellt.
owner.settings.cargo.rebuild=Index neu erstellen
owner.settings.cargo.rebuild.description=Neubauen kann hilfreich sein, wenn der Index nicht mit den gespeicherten Cargo-Paketen synchronisiert ist.
owner.settings.cargo.rebuild.error=Cargo-Index konnte nicht neu erstellt werden: %v
owner.settings.cargo.rebuild.success=Der Cargo-Index wurde erfolgreich neu erstellt.
owner.settings.cleanuprules.title=Bereinigungsregeln verwalten
owner.settings.cleanuprules.add=Bereinigungsregel hinzufügen
owner.settings.cleanuprules.edit=Bereinigungsregel bearbeiten
owner.settings.cleanuprules.none=Keine Bereinigungs-Regeln verfügbar. Bitte konsultiere die Dokumentation.
owner.settings.cleanuprules.preview=Vorschau der Bereinigungsregel
owner.settings.cleanuprules.preview.overview=%d Pakete sollen entfernt werden.
owner.settings.cleanuprules.preview.none=Bereinigungsregel stimmt mit keinem Paket überein.
@ -3288,6 +3455,7 @@ owner.settings.cleanuprules.success.update=Bereinigungsregel wurde aktualisiert.
owner.settings.cleanuprules.success.delete=Bereinigungsregel wurde gelöscht.
owner.settings.chef.title=Chef-Registry
owner.settings.chef.keypair=Schlüsselpaar generieren
owner.settings.chef.keypair.description=Ein Schlüsselpaar ist notwendig, um mit der Chef-Registry zu authentifizieren. Wenn du bereits eins erstellt hast, wird dieses durch eine Neuerstellung verworfen.
[secrets]
secrets=Secrets
@ -3314,6 +3482,7 @@ status.waiting=Wartend
status.running=Laufend
status.success=Erfolg
status.failure=Fehler
status.cancelled=Abgebrochen
status.skipped=Übersprungen
status.blocked=Blockiert
@ -3330,6 +3499,7 @@ runners.labels=Labels
runners.last_online=Letzte Online-Zeit
runners.runner_title=Runner
runners.task_list=Letzte Aufgaben dieses Runners
runners.task_list.no_tasks=Es gibt noch keine Aufgabe.
runners.task_list.run=Ausführen
runners.task_list.status=Status
runners.task_list.repository=Repository
@ -3350,17 +3520,45 @@ runners.status.idle=Inaktiv
runners.status.active=Aktiv
runners.status.offline=Offline
runners.version=Version
runners.reset_registration_token=Registrierungs-Token zurücksetzen
runners.reset_registration_token_success=Runner-Registrierungstoken erfolgreich zurückgesetzt
runs.all_workflows=Alle Workflows
runs.commit=Commit
runs.scheduled=Geplant
runs.pushed_by=gepusht von
runs.invalid_workflow_helper=Die Workflow-Konfigurationsdatei ist ungültig. Bitte überprüfe Deine Konfigurationsdatei: %s
runs.no_matching_runner_helper=Kein passender Runner: %s
runs.actor=Initiator
runs.status=Status
runs.actors_no_select=Alle Initiatoren
runs.status_no_select=Alle Status
runs.no_results=Keine passenden Ergebnisse gefunden.
runs.no_runs=Der Workflow hat noch keine Ausführungen.
workflow.disable=Workflow deaktivieren
workflow.disable_success=Workflow '%s' erfolgreich deaktiviert.
workflow.enable=Workflow aktivieren
workflow.enable_success=Workflow '%s' erfolgreich aktiviert.
workflow.disabled=Workflow ist deaktiviert.
need_approval_desc=Um Workflows für den Pull-Request eines Forks auszuführen, ist eine Genehmigung erforderlich.
variables=Variablen
variables.management=Variablenverwaltung
variables.creation=Variable hinzufügen
variables.none=Es gibt noch keine Variablen.
variables.deletion=Variable entfernen
variables.deletion.description=Das Entfernen einer Variable ist dauerhaft und kann nicht rückgängig gemacht werden. Fortfahren?
variables.description=Variablen werden an bestimmte Aktionen übergeben und können nicht anderweitig gelesen werden.
variables.id_not_exist=Variable mit ID %d existiert nicht.
variables.edit=Variable bearbeiten
variables.deletion.failed=Fehler beim Entfernen der Variable.
variables.deletion.success=Die Variable wurde entfernt.
variables.creation.failed=Fehler beim Hinzufügen der Variable.
variables.creation.success=Die Variable „%s“ wurde hinzugefügt.
variables.update.failed=Fehler beim Bearbeiten der Variable.
variables.update.success=Die Variable wurde bearbeitet.
[projects]
type-1.display_name=Individuelles Projekt
@ -3368,5 +3566,10 @@ type-2.display_name=Repository-Projekt
type-3.display_name=Organisationsprojekt
[git.filemode]
changed_filemode=%[1]s → %[2]s
directory=Verzeichnis
normal_file=Normale Datei
executable_file=Ausführbare Datei
symbolic_link=Softlink
submodule=Submodul

Some files were not shown because too many files have changed in this diff Show More