Compare commits

...

184 Commits

Author SHA1 Message Date
petru 43c8d014e8 Modified - [scripts] [configure] [git-lfs] Added conditional Git LFS setup to configure.sh when repository LFS hooks are installed.
release-nightly / nightly-binary (push) Has been cancelled
release-nightly / nightly-container (push) Has been cancelled
release-tag-version / binary (push) Has been cancelled
release-tag-version / container (push) Has been cancelled
- 1 - I updated `.configure.sh` so repositories that already have Git LFS hook scripts in `.git/hooks` now treat `git-lfs` as a required dependency during verification, install the `git-lfs` system package on supported package managers, and run `git lfs install --local` during non-verify setup.

(cherry picked from commit b66ec8c19d)
2026-05-20 00:32:29 +03:00
petru c2a0fe8c51 Modified - [scripts] [smart-build] [darwin] Added macOS amd64/arm64 smart-build support, including SQLite-aware Docker-host handling for containerized workspaces.
- 1 - I updated `smart-build.sh` so its interactive architecture menu now offers `macos-amd64`, `macos-arm64`, and includes both Darwin targets in `All Arch`, while preserving the existing `darwin` artifact naming in `dist/`.
- 2 - I added a dedicated Darwin SQLite build path in `smart-build.sh` that routes macOS `bindata sqlite sqlite_unlock_notify` builds through `make release-darwin`, and I updated `Makefile` to make `release-darwin` configurable through `DARWIN_ARCHS` so helper scripts can request only `darwin-10.12/amd64` or `darwin-10.12/arm64`.
- 3 - I hardened the Darwin SQLite flow in `smart-build.sh` for `code-server`-style containerized workspaces by distinguishing between a missing Docker CLI and an unreachable Docker daemon, by validating that the host Docker daemon can see the same mounted repository `go.mod` path as the current workspace, and by moving the temporary release output under `dist/` instead of `/tmp`.
- 4 - I added `SMART_BUILD_DARWIN_HOST_REPO_PATH` support to `smart-build.sh` so Darwin SQLite builds can be redirected to a host-visible repository mount path when the interactive workspace path inside the container differs from the real host path used by the Docker daemon.

(cherry picked from commit 06e5bd7f46)
2026-05-20 00:30:57 +03:00
petru 379da5c828 Updated CHANGELOG for v1.26.1-by-petru - [docs] [changelog] [github-links] Added explicit GitHub links for the remaining bare PR references in CHANGELOG.md for the v1.26.1-by-petru release notes.
release-nightly / nightly-binary (push) Has been cancelled
release-nightly / nightly-container (push) Has been cancelled
release-tag-version / binary (push) Has been cancelled
release-tag-version / container (push) Has been cancelled
- 1 - I updated the remaining bare `#NNNNN` pull-request references in `CHANGELOG.md` so they now point directly to `https://github.com/go-gitea/gitea/pull/...`, without folding this tag-specific changelog cleanup into the earlier generic changelog-link conversion entry.

(cherry picked from commit 2d228475fc)
2026-05-18 10:23:47 +00:00
silverwind 5772454b31 Stabilize e2e logout propagation test (#37408)
Backport of #37403 to `release/v1.26`.

The `events › logout propagation` e2e test was racing the SSE connection
setup: if page2's SharedWorker had not finished registering its
messenger by the time page1 triggered logout, the event was silently
dropped and page2 stayed on the authenticated page.

Wait 500ms after verifying page2 is signed in, before triggering the
logout from page1, so the SharedWorker has time to register. Comment
points at a cleaner future fix (expose a ready attribute on the page)
that will also work for the planned WebSocket SharedWorker.

---
This PR was written with the help of Claude Opus 4.7

Co-authored-by: Claude (Opus 4.7) <noreply@anthropic.com>
(cherry picked from commit 64d12024d65c5f343f4ae89ea9a6f6ed5616ef82)
(cherry picked from commit a6b0bd9755)
2026-05-18 10:03:48 +00:00
Giteabot 4c47020d37 fix: dump with default zip type produces uncompressed zip (#37401) (#37402)
Backport #37401

Fix #37393

Co-authored-by: Copilot <198982749+Copilot@users.noreply.github.com>
Co-authored-by: wxiaoguang <2114189+wxiaoguang@users.noreply.github.com>
(cherry picked from commit 6cc1ee9424c61b234987a7e0b72f8d82ae78f2ff)
(cherry picked from commit 5ad76cda47)
2026-05-18 10:03:40 +00:00
Giteabot c95a092b4c Fix repo init README EOL (#37388) (#37399)
Backport #37388 by @wxiaoguang

Fix #27120

By the way, refactor ReserveLineBreakForTextarea to NormalizeStringEOL

Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit 5d7768f34ca7d100823a2ced855c288409478690)
(cherry picked from commit ef0e2ecdc1)
2026-05-18 10:03:31 +00:00
Giteabot bfac06111e Fix org team assignee/reviewer lookups for team member permissions (#37365) (#37391)
Backport #37365 by @pisarz77

Fix team members missing from assignee list when `team_unit.access_mode`
is 0 but the doer is owner.

Fix  #34871

1. Use `GetTeamUserIDsWithAccessToAnyRepoUnit` for repo assignee list
2. Load assignee list for project issues directly
3. Use `GetTeamUserIDsWithAccessToAnyRepoUnit` for repo reviewer list

Signed-off-by: Jakub Pisarczyk <pisarz77@gmail.com>
Signed-off-by: wxiaoguang <wxiaoguang@gmail.com>
Co-authored-by: pisarz77 <pisarz77@gmail.com>
Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
Co-authored-by: silverwind <me@silverwind.io>
Co-authored-by: Claude (Opus 4.7) <noreply@anthropic.com>
(cherry picked from commit 55a6cfe79b57a42b0ae279fa5c7a5f261d7823eb)
(cherry picked from commit 7ed64f3c94)
2026-05-18 10:03:20 +00:00
Giteabot a02e97d52b fix: commit status reporting (#37372) (#37386)
Backport #37372 by @bircni

Fixes the issue that status report always shows waiting to run, when
already running

https://github.com/go-gitea/gitea/issues/36906#issuecomment-4294545813

Co-authored-by: Nicolas <bircni@icloud.com>
Co-authored-by: silverwind <me@silverwind.io>
Co-authored-by: Claude (Opus 4.7) <noreply@anthropic.com>
(cherry picked from commit 1f643072c18bf924ec131e7fc059397704a659fe)
(cherry picked from commit 8ba8b9cde4)
2026-05-18 10:03:11 +00:00
Giteabot fe0ccc2806 Fix button layout shift when collapsing file tree in editor (#37363) (#37375)
Backport #37363 by @bytedream

---
old:

https://github.com/user-attachments/assets/136a9ce8-f229-4583-bf19-75258d085513

new:

https://github.com/user-attachments/assets/21b7c885-00f4-4295-9191-07b66ca58b64

Signed-off-by: wxiaoguang <wxiaoguang@gmail.com>
Co-authored-by: bytedream <me@bytedream.dev>
Co-authored-by: silverwind <me@silverwind.io>
Co-authored-by: Claude (Opus 4.7) <noreply@anthropic.com>
Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit 028045535689d2c5f0d100f3fb928a7f11df3c84)
(cherry picked from commit f50a9158aa)
2026-05-18 10:03:00 +00:00
Giteabot 792d0dd224 Add URL to Learn more about blocking a user. (#37355) (#37367)
Backport #37355 by @PineBale

Closes #29992

<img width="1308" height="828" alt="1"
src="https://github.com/user-attachments/assets/552c2e0f-8da6-4f71-8660-8e3f5a78ace5"
/>

Co-authored-by: PineBale <272794187+PineBale@users.noreply.github.com>
(cherry picked from commit a8e465e893b6efe0184e68f2e6dfaeb3e60c5678)
(cherry picked from commit 73a4930fc3)
2026-05-18 10:02:47 +00:00
Giteabot 28a8361033 fix: use TriggerEvent instead of Event in workflow runs API response for scheduled runs (#37288) (#37360)
Backport #37288 by @KalashThakare

## Summary

Fixes #37252

The `/api/v1/repos/{owner}/{repo}/actions/runs` endpoint was returning
`event: "push"` for workflow runs triggered by `schedule:` (cron),
instead
of `event: "schedule"`.

## Root Cause

`ActionRun` has two separate fields:
- `Event` — the workflow registration event (e.g. `push`, set when the
workflow file was first pushed)
- `TriggerEvent` — the actual event that triggered the run (e.g.
`schedule`)

`ToActionWorkflowRun` in `services/convert/action.go` was serializing
`run.Event` into the API response instead of `run.TriggerEvent`, causing
scheduled runs to be indistinguishable from push events via the API.

This was already asymmetric — the tasks/jobs API correctly used
`TriggerEvent`.

## Fix

Changed `ToActionWorkflowRun` to use `run.TriggerEvent` for the `event`
field in the API response, consistent with how the jobs API works.

## Before

`event: "push"` returned for all scheduled runs:

<img width="1112" height="191" alt="Screenshot 2026-04-19 115642"
src="https://github.com/user-attachments/assets/c0a169f5-bbd9-4f5d-9474-e4c3795110e4"
/>

## After

`event: "schedule"` correctly returned for scheduled runs:

<img width="890" height="166" alt="Screenshot 2026-04-19 121723"
src="https://github.com/user-attachments/assets/860e99ac-0935-4a43-86a1-7b60f8113480"
/>

## Testing

- Added unit test `TestToActionWorkflowRun_UsesTriggerEvent` in
  `services/convert/action_test.go` that explicitly verifies the API
  returns `TriggerEvent` and not `Event` for a scheduled run.
- Manually verified via the API against a live Gitea instance with a
  `cron: "* * * * *"` workflow.

Co-authored-by: Kalash Thakare ☯︎ <kalashthakare898@gmail.com>
Co-authored-by: Nicolas <bircni@icloud.com>
(cherry picked from commit fc9dfe0e56a84f2eb8e389d364f2da0b9c24d917)
(cherry picked from commit 836d451d6a)
2026-05-18 10:02:33 +00:00
Giteabot fca2db6c11 Add event.schedule context for schedule actions task (#37320) (#37348)
Backport #37320 by @lunny

Fix #35452

Co-authored-by: Lunny Xiao <xiaolunwen@gmail.com>
Co-authored-by: silverwind <me@silverwind.io>
Co-authored-by: Claude (Opus 4.7) <noreply@anthropic.com>
(cherry picked from commit 0916039c2a54f4a6f2139558792b476edece48a5)
(cherry picked from commit e5d2c03f39)
2026-05-18 10:02:03 +00:00
Giteabot e91a744803 Fix an issue where changing an organization’s visibility caused problems when users had forked its repositories. (#37324) (#37344)
Backport #37324 by @lunny

A quick fix #37317

---

The current behavior for forks when an organization or repository is
changed to private differs from GitHub.

On GitHub, when a parent repository becomes private, the fork
relationship is removed, which keeps the behavior simple and avoids
visibility conflicts.

I think we need a similar solution to handle cases where the parent
repository becomes private while a fork remains public and the fork
relationship is still preserved.

Signed-off-by: Lunny Xiao <xiaolunwen@gmail.com>
Co-authored-by: Lunny Xiao <xiaolunwen@gmail.com>
Co-authored-by: silverwind <me@silverwind.io>
Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit 291f6cbd3abfd0ffb6a9d70efb2d943e581ff257)
(cherry picked from commit f31163e6de)
2026-05-18 10:01:50 +00:00
Giteabot e929533398 Use modern "git update-index --cacheinfo" syntax to support more file names (#37338) (#37343)
Backport #37338 by @wxiaoguang

Modern syntax was added in git 2.0

And add more tests

Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit f536bcd5084a9fb1864977b90a86e206ca6e6f5d)
(cherry picked from commit a5b92e70ab)
2026-05-18 10:01:42 +00:00
Giteabot f278b9697b Fix URL related escaping for oauth2 (#37334) (#37340)
Backport #37334 by wxiaoguang

Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit fc4296a21a1fe55104581fd590b1bcb073bd9f92)
(cherry picked from commit a3e5814a12)
2026-05-18 10:01:31 +00:00
Giteabot 0b4e05fcb3 When the requested arch rpm is missing fall back to noarch (#37236) (#37339)
Backport #37236 by chethenry

This fixes: https://github.com/go-gitea/gitea/issues/37235

It uses the same changeset alpine packages got in:
https://github.com/go-gitea/gitea/issues/26691

Co-authored-by: chethenry <henry@visionlink.org>
Co-authored-by: Lunny Xiao <xiaolunwen@gmail.com>
Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit 657ea10cf19c4525836a16e9874d4d0d7fa12b8f)
(cherry picked from commit 4f2bffba44)
2026-05-18 10:01:16 +00:00
Giteabot b67937faf1 fix(oauth): Error on auth sources with spaces (#37327) (#37332)
Backport #37327 by @prettysunflower

Nyallo~

In pull request #36901, a change is made so that the link to
authentication sources is now escaped with the QueryEscape filter.
https://github.com/go-gitea/gitea/pull/36901/changes#diff-34c39c9736a8b62e293c0c0b24c4b5b8c1c792790018c5809f9ff2cbc12b16b1R4

The problem is that [QueryEscape replace spaces with the `+`
character](https://cs.opensource.google/go/go/+/refs/tags/go1.26.2:src/net/url/url.go;l=234;drc=917949cc1d16c652cb09ba369718f45e5d814d8f),
and this is not unescaped when a user tries to log in with an
authentication source that contains a space, which throws an error.

This commit fixes that by unescaping the provider name in the URL.

---

Example of the error, on my instance, when I try to log in with
`prettysunflower's auth`
```
2026/04/21 00:11:41 routers/web/auth/oauth.go:42:SignInOAuth() [E] SignIn: oauth2 source not found, name: "prettysunflower's+auth"
	/go/src/code.gitea.io/gitea/routers/web/auth/oauth.go:42 (0x2cfa5c5)
	/usr/local/go/src/reflect/value.go:586 (0x51e245)
	/usr/local/go/src/reflect/value.go:369 (0x51d0f8)
	/go/src/code.gitea.io/gitea/modules/web/handler.go:181 (0x1a6aaf6)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/src/code.gitea.io/gitea/modules/web/handler.go:188 (0x1a6ab65)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/src/code.gitea.io/gitea/modules/web/handler.go:188 (0x1a6ab65)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/src/code.gitea.io/gitea/modules/web/handler.go:188 (0x1a6ab65)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/src/code.gitea.io/gitea/services/context/context.go:217 (0x2df1b23)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/src/code.gitea.io/gitea/modules/web/handler.go:145 (0x1a6afb5)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/pkg/mod/gitea.com/go-chi/session@v0.0.0-20251124165456-68e0254e989e/session.go:258 (0x197eb82)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/src/code.gitea.io/gitea/modules/web/handler.go:145 (0x1a6afb5)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/pkg/mod/github.com/go-chi/chi/v5@v5.2.5/chain.go:31 (0x1a61d05)
	/go/pkg/mod/github.com/go-chi/chi/v5@v5.2.5/mux.go:479 (0x1a64fae)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/pkg/mod/github.com/go-chi/chi/v5@v5.2.5/mux.go:73 (0x1a628c2)
	/go/pkg/mod/github.com/go-chi/chi/v5@v5.2.5/mux.go:321 (0x1a6421a)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/pkg/mod/github.com/go-chi/chi/v5@v5.2.5/chain.go:31 (0x1a61d05)
	/go/pkg/mod/github.com/go-chi/chi/v5@v5.2.5/mux.go:479 (0x1a64fae)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/pkg/mod/github.com/go-chi/chi/v5@v5.2.5/middleware/get_head.go:37 (0x2c33a67)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/src/code.gitea.io/gitea/modules/web/handler.go:145 (0x1a6afb5)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/pkg/mod/github.com/go-chi/chi/v5@v5.2.5/mux.go:73 (0x1a628c2)
	/go/pkg/mod/github.com/go-chi/chi/v5@v5.2.5/mux.go:321 (0x1a6421a)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/src/code.gitea.io/gitea/routers/common/maintenancemode.go:50 (0x2b752da)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/src/code.gitea.io/gitea/modules/web/handler.go:145 (0x1a6afb5)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/pkg/mod/github.com/go-chi/chi/v5@v5.2.5/chain.go:31 (0x1a61d05)
	/go/pkg/mod/github.com/go-chi/chi/v5@v5.2.5/mux.go:479 (0x1a64fae)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/src/code.gitea.io/gitea/modules/web/routing/logger_manager.go:124 (0x127d1ec)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/src/code.gitea.io/gitea/modules/web/handler.go:145 (0x1a6afb5)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/pkg/mod/github.com/chi-middleware/proxy@v1.1.1/middleware.go:37 (0x2b76acf)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/src/code.gitea.io/gitea/modules/web/handler.go:145 (0x1a6afb5)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/src/code.gitea.io/gitea/routers/common/middleware.go:89 (0x2b78cd6)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/src/code.gitea.io/gitea/modules/web/handler.go:145 (0x1a6afb5)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/src/code.gitea.io/gitea/routers/common/middleware.go:104 (0x2b7890f)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/src/code.gitea.io/gitea/modules/web/handler.go:145 (0x1a6afb5)
	/usr/local/go/src/net/http/server.go:2286 (0x94dc88)
	/go/pkg/mod/github.com/go-chi/chi/v5@v5.2.5/mux.go:90 (0x1a62881)
	/go/src/code.gitea.io/gitea/modules/web/router.go:286 (0x1a6d2a2)
	/go/src/code.gitea.io/gitea/modules/web/router.go:221 (0x1a6cbc6)
	/usr/local/go/src/net/http/server.go:3311 (0x96e36d)
	/usr/local/go/src/net/http/server.go:2073 (0x94bd6f)
	/usr/local/go/src/runtime/asm_amd64.s:1771 (0x49af20)
```

Signed-off-by: prettysunflower <me@prettysunflower.moe>
Signed-off-by: wxiaoguang <wxiaoguang@gmail.com>
Co-authored-by: prettysunflower <me@prettysunflower.moe>
Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
Co-authored-by: silverwind <me@silverwind.io>
(cherry picked from commit ef096b0f9025122957b049b5d1a9c4f27bcc1d78)
(cherry picked from commit b14015efe9)
2026-05-18 10:01:01 +00:00
Giteabot f10391597d Fix actions concurrency groups cross-branch leak (#37311) (#37331)
Backport #37311 by @silverwind

## Problem

Workflow-level concurrency groups were evaluated — and jobs were parsed
— before the run was persisted, so `run.ID` was `0` and `github.run_id`
in the expression context resolved to an empty string. Expressions like:

```yaml
concurrency:
  group: ${{ github.workflow }}-${{ github.head_ref || github.run_id }}
  cancel-in-progress: true
```

collapsed to `<workflow>-` on every push event (`head_ref` is empty on
push), so `cancel-in-progress` cancelled in-progress runs across
**unrelated branches**, not just the current one.

Reproduced on a 1.26 instance:
- push to `master` → `ci` run starts
- push to `feature-branch` → the `master` run gets cancelled

GitHub Actions' documented semantic: on push events `github.run_id` is
unique per run, so the group is unique → no cancellation; on PR events
`github.head_ref` is the source branch → cancellation is per-PR.

## Fix

Insert the run **before** parsing jobs or evaluating workflow-level
concurrency, so `run.ID` is populated in time for every expression that
reads `github.run_id` — not just the concurrency group, but also
`run-name`, job names, and `runs-on`.

`jobparser.Parse` now runs inside the `InsertRun` transaction, after
`db.Insert(ctx, run)`. Workflow-level concurrency evaluation runs next
and only mutates `run` in memory. All concurrency-derived fields
(`raw_concurrency`, `concurrency_group`, `concurrency_cancel`) plus
`status` and `title` are persisted in a single final `UpdateRun` at
end-of-transaction — one `INSERT` + one `UPDATE` per run in both the
concurrency and non-concurrency paths (matches pre-branch parity, one
fewer `UpdateRepoRunsNumbers` `COUNT` than the interim state).

`GenerateGiteaContext` now sets `run_id` from `run.ID` unconditionally;
every caller passes a persisted run.

**Verification**: tested end-to-end on a 1.26 deployment. Before the
patch, two successive `ci` pushes (one to master, one to a feature
branch) cross-cancelled each other. After the patch, the same pushes —
in both orders (master→branch, branch→master) — run to completion
simultaneously across 15+ runs with zero cancellations.

**Regression tests** in `services/actions/context_test.go`:
- `TestEvaluateRunConcurrency_RunIDFallback` — unit check that
`EvaluateRunConcurrencyFillModel` resolves `github.run_id` from
`run.ID`.
- `TestPrepareRunAndInsert_ExpressionsSeeRunID` — full-flow check: calls
`PrepareRunAndInsert` with `${{ github.run_id }}` in both `run-name` and
the concurrency group, then asserts the persisted `Title`,
`ConcurrencyGroup`, and `RawConcurrency` contain / survive the run's ID.
Re-ordering `db.Insert` relative to either parse or concurrency eval
fails this test.

## Relation to #37119

[#37119](https://github.com/go-gitea/gitea/pull/37119) also moves
concurrency evaluation into `InsertRun` but keeps it **before**
`db.Insert`, then tries to populate `run_id` only when `run.ID > 0` —
which is still `0` at that call site, so the cross-branch leak would
survive that PR as written. This PR fixes the ordering so that `run.ID`
is actually populated at eval time, and broadens it to cover parse-time
expression interpolation too.

---
This PR was written with the help of Claude Opus 4.7

Co-authored-by: silverwind <me@silverwind.io>
Co-authored-by: Claude (Opus 4.7) <noreply@anthropic.com>
(cherry picked from commit 7bd55deab302d1de482737340954a8be7efb132d)
(cherry picked from commit 433efc6093)
2026-05-18 10:00:54 +00:00
Giteabot 9264ef61d4 Fix bug when accessing user badges (#37321) (#37329)
Backport #37321 by @lunny

Fix #37302

Co-authored-by: Lunny Xiao <xiaolunwen@gmail.com>
Co-authored-by: silverwind <me@silverwind.io>
(cherry picked from commit e4b7120bc2cc45a928365554fdc83132c0ffdc17)
(cherry picked from commit 255fd3e519)
2026-05-18 10:00:46 +00:00
Giteabot 4ab92b3365 Fix AppFullLink (#37325) (#37328)
Backport #37325 by @lunny

Fix a bug the checkout command line hint become `git fetch -u
https://gitea.combircni/tea`

Co-authored-by: Lunny Xiao <xiaolunwen@gmail.com>
(cherry picked from commit f0fd185f14fdcc13a0ec50f3134515623abbf0a2)
(cherry picked from commit aff9a28fa4)
2026-05-18 10:00:16 +00:00
Giteabot 4de459603c Fix vite manifest update masking build errors (#37279) (#37310)
Backport #37279 by @silverwind

Moves the manifest patching from `closeBundle` to `writeBundle`. Thrown
errors in `writeBundle` work correctly and exit the build.

Signed-off-by: silverwind <me@silverwind.io>
Signed-off-by: wxiaoguang <wxiaoguang@gmail.com>
Co-authored-by: silverwind <me@silverwind.io>
Co-authored-by: Claude (Opus 4.7) <noreply@anthropic.com>
Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit adfa535dc200f81f6452b22f36d94f1ca8de9606)
(cherry picked from commit 3249dedde1)
2026-05-18 10:00:04 +00:00
wxiaoguang 80ba739abe Fix Mermaid diagrams failing when node labels contain line breaks (#37296) (#37299)
Backport #37296

Co-authored-by: Nicolas <bircni@icloud.com>
(cherry picked from commit e6691b0e8d2948c609fabb95967de1209f3c4520)
(cherry picked from commit e28eec37ea)
2026-05-18 09:59:46 +00:00
Giteabot e8e6177e8a Fix container auth for public instance (#37290) (#37294)
Backport #37290 by wxiaoguang

Fix #37289

Don't tell container client that the instance needs basic auth if the
public access is available.

Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit 82613a40a02908eca7b256567354931500b94253)
(cherry picked from commit 2de0b4f34d)
2026-05-18 09:59:16 +00:00
Giteabot 62933b0eda Enhance GetActionWorkflow to support fallback references (#37189) (#37283)
Backport #37189 by @bircni

If a workflow is not in default branch the hooks could not be detected

Fixes #37169

Co-authored-by: Nicolas <bircni@icloud.com>
Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
(cherry picked from commit ba5117e4e4327c69f1b24dcf5c408279b4e80781)
(cherry picked from commit bff8f3d2e4)
2026-05-18 09:58:04 +00:00
petru bef4b822cd v1.26-custom releases branch - Modified - [docs] [changelog] [github-links] Converted changelog PR references to explicit GitHub pull-request links.
release-tag-version / binary (push) Has been cancelled
release-tag-version / container (push) Has been cancelled
(cherry picked from commit 4dba5de64c)
2026-05-18 09:28:36 +00:00
petru 84bcea290c Fixed - [admin-users] [delete-user] [fetch-action] Made the admin user-table trash action return fetch-compatible delete responses.
- 1 - I updated the `/-/admin/users` delete modal in the user table to submit an explicit inline fetch flag, and I changed the web admin `DeleteUser` handler so that this table-specific fetch flow now returns `JSONRedirect` on success and `JSONError` for expected validation failures, while the classic edit-page delete form keeps its normal redirect behavior; I also added integration coverage for the table delete path.

(cherry picked from commit 849cb3f6ae)
2026-05-18 09:19:07 +00:00
petru 9242cd6655 Fixed - [build] [versioning] Preserved custom tag names in GITEA_VERSION while keeping git describe build metadata.
- 1 - I updated `Makefile` so `GITEA_VERSION` now strips the leading `v`, preserves exact custom tag names such as `1.26.0-by-petru`, and converts only the trailing `-N-gSHA` suffix from `git describe` into `+N-gSHA` for in-between builds like `1.26.0-by-petru+3-g...` and `1.27.0-dev+143-g...`.

(cherry picked from commit adb90b3453)
2026-05-18 09:19:07 +00:00
petru bff70ba3de Modified - [scripts] [smart-build] [artifacts] Renamed smart-build outputs to include the tag/ref and generated per-file SHA-256 checksums.
- 1 - I updated [`.smart-build.sh`](/config/workspace/gitea-dev/gitea/.smart-build.sh) so each build artifact is now written as `gitea-<tag-or-ref>-<os>-<platform><-sqlite>` with the original executable extension preserved, and each output also gets its own adjacent `.sha256` file generated with `sha256sum` or `shasum -a 256`.

(cherry picked from commit c6f2b32f0b)
2026-05-18 09:19:06 +00:00
petru 63b691c29e Fixed - [scripts] [custom-release] [release-target] Stopped release-target sync from requiring the remote release branch when an explicit target tag/ref is configured.
- 1 - I updated [`.maintain-custom-release.sh`](/config/workspace/gitea-dev/gitea/.maintain-custom-release.sh) so `Sync upstream release target commits` validates only the configured `UPSTREAM_RELEASE_TARGET_REF` when one is set, instead of still failing on a missing local `upstream/release/...` remote-tracking branch after successfully fetching a target tag such as `v1.26.1`.

(cherry picked from commit 244a472691)
2026-05-18 09:19:06 +00:00
petru a1052dbf96 Fixed - [admin-users] [terminology] [locale] [en] [ro] Corrected the bootstrap-admin label from GOOD to GOD.
(cherry picked from commit 1f2bb43f46)
2026-05-18 07:10:56 +00:00
silverwind 70e1e99ff7 Upgrade go-git to v5.18.0 (#37269)
Backport of go-git upgrade to v5.18.0 for the v1.26 release branch.

Fixes GHSA-3xc5-wrhm-f963 (credential exposure on HTTP redirects).

---
This PR was written with the help of Claude Opus 4.6

Co-authored-by: Claude (Opus 4.6) <noreply@anthropic.com>
(cherry picked from commit eb43da41f58f95aa014a80e333baa44d264d5a38)
2026-05-16 23:05:30 +00:00
wxiaoguang 32c9ac12e6 Frontend iframe renderer framework: 3D models, OpenAPI (#37233) (#37273)
Backport

* #37233
* #37272

---------

Co-authored-by: silverwind <me@silverwind.io>
(cherry picked from commit 1412009d0a58510d0313ed9e8fcc6cba85e21e14)
2026-05-16 23:05:20 +00:00
Giteabot bbcc540c0a pull: Fix CODEOWNERS absolute path matching. (#37244) (#37264)
Backport #37244 by @JoeGruffins

Patterns starting with "/" (e.g. /docs/.*\.md) never matched because git
returns relative paths without a leading slash. Strip the leading "/"
before compiling the regex since the ^...$ anchoring already provides
root-relative semantics.

closes #28107

Co-authored-by: JoeGruffins <34998433+JoeGruffins@users.noreply.github.com>
Co-authored-by: silverwind <me@silverwind.io>
Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit 26a618ac1a773da722dfa13c7647dfdcc1c64355)
2026-05-16 23:05:08 +00:00
wxiaoguang 17ebac5c3c Swift registry metadata: preserve more JSON fields and accept empty metadata (#37254) (#37261)
Backport #37254

Co-authored-by: Copilot <198982749+Copilot@users.noreply.github.com>
(cherry picked from commit 145898b3582085e4f54b098d2c65523169bdef0b)
2026-05-16 23:04:56 +00:00
Giteabot 699803d1d7 Fix user ssh key exporting and tests (#37256) (#37258)
Backport #37256 by wxiaoguang

1. Make sure OmitEmail won't panic
2. SSH principal keys are not for signing or authentication

Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit b191cf7e7708e122be300f8e88554413680c34e4)
2026-05-16 23:04:45 +00:00
wxiaoguang e97842d0a0 Fix team member avatar size and add tooltip (#37253)
1. Make team member avatar size=32
2. Add tooltip to the avatar

(cherry picked from commit 4adee80f58e5178a65e3cfe9c63eadfd102d2acb)
2026-05-16 23:04:34 +00:00
Giteabot 579558f74a Fix commit title rendering in action run and blame (#37243) (#37251)
Backport #37243 by @silverwind

Co-authored-by: silverwind <me@silverwind.io>
Co-authored-by: Claude (Opus 4.7) <noreply@anthropic.com>
(cherry picked from commit 4de12baf9b8fa1016d4b7c91cbb1104b94287868)
2026-05-16 23:04:27 +00:00
wxiaoguang a3c50ac2cd Add test for "fetch redirect", add CSS value validation for external render (#37207) (#37216)
Backport #37207

(cherry picked from commit 5d852d2d0a89fcffd13148496184e85736a687ad)
2026-05-16 23:04:02 +00:00
Giteabot 3f8775bce5 Fix incorrect concurrency check (#37205) (#37215)
Backport #37205 by @Zettat123

This bug was identified in
https://github.com/go-gitea/gitea/pull/37119/changes#diff-37655a02d5a44d5c0e3e19c75fb58adb47a8e7835cbd619345d5b556292935a7L180

Co-authored-by: Zettat123 <zettat123@gmail.com>
Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
Co-authored-by: Lunny Xiao <xiaolunwen@gmail.com>
(cherry picked from commit 2aca966c5f02893d4dcd48c133e2c17f1c8bba8d)
2026-05-16 23:03:51 +00:00
petru 1f0d9b3471 First try for Codex AI routine optimisation
(cherry picked from commit f4e7ba76d8)
2026-05-16 22:21:37 +00:00
petru 3b2bf52e62 Added Routing Rules for Tasks (Multi-Model Delegation) for OpenAI Codex.
(cherry picked from commit 59bc832f0a)
2026-05-16 22:21:23 +00:00
petru 7131424da1 Fix - For .maintain-custom-release.sh - Hardened recovery so rollback, restore-point, restore-snapshot, restore-stash, and restore-deletion correctly preserve or clean script-managed refs, maintenance branches, state files, backup branches, and snapshots, including rollback from the original entry branch after a bootstrap-created maintenance branch, cleanup of legacy restore-point leftovers, and removal of the correctly paired backup/maint-* Git Graph marker when a saved snapshot is deleted.
(cherry picked from commit ac76745362)
2026-05-16 22:21:13 +00:00
petru 171850b8f9 Modified - Finalized the custom-release maintenance helper workflow and recovery behavior.
- 1 - I made `bootstrap` a clean branch-creation step from `BASE_TAG`, separated fetch and sync into explicit compare/release-target/custom actions, added `UPSTREAM_RELEASE_TARGET_REF`, and updated the built-in help so the recommended workflow matches the current menu structure.
- 2 - I hardened recovery so rollback, restore-point, restore-snapshot, restore-stash, and restore-deletion correctly preserve or clean script-managed refs, maintenance branches, state files, backup branches, and snapshots, including rollback from the original entry branch after a bootstrap-created maintenance branch, cleanup of legacy restore-point leftovers, and removal of the paired `backup/maint-*` Git Graph marker when a saved snapshot is deleted.
- 3 - I finalized the interactive UX by keeping a self-updating runtime copy in `/tmp`, persisting the last-used settings in `/tmp/.maintain-custom-release.env`, and reorganizing the menu into `Manual Backups >`, `Fetch upstreams >`, `Sync >`, `Rollback >`, and `Restore >` submenus, including `Delete Restore >` with numbered stash and snapshot selection, with numbered selections, `b`/`B` or `Enter` for Back, correct return-to-parent behavior from every submenu, and `0` for Exit.

(cherry picked from commit 5eae94f95a)
2026-05-16 22:21:02 +00:00
petru 4991e019a5 Modified - Finalized the custom-release maintenance helper workflow and recovery behavior.
- 1 - I made `bootstrap` a clean branch-creation step from `BASE_TAG`, separated fetch and sync into explicit compare/release-target/custom actions, added `UPSTREAM_RELEASE_TARGET_REF`, and updated the built-in help so the recommended workflow matches the current menu structure.
- 2 - I hardened recovery so rollback, restore-point, restore-snapshot, and restore-stash correctly preserve or clean script-managed refs, maintenance branches, state files, backup branches, and snapshots, including rollback from the original entry branch after a bootstrap-created maintenance branch and cleanup of legacy restore-point leftovers.
- 3 - I finalized the interactive UX by keeping a self-updating runtime copy in `/tmp`, persisting the last-used settings in `/tmp/.maintain-custom-release.env`, and reorganizing the menu into `Backups >`, `Fetch upstreams >`, `Sync >`, `Rollback >`, and `Restore >` submenus with numbered selections, `b`/`B` or `Enter` for Back, and `0` for Exit.

(cherry picked from commit 3bbe60b6b7)
2026-05-16 22:20:51 +00:00
petru 70ec5f9976 Moved in .maintain-custom-release.sh bootstrap ahead of the explicit fetch actions in the interactive menu, kept it in the menu flow instead of exiting the script, removed automatic fetching from bootstrap and plan, and split both the fetch and sync flows into separate compare-branch and release-target actions while clarifying that custom commits are cherry-picked from oldest to newest.
(cherry picked from commit 1d43078c0b)
2026-05-16 22:20:42 +00:00
petru dae225ec3a Updated [.maintain-custom-release.sh](/config/workspace/gitea-dev/gitea/.maintain-custom-release.sh) so bootstrap now only creates or switches to the maintenance branch from BASE_TAG, without automatically fetching or importing anything.
- Added a persistent `/tmp/.maintain-custom-release.env` settings file so the last used configuration survives script restarts.
- Moved `bootstrap` ahead of the explicit fetch actions in the interactive menu, removed automatic fetching from `bootstrap` and `plan`, and split both the fetch and sync flows into separate compare-branch and release-target actions while clarifying that custom commits are cherry-picked from oldest to newest.

(cherry picked from commit f5718dd509)
2026-05-16 22:20:27 +00:00
petru 729d063f3d Taught the .maintain-custom-release.sh script to maintain and relaunch itself from a runtime copy in /tmp, automatically creating or refreshing that copy from the repo version when needed while still falling back to the existing /tmp copy if the current checkout no longer contains the script, and I split both the fetch and sync flows into separate compare-branch and release-target actions while clarifying that custom commits are cherry-picked from oldest to newest.
(cherry picked from commit f765bfdc05)
2026-05-16 22:20:20 +00:00
petru b46aa97fff Taught the .maintain-custom-release.sh script to maintain and relaunch itself from a runtime copy in /tmp, automatically creating or refreshing that copy from the repo version when needed while still falling back to the existing /tmp copy if the current checkout no longer contains the script, and I split the upstream sync flow into separate sync-upstream-compare and sync-upstream-target actions while clarifying that custom commits are cherry-picked from oldest to newest.
(cherry picked from commit 2c95b1faf4)
2026-05-16 22:20:12 +00:00
petru c401ffb2c4 Added to .maintain-custom-release.sh an explicit UPSTREAM_RELEASE_TARGET_REF setting so the upstream import can stop at a chosen tag such as v1.26.0 instead of always importing to the current head of upstream/release/v1.26, and I also made rollback clean up the original backup/maint-* branch and fetched upstream/* refs so a canceled bootstrap leaves the branch graph closer to its pre-run state.
(cherry picked from commit 2d37281725)
2026-05-16 22:20:05 +00:00
petru 12474983f1 Tightened in .maintain-custom-release.sh the manual restore-point management so list-restore-points now shows only valid restore points that still have their Git Graph marker branch, while delete-restore-point can still remove orphaned restore-point directories even after their associated backup branch has already been deleted manually.
(cherry picked from commit c8bd47f0d9)
2026-05-16 22:19:56 +00:00
petru e38d9eca83 Fixed the script-managed ref discovery itself so restore cleanup now matches refs/remotes/upstream/... and backup/maint-... by prefix instead of a non-matching glob pattern, which was the reason upstream/release/v1.26 could still remain after a restore.
(cherry picked from commit aba98b9361)
2026-05-16 22:19:49 +00:00
petru d1845fa0b3 Added a legacy restore-point fallback so older restore points that predate the script-managed ref snapshot files now explicitly remove current upstream/*, maintenance-branch, backup/maint-*, state-file, and snapshot artifacts instead of leaving them behind after restore.
(cherry picked from commit b31ce595d3)
2026-05-16 22:19:40 +00:00
petru f93d28f277 fixed the restore flows so manual restore points now capture and restore the script-managed refs, state file, and snapshot directories, while successful rollback, restore-snapshot, and restore-point operations automatically clean up their temporary safety backup branches and snapshots when no preserved local stash needs to be kept.
(cherry picked from commit 8f9b67397e)
2026-05-16 22:19:33 +00:00
petru 78f8fb8307 Modified - Simplified bootstrap and tightened rollback cleanup in the custom-release maintenance helper.
(cherry picked from commit f527cf4ce3)
2026-05-16 22:19:22 +00:00
petru 512ecb175f Fix - fixing the interactive configuration prompts so they are shown correctly during Edit configuration.
(cherry picked from commit 209224d0cc)
2026-05-16 22:19:09 +00:00
petru edc292d12c Modified - Extended the custom-release maintenance helper with manual restore points and corrected its fetch behavior.
(cherry picked from commit 363c86ecaf)
2026-05-16 22:19:03 +00:00
petru 400928623b Set script as .update-gitea.sh as executable.
(cherry picked from commit 92c6dad4b9)
2026-05-16 22:18:43 +00:00
petru 249fc8bf0b Added - Added a dedicated safe upstream import helper based on cherry-pick.
Added - Added an interactive custom-release maintenance helper for stable patch lines.

Added - Added a dedicated safe upstream import helper based on `cherry-pick`.
Added - Added an interactive custom-release maintenance helper for stable patch lines.

Added - Added a dedicated safe upstream import helper based on cherry-pick.
Added - Added an interactive custom-release maintenance helper for stable patch lines.

(cherry picked from commit a6a278b551)
2026-05-16 22:18:35 +00:00
petru f608948bf7 Added - Finalized the safe upstream update helper script as .update-gitea.sh.
- 5 - I improved conflict reporting so package.json conflicts show the upstream scripts block, the conflicting commit side, and the current branch working-tree side, and the final dry-run summary now includes the total conflict-step count, the local commits that conflicted, and the unique conflicted files.

(cherry picked from commit 6d0a7ec238)
2026-05-16 22:17:56 +00:00
petru e77ede6a9f Added - Finalized the safe upstream update helper script as .update-gitea.sh.
- 1 - I renamed the updater to `.update-gitea.sh`, documented its purpose and ordered usage steps, and added an interactive menu plus direct commands for `sync`, `dry-run`, `fetch`, `backup`, `status`, `list-backups`, `rollback`, `restore-stash`, and `clean-dry-run`.
- 2 - I hardened real update actions so they verify repository state, enforce or offer safety backups before modifying the branch, stash tracked and untracked local changes, record sync state inside `.git`, and support rollback to the exact saved starting commit or to a selected backup branch while preserving recoverability of local changes.
- 3 - I implemented a reusable dry-run workspace under `.git/.update-gitea-dry-run`, added cleanup for both that workspace and legacy temporary dry-run directories, and made dry-run collect and report all detected rebase conflict steps without modifying the real repository.
- 4 - I improved conflict reporting so package.json conflicts show the upstream scripts block, the conflicting commit side, and the current branch working-tree side, and the final dry-run summary now includes the total conflict-step count, the local commits that conflicted, and the unique conflicted files.

(cherry picked from commit cca877c06e)
2026-05-16 22:17:50 +00:00
petru 52ce12c13f Added - Added optional sensitive-secret import for installer app.ini uploads.
- 1 - I added an explicit installer checkbox for importing sensitive secrets from `app.ini` in `templates/install.tmpl`.
- 2 - I extended the installer form, submit pipeline, and final config writer so the optional import reuses `LFS_JWT_SECRET`, `INTERNAL_TOKEN`, and `oauth2.JWT_SECRET` from the uploaded `app.ini` instead of generating new values, including a submit-time fallback that re-reads the uploaded file if the checkbox was enabled after the first auto-import.
- 3 - I finalized secret resolution for both direct values and `LFS_JWT_SECRET_URI` / `INTERNAL_TOKEN_URI` / `JWT_SECRET_URI` file-based references, and added regression coverage for direct imports, URI-based imports, the real `POST /import_app_ini` flow, and the persisted `app.ini` output.

(cherry picked from commit 512e577c3f)
2026-05-16 22:14:50 +00:00
petru 7070660554 Modified - Enabled shared branding assets by default in the installer.
- 1 - I updated `routers/install/install.go` so `BrandingUseSharedAssets` starts as enabled on the install form, making `Use the same logo files for favicon assets` checked by default.

(cherry picked from commit e69839ed88)
2026-05-16 22:13:22 +00:00
petru b36fd283af Added - added installer locale strings in both options/locale/locale_en-US.json and options/locale/locale_ro-RO.json for the new import UI, success message, and import errors, and the success flash now auto-dismisses after 5 seconds both on initial page load and after the AJAX import injects a new flash message.
(cherry picked from commit b907e4c38c)
2026-05-16 22:13:15 +00:00
petru 9bf972379b Added - Added installer support for importing an existing app.ini.
- 1 - I added an `Import Existing Configuration` section at the top of `templates/install.tmpl` with an `app.ini` upload control that imports automatically as soon as a file is selected, without a separate `Load app.ini` button.
- 2 - I kept the dedicated installer route `POST /import_app_ini` in `routers/install/routes.go`, but the page now posts to it via `fetch` and applies the imported values back into the existing form with `DOMParser`, so the browser is not visibly navigated to `/import_app_ini` and the page scripts are not re-executed.
- 3 - In `routers/install/install.go`, I factored the installer defaults into reusable helpers, added `app.ini` upload parsing with size/error handling, and mapped the imported config into the existing install form fields for database, general server paths, mailer, registration, OpenID, security, and admin policy settings.
- 4 - I added installer locale strings in both `options/locale/locale_en-US.json` and `options/locale/locale_ro-RO.json` for the new import UI, success message, and import errors, and the success flash now auto-dismisses after 5 seconds.
- 5 - I added regression coverage in `routers/install/routes_test.go` for the new upload control and the config-to-form mapping behavior.

(cherry picked from commit 52f3495ca0)
2026-05-16 22:12:38 +00:00
petru 981d9d0d9b Added - Added the password visibility toggle to /user/settings/change_password.
- 1 - I wrapped the forced-change password field in `templates/user/auth/change_passwd_inner.tmpl` with the shared `js-password-toggle-group`, reusing the existing eye-toggle logic and show/hide labels.
- 2 - I wired the confirm-password field into the existing toggle sync behavior so revealing the new password hides the confirm field and keeps it synchronized like the other password-update forms.

(cherry picked from commit 70479ea5a0)
2026-05-16 22:12:26 +00:00
petru 23cff646b5 Modified - Finalized Register behavior for admin-created notification accounts without altering the invitation flow.
- 1 - I extended `POST /user/sign_up` in `routers/web/auth/auth.go` for existing active local accounts created by an admin when `username` and `email` match, while explicitly leaving pending admin invitations on their existing flow.
- 2 - If password is correct, the user is now authenticated into that existing account; when `MustChangePassword` is enabled, the flow redirects directly to `/user/settings/change_password`, otherwise it follows the normal post-auth redirect.
- 3 - If password is incorrect, the flow now redirects to `/user/forgot_password?email=<email>` and shows a warning to use account recovery plus check Spam/Junk.
- 4 - I added the locale key `auth.admin_notify_recover_password_spam_hint` in both `options/locale/locale_en-US.json` and `options/locale/locale_ro-RO.json`.
- 5 - I added regression tests in `routers/web/auth/auth_test.go` for normal sign-in, forced change-password redirect, wrong-password recovery redirect, and a guard that the admin-invitation flow still redirects to `/user/invitation`.

(cherry picked from commit 9ee45b3392)
2026-05-16 22:12:07 +00:00
petru 223d2f3f58 Added - Added optional custom branding uploads to the install page.
- 1 - I finalized the installer `Branding` section with optional uploads for `logo.svg`, `logo.png`, `loading.png`, `favicon.svg`, and `favicon.png`, including clear format/size guidance plus a shared-assets checkbox for using one SVG and one PNG upload for both logo and favicon.
- 2 - I implemented backend validation and persistence for all branding uploads in `routers/install/install.go` (expected type checks, 1 MB limit, square PNG with minimum 64x64) and save accepted overrides under `custom/public/assets/img/`.
- 3 - I completed the runtime behavior so uploaded branding files override built-in assets through layered serving, `logo.svg` is mirrored to `gitea.svg` for legacy lookups, post-install progress prefers a custom `loading.png`, and the shared-assets mode hides favicon fields while relabeling logo fields to `Logo & Favicon SVG/PNG`.
- 4 - I manually updated Romanian locale wording for the final branding texts and labels.

(cherry picked from commit d81fdfc31f)
2026-05-16 21:57:54 +00:00
petru 53a6ca83a5 Added - Added the password visibility toggle and confirm-password behavior to /user/settings/account.
(cherry picked from commit 7dbc4726fa)
2026-05-16 21:57:44 +00:00
petru 03898ed70d Added - Added the password visibility toggle to the install-page database password field.
+ Fix - some new correction Romanian wording and grammar in locale_ro-RO.json.

(cherry picked from commit 3b52932acd)
2026-05-16 21:57:30 +00:00
petru 57a91789c5 Added - Added the password visibility toggle and confirm-password behavior to the install-page super-admin password fields.
+ Fix - some new correction Romanian wording and grammar in locale_ro-RO.json.

(cherry picked from commit 4ff2054a83)
2026-05-16 21:57:03 +00:00
petru 4a2c81d044 Modified - Enabled install-page email notifications by default for fresh setups.
(cherry picked from commit fb34e858c1)
2026-05-16 21:56:05 +00:00
petru 5866b9de18 Added - Added the password visibility toggle to the SMTP password field on the install page.
(cherry picked from commit a59bb9753f)
2026-05-16 21:55:59 +00:00
petru f5e38807f0 Added - Added column-wide Select all controls to the organization team-units permissions table.
+ Fix - some new correction Romanian wording and grammar in locale_ro-RO.json.

(cherry picked from commit ca7092e23c)
2026-05-16 21:55:50 +00:00
petru 8d9ce66c91 Fix - some new correction Romanian wording and grammar in locale_ro-RO.json.
(cherry picked from commit 490e119254)
2026-05-16 21:55:42 +00:00
petru e215adbc70 Modified - Unified the persistent appearance toggles into a single settings group.
(cherry picked from commit 3b121911c1)
2026-05-16 21:55:34 +00:00
petru 76ec1d4552 Modified - Some changes in .gitignore
(cherry picked from commit 354521fbd3)
2026-05-16 21:55:24 +00:00
petru 93d2710d8e Fix - some new correction Romanian wording and grammar in locale_ro-RO.json.
(cherry picked from commit aaaada5129)
2026-05-16 21:55:18 +00:00
petru 23a76e0cc0 Modified - Finalized the manual-only password visibility toggle behavior for login and signup.
(cherry picked from commit cbedf15d3b)
2026-05-16 21:55:11 +00:00
petru 5786d40338 Modified - Added an audio bell for interactive prompts in 'smart-build.sh'.
(cherry picked from commit 1525c9c8ee)
2026-05-16 21:55:05 +00:00
petru c1cc5cf8fd Added - Added pilot partial navigation for the repository Actions sidebar.
(cherry picked from commit 75bc9606d5)
2026-05-16 21:54:37 +00:00
petru eb595cd684 Modified - Applied the shared sticky side-menu behavior to repository Actions pages.
(cherry picked from commit 0f3876c0b1)
2026-05-16 21:54:30 +00:00
petru ffc1c0931c Modified - Applied the shared sticky side-menu behavior to repository settings pages.
(cherry picked from commit 652d3c20da)
2026-05-16 21:54:25 +00:00
petru 5319872a75 Added - Added password visibility toggles to the login and signup forms.
(cherry picked from commit bfb584f161)
2026-05-16 21:54:17 +00:00
petru 1679a81f34 Fix - some new correction Romanian wording and grammar in locale_ro-RO.json.
(cherry picked from commit 01e3eb1306)
2026-05-16 21:54:04 +00:00
petru 8a2b349a66 Modified - Applied the shared sticky side-menu behavior to organization settings pages.
(cherry picked from commit 827a35ce09)
2026-05-16 21:53:57 +00:00
petru 86a695b2d1 Added - Added header-level Select all controls to the shared Actions maximum-permissions table.
(cherry picked from commit 021f12509f)
2026-05-16 21:53:50 +00:00
petru 41908de091 Added - Added column-wide Select all controls to the user access-token permissions table.
(cherry picked from commit ab1135d1c6)
2026-05-16 21:53:40 +00:00
petru ac42a80034 Modified - Highlighted the active submenu entry with the standard active background color.
(cherry picked from commit 8a0d319607)
2026-05-16 21:53:35 +00:00
petru 2abc050929 Modified - Finalized the sticky side-menu bottom-edge behavior by compacting menu items and increasing the viewport reserve.
(cherry picked from commit 06b7bd3ca1)
2026-05-16 21:53:26 +00:00
petru 60f48b91ad Modified - Restored the pre-122 /user/settings layout baseline while keeping the current sticky-menu behavior.
(cherry picked from commit bb77e80bf5)
2026-05-16 21:53:18 +00:00
petru d5c8a106ec Modified - Restored the agreed /user/settings sticky-menu item padding behavior.
(cherry picked from commit 71246d4ee1)
2026-05-16 21:52:35 +00:00
petru 33cb73228e Modified - Preserved the /user/settings left-menu scroll position without the visible reset flicker during navigation.
(cherry picked from commit 3dd2ffc195)
2026-05-16 21:52:15 +00:00
petru 319ecf0bec Modified - Made the Admin Settings menu header sticky while the admin left-menu options scroll.
(cherry picked from commit 5e31019b99)
2026-05-16 21:51:32 +00:00
petru 201a4c3f69 Modified - Made the footer Licenses and API links open in a new browser tab and finalized the sticky User Settings header plus its top green scroll indicator.
(cherry picked from commit cfd1c9ddbb)
2026-05-16 21:40:48 +00:00
petru 4bf723f382 Modified - Preserved the /user/settings left-menu scroll position across settings-page navigation
+ Fix - some new correction Romanian wording and grammar in `locale_ro-RO.json`.

(cherry picked from commit a8a099edea)
2026-05-16 21:40:36 +00:00
petru 9b81fbf2ce Modified - Added a persistent navigation-bar preference in /user/settings/appearance.
(cherry picked from commit 90735ea826)
2026-05-16 21:40:05 +00:00
petru 85149bde8d Modified - Added the persistent sticky side-menu preference and the finalized sidebar behavior for /user/settings and /-/admin.
(cherry picked from commit 351d6b0811)
2026-05-16 21:39:56 +00:00
petru 19d0586b47 Modified - Moved the persistent footer outside the page scroll area
+ some new correction Romanian wording and grammar in `locale_ro-RO.json`.

(cherry picked from commit 61a9e4bd06)
2026-05-16 21:39:19 +00:00
petru 95a23e426a Modified - Reverted the global fixed-footer behavior and replaced it with a persistent per-user footer preference in /user/settings/appearance.
(cherry picked from commit b3a7692ce9)
2026-05-16 21:38:40 +00:00
petru 35dc5df4d9 Modified - Made the admin-created account notification link behave like an invitation by signing the user in through /user/activate
+ Modified - Simplified the admin-created account notification email to show only the personalized activation link.

(cherry picked from commit 10495b7cd1)
2026-05-16 21:25:57 +00:00
petru 741f4c0413 Modified - Made the admin-created account notification link behave like an invitation by signing the user in through /user/activate.
(cherry picked from commit 2ecb570a7d)
2026-05-16 21:25:51 +00:00
petru 15bf8de3a1 Fixed - Corrected the admin-created account password-setup email link to use the public recovery route
+ some new correction Romanian wording and grammar in `locale_ro-RO.json`.

(cherry picked from commit 146013827c)
2026-05-16 21:24:54 +00:00
petru 21e0121676 Modified - Personalized the admin-created account notification email with the creator name and a direct set-password link.
(cherry picked from commit 85620a4f29)
2026-05-16 21:24:41 +00:00
petru ab299063b1 Fixed - Made admin-created user notification and invitation emails use the current page locale
+ ome new correction Romanian wording and grammar in `locale_ro-RO.json`.

(cherry picked from commit 70ef46362e)
2026-05-16 21:24:00 +00:00
petru 57ee21d53e Fixed - Prevented the new-organization modal from inheriting unrelated global success flashes from the underlying page.
+ Some new correction Romanian wording and grammar in `locale_ro-RO.json`.

(cherry picked from commit fc43980a5c)
2026-05-16 21:23:54 +00:00
petru ad36689444 Modified - Reduced the resend button size on the invitation acceptance prompt.
(cherry picked from commit 5f0f52d04f)
2026-05-16 21:23:41 +00:00
petru 37ada5c0d9 Modified - Reduced the resend button size on the invitation acceptance prompt.
(cherry picked from commit 17814a4dda)
2026-05-16 21:23:35 +00:00
petru 6c16930c07 Modified - Some new correction Romanian wording and grammar in locale_ro-RO.json.
(cherry picked from commit 7c7357f314)
2026-05-16 21:23:11 +00:00
petru e20cd8a329 Modified - Some new correction Romanian wording and grammar in locale_ro-RO.json.
(cherry picked from commit f00f80bae7)
2026-05-16 21:23:06 +00:00
petru b82c82ee57 Modified - Fix align new-user check-boxes help text.
(cherry picked from commit d1e10b41a5)
2026-05-16 21:22:58 +00:00
petru 529a6603db Modified - Somes correction Romanian wording and grammar in locale_ro-RO.json
(cherry picked from commit c80f065a09)
2026-05-16 21:22:46 +00:00
petru 659abcfd5f Modified - Converted the organization creation page to a modal-style dialog and preserved the caller page for cancel.
(cherry picked from commit 5338d5f7f6)
2026-05-16 21:22:38 +00:00
petru c06bed2dce Modified - Converted the organization creation page to a modal-style dialog and preserved the caller page for cancel.
(cherry picked from commit ba0da47957)
2026-05-16 21:22:32 +00:00
petru 38fef3bcd7 Updated .codex-history.md
(cherry picked from commit 75a9dbf7d7)
2026-05-16 21:22:21 +00:00
petru 1c133b3454 Modified - Another visual polish of Romanian translation for locale_ro-RO.json.
(cherry picked from commit cc36930cdd)
2026-05-16 21:22:12 +00:00
petru 1bf070ae1d Modified - Visual polish of Romanian translation for locale_ro-RO.json.
(cherry picked from commit cb765b81a7)
2026-05-16 21:22:00 +00:00
petru 38a1b1dffe Modified - Added a first complete Romanian translation pass for locale_ro-RO.json.
(cherry picked from commit 144bc4796f)
2026-05-16 21:21:46 +00:00
petru b10c956c1e Modified - Added official bootstrap support for the Romanian locale.
(cherry picked from commit 414c77278b)
2026-05-16 21:21:26 +00:00
petru a2cf18e98e Modified - Added an install-page language hint balloon anchored to the footer language selector.
(cherry picked from commit 4eaa42bccd)
2026-05-16 21:21:19 +00:00
petru ae7eeaafbb Modified - Aligned the admin new-user invitation help text with the install-page help layout.
(cherry picked from commit f60b2af5a6)
2026-05-16 21:21:12 +00:00
petru dcac42161e Modified - Added a dedicated pending-invitation flow for admin-created invite accounts and pinned the install footer.
(cherry picked from commit f7bc24d4e8)
2026-05-16 21:20:31 +00:00
petru e71c56d8a2 Modified - Disabled forbidden email deletion actions in the admin email list.
(cherry picked from commit f8f988e85e)
2026-05-16 21:20:06 +00:00
petru 35a7f9184c Modified - Added default language selection to the install page initial configuration.
(cherry picked from commit b7e7b32caa)
2026-05-16 21:19:48 +00:00
petru 25c22c5c93 Modified - Unified classic email-confirmation signup with the resend-based pending validation flow.
(cherry picked from commit 4ab8063966)
2026-05-16 21:19:42 +00:00
petru 6be878abca Modified - Moved admin-created account delivery mode selection from install to the admin new-user form.
(cherry picked from commit a6695a6e73)
2026-05-16 21:19:35 +00:00
petru 97121edd6b Modified - Completed install-page admin-managed account modes and aligned locale install sections-v.1
(cherry picked from commit ad0ab4be60)
2026-05-16 21:19:10 +00:00
petru 4c60b2bf00 Modified - v.1-Added install-page Registration Management with coherent mode-driven registration settings.
(cherry picked from commit 19fb194db6)
2026-05-16 21:18:49 +00:00
petru 44276e2eba Type: Modified - Added install-page testing email verification using the entered SMTP settings.
(cherry picked from commit 362d01abbc)
2026-05-16 21:17:09 +00:00
petru b40d828934 Modified - Updated install-page administrator labels to super administrator wording.
(cherry picked from commit d4a1b88385)
2026-05-16 21:16:16 +00:00
petru e3e8edc143 Modified - Updated install-page administrator labels to super administrator wording.
(cherry picked from commit f13470096f)
2026-05-16 21:16:09 +00:00
petru ab0f52ea51 Modified - Added install-time admin management policy choices with direct-grantor and inherited-grantor enforcement.
Modified - Updated the example app.ini documentation for the new administrator management policies.

(cherry picked from commit 1e13af4d6e)
2026-05-16 21:15:38 +00:00
petru 4b7b647c30 Modified - Restored normal self-edit access for super admins and disabled only the admin actions that are truly forbidden.
(cherry picked from commit 43161732e3)
2026-05-16 21:15:20 +00:00
petru 089863052d Modified - Protected GOOD-granted admin accounts and blocked deleting the direct grantor.
(cherry picked from commit 80497e4194)
2026-05-16 21:14:58 +00:00
petru 6484fc06ef Modified - Protected GOOD-granted admin accounts and blocked deleting the direct grantor.
(cherry picked from commit 0cbec16f84)
2026-05-16 21:14:44 +00:00
petru 344ef1fad6 Modified - Protected GOOD-granted admin accounts and blocked deleting the direct grantor.
(cherry picked from commit 22a6945b9d)
2026-05-16 21:14:34 +00:00
petru 63b93a7048 Modified - Kept super administrator Edit and Delete controls visible but disabled for regular admins.
(cherry picked from commit 5da24d2c7b)
2026-05-16 21:13:19 +00:00
petru c7d6f61d9e Fixed - Blocked regular administrators from editing super administrator accounts.
(cherry picked from commit 0fc6f30a30)
2026-05-16 21:12:55 +00:00
petru 384fba3fc3 Fixed - Enabled super administrator bootstrap by default.
(cherry picked from commit 35b9fa65d3)
2026-05-16 21:12:40 +00:00
petru f2fae6095b Added - Added persistent super administrator protection & Enabled super administrator bootstrap by default.
(cherry picked from commit a14158b63a)
2026-05-16 21:11:19 +00:00
petru cab2a9371f Fixed - Hidde Is Administrator reason unless admin rights were revoked.
(cherry picked from commit cff1b46f50)
2026-05-16 21:11:09 +00:00
petru b588b3d2b2 Modified - Added admin actor badge beside the Is Administrator option.
(cherry picked from commit 4aacf3bd20)
2026-05-16 21:10:15 +00:00
petru e40acbea0b Fixed - Disabled critical self-edit account state checkboxes.
(cherry picked from commit 3afb4e8afa)
2026-05-16 21:01:30 +00:00
petru 05318e0933 Added - Added Is Administrator reason and admin-grant badges.
(cherry picked from commit 067a09c2ac)
2026-05-16 21:01:20 +00:00
petru 30f9ff7478 Added - Added restricted-admin badges and reason actor badges.
(cherry picked from commit 396b15372d)
2026-05-16 21:01:09 +00:00
petru 61f9e3bf06 Fixed - Corrected admin status reason behavior and reactivation emails.
(cherry picked from commit b3204f3db6)
2026-05-16 21:00:54 +00:00
petru 3fbd617767 Fixed - Corrected admin status reason behavior and reactivation emails.
(cherry picked from commit 936ccf3738)
2026-05-16 21:00:39 +00:00
petru caff3a8315 Added - Added admin status-change reasons and user email notifications.
(cherry picked from commit 210955465e)
2026-05-16 21:00:27 +00:00
petru b50134da2f Added - Added Disable Sign-In metadata to the admin users list.
(cherry picked from commit 1dcd81b420)
2026-05-16 21:00:11 +00:00
petru 35e79a8393 Modified - Defaulted admin user purge checkboxes to enabled.
(cherry picked from commit a8d9e5e659)
2026-05-16 20:59:59 +00:00
petru d3b5d47e76 Modified - Moved account request review controls to the top of the admin user edit panel.
Fixed - Prevented empty `by` badges in the admin users list.

(cherry picked from commit c7c7af77a1)
2026-05-16 20:59:45 +00:00
petru e2a750824d Modified - Added persistent admin email tooltip to creator badges.
Add: Activated column show a `by <admin>` badge with the stored admin email as a hover tooltip.

(cherry picked from commit a3e09bb819)
2026-05-16 20:59:36 +00:00
petru 2e2756c16a Fixed - Kept creator-admin badges permanently attached to invited accounts.
(cherry picked from commit cd96c721e0)
2026-05-16 20:59:22 +00:00
petru 137243c988 Modified - Added a user creator-admin badges to the admins users list.
(cherry picked from commit cfd7cfa1dc)
2026-05-16 20:59:09 +00:00
petru 12e140bf68 Added - Notified inviting admins when admin-created invitations are accepted.
(cherry picked from commit 8147f7a798)
2026-05-16 20:58:56 +00:00
petru 8557aeca72 Added - Added admin-created account invitation flow when registration is disabled.
(cherry picked from commit 20405fe5e7)
2026-05-16 20:58:37 +00:00
petru fb23ea28bc Modified - Added password confirmation to account recovery.
(cherry picked from commit 25a1d84c2e)
2026-05-16 20:58:26 +00:00
petru a25837d735 Blocked inactive account-request users from getting a signed-in session
(cherry picked from commit f21b6b7a3b)
2026-05-16 20:54:37 +00:00
petru 6e9ea05a4f Added an admin user-list delete account action button
(cherry picked from commit 8b14814199)
2026-05-16 20:34:42 +00:00
petru 296c2a1689 Added inline test email feedback, keep page scroll position & display email delivery status messages.
(cherry picked from commit 62164e3fd8)
2026-05-16 20:34:25 +00:00
petru cfb6f32204 admin registration confirm OK
(cherry picked from commit 1a438e765d)
2026-05-16 20:33:43 +00:00
wxiaoguang e0e7f0c4ed Fix corrupted JSON caused by goccy library (#37214) (#37220)
Backport #37214

The only conflict is go.mod

Co-authored-by: Lunny Xiao <xiaolunwen@gmail.com>
(cherry picked from commit 3b253e06a3)
2026-05-16 20:21:13 +00:00
Giteabot b79074aeb1 Implement logout redirection for reverse proxy auth setups (#36085) (#37171)
Backport #36085 by @eliroca

When authentication is handled externally by a reverse proxy SSO
provider, users can be redirected to an external logout URL or relative
path defined on the reverse proxy.

Co-authored-by: Elisei Roca <eroca@suse.de>
Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit 7a7376dfc8)
2026-05-16 20:09:44 +00:00
Giteabot 64f52201b1 Fix UI regression (#37218) (#37219)
Backport #37218 by wxiaoguang

Fix  #37213

Also fix the misaligned tags, remove unused classes, etc.

Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit df0ad4e8c1)
2026-05-16 20:02:15 +00:00
Giteabot af15978c31 fix(api): handle missing base branch in PR commits API (#37193) (#37203)
Backport #37193 by @Mohit25022005

fix(api): handle missing base branch in PR commits API

Closes #36366

Previously, the PR commits API returned a 500 Internal Server Error
when the base branch was missing due to an unhandled git "bad revision"
error.

This change:
- Checks for base branch existence before performing git operations
- Returns 404 when the base branch does not exist
- Prevents git errors from surfacing as 500 responses

This improves API robustness and aligns behavior with expected error
handling.

Tested locally by:
- Creating a pull request
- Deleting the base branch
- Verifying that the API returns 404 instead of 500

Co-authored-by: Mohit Swarnkar <mohitswarnkar13@gmail.com>
Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
Co-authored-by: Lunny Xiao <xiaolunwen@gmail.com>
(cherry picked from commit 68f5e40e46)
2026-05-16 20:01:47 +00:00
Giteabot 511f9bfd20 Fix encoding for Matrix Webhooks (#37190) (#37201)
Backport #37190 by @bircni

`url.PathEscape` unnecessarily encodes ! to %21, causing Matrix
homeservers to reject the request with 401. Replace %21 back to ! after
escaping.

Fixes #36012

Signed-off-by: wxiaoguang <wxiaoguang@gmail.com>
Co-authored-by: Nicolas <bircni@icloud.com>
Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit d1be5c3612)
2026-05-16 20:01:40 +00:00
Giteabot 8d921a67ff Always show owner/repo name in compare page dropdowns (#37172) (#37200)
Backport #37172 by @xingxing21

Fixes: https://github.com/go-gitea/gitea/issues/36677

The fix is a template-only change in
[templates/repo/diff/compare.tmpl:16-25](vscode-webview://1ca9j6f1e3qtaf59o0cr4ind65ulf8mevvbbbq88int1gg2lncar/templates/repo/diff/compare.tmpl#L16-L25).

Before, the display names were built with conditional logic:

All four variables defaulted to just the owner name (Examples)
$HeadCompareName was only upgraded to owner/repo format in two narrow
cases:
Same org, different repos
A root repo exists with the same owner as the head repo
All other cases (same-repo PRs, cross-org PRs) got owner-only labels
After, all four variables are unconditionally set to owner/repo format
using printf "%s/%s":

```
- {{$BaseCompareName := printf "%s/%s" $.BaseName $.Repository.Name -}}
- {{- $HeadCompareName := printf "%s/%s" $.HeadRepo.OwnerName $.HeadRepo.Name -}}
- {{- $OwnForkCompareName := "" -}}
- {{- if .OwnForkRepo -}}
-	{{- $OwnForkCompareName = printf "%s/%s" .OwnForkRepo.OwnerName .OwnForkRepo.Name -}}
- {{- end -}}
- {{- $RootRepoCompareName := "" -}}
- {{- if .RootRepo -}}
-	{{- $RootRepoCompareName = printf "%s/%s" .RootRepo.OwnerName .RootRepo.Name -}}
- {{- end -}}

+ {{$BaseCompareName := $.Repository.FullName -}}
+ {{$HeadCompareName := $.HeadRepo.FullName -}}
+ {{$OwnForkCompareName := "" -}}
+ {{if $.OwnForkRepo -}}
+	{{$OwnForkCompareName = $.OwnForkRepo.FullName -}}
+ {{end -}}
+ {{$RootRepoCompareName := "" -}}
+ {{if $.RootRepo -}}
+	{{$RootRepoCompareName = $.RootRepo.FullName -}}
+ {{end -}}
```

These variables drive the labels in the base and head branch selector
buttons and their dropdown items. No backend changes were needed —
$.BaseName, $.Repository.Name, $.HeadRepo.OwnerName, and $.HeadRepo.Name
were already available in the template context.

Co-authored-by: Xing Hong <39619359+xingxing21@users.noreply.github.com>
Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit 8687faaf3a)
2026-05-16 20:01:32 +00:00
Giteabot b56db2ff18 fix(api): handle fork-only commits in compare API (#37185) (#37199)
Backport #37185 by @Mohit25022005

Fix 500 error when comparing branches across fork repositories

## Problem

The compare API returns a 500 Internal Server Error when comparing
branches where the head commit exists only in the fork repository.

## Cause

The API was using the base repository's GitRepo and repository context
when converting commits. This fails when the commit does not exist in
the base repository, resulting in a "fatal: bad object" error.

## Solution

Use the head repository and HeadGitRepo when available to ensure commits
are resolved in the correct repository context.

## Result

* Fixes "fatal: bad object" error
* Enables proper comparison between base and fork repositories
* Prevents 500 Internal Server Error

Fixes #37168

Co-authored-by: Mohit Swarnkar <mohitswarnkar13@gmail.com>
Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit 789a3d3a4d)
2026-05-16 20:00:09 +00:00
Giteabot 367a72ce11 Indicate form field readonly via background, fix RunUser config (#37175, #37180) (#37184)
Backport #37175 by @silverwind

The `Run As Username` field on the install page was a `readonly` input
that looked editable but wasn't, confusing users. Style `readonly`
inputs with a subtle background, matching other frameworks.

<img width="735" height="131" alt="image"
src="https://github.com/user-attachments/assets/cb76ce71-faab-4300-811e-e4c503b59f9a"
/>

Backport #37180

The comment "so just use current one if config says default" is not
right anymore: "git" isn't the "default" value of RunUser (Comment out
app.example.ini #15807). The RunUser's value is from current session's
username.

Fixes #37174

---------

Signed-off-by: wxiaoguang <wxiaoguang@gmail.com>
Signed-off-by: silverwind <me@silverwind.io>
Co-authored-by: silverwind <me@silverwind.io>
Co-authored-by: Claude (Opus 4.6) <noreply@anthropic.com>
Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit b37e098ff0)
2026-05-16 20:00:01 +00:00
Giteabot 4957f351d0 Remove dead CSS rules (#37173) (#37177)
Backport #37173 by @silverwind

Remove CSS rules whose HTML classes/IDs are no longer referenced in any
template, Go source, or JavaScript/TypeScript file:

- `.archived-icon`: removed from templates in c85bb62635
- `.bottom-line`: removed from blame rendering in 9c6aeb47f7
- `.commit-status-link`: removed from templates in f3c4baa84b
- `.instruct-toggle`: removed from templates in 75e85c25c1
- `.runner-new-text`, `#runner-new`: never referenced outside CSS
- `.ap-terminal`: stale, asciinema-player uses `.ap-term`, still not
needed
- `.scrolling.dimmable.dimmed`: dimmer stand-in never adds this class
- `.markup span.align-center/align-right/float-left/float-right`: never
produced by any renderer, sanitizer strips class attributes
- `.markup ul.no-list`, `.markup ol.no-list`: same as above

---
This PR was written with the help of Claude Opus 4.6

Signed-off-by: silverwind <me@silverwind.io>
Co-authored-by: silverwind <me@silverwind.io>
Co-authored-by: Claude (Opus 4.6) <noreply@anthropic.com>
Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit f9b808a8d2)
2026-05-16 19:59:44 +00:00
Giteabot 43197a9efd Fix flaky TestCatFileBatch/QueryTerminated test (#37159) (#37178)
Backport #37159 by @silverwind

`TestCatFileBatch/QueryTerminated` relied on timing to distinguish
`os.ErrClosed` vs `io.EOF` error paths. Replace `time.Sleep`-based
synchronization with a channel-based hook on pipe close, making both
error paths fully deterministic regardless of CI runner speed.

Ref:
https://github.com/go-gitea/gitea/actions/runs/24193070536/job/70615366804

---
This PR was written with the help of Claude Opus 4.6

Co-authored-by: silverwind <me@silverwind.io>
Co-authored-by: Claude (Opus 4.6) <noreply@anthropic.com>
Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit 0112ec9b34)
2026-05-16 19:59:32 +00:00
Giteabot e334806d4e Add missing //nolint:depguard (#37162) (#37170)
Backport #37162 by @silverwind

When running `golangci-lint` without `GOEXPERIMENT=jsonv2`, a lint error
`import 'encoding/json' is not allowed` is seen.

All other files in the module that import `encodings/json` have
`//nolint` already, so add it.

---
This PR was written with the help of Claude Opus 4.6

Co-authored-by: silverwind <me@silverwind.io>
Co-authored-by: Claude (Opus 4.6) <noreply@anthropic.com>
(cherry picked from commit fc5e0ec877)
2026-05-16 19:59:19 +00:00
silverwind 3759793fa8 Replace rollup-plugin-license with rolldown-license-plugin (#37130) (#37158)
Backport #37130. Only one merge conflict in lockfile.

---
This PR was written with the help of Claude Opus 4.6

Co-authored-by: Claude (Opus 4.6) <noreply@anthropic.com>
(cherry picked from commit d0a39bc3a4)
2026-05-16 19:59:03 +00:00
Giteabot 7e79b87136 Report structurally invalid workflows to users (#37116) (#37164)
Backport #37116 by @bircni

`model.ReadWorkflow` succeeds for YAML that is syntactically valid but
fails deeper parsing in `jobparser.Parse` (e.g. blank lines inside `run:
|` blocks cause a SetJob round-trip error). Add
`ValidateWorkflowContent` which runs the full `jobparser.Parse` to catch
these cases, and use it in the file view, the actions workflow list, and
the workflow detection loop so users see the error instead of silently
getting a 500 or a dropped workflow.

Fixes #37115

Signed-off-by: Nicolas <bircni@icloud.com>
Co-authored-by: Nicolas <bircni@icloud.com>
Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-authored-by: Zettat123 <zettat123@gmail.com>
Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
(cherry picked from commit 4eca71d6d4)
2026-05-16 19:58:52 +00:00
Giteabot 09d8f9bc47 Clean up and improve non-gitea js error filter (#37148) (#37155)
Backport #37148 by @silverwind

1. Filter out errors that contain `chrome-extension://` etc protocols
2. Extract filtering into its own function and test it
3. Fix the `window.config.assetUrlPrefix` mock, guaranteed to end with
`/assets`
4. Remove useless `??` and `?.` for properties that always exist

---
This PR was written with the help of Claude Opus 4.6

Co-authored-by: silverwind <me@silverwind.io>
Co-authored-by: Claude (Opus 4.6) <noreply@anthropic.com>
(cherry picked from commit a2283a0c03)
2026-05-16 19:58:30 +00:00
Giteabot 469daf5924 Bump min go version to 1.26.2 (#37139) (#37143)
Backport #37139 by @silverwind

Update Go from 1.26.1 to 1.26.2 to fix 6 stdlib vulnerabilities:
- GO-2026-4947: `crypto/x509` chain building
- GO-2026-4946: `crypto/x509` policy validation
- GO-2026-4870: `crypto/tls` KeyUpdate DoS
- GO-2026-4869: `archive/tar` unbounded allocation
- GO-2026-4866: `crypto/x509` name constraints bypass
- GO-2026-4865: `html/template` XSS

Co-authored-by: silverwind <me@silverwind.io>
Co-authored-by: Claude (Opus 4.6) <noreply@anthropic.com>
(cherry picked from commit 3e6b9e5312)
2026-05-16 19:57:58 +00:00
petru 7ae0c597f1 feat(auth): add staged account request validation and admin review workflow
(cherry picked from commit b2b024d0b6)
2026-05-16 19:56:37 +00:00
petru 9da2215095 feat(admin): improve new account request notification safeguards
feat(admin): enforce fallback and subscription rules for new account request notifications

(cherry picked from commit 81727dd3e9)
2026-05-16 19:55:55 +00:00
petru f9131d4261 Added administrator notifications for pending account requests-Step1
(cherry picked from commit 97eee0a9a8)
2026-05-16 19:54:13 +00:00
petru 5acdf62b9a Disable last Admin to self delete
(cherry picked from commit c3b9d21472)
2026-05-16 19:53:43 +00:00
petru 0c3f3b85e8 Disable admin users to downgrade
(cherry picked from commit 5c88e0bc76)
2026-05-16 19:41:23 +00:00
petru fdb233150a Added Public/Private Badges & repos Settings links
(cherry picked from commit 4b334df6d4)
2026-05-16 19:39:51 +00:00
petru ffb13c1136 Added menu to smart-build.sh, fixed errors in some files
(cherry picked from commit db1e8b4021)
2026-05-16 19:39:41 +00:00
petru 0716d3fa15 Add some fetch & builing scripts
(cherry picked from commit eb0b9b2dee)
2026-05-16 19:36:28 +00:00
Lunny Xiao 1ad9e996be Changelog for 1.26.0-rc0 (#37134) 2026-04-07 20:33:38 -07:00
307 changed files with 34364 additions and 11392 deletions
+358
View File
@@ -0,0 +1,358 @@
.
./types.d.ts
./docker
./docker/manifest.rootless.tmpl
./docker/root
./docker/manifest.tmpl
./docker/README.md
./docker/rootless
./BSDmakefile
./tests
./tests/integration
./tests/gitea-lfs-meta
./tests/mysql.ini.tmpl
./tests/e2e
./tests/testdata
./tests/fuzz
./tests/test_utils.go
./tests/sqlite.ini.tmpl
./tests/gitea-repositories-meta
./tests/pgsql.ini.tmpl
./tests/mssql.ini.tmpl
./eslint.json.config.ts
./LICENSE
./models
./models/repo.go
./models/avatars
./models/system
./models/auth
./models/migrations
./models/pull
./models/main_test.go
./models/fixtures
./models/asymkey
./models/packages
./models/unittest
./models/admin
./models/repo
./models/activities
./models/unit
./models/db
./models/dbfs
./models/shared
./models/webhook
./models/secret
./models/perm
./models/user
./models/renderhelper
./models/actions
./models/git
./models/organization
./models/issues
./models/repo_test.go
./models/project
./eslint.config.ts
./flake.lock
./tools
./tools/generate-svg-vscode-extensions.json
./tools/test-e2e.sh
./tools/code-batch-process.go
./tools/gocovmerge.go
./tools/lint-templates-svg.ts
./tools/generate-images.ts
./tools/codeformat
./tools/generate-svg.ts
./tools/test-echo.go
./tools/watch.sh
./vitest.config.ts
./CHANGELOG.md
./+x
./CODE_OF_CONDUCT.md
./CLAUDE.md
./README.zh-tw.md
./web_src
./web_src/svg
./web_src/fomantic
./web_src/js
./web_src/css
./CHANGELOG-archived.md
./custom
./custom/conf
./contrib
./contrib/systemd
./contrib/init
./contrib/update_dependencies.sh
./contrib/fhs-compliant-script
./contrib/launchd
./contrib/backport
./contrib/README
./contrib/legal
./contrib/supervisor
./contrib/options
./contrib/upgrade.sh
./contrib/ide
./contrib/gitea-monitoring-mixin
./templates
./templates/package
./templates/post-install.tmpl
./templates/status
./templates/devtest
./templates/projects
./templates/base
./templates/org
./templates/swagger
./templates/custom
./templates/admin
./templates/repo
./templates/shared
./templates/webhook
./templates/api
./templates/home.tmpl
./templates/install.tmpl
./templates/user
./templates/explore
./templates/mail
./update-gitea.sh
./flake.nix
./DCO
./MAINTAINERS
./routers
./routers/common
./routers/install
./routers/web
./routers/private
./routers/init.go
./routers/api
./routers/utils
./pnpm
./package.json
./snap
./snap/snapcraft.yaml
./services
./services/uinotification
./services/convert
./services/secrets
./services/wiki
./services/auth
./services/migrations
./services/pull
./services/projects
./services/repository
./services/markup
./services/oauth2_provider
./services/asymkey
./services/org
./services/task
./services/packages
./services/mailer
./services/forms
./services/issue
./services/webtheme
./services/attachment
./services/mirror
./services/versioned_migration
./services/agit
./services/context
./services/release
./services/doctor
./services/gitdiff
./services/webhook
./services/automerge
./services/contexttest
./services/cron
./services/user
./services/automergequeue
./services/feed
./services/actions
./services/git
./services/lfs
./services/notify
./services/indexer
./services/externalaccount
./go.mod
./assets
./assets/misspellings.csv
./assets/logo.svg
./assets/emoji.json
./assets/go-licenses.json
./assets/favicon.svg
./smart-build.sh
./Dockerfile.rootless
./build
./build/generate-go-licenses.go
./build/update-locales.sh
./build/generate-emoji.go
./build/generate-bindata.go
./build/generate-gitignores.go
./build/test-env-check.sh
./build/test-env-prepare.sh
./pyproject.toml
./updates.config.ts
./tsconfig.json
./pnpm-lock.yaml
./crowdin.yml
./SECURITY.md
./options
./options/locale
./options/gitignore
./options/fileicon
./options/label
./options/license
./options/readme
./docs
./docs/guideline-frontend.md
./docs/release-management.md
./docs/guideline-backend.md
./docs/community-governance.md
./playwright.config.ts
./cmd
./cmd/manager_logging.go
./cmd/admin_auth_ldap_test.go
./cmd/web_acme.go
./cmd/admin_user_delete.go
./cmd/admin_user_must_change_password_test.go
./cmd/admin_user_create.go
./cmd/admin_regenerate.go
./cmd/generate.go
./cmd/admin_auth.go
./cmd/dump.go
./cmd/admin_user_must_change_password.go
./cmd/doctor_test.go
./cmd/migrate.go
./cmd/admin_auth_oauth.go
./cmd/main_test.go
./cmd/actions.go
./cmd/cmd_test.go
./cmd/cert_test.go
./cmd/migrate_storage_test.go
./cmd/web_graceful.go
./cmd/doctor.go
./cmd/admin_user_delete_test.go
./cmd/embedded.go
./cmd/manager.go
./cmd/config.go
./cmd/admin_user_change_password.go
./cmd/cert.go
./cmd/hook_test.go
./cmd/web.go
./cmd/hook.go
./cmd/admin_auth_ldap.go
./cmd/admin_user_list.go
./cmd/admin_user_change_password_test.go
./cmd/admin_auth_smtp_test.go
./cmd/web_https.go
./cmd/docs.go
./cmd/admin_user_create_test.go
./cmd/migrate_storage.go
./cmd/admin_auth_oauth_test.go
./cmd/serv.go
./cmd/admin_user_generate_access_token.go
./cmd/admin.go
./cmd/config_test.go
./cmd/doctor_convert.go
./cmd/main.go
./cmd/dump_repo.go
./cmd/keys.go
./cmd/admin_user.go
./cmd/admin_auth_smtp.go
./cmd/restore_repo.go
./cmd/mailer.go
./cmd/cmd.go
./AGENTS.md
./README.zh-cn.md
./Dockerfile
./tailwind.config.ts
./Makefile
./README.md
./main.go
./go.sum
./uv.lock
./stylelint.config.js
./CONTRIBUTING.md
./modules
./modules/reqctx
./modules/public
./modules/references
./modules/httplib
./modules/hcaptcha
./modules/generate
./modules/tailmsg
./modules/turnstile
./modules/system
./modules/badge
./modules/eventsource
./modules/htmlutil
./modules/setting
./modules/fileicon
./modules/auth
./modules/migration
./modules/svg
./modules/repository
./modules/markup
./modules/typesniffer
./modules/test
./modules/web
./modules/pprof
./modules/validation
./modules/base
./modules/tempdir
./modules/zstd
./modules/gitrepo
./modules/packages
./modules/testlogger
./modules/process
./modules/templates
./modules/label
./modules/issue
./modules/dump
./modules/metrics
./modules/assetfs
./modules/nosql
./modules/avatar
./modules/updatechecker
./modules/private
./modules/cache
./modules/regexplru
./modules/gtprof
./modules/log
./modules/commitstatus
./modules/session
./modules/highlight
./modules/csv
./modules/proxy
./modules/queue
./modules/uri
./modules/httpcache
./modules/lfstransfer
./modules/options
./modules/webhook
./modules/secret
./modules/json
./modules/globallock
./modules/emoji
./modules/charset
./modules/recaptcha
./modules/user
./modules/paginator
./modules/proxyprotocol
./modules/actions
./modules/optional
./modules/structs
./modules/ssh
./modules/timeutil
./modules/glob
./modules/git
./modules/lfs
./modules/mcaptcha
./modules/util
./modules/sitemap
./modules/graceful
./modules/storage
./modules/cachegroup
./modules/hostmatcher
./modules/container
./modules/translation
./modules/indexer
./modules/analyze
./vite.config.ts
./main_timezones.go
+64
View File
@@ -0,0 +1,64 @@
# Gitea Codex Context
This file is Codex's persistent operating context for this repository.
Related orientation documents:
- Full project change log: `./.codex-history.md`
- Persistent implementation map: `./.codex-project-map.md`
- Raw structural baseline: `./.ai-structure.md`
## Recommended Read Order
1. `./.codex-context.md`
2. `./.codex-project-map.md`
3. The concrete files involved in the current task
4. `./.codex-history.md` only through targeted search, tags, or the latest relevant entries
## High-Value Project Anchors
- App entry point and default version wiring: `main.go`
- Web command and server startup: `cmd/web.go`
- Installed-instance initialization and route mounting: `routers/init.go`
- Main web router: `routers/web/web.go`
- Authentication handlers: `routers/web/auth/`
- Request context, session, template data, and response helpers: `services/context/`
- Domain business logic: `services/`
- Persistence, DB infrastructure, and migrations: `models/`, `models/db/`, `models/migrations/`
- Server-side UI templates: `templates/`
- Browser-side JS/CSS/frontend: `web_src/`
For detailed request flow, auth flow, extension points, and task-oriented entry points, use `./.codex-project-map.md` instead of duplicating them here.
## Persistent Workflow Rules
- Update `./.codex-history.md` after real project code changes.
- Do not add Codex-only preference or memory edits to `./.codex-history.md`.
- Do not reread unchanged context files within the same session unless the current task explicitly depends on them.
- Prefer targeted search in `./.codex-history.md` by keyword, tag, or subsystem before reading larger ranges.
- When the user asks for `revert`:
- first show the latest 10 commits as a numbered list with short descriptions;
- wait for the user's numeric choice before doing anything;
- if the target change is not committed, explain that the safe path is `git restore`, not `git revert`.
- Revert flows must stay non-destructive by default; prefer `git revert` for committed changes and avoid destructive reset-style actions unless the user explicitly asks for them.
## Persistent `.codex-history.md` Rules
- Numeric IDs are reserved only for real project code changes.
- IDs start at `0` and increase sequentially by `1`.
- Use the format `N - [YYYY-MM-DD HH:MM:SS]`.
- Store the real repository-derived application version, without a `Version:` label.
- Keep only the final consolidated result of a task; do not keep intermediate attempts or failed correction steps.
- Append to the same task only while the changes are consecutive follow-ups to the same problem.
- If unrelated tasks happened in between, record the new work as a new task even if it returns to the same area.
## Persistent Communication Preferences
- After finishing a task, respond briefly and directly unless there are blockers or problems.
- Re-check the rules in this file before and after making changes.
## Current Working Notes
- `main.go` defaults `setting.AppVer` to `development`; derive the real build/version string from the repository when writing `./.codex-history.md`.
- The repository is predictably split across `cmd/`, `routers/`, `services/`, `models/`, `templates/`, and `web_src/`, so changes should normally stay localized to one or two layers plus their tests.
- For custom release maintenance and repo-sync tasks, consult `./.codex-script-notes.md` before reanalyzing the large helper scripts.
- New UI-visible functionality in this fork often also requires locale updates, so UI tasks and related history searches should usually consider `options/locale/`, especially `locale_en-US.json` and any actively maintained translated locale files.
+812
View File
@@ -0,0 +1,812 @@
Project Change ID[date-time] - application-version - Type - Summary:
History search guidance:
- Prefer targeted search by task tag, subsystem keyword, or file/path before reading long ranges.
- Entries are tagged inline as `[tag] [tag]` to support targeted search and filtering.
0 - [2026-04-16 02:46:18] - v.1.27.0-dev-38-g4b334df6d4 - Type: Modified - [repo-ui] [visibility] [badges] Added explicit repository visibility badges to match the requested GitHub-style presentation more closely.
- 1 - I modified `templates/repo/header.tmpl` so the repository page header now always shows a visibility badge on the right side: `Private`, `Internal`, or `Public`.
- 2 - I modified `templates/shared/repo/list.tmpl` so each repository entry in shared repository lists also shows an explicit visibility badge for `Private`, `Internal`, or `Public`.
- 3 - I added the `Public` label for repositories that previously had no explicit visibility badge, while preserving the existing archived, template, and sha256 labels.
- 4 - I reused existing translation keys and existing badge styling so the change stays visually consistent with the current Gitea UI.
1 - [2026-04-16 03:31:29] - v.1.27.0-dev-38-g4b334df6d4 - Type: Modified - [repo-ui] [visibility] [badges] [repo-settings] Refined repository visibility badges with semantic colors, owner-aware navigation, and broader coverage in repository settings views.
- 1 - I modified `templates/shared/repo/list.tmpl` so `Public` now uses a basic green badge and `Private` now uses a basic red badge, while `Internal` remains neutral.
- 2 - I modified `templates/repo/header.tmpl` so the repository header uses the same color-coded visibility badges and keeps the mobile icon behavior unchanged.
- 3 - I added owner-aware navigation for the `Public` and `Private` badges so they link to the repository `Settings` page only when the signed-in user is the repository owner.
- 4 - I modified `templates/user/settings/repos.tmpl` so the same visibility badge now appears next to repository names in `/user/settings/repos`, in both list variants rendered by that page.
- 5 - I preserved the existing archived, template, fork, mirror, and object-format indicators so only the requested visibility presentation changed.
2 - [2026-04-16 03:45:08] - v.1.27.0-dev-38-g4b334df6d4 - Type: Fixed - [user-settings] Corrected a template rendering error in /user/settings/repos caused by dereferencing a missing Owner object.
- 1 - I fixed `templates/user/settings/repos.tmpl` so the internal-visibility check now guards against a nil `Owner` before accessing `Owner.Visibility`.
- 2 - I applied the null-safe visibility guard in both repository list variants rendered by `/user/settings/repos`.
- 3 - I preserved the new green/red visibility badge styling and owner-aware settings links while removing the nil-pointer render failure.
3 - [2026-04-16 04:53:24] - v.1.27.0-dev-38-g4b334df6d4 - Type: Modified - [admin-users] Hid the admin privilege toggle when an administrator edits their own account from the admin user edit page.
- 1 - I modified `templates/admin/user/edit.tmpl` so the `Is Administrator` checkbox is no longer rendered when the edited user ID matches the signed-in admin ID.
- 2 - I preserved the existing checkbox behavior for editing other users, so administrators can still grant or revoke admin rights for other accounts.
- 3 - I kept the change limited to the admin edit UI without altering unrelated fields or backend update logic.
4 - [2026-04-16 03:11:08] - v.1.27.0-dev-38-g4b334df6d4 - Type: Modified - [admin-users] [account-deletion] Disabled the self-account deletion option only for the last administrator and aligned the backend rule with that behavior.
- 1 - I modified `templates/user/settings/account.tmpl` so the `Delete Your Account` action is disabled and shows the last-admin warning when the signed-in user is the only remaining admin.
- 2 - I modified `routers/web/user/setting/account.go` so the account settings page now receives an `IsLastAdminUser` flag used by the template.
- 3 - I updated the self-delete backend flow so it blocks account deletion only when the signed-in user is the last admin, instead of blocking every admin unconditionally.
5 - [2026-04-16 03:26:40] - v.1.27.0-dev-38-g4b334df6d4 - Type: Fixed - [admin-users] [account-deletion] Adjusted the shared last-admin detection to count only active administrators so account deletion and admin demotion rules behave correctly in real instances.
- 1 - I modified `models/user/user.go` so `IsLastAdminUser` now treats only active admins as candidates when deciding whether a user is the last admin.
- 2 - This aligns the shared last-admin protection used by account deletion and admin privilege update flows with practical instance behavior.
- 3 - The existing `/user/settings/account` UI and backend guards now work against the refined active-admin definition without additional template changes.
6 - [2026-04-16 03:43:20] - v.1.27.0-dev-38-g4b334df6d4 - Type: Modified - [user-settings] [admin-users] [account-deletion] [ui] Updated the Delete Your Account panel for the last-admin case so it shows a direct warning message and hides the deletion controls.
- 1 - I modified `templates/user/settings/account.tmpl` so the panel now shows `You cannot remove the last admin. There must be at least one admin.` while keeping the existing alert icon.
- 2 - I hid the `Password` field for the last-admin case.
- 3 - I hid the `Confirm Deletion` button for the last-admin case while preserving the normal delete flow for other users.
7 - [2026-04-16 17:37:53] - v.1.27.0-dev-40-gc3b9d21472 - Type: Added - [auth] [account-requests] [mailer] [locale] [en] Added administrator notifications for pending account requests and delayed the user activation email until manual approval.
- 1 - I added a new `email_notification.new_account_requests` user setting in `models/user/setting_options.go`, with an admin-default enabled preference and helper functions to read the preference consistently.
- 2 - I modified `routers/web/user/setting/notifications.go`, `routers/web/web.go`, and `templates/user/settings/notifications.tmpl` so administrators now get a `New account request notifications` checkbox in `/user/settings/notifications`, and the last active admin cannot disable it.
- 3 - I modified `routers/web/auth/auth.go`, `services/mailer/mail_user.go`, `templates/mail/user/auth/new_account_request.tmpl`, and `options/locale/locale_en-US.json` so manual account requests now send notification emails to opted-in active admins with a direct review link.
- 4 - I modified `routers/web/admin/users.go` so when an administrator activates a manually approved account while registration email confirmation is disabled, the applicant receives the standard account activation email at that approval moment.
8 - [2026-04-16 18:59:58] - v.1.27.0-dev-41-g97eee0a9a8 - Type: Fixed - [account-requests] [locale] [en] Corrected the new account request notification rule so at least one active administrator must remain subscribed.
- 1 - I modified `models/user/setting_options.go` to count active administrators who still have new account request notifications enabled and to detect when the current admin is the last enabled recipient.
- 2 - I modified `routers/web/user/setting/notifications.go` so the backend now blocks disabling the preference only when the signed-in admin is the last enabled notification recipient, instead of checking whether they are merely the last admin user.
- 3 - I modified `templates/user/settings/notifications.tmpl` so the checkbox and submit button are disabled only for the last enabled notification recipient.
- 4 - I updated `options/locale/locale_en-US.json` so the warning message now states the real rule clearly: at least one admin must keep these notifications enabled.
9 - [2026-04-16 20:53:32] - v.1.27.0-dev-41-g97eee0a9a8 - Type: Added - [account-requests] Added automatic notification fallback when deleting the only admin who still receives new account request notifications.
- 1 - I added `ShouldEnableNewAccountRequestNotificationsFallback` in `models/user/setting_options.go` so the code can detect when the deleted user is the last active admin with this notification enabled and the acting admin is currently unsubscribed.
- 2 - I modified `routers/web/admin/users.go` so, after a successful admin-driven user deletion, the acting admin is automatically subscribed to new account request notifications when they deleted the last subscribed admin.
- 3 - I modified `routers/api/v1/admin/user.go` so the same automatic fallback also applies to admin deletions performed through the API, keeping the behavior consistent across both deletion entry points.
10 - [2026-04-16 23:02:55] - v.1.27.0-dev-42-g81727dd3e9 - Type: Added - [account-requests] [mailer] [locale] [en] Implemented a staged new account request workflow with email validation, admin review, request statuses, and automatic expiry cleanup.
- 1 - I added `models/user/account_request.go` to store and manage account request states, validation expiry, retry counting, approval or rejection metadata, validation code generation, and expired pending-request cleanup.
- 2 - I modified `routers/web/auth/auth.go`, added `routers/web/auth/account_request.go`, and updated `templates/user/auth/signup_inner.tmpl` so registration now creates pending account requests, resends validation mail when appropriate, blocks repeated unconfirmed attempts after five tries, and moves validated requests into administrator review instead of activating them immediately.
- 3 - I modified `routers/web/admin/users.go`, added `routers/web/admin/account_request.go`, updated `routers/web/web.go`, and updated `templates/admin/user/edit.tmpl` so administrators can see the account request status for a user and explicitly activate, reject, or unblock requests from the admin user edit page.
- 4 - I modified `services/mailer/mail_user.go`, added the new account request mail templates, updated `options/locale/locale_en-US.json`, and modified `services/user/user.go` with `services/cron/tasks_extended.go` so the workflow now sends dedicated validation, approval, and rejection emails, preserves rejected or blocked accounts from inactive-user cleanup, and automatically deletes only expired requests that never completed email validation.
11 - [2026-04-16 23:18:45] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Fixed - [account-requests] [locale] [en] Added the missing admin dashboard translation entries for the expired account request cleanup cron task.
- 1 - I modified `options/locale/locale_en-US.json` to add `admin.dashboard.delete_expired_account_requests` so the new cron task can be rendered correctly in the admin dashboard task list.
- 2 - I added `admin.dashboard.delete_expired_account_requests.started` alongside it so the matching task start message is also available and the cron task follows the same translation pattern as the existing dashboard tasks.
- 3 - I verified the locale file remains valid JSON after the change.
12 - [2026-04-17 00:05:29] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Fixed - [account-requests] [mailer] [signup] Hardened the account request validation email flow so manual approval registrations do not silently skip or hide validation mail failures.
- 1 - I modified `routers/web/auth/auth.go` so the `RegisterManualConfirm` path now runs before the generic activation shortcut for normal self-registrations, while still preserving the first-user bootstrap exception.
- 2 - I modified `services/mailer/mail_user.go` so account request validation, approval, and rejection emails now return explicit errors when their templates cannot be rendered instead of failing silently.
- 3 - I modified `routers/web/auth/account_request.go` and `routers/web/admin/account_request.go` so resend and unblock flows now surface validation-email rendering failures immediately, while approval and rejection actions log mail errors without rolling back the already completed admin decision.
- 4 - I verified the updated flow builds cleanly after formatting with compile-only Go tests on the touched packages.
13 - [2026-04-17 00:53:04] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Fixed - [account-requests] [mailer] Reworked the first-user bootstrap path so manual confirmation sends the validation email instead of bypassing the new account request flow.
- 1 - I modified `routers/web/auth/auth.go` so the automatic first-user admin bootstrap now only bypasses email handling when manual confirmation is disabled, while manual-confirm registrations still go through the validation email path.
- 2 - I modified `routers/web/auth/account_request.go` so when the validated account is the only user in the instance, the system activates it directly and grants admin rights immediately instead of sending it into an impossible admin-review deadlock.
- 3 - I preserved the normal staged workflow for all non-bootstrap registrations, so other users still go from email validation to pending admin review as before.
- 4 - I formatted the code and verified the touched packages with compile-only Go tests after the bootstrap flow change.
14 - [2026-04-17 01:14:35] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Added - [account-requests] [admin-users] [mailer] [locale] [en] Added an admin-side validation email send indicator with success or failure icon and attempt timestamp.
- 1 - I modified `models/user/account_request.go` to persist the last validation email attempt status and timestamp for each account request.
- 2 - I modified `routers/web/auth/auth.go`, `routers/web/auth/account_request.go`, and `routers/web/admin/account_request.go` so initial send, resend, and unblock flows now record whether the validation email send function returned success or error.
- 3 - I modified `routers/web/admin/account_request.go` and `templates/admin/user/edit.tmpl` so the account request panel in the admin user edit page now shows a `✔` or `❌` together with the last validation email attempt timestamp.
- 4 - I updated `options/locale/locale_en-US.json`, validated the JSON file, formatted the code, and verified the touched packages with compile-only Go tests.
15 - [2026-04-17 06:26:17] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Modified - [account-requests] [mailer] [ui] [signup] Extended the validation email attempt indicator so it is visible in the user-facing registration flow as well as in the admin account request panel.
- 1 - I modified `routers/web/auth/account_request.go` and `routers/web/auth/auth.go` so the last validation email attempt status and timestamp are loaded into the user-facing signup retry and activation prompt pages.
- 2 - I modified `templates/user/auth/signup_inner.tmpl` so the `✔` or `❌` indicator and timestamp now appear next to the pending request message and beside the `Resend` button area.
- 3 - I modified `templates/user/auth/activate_prompt.tmpl` so the same indicator and timestamp now appear after the initial validation email attempt triggered by account creation.
- 4 - I adjusted `templates/admin/user/edit.tmpl` so the admin panel also shows the indicator when there is mail-attempt data even if the current account request status line is otherwise absent.
16 - [2026-04-17 07:05:39] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Fixed - [account-requests] [mailer] Switched the account request validation email to a real synchronous send path and added logging for silent mail queue enqueue failures.
- 1 - I modified `services/mailer/mail_user.go` so `SendAccountRequestValidationMail` now uses a synchronous sender path instead of only enqueueing the message asynchronously.
- 2 - I modified `services/mailer/mailer.go` to add `SendImmediately`, which uses the initialized configured sender directly and returns the real SMTP or sendmail error back to the caller.
- 3 - I modified `services/mailer/mailer.go` so `SendAsync` now logs queue initialization and enqueue failures instead of silently discarding them.
- 4 - This makes the new-user validation mail behave much closer to `SendTestMail`, which was already using direct sending and was one likely reason test emails succeeded while queued validation emails still appeared to disappear.
17 - [2026-04-17 08:20:46] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Fixed - [auth] [mailer] Switched the remaining user-facing activation emails to synchronous delivery and stopped showing success when the actual send fails.
- 1 - I modified `services/mailer/mail_user.go` so `SendActivateAccountMail` and `SendActivateEmailMail` now return real errors and use direct synchronous sending instead of only queueing the message.
- 2 - I modified `services/mailer/mail_user.go` so account request approval and rejection emails sent to the user now use the same synchronous delivery path for consistent behavior.
- 3 - I modified `routers/web/auth/auth.go` and `routers/web/user/setting/account.go` so signup and email-confirmation flows stop reporting success when the mail send to the user fails.
- 4 - I modified `routers/web/admin/users.go` so administrator-triggered account activation now logs and warns when the activation email to the user could not be sent.
18 - [2026-04-17 18:54:53] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Modified - [auth] [account-requests] [signup] [locale] [en] Refined the account request resend UX so pending users can retry from both activation and signup pages without losing their entered registration data.
- 1 - I modified `templates/user/auth/activate_prompt.tmpl` so the activation page now shows a separate `Did not receive the email?` prompt, a standalone `Resend` button under the mail status indicator, and a Spam/Junk reminder.
- 2 - I modified `templates/user/auth/signup_inner.tmpl` so the pending-registration panel now uses plain prompt text plus a dedicated `Resend` button instead of the combined button label, while also preserving the signup form values through the resend action.
- 3 - I modified `models/user/account_request.go` and `routers/web/auth/account_request.go` so account request validation emails now track up to five resend actions and automatically hide the resend button after that limit is reached.
- 4 - I modified `routers/web/auth/auth.go` and `options/locale/locale_en-US.json` so the activation prompt receives the same resend controls immediately after registration and the new texts are available consistently across both user-facing flows.
19 - [2026-04-17 22:10:39] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Fixed - [auth] [account-requests] [mailer] [signup] Prevented invalid signup email input from triggering an internal server error in the account request pre-check flow.
- 1 - I modified `models/user/account_request.go` so `GetUserByAnyEmail` now trims and validates the email address before querying, reusing the normal email validation behavior instead of treating malformed input like a server-side lookup problem.
- 2 - I modified `routers/web/auth/account_request.go` so the signup pre-check now treats invalid or unsupported email formats as normal invalid input and lets the standard registration validation flow handle the user-facing error message.
- 3 - I modified `routers/web/auth/account_request.go` so the resend endpoint also treats malformed email input as unavailable instead of escalating it into a 500 error.
20 - [2026-04-17 23:13:17] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Fixed - [mailer] [signup] [locale] [en] Rolled back newly created self-registration accounts when the initial confirmation email cannot actually be sent.
- 1 - I modified `routers/web/auth/auth.go` so `createAndHandleCreatedUser` now passes the template and form context into the post-create flow, allowing failed registration emails to return a normal form error instead of a 500 page.
- 2 - I modified `routers/web/auth/auth.go` so the initial account-request validation mail and the initial standard activation mail both delete the newly created user if sending fails, preventing orphaned accounts from being left in the database.
- 3 - I added a dedicated `auth.confirmation_mail_failed` user-facing message in `options/locale/locale_en-US.json` so registration now tells the user that the account was not created because the confirmation email could not be sent.
- 4 - I preserved the existing resend behavior for already created inactive users, so the rollback applies only to the first mail send during new self-registration.
21 - [2026-04-26 22:55:56] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Fixed - [scripts] [smart-build] Updated the smart build script for PNPM 10 and the repository frontend build flow.
- 1 - I modified `smart-build.sh` to remove the unsupported `--ignore-engines` PNPM option from dependency installation.
- 2 - I changed the frontend rebuild step to call `make frontend`, matching the Gitea Makefile target instead of calling a missing `pnpm run build` script.
- 3 - I fixed the architecture menu echo line so `Initialization checks` is no longer appended as stray shell text.
22 - [2026-04-26 23:01:28] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Fixed - [scripts] [smart-build] Made the smart build script find the local Go toolchain before running backend builds.
- 1 - I modified `smart-build.sh` to prepend `/usr/local/go/bin` to `PATH` when the local Go binary exists.
- 2 - I added an early Go availability check so the script stops with a clear message before invoking `make build` if Go is not installed or visible.
- 3 - I added explicit failure handling for dependency installation and frontend asset builds so the script does not continue after a failed prerequisite step.
23 - [2026-04-26 23:20:08] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Modified - [scripts] [smart-build] [bindata] Added a smart build menu option for SQLite-enabled bindata builds.
- 1 - I modified `smart-build.sh` to add a build-tag selection menu with the existing `bindata` build and a new `bindata sqlite sqlite_unlock_notify` option.
- 2 - I changed the backend build command to use the selected tag set instead of always passing `TAGS="bindata"`.
- 3 - I made SQLite builds enable CGO and write artifacts with a `-sqlite` suffix so they are distinguishable from default bindata builds.
24 - [2026-04-27 00:18:15] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Fixed - [account-requests] [auth] Made account request validation links robust after account data changes.
- 1 - I modified `models/user/account_request.go` so account request validation codes can be stored as hashes and later accepted as a fallback when the stateless code can no longer be recalculated from current user data.
- 2 - I modified the registration, resend, and admin unblock flows to generate one validation code, send that exact code by email, and store its hash only after the email send succeeds.
- 3 - I cleared stored validation-code hashes when account requests are reset, validated, or approved so old validation links cannot keep working after the request leaves email validation.
- 4 - I added focused tests for account request code verification and `/user/activate` handling, including the case where user data changes after the validation email is sent.
25 - [2026-04-27 00:49:34] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Fixed - [account-requests] [signup] [auth] Corrected pending account request detection for validation links and repeated registration attempts.
- 1 - I modified account request status detection so inactive users with validation markers are treated as pending email validation even if `account_request.status` is missing.
- 2 - I added a dedicated account-request time-limit code purpose while keeping compatibility with older account-request links, preventing normal activation links from being intercepted by the account request path.
- 3 - I moved the pending account request pre-check before generic signup form errors so repeated registration attempts show the pending-request message and resend option instead of `The username is already taken`.
- 4 - I updated the pending signup message to include the email address that received the validation email and added focused tests for missing-status validation, classic activation separation, and repeated registration.
26 - [2026-04-27 01:10:03] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Fixed - [account-requests] Restored the admin account request review flow link to the page with approval controls.
- 1 - I modified `services/mailer/mail_user.go` so new account request notification emails now link directly to `/-/admin/users/{id}/edit`, where the `Activate Request` and `Reject` controls are rendered.
- 2 - I added a focused mailer test to ensure future account request notifications keep pointing to the admin edit page instead of the read-only user view page.
27 - [2026-04-27 01:47:34] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Modified - [admin-users] [account-deletion] Hid admin-side account deletion controls for the last active administrator.
- 1 - I modified `routers/web/admin/users.go` so the admin user edit page receives `IsLastAdminUser` for the edited user.
- 2 - I modified `templates/admin/user/edit.tmpl` so `Delete User Account` is replaced by the existing last-admin warning when the edited user is the only active admin.
- 3 - I hid the admin delete confirmation modal for the last-admin case while preserving the backend `DeleteUser` last-admin guard as the final protection.
28 - [2026-04-27 02:06:06] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Modified - [admin-users] [account-deletion] Kept last-admin account deletion actions visible but disabled.
- 1 - I modified `templates/admin/user/edit.tmpl` so `Delete User Account` remains visible as a disabled button for the last active admin while showing the existing last-admin warning.
- 2 - I modified `templates/user/settings/account.tmpl` so the self-delete confirmation button remains visible as disabled for the last active admin while showing the same warning.
- 3 - I kept delete confirmation modals unavailable for the disabled last-admin actions so blocked actions cannot be submitted from the UI.
29 - [2026-04-27 09:12:11] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Modified - [admin-users] Adjusted last-admin delete warning placement and spacing.
- 1 - I modified `templates/admin/user/edit.tmpl` so the last-admin warning appears above the disabled `Delete User Account` button with vertical spacing.
- 2 - I modified `templates/user/settings/account.tmpl` so the disabled self-delete confirmation button has spacing below the warning message.
30 - [2026-04-27 09:28:16] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Modified - [admin-users] [ui] Restored admin edit action button alignment while keeping the last-admin warning above them.
- 1 - I modified `templates/admin/user/edit.tmpl` so the last-admin warning appears above the action button row.
- 2 - I kept `Update Profile` and the disabled `Delete User Account` button in the same button row and original order.
31 - [2026-04-27 10:07:15] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Modified - [account-requests] Adjusted account request resend button sizing and delivery-state feedback.
- 1 - I modified the pending signup and activation prompt templates so the resend button is smaller, blue by default, and spaced away from the spam-folder hint.
- 2 - I added resend result state rendering so successful sends turn the button green for five seconds and failed sends keep it red.
- 3 - I changed the resend handler to re-render the current account-request page with a failed send message instead of showing a server-error page when email delivery fails.
32 - [2026-04-27 14:41:33] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Added - [scripts] [build-env] Added a build environment configuration script.
- 1 - I added `configure.sh` to install and verify the system packages, Go version, Node version, pnpm version, and frontend dependencies required by this Gitea tree.
- 2 - I made the script read the required Go, Node, and pnpm versions from `go.mod` and `package.json`, while still allowing environment overrides.
- 3 - I added an optional `--with-cross-cgo` mode that installs/configures the heavier cross-CGO toolchains needed for SQLite builds targeting linux/armv7 and windows/amd64.
33 - [2026-04-27 14:51:16] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Modified - [scripts] [build-env] Added an interactive run menu to the build environment configuration script.
- 1 - I modified `configure.sh` so running it without arguments in an interactive terminal shows a description of what the script installs and verifies.
- 2 - I added a run menu with Normal, With cross cgo, Verify only, and Quit options.
- 3 - I added a `--menu` flag so the same interactive menu can be requested explicitly while keeping the existing command-line options for automated runs.
34 - [2026-04-27 14:59:01] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Modified - [scripts] [build-env] Made interactive environment verification report missing requirements without failing the menu run.
- 1 - I modified `configure.sh` so the interactive `Verify only` menu option lists all detected missing commands and configuration issues instead of stopping at the first missing requirement.
- 2 - I kept the direct `./configure.sh --verify-only` mode strict for automated checks, returning a failure when requirements are missing.
- 3 - I adjusted the final interactive verification message so it recommends rerunning the menu with Normal or With cross cgo instead of suggesting a build when requirements are still missing.
35 - [2026-04-27 15:20:01] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Modified - [scripts] [build-env] Translated the build environment configuration script text to English.
- 1 - I modified `configure.sh` so the interactive description is written in English.
- 2 - I translated the interactive menu option descriptions to English while keeping the existing script behavior unchanged.
36 - [2026-04-27 19:28:55] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Modified - [mailer] [mailer-ui] Moved test email feedback inline and aligned mail action button states.
- 1 - I modified `routers/web/admin/config.go` so the test email result redirects back to the config page with local test-mail state instead of using the global flash alert.
- 2 - I modified `templates/admin/config.tmpl` so the test email result appears beside the `Send` button, with the button using primary, green, or red state colors.
- 3 - I changed the account request `Resend` button default state from `blue` to `primary` so it uses the same visible blue styling as the rest of the Gitea UI.
37 - [2026-04-27 19:56:31] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Fixed - [mailer] [mailer-ui] [scripts] [bindata] Forced mail action button colors and refreshed local template bindata.
- 1 - I modified the admin test mail and account request resend templates so their default, success, and failure colors are set directly with Gitea theme variables.
- 2 - I updated the success timeout scripts to restore the direct primary-color styling after five seconds.
- 3 - I regenerated the local ignored `modules/templates/bindata.dat` file so local bindata builds can include the updated templates.
38 - [2026-04-27 20:05:18] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Modified - [scripts] [smart-build] [bindata] Added bindata freshness checks to the smart build script.
- 1 - I modified `smart-build.sh` so bindata builds check the generated templates, options, public, and migration schema bindata files before compilation.
- 2 - I made the script regenerate any missing or stale bindata file with `go generate -tags bindata` before running `make build`.
- 3 - I kept the regeneration step neutral from cross-build environment variables by clearing `GOOS`, `GOARCH`, `CGO_ENABLED`, and `CC` for the go generate command.
39 - [2026-04-27 20:35:07] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Fixed - [mailer] [mailer-ui] [admin-config] [ui] [sticky-layout] Preserved scroll position after sending a test email from the admin config page.
- 1 - I modified `templates/admin/config.tmpl` so the test email form records the current scroll position before submit.
- 2 - I modified `routers/web/admin/config.go` so the test email redirect carries the saved scroll position and returns to the local test-email anchor.
- 3 - I regenerated the local ignored `modules/templates/bindata.dat` file so bindata builds can include the scroll-preserving template update.
40 - [2026-04-27 21:03:25] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Fixed - [mailer] [mailer-ui] [admin-config] [ui] Removed page reload and scroll movement from the admin test email action.
- 1 - I modified `templates/admin/config.tmpl` so the `Send Testing Email` form submits through `fetch` and updates the inline message without changing the page URL or scroll position.
- 2 - I modified `routers/web/admin/config.go` so inline test email requests return JSON state and message data instead of redirecting.
- 3 - I regenerated the local ignored `modules/templates/bindata.dat` file so bindata builds can include the no-jump test email behavior.
41 - [2026-04-27 21:14:20] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Modified - [mailer] [mailer-ui] [admin-config] Shortened admin test email delivery error messages.
- 1 - I modified `routers/web/admin/config.go` so `Send Testing Email` displays a concise SMTP failure reason instead of the full command chain.
- 2 - I added normalization for common mail errors such as user unknown, mailbox unavailable, relay access denied, and authentication failure.
- 3 - I added a focused unit test for the short test mail error formatter.
42 - [2026-04-27 21:47:26] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Added - [admin-users] [account-deletion] Added an admin user-list delete account action.
- 1 - I modified `templates/admin/user/list.tmpl` so each user row now shows a red trash icon beside the existing User Details and Edit actions.
- 2 - I added a shared delete-account confirmation modal on the user management list, including the existing purge option and delete-account warning text.
- 3 - I regenerated the local ignored `modules/templates/bindata.dat` file so bindata builds can include the new list action.
43 - [2026-04-27 22:17:13] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Modified - [admin-users] Matched the admin user-list delete action to the edit-page delete state.
- 1 - I modified `routers/web/explore/user.go` so user search pages can receive optional per-user extra data before rendering.
- 2 - I modified `routers/web/admin/users.go` so the admin user list marks rows where the user is the last active administrator using the same condition as the edit page.
- 3 - I modified `templates/admin/user/list.tmpl` so the trash icon is disabled with the existing last-admin warning tooltip whenever the edit-page `Delete User Account` button would be disabled.
44 - [2026-04-28 09:12:49] - v.1.27.0-dev-43-gb2b024d0b6 - Type: Fixed - [auth] [account-requests] Blocked inactive account-request users from getting a signed-in session.
- 1 - I modified the password sign-in flow so inactive account-request users are stopped before session, 2FA, or remember-cookie creation and are shown the activation prompt instead.
- 2 - I added account-request login prompts for pending email validation, pending admin review, rejected, and blocked states, while keeping the resend button available only for pending email validation.
- 3 - I modified existing inactive signed sessions on web pages to be signed out before rendering the activation/account-request prompt so the account menu and Sign Out action are not shown.
- 4 - I added targeted auth tests for pending email validation and pending admin review login attempts, including username and email login for the validation case.
- 5 - I regenerated the local ignored `modules/options/bindata.dat` file so bindata builds can include the new login prompt locale string.
45 - [2026-04-28 16:01:28] - v1.27.0-dev-47-gf21b6b7a3b - Type: Modified - [auth] [recovery] Added password confirmation to account recovery.
- 1 - I modified `templates/user/auth/reset_passwd.tmpl` so the account recovery reset form includes a required `Confirm Password` field.
- 2 - I modified `routers/web/auth/password.go` so reset submissions reject mismatched passwords before two-factor checks or password updates.
- 3 - I added a focused auth test for mismatched recovery password confirmation and regenerated the local ignored `modules/templates/bindata.dat` file for bindata builds.
46 - [2026-04-28 19:05:06] - v1.27.0-dev-48-g25a1d84c2e - Type: Fixed - [auth] [recovery] Used the reset-password lifetime for account recovery codes.
- 1 - I modified `models/user/user.go` so reset-password time-limit codes are generated and verified with `RESET_PASSWD_CODE_LIVE_MINUTES` instead of `ACTIVE_CODE_LIVE_MINUTES`.
- 2 - I kept activation, email activation, and account-request time-limit codes on the existing active-code lifetime.
- 3 - I added a focused user-model test that proves reset-password codes remain valid when only `RESET_PASSWD_CODE_LIVE_MINUTES` allows them.
47 - [2026-04-28 20:31:34] - v1.27.0-dev-48-g25a1d84c2e - Type: Added - [admin-invite] [admin-created-user] [signup] Added admin-created account invitation flow when registration is disabled.
- 1 - I modified admin user creation so `DISABLE_REGISTRATION = true` creates inactive, sign-in-prohibited accounts and checks `Send User Registration Notification` by default when mail is configured.
- 2 - I added a 24-hour admin invitation token and email template that lets the invited user accept the account, activate the email, and clear `Disable Sign-In`.
- 3 - I added targeted tests for invitation token lifetime, invitation acceptance, and disabled-registration admin account creation defaults, then regenerated local ignored template and options bindata.
48 - [2026-04-28 21:56:08] - v1.27.0-dev-48-g25a1d84c2e - Type: Modified - [scripts] [smart-build] Added smart-build load profile options.
- 1 - I modified `smart-build.sh` so it asks for a build load profile before dependency checks, frontend build, bindata generation, and Go compilation.
- 2 - I added Moderate and Low Resource profiles that set `GOMAXPROCS`, `MAKEFLAGS=-j1`, and a conservative Node memory limit to reduce CPU and RAM pressure.
- 3 - I kept the Normal profile available for the existing unrestricted build behavior.
49 - [2026-04-28 23:00:25] - v1.27.0-dev-49-g20405fe5e7 - Type: Added - [admin-invite] Notified inviting admins when admin-created invitations are accepted.
- 1 - I stored the creator admin ID on disabled-registration admin-created invitation accounts so the invitation acceptance flow knows who to notify.
- 2 - I added an invitation-accepted email template and mailer function that sends the accepting user's details back to the admin who created the account.
- 3 - I updated targeted admin/auth tests and regenerated local ignored template and options bindata for the new email template and locale strings.
50 - [2026-04-28 23:52:04] - v1.27.0-dev-50-g8147f7a798 - Type: Modified - [admin-created-user] [admin-users] [badges] Added creator-admin badges to the admin users list.
- 1 - I modified the admin user list data loader so users created through the disabled-registration invitation flow include the admin creator name.
- 2 - I modified `templates/admin/user/list.tmpl` so the Created column shows a `by <admin>` mini badge next to the creation date when creator data exists.
- 3 - I added a focused admin list test for the creator-admin mapping and regenerated local ignored template bindata.
51 - [2026-04-29 01:55:04] - v1.27.0-dev-51-gcfd7cfa1dc - Type: Fixed - [admin-invite] [admin-created-user] [badges] Kept creator-admin badges permanently attached to invited accounts.
- 1 - I modified the admin invitation acceptance notification flow so it no longer deletes the stored creator-admin ID.
- 2 - I updated the invitation acceptance test to assert the creator-admin marker remains after the user accepts the invitation.
52 - [2026-04-29 02:04:41] - v1.27.0-dev-52-gcd96c721e0 - Type: Modified - [admin-created-user] [badges] [mailer] Added persistent admin email tooltip to creator badges.
- 1 - I modified admin-created invitation account storage so it permanently saves the creator admin ID, username, and email address.
- 2 - I modified the admin users list creator badge so it shows `by <admin>` and exposes the stored admin email as a hover tooltip.
- 3 - I updated the focused admin list tests to prove the badge data still renders from stored name/email even without looking up the admin account, then regenerated local ignored template bindata.
53 - [2026-04-29 02:30:55] - v1.27.0-dev-52-gcd96c721e0 - Type: Modified - [auth] [admin-created-user] [badges] Added admin activation badges and first-admin GOD badge.
- 1 - I modified the admin users list so the Activated column can show a `by <admin>` badge with the stored admin email as a hover tooltip.
- 2 - I stored admin activation ID, username, and email address when account requests are approved or inactive users are manually activated by an admin.
- 3 - I added the special `by GOD` Created-column badge for the first admin account, updated focused admin list tests, and regenerated local ignored template bindata.
54 - [2026-04-29 08:25:36] - v1.27.0-dev-53-ga3e09bb819 - Type: Fixed - [admin-users] [badges] Prevented empty `by` badges in the admin users list.
- 1 - I changed the admin users list badge maps to use pointer values so missing entries render as empty instead of truthy zero-value structs.
- 2 - I guarded the Created and Activated badge rendering so badges only appear when a display name exists.
- 3 - I reran the focused admin badge tests and regenerated local ignored template bindata.
55 - [2026-04-29 09:02:42] - v1.27.0-dev-53-ga3e09bb819 - Type: Modified - [account-requests] [admin-users] [ui] Moved account request review controls to the top of the admin user edit panel.
- 1 - I moved the account request status message to the top of the admin user edit segment, immediately under the panel header.
- 2 - I moved the Activate/Reject/Unblock request controls above the profile edit form so admins can review pending accounts without scrolling down.
- 3 - I regenerated local ignored template bindata for the updated admin user edit template.
56 - [2026-04-29 09:32:09] - v1.27.0-dev-54-gc7c7af77a1 - Type: Modified - [admin-users] Defaulted admin user purge checkboxes to enabled.
- 1 - I set the Purge User checkbox to checked by default in the admin user edit delete modal.
- 2 - I set the Purge User checkbox to checked by default in the admin users list delete modal.
- 3 - I regenerated local ignored template bindata for the updated admin templates.
57 - [2026-04-29 09:53:08] - v1.27.0-dev-55-ga8d9e5e659 - Type: Added - [auth] [admin-users] [account-status] Added Disable Sign-In metadata to the admin users list.
- 1 - I added persistent admin metadata for Disable Sign-In actions, including timestamp, admin ID, admin name, and admin email.
- 2 - I added a Disable Sign-In column to the admin users list that displays the block date and `by <admin>` badge with email tooltip.
- 3 - I stored the same metadata when admin-created invitation accounts start disabled, when an admin disables sign-in from the edit form, and when an account request is rejected.
58 - [2026-04-29 10:09:41] - v1.27.0-dev-55-ga8d9e5e659 - Type: Modified - [auth] [admin-users] [account-status] Added inactive marker to the Disable Sign-In admin users column.
- 1 - I changed the Disable Sign-In column so users without sign-in disabled show the same `octicon-x` marker style as the other status columns.
- 2 - I kept the block date and `by <admin>` badge for users that do have Disable Sign-In metadata.
- 3 - I regenerated local ignored template bindata for the updated admin users list template.
59 - [2026-04-29 14:49:39] - v1.27.0-dev-56-g1dcd81b420 - Type: Added - [admin-users] [account-status] [mailer] Added admin status-change reasons and user email notifications.
- 1 - I added reason fields under the admin edit checkboxes for account activation, Disable Sign-In, and restricted status.
- 2 - I require a reason when an admin newly deactivates an account, enables Disable Sign-In, or enables restricted mode, then email the user with the action, admin name, and reason.
- 3 - I added the status-change email template, locale strings, regenerated local ignored template/options bindata, and reran the focused admin tests.
60 - [2026-04-29 19:01:39] - v1.27.0-dev-57-g210955465e - Type: Fixed - [auth] [account-status] [mailer] Corrected admin status reason behavior and reactivation emails.
- 1 - I changed the admin edit form so reason fields belong to the existing checkboxes and only appear for the restrictive state of each checkbox.
- 2 - I persisted the deactivation, Disable Sign-In, and restricted reasons in user settings so later administrators can see the saved reason.
- 3 - I changed status-change emails to describe the actual account effect, added notifications when restrictions are lifted, and stopped sending the old activation email on admin reactivation.
61 - [2026-04-29 19:56:22] - v1.27.0-dev-59-gb3204f3db6 - Type: Added - [admin-users] [badges] Added restricted-admin badges and reason actor badges.
- 1 - I added persistent admin metadata for Restricted actions, including timestamp, admin ID, admin name, and admin email.
- 2 - I changed the admin users list Restricted column so newly restricted users show the restriction date and `by <admin>` badge with email tooltip.
- 3 - I added `by <admin>` badges next to the saved Reason labels in the admin user edit panel for deactivation, Disable Sign-In, and Restricted reasons.
62 - [2026-04-29 21:00:30] - v1.27.0-dev-60-g396b15372d - Type: Added - [admin-users] [badges] Added Is Administrator reason and admin-grant badges.
- 1 - I added persistent metadata for granting administrator privileges, including timestamp, admin ID, admin name, admin email, and reason.
- 2 - I changed the admin users list so administrator accounts with grant metadata show an `Admin by <admin>` badge with email tooltip.
- 3 - I added the Is Administrator reason field, reason actor badge, grant/revoke email notifications, regenerated local ignored bindata, and added focused admin grant tests.
63 - [2026-04-29 21:30:55] - v1.27.0-dev-60-g396b15372d - Type: Fixed - [admin-users] Made Is Administrator reasons apply only when admin rights are revoked.
- 1 - I changed the Is Administrator reason field so it appears only when the checkbox is unchecked.
- 2 - I stopped requiring or sending a reason when administrator privileges are granted and changed that email to a congratulatory promotion message.
- 3 - I kept the reason on administrator privilege removal, regenerated template/options bindata, and reran the focused admin grant tests.
64 - [2026-04-29 22:03:18] - v1.27.0-dev-61-g067a09c2ac - Type: Fixed - [admin-users] Disabled critical self-edit account state checkboxes.
- 1 - I disabled User Account Is Activated and Is Restricted when an administrator edits their own account, matching the existing self-edit protection for Disable Sign-In.
- 2 - I hardened the admin user update handler so manually submitted self-edit forms cannot change the current admin's active, restricted, or prohibit-login state.
- 3 - I regenerated local ignored template bindata and verified the admin package compilation with reduced build pressure.
65 - [2026-04-29 22:37:56] - v1.27.0-dev-62-g3afb4e8afa - Type: Added - [auth] [scripts] Added Codex ChatGPT login helper script.
- 1 - I added `.codex_gpt_login`, an interactive helper for completing the local Codex ChatGPT auth callback in code-server environments.
- 2 - The script accepts either a raw received code or a full URL/query containing `code=...`, calls the local callback endpoint, extracts `id_token`, and completes the `/success` request.
- 3 - I made the script executable and verified its shell syntax with `bash -n`.
66 - [2026-04-29 22:55:08] - v1.27.0-dev-62-g3afb4e8afa - Type: Modified - [admin-users] [badges] Added admin actor badge beside the Is Administrator option.
- 1 - I updated the admin user edit panel so the Is Administrator checkbox label shows `by <admin>` when administrator grant metadata exists.
- 2 - I reused the stored admin email as the badge hover tooltip and regenerated local ignored template bindata.
67 - [2026-04-30 00:30:40] - v1.27.0-dev-63-g4aacf3bd20 - Type: Fixed - [admin-users] Hid Is Administrator reason unless admin rights were revoked.
- 1 - I changed the Is Administrator reason field so normal non-admin users do not see it just because the checkbox is unchecked.
- 2 - The reason field now appears only when a saved admin-revocation reason exists or when an existing administrator is being unchecked during the current edit.
- 3 - I regenerated local ignored template bindata and verified whitespace with `git diff --check`.
68 - [2026-04-30 01:44:17] - v1.27.0-dev-64-gcff1b46f50 - Type: Added - [admin-users] [super-admin] Added persistent super administrator protection.
- 1 - I added `SUPER_ADMIN_ENABLED` and `ADMIN_MANAGEMENT_POLICY` configuration options for administrator permission management.
- 2 - I stored the super administrator role and grant/revoke metadata in persistent user settings, with automatic `by GOD` bootstrap for the first active admin.
- 3 - I protected administrator and super administrator changes so regular admins cannot alter existing admins unless the selected policy allows a regular-user promotion.
- 4 - I added super administrator badges, reason tracking, and status-change emails, then regenerated template and options bindata.
69 - [2026-04-30 02:20:26] - v1.27.0-dev-64-gcff1b46f50 - Type: Fixed - [admin-users] [super-admin] Enabled super administrator bootstrap by default.
- 1 - I changed `SUPER_ADMIN_ENABLED` to default to `true` so existing installations without the new app.ini key bootstrap the first active administrator automatically.
- 2 - I updated the app.ini example to document the enabled default and kept `SUPER_ADMIN_ENABLED = false` available as the explicit opt-out.
- 3 - I made the super administrator list badge fall back to `by GOD` for the bootstrapped first administrator and regenerated options bindata.
70 - [2026-04-30 04:08:23] - v1.27.0-dev-66-g35b9fa65d3 - Type: Fixed - [admin-users] [super-admin] Blocked regular administrators from editing super administrator accounts.
- 1 - I modified `routers/web/admin/users.go` so non-super-admins are redirected away from super-admin edit actions, including profile edits and avatar changes.
- 2 - I modified `routers/api/v1/admin/user.go` so the admin user edit API now returns forbidden when a regular admin targets a super admin.
- 3 - I modified `templates/admin/user/list.tmpl` and `templates/admin/user/view.tmpl` so edit actions are hidden for super-admin accounts when the acting admin is not also a super admin.
- 4 - I added `TestAdminCannotEditSuperAdminUser` in `tests/integration/admin_user_test.go` to cover the denied web-edit flow.
71 - [2026-04-30 04:19:14] - v1.27.0-dev-67-g0fc6f30a30 - Type: Modified - [admin-users] [super-admin] Kept super administrator Edit and Delete controls visible but disabled for regular admins.
- 1 - I modified `templates/admin/user/list.tmpl` so super-admin rows still show the `Edit` and `Delete` icons for regular admins, but as disabled muted controls with the super-admin-required tooltip.
- 2 - I modified `templates/admin/user/view.tmpl` so the `Edit` button remains visible on the super-admin user details page for regular admins, but in a disabled state.
72 - [2026-04-30 04:58:16] - v1.27.0-dev-68-g5da24d2c7b - Type: Modified - [admin-users] [admin-policy] Protected GOD-granted admin accounts and blocked deleting the direct grantor.
- 1 - I added `models/user/admin_grant.go` with helpers to read admin and super-admin grantor metadata, detect `by GOD` bootstrap grants, and check whether a target user is the direct grantor of another admin.
- 2 - I modified `routers/web/admin/users.go` so GOD-granted accounts cannot be edited or deleted through admin actions, and regular admins may delete other admin accounts except their direct grantor and protected super-admin cases.
- 3 - I modified `routers/api/v1/admin/user.go` so the admin API now enforces the same GOD-protection and direct-grantor deletion rule.
- 4 - I added locale messages for the new admin restrictions and added focused integration coverage for deleting another admin versus the direct grantor, plus GOD-protected admin API edits.
73 - [2026-04-30 16:51:42] - v1.27.0-dev-71-g80497e4194 - Type: Modified - [admin-users] Restored normal self-edit access for super admins and disabled only the admin actions that are truly forbidden.
- 1 - I modified `routers/web/admin/users.go` so a GOD-granted or super-admin user can still edit their own ordinary account fields, while forbidden cross-user edits remain blocked and table action states are computed per target user.
- 2 - I modified `routers/api/v1/admin/user.go` so GOD-protection no longer blocks a user from editing their own account through the admin API.
- 3 - I modified `templates/admin/user/list.tmpl`, `templates/admin/user/view.tmpl`, and `templates/admin/user/edit.tmpl` so `Edit` stays enabled for allowed self-edits, while forbidden `Edit` and `Delete` actions are shown disabled with the specific reason tooltip or warning message.
74 - [2026-04-30 20:11:48] - v1.27.0-dev-72-g43161732e3 - Type: Modified - [installer] [locale] [en] Added install-time admin management policy choices with direct-grantor and inherited-grantor enforcement.
- 1 - I modified `modules/setting/admin.go`, `services/forms/user_form.go`, `routers/install/install.go`, `templates/install.tmpl`, and `options/locale/locale_en-US.json` so installation now exposes three administrator-management policies: `super_admin_only`, `grantor_only`, and `grantor_inheritance`, while normalizing the old legacy policy names.
- 2 - I modified `models/user/admin_grant.go` so the code can resolve the effective admin grantor by walking the admin-grant chain until it finds an active administrator who still has sign-in enabled.
- 3 - I modified `routers/web/admin/users.go` so regular admins can edit or delete only the administrator accounts allowed by the selected policy, while keeping super-admin protections, GOD protections, self-edit exceptions, and disabled forbidden actions intact in the admin UI.
- 4 - I modified `routers/api/v1/admin/user.go` so the admin API now applies the same grantor-based restrictions for editing and deleting administrator accounts.
- 5 - I added focused integration coverage in `tests/integration/admin_user_test.go` and `tests/integration/api_admin_test.go` for direct-grantor edits, inherited-grantor edits, and API denial for unrelated admins.
75 - [2026-04-30 20:37:01] - v1.27.0-dev-72-g43161732e3 - Type: Modified - [installer] [app-ini-import] [admin-policy] Updated the example app.ini documentation for the new administrator management policies.
- 1 - I modified `custom/conf/app.example.ini` so the `ADMIN_MANAGEMENT_POLICY` comments now document `super_admin_only`, `grantor_only`, and `grantor_inheritance`, and changed the documented default to `grantor_only`.
76 - [2026-04-30 22:03:50] - v1.27.0-dev-73-g1e13af4d6e - Type: Modified - [admin-users] [super-admin] [installer] [locale] [en] Updated install-page administrator labels to super administrator wording.
- 1 - I modified `options/locale/locale_en-US.json` so the install-page administrator account title, description, and username label now refer to the super administrator role.
- 2 - I renamed the install-page policy label from `Administrator Management Policy` to `Administration Management Policy`.
77 - [2026-04-30 23:05:46] - v1.27.0-dev-75-gd4a1b88385 - Type: Modified - [mailer] [installer] [locale] [en] Added install-page testing email verification using the entered SMTP settings.
- 1 - I modified `routers/install/routes.go`, `routers/install/install.go`, and `templates/install.tmpl` so the install page now has an inline `Send Testing Email` action that posts the current SMTP form values to a dedicated install endpoint.
- 2 - I modified `services/mailer/mail.go` and `routers/web/admin/config.go` so compact test-mail error formatting is shared and install can send a test message with a temporary mailer configuration instead of relying on saved global settings.
- 3 - I modified `options/locale/locale_en-US.json` for the install-page test-mail labels and regenerated template and options bindata after verifying the affected Go packages compile.
78 - [2026-04-30 23:25:10] - v1.27.0-dev-75-gd4a1b88385 - Type: Modified - [mailer] [mailer-ui] [installer] Repositioned install-page Send Testing Email under SMTP Password.
- 1 - I modified `templates/install.tmpl` so the `Send Testing Email` row now appears immediately below the `SMTP Password` field inside `Email Settings`.
- 2 - I kept the existing selectors, inline message area, and button behavior unchanged while preserving the remaining field order.
- 3 - I regenerated template bindata and rechecked the install package compile path after the layout-only change.
79 - [2026-04-30 23:48:41] - v1.27.0-dev-75-gd4a1b88385 - Type: Fixed - [mailer] [mailer-ui] [installer] Aligned install-page Send Testing Email with the standard inline form grid.
- 1 - I modified `templates/install.tmpl` so the `Send Testing Email` input, button, and message now render inside the same `right-content` column used by the other install-page inline fields.
- 2 - I kept the existing selectors and behavior unchanged and only corrected the layout alignment relative to `SMTP Password`.
80 - [2026-05-01 00:36:35] - v1.27.0-dev-75-gd4a1b88385 - Type: Fixed - [mailer] [mailer-ui] [installer] [ui] Matched install-page Send Testing Email row to the target inline layout.
- 1 - I modified `templates/install.tmpl` so the `Send Testing Email` controls now use an inline wrapper with the same 60 percent content width as the standard install-form inputs instead of the block-style `right-content` helper.
- 2 - I kept the existing selectors and behavior unchanged and only corrected the horizontal alignment to match the target SMTP Password row layout.
81 - [2026-05-01 00:56:45] - v1.27.0-dev-75-gd4a1b88385 - Type: Modified - [mailer] [mailer-ui] [installer] [ui] Brightened install-page Send Testing Email status message colors.
- 1 - I modified `templates/install.tmpl` so the inline status message now uses `var(--color-green)` for success and `var(--color-red)` for failure instead of the softer Tailwind utility classes.
- 2 - I kept the existing button behavior unchanged and only adjusted the message text color handling in the install-page JavaScript.
82 - [2026-05-01 13:09:43] - v1.27.0-dev-76-g362d01abbc - Type: Modified - [installer] [signup] [locale] [en] Added install-page Registration Management with coherent mode-driven registration settings.
- 1 - I modified `templates/install.tmpl`, `services/forms/user_form.go`, and `routers/install/install.go` so the install page now exposes a dedicated `Registration Management` section with radio-button registration modes plus dependent local and external sub-options.
- 2 - I mapped the new UI to the existing service settings by deriving `DISABLE_REGISTRATION`, `ALLOW_ONLY_INTERNAL_REGISTRATION`, `ALLOW_ONLY_EXTERNAL_REGISTRATION`, `REGISTER_EMAIL_CONFIRM`, and `REGISTER_MANUAL_CONFIRM` consistently from the selected mode and sub-options.
- 3 - I updated `web_src/js/features/install.ts` and `options/locale/locale_en-US.json` so contradictory options are hidden or disabled in the browser, added the new English labels and descriptions, and regenerated template and options bindata.
83 - [2026-05-01 18:14:40] - v1.27.0-dev-77-g19fb194db6 - Type: Modified - [installer] [locale] [en] Completed install-page admin-managed account modes and aligned locale install sections.
- 1 - I modified `modules/setting/service.go`, `custom/conf/app.example.ini`, `services/forms/user_form.go`, `routers/install/install.go`, `templates/install.tmpl`, and `web_src/js/features/install.ts` so `Registration Management` now includes administrator-managed local versus invitation-based account provisioning, plus a helper for `Enable Email Notifications`.
- 2 - I updated `routers/web/admin/users.go` and `routers/api/v1/admin/user.go` so disabled-registration account creation follows the configured administrator-created account mode, stores creator metadata for admin-created users, and sends either invitation mail or standard registration notification accordingly.
- 3 - I aligned every `options/locale/locale_*.json` install section to the new key set and en-US fallback order, regenerated template and options bindata, and verified the affected install, admin web, and admin API packages.
84 - [2026-05-02 00:16:23] - v1.27.0-dev-78-gad0ab4be60 - Type: Modified - [admin-created-user] [admin-users] [installer] [locale] [en] Moved admin-created account delivery mode selection from install to the admin new-user form.
- 1 - I updated `templates/install.tmpl` and `web_src/js/features/install.ts` to remove the install-page `Administrator-managed accounts only` sub-mode choice so registration mode no longer decides how `/admin/users/new` delivers newly created accounts.
- 2 - I extended `services/forms/admin.go`, `templates/admin/user/new.tmpl`, `web_src/js/features/admin/common.ts`, and `routers/web/admin/users.go` so `/admin/users/new` now offers mutually exclusive `Send User Registration Notification` and `Send User Registration Invitation` checkboxes, defaults the invitation checkbox when mail is available, preserves checkbox state on form re-render, and sends the matching email flow.
- 3 - I adjusted `routers/web/admin/users_test.go`, added the new `admin.users.send_register_invite` locale key across `options/locale/locale_*.json`, regenerated template and options bindata, and re-verified the focused admin user flow.
85 - [2026-05-02 01:52:40] - v1.27.0-dev-79-ga6695a6e73 - Type: Modified - [auth] [mailer] [signup] [locale] [en] Unified classic email-confirmation signup with the resend-based pending validation flow.
- 1 - I updated `routers/web/auth/auth.go` and `routers/web/auth/account_request.go` so classic `REGISTER_EMAIL_CONFIRM` signups now render the same resend-capable activation prompt after account creation, redirect repeated signups with the same unconfirmed email to the resend-capable pending state instead of `The username is already taken`, and show the same resend-capable prompt when an unconfirmed user attempts to sign in.
- 2 - I added classic activation resend state tracking in `models/user/account_request.go`, re-used the existing resend UI data contract for both signup and activation prompts, and extended `/user/sign_up/resend` to handle classic email-confirmation accounts with a five-resend limit.
- 3 - I added focused auth tests in `routers/web/auth/auth_test.go`, aligned all `options/locale/locale_*.json` files with the new confirmation-mail keys, regenerated options bindata, and re-verified the affected auth package.
86 - [2026-05-02 02:20:53] - v1.27.0-dev-80-g4ab8063966 - Type: Modified - [installer] [locale] [en] Added default language selection to the install page initial configuration.
- 1 - I extended `services/forms/user_form.go`, `routers/install/install.go`, and `templates/install.tmpl` so `General Settings` now includes a `Default Language` selector backed by the existing `AllLangs` list and validated against configured locales.
- 2 - I wired install submission to persist the selection by reordering `[i18n] LANGS` so the chosen language becomes the first fallback/default locale, while keeping the remaining languages available.
- 3 - I added focused install tests in `routers/install/routes_test.go`, aligned all `options/locale/locale_*.json` files with the new install language keys, regenerated template and options bindata, and re-verified the install package.
87 - [2026-05-02 02:36:07] - v1.27.0-dev-80-g4ab8063966 - Type: Modified - [mailer] Disabled forbidden email deletion actions in the admin email list.
- 1 - I extended `routers/web/admin/emails.go` so each listed email now carries explicit delete permission state and, for primary addresses, the existing `admin.emails.delete_primary_email_error` reason for the disabled UI.
- 2 - I updated `templates/admin/emails/list.tmpl` so the trash icon remains clickable only for deletable addresses and renders as a muted disabled control with a tooltip when deletion is forbidden, such as for a primary email address.
- 3 - I kept the existing backend deletion guard in place, regenerated template bindata, and re-verified the affected admin package plus whitespace consistency.
88 - [2026-05-02 03:12:25] - v1.27.0-dev-82-gf8f988e85e - Type: Modified - [admin-invite] [installer] [sticky-layout] [locale] [en] Added a dedicated pending-invitation flow for admin-created invite accounts and pinned the install footer.
- 1 - I updated `templates/admin/user/new.tmpl`, `routers/web/admin/users.go`, `routers/api/v1/admin/user.go`, `models/user/account_request.go`, and `services/mailer/mail_user.go` so admin-created invitation accounts remain inactive without forcing `Disable Sign-In`, carry explicit pending-invitation state, and show helper text for the notification versus invitation options.
- 2 - I added the dedicated invitation prompt and resend flow through `templates/user/auth/invite_prompt.tmpl`, `routers/web/auth/auth.go`, `routers/web/auth/account_request.go`, and `routers/web/web.go`, including sign-in redirection for pending invitations, backward-compatible handling for legacy prohibited invite accounts, and resend tracking for invitation emails.
- 3 - I updated `templates/base/footer_content.tmpl`, `web_src/css/install.css`, and all `options/locale/locale_*.json` files so the install footer stays continuously visible on the install page, the new invitation strings are available across locales, template and option bindata were regenerated, and the affected auth/admin/API packages were re-verified.
89 - [2026-05-02 04:05:54] - v1.27.0-dev-83-gf7bc24d4e8 - Type: Modified - [admin-invite] [installer] [ui] Aligned the admin new-user invitation help text with the install-page help layout.
- 1 - I updated `templates/admin/user/new.tmpl` so the `Send User Registration Notification` and `Send User Registration Invitation` rows now use a dedicated right-side content wrapper instead of rendering the help text directly under the checkbox.
- 2 - I extended `web_src/css/admin.css` with scoped layout rules for `.admin-user-mail-option` so the help text sits under the checkbox content in the same visual column style used on the install page, including responsive behavior for narrow screens.
- 3 - I regenerated template bindata after the markup change and re-verified whitespace consistency for the affected files.
90 - [2026-05-02 12:11:50] - v1.27.0-dev-84-gf60b2af5a6 - Type: Modified - [installer] [locale] [en] [ui] [sticky-layout] Added an install-page language hint balloon anchored to the footer language selector.
- 1 - I updated `templates/base/footer_content.tmpl` and `templates/install.tmpl` so the install page now renders a green `Choose a language` hint balloon tied to the footer language selector and dismisses it on the first page click.
- 2 - I extended `web_src/css/install.css` with fixed-position balloon styling and responsive placement above the install footer so the hint remains visible without overlapping the footer controls.
- 3 - I added the new `install.language_balloon` locale key to `options/locale/locale_en-US.json`, aligned all `options/locale/locale_*.json` files to include it, and re-generated the template and options bindata assets.
91 - [2026-05-02 12:28:12] - v1.27.0-dev-84-gf60b2af5a6 - Type: Fixed - [installer] [locale] [ui] [sticky-layout] Delayed the install-page language hint balloon initialization until the footer exists in the DOM.
- 1 - I updated `templates/install.tmpl` so the `Choose a language` balloon now initializes on `DOMContentLoaded` instead of running before the footer language selector has been parsed.
- 2 - I kept the existing dismiss-on-first-click behavior unchanged and only fixed the timing issue that prevented the balloon from appearing at first page load.
- 3 - I regenerated the template bindata assets and re-verified whitespace consistency after the template-only fix.
92 - [2026-05-02 13:31:45] - v1.27.0-dev-85-g4eaa42bccd - Type: Modified - [locale] [en] [ro] Added official bootstrap support for the Romanian locale.
- 1 - I updated `modules/setting/i18n.go` so `ro-RO` is now part of the built-in language list with the display name `Română`.
- 2 - I updated `custom/conf/app.example.ini` so the example `[i18n] LANGS` and `NAMES` lists now include `ro-RO` and `Română`.
- 3 - I added `options/locale/locale_ro-RO.json` as an initial bootstrap locale copied from `locale_en-US.json`, so the Romanian locale can be selected and loaded cleanly before the dedicated translation pass.
93 - [2026-05-02 14:41:58] - v1.27.0-dev-86-g414c77278b - Type: Modified - [locale] [en] [ro] Added a first complete Romanian translation pass for `locale_ro-RO.json`.
- 1 - I translated `options/locale/locale_ro-RO.json` from the current `locale_en-US.json` structure, preserving placeholders and HTML fragments, then applied targeted manual overrides for the install, auth, mail, and admin account-management flows customized in this fork.
- 2 - I normalized key Git and administration terms in Romanian and fixed token-protection artifacts that surfaced during the automated translation pass, including the affected `WebAuthn`, `OpenID`, `CAPTCHA`, `Gitea`, milestone completeness, delete-warning, and GPG warning strings.
- 3 - I regenerated `modules/options/bindata.dat` so the updated Romanian locale is embedded in the build output.
94 - [2026-05-05 02:30:50] - v1.27.0-dev-86-g414c77278b - Type: Modified - [locale] [ro] Refined Romanian UI wording in `locale_ro-RO.json`.
- 1 - I adjusted Romanian phrasing across the translated locale to improve readability and consistency in general UI strings.
- 2 - I normalized terminology for navigation, repository, authentication, and administration labels to better match the existing Gitea interface.
- 3 - I kept placeholders, HTML fragments, and technical tokens intact while polishing the translated text.
95 - [2026-05-06 03:15:10] - v1.27.0-dev-86-g414c77278b - Type: Modified - [locale] [ro] Corrected Romanian wording and grammar in `locale_ro-RO.json`.
- 1 - I fixed a small set of Romanian phrasing and grammar issues identified after the previous translation polish pass.
- 2 - I kept the scope limited to wording corrections without changing the locale structure or translation coverage.
- 3 - I preserved existing placeholders, HTML fragments, and technical tokens while applying the text fixes.
96 - [2026-05-06 00:47:16] - v1.27.0-dev-90-g75a9dbf7d7 - Type: Modified - [org-ui] [ui] Restyled the organization creation panel and added a cancel action.
- 1 - I updated `templates/org/create.tmpl` so `/org/create` now renders inside a settings-style attached header and segment panel instead of the older standalone form block.
- 2 - I kept the existing organization creation fields intact, but changed the action row to a right-aligned button group with a new `Cancel` button beside `Create Organization`.
- 3 - I updated `routers/web/org/org.go` to provide a `CancelLink` back to `/user/settings/organization`, regenerated template bindata, and re-verified the `routers/web/org` package.
97 - [2026-05-06 01:08:23] - v1.27.0-dev-90-g75a9dbf7d7 - Type: Modified - [org-ui] [modal] Converted the organization creation page to a modal-style dialog and preserved the caller page for cancel.
- 1 - I updated `templates/org/create.tmpl` so `/org/create` now renders as a visible `ui small modal` dialog with header, content, and actions matching the visual structure used by the Actions secrets and variables modals.
- 2 - I extended `web_src/css/org.css` with page-scoped layout rules that center the active modal on the standalone page while keeping the styling limited to `page-content.organization.new.org`.
- 3 - I updated `routers/web/org/org.go` so `Cancel` now returns to a safe current-site `redirect_to` target or same-site referrer instead of always forcing `/user/settings/organization`, regenerated template bindata, and re-verified the `routers/web/org` package.
98 - [2026-05-06 02:02:33] - v1.27.0-dev-91-gba0da47957 - Type: Added - [codex-docs] Added persistent Codex project-orientation documents for fast task handoff and recovery.
- 1 - I added `.codex-project-map.md` as a durable project guide that captures the web request flow, authentication architecture, practical extension points, and a restart procedure for new tasks.
- 2 - I modified `.codex-context.md` so it now points explicitly to `.codex-project-map.md` and documents the recommended read order for resuming work after a blocked session.
- 3 - I refreshed the repository-derived version reference in `.codex-context.md` so future history updates can use the current application version format consistently.
99 - [2026-05-06 02:18:58] - v1.27.0-dev-91-gba0da47957 - Type: Modified - [org-ui] [modal] [ui] Reworked organization creation into a real overlay modal on top of the organization settings page and made outside clicks close it.
- 1 - I modified `templates/user/settings/organization.tmpl` so the `New Organization` action now opens the create dialog with the standard `show-modal` flow while keeping the organization settings page visible in the background.
- 2 - I converted `templates/org/create.tmpl` into a reusable modal partial and updated `routers/web/org/org.go` so `/org/create` now renders the same organization settings page with that modal auto-opened, preserving `CancelLink` for close and validation-error flows.
- 3 - I simplified `web_src/css/org.css` to keep only the create-modal helper text styling and removed the previous fake standalone modal layout that replaced the background page.
100 - [2026-05-06 10:13:49] - v1.27.0-dev-91-gba0da47957 - Type: Fixed - [org-ui] [ui] Corrected the organization settings cancel-link build regression.
- 1 - I fixed `routers/web/user/setting/profile.go` so it uses the `ctx.Req.RequestURI` field instead of calling it like a function.
- 2 - This removes the compile error in `code.gitea.io/gitea/routers/web/user/setting` that was blocking the Windows build after the organization-create modal refactor.
101 - [2026-05-06 10:54:10] - v1.27.0-dev-91-gba0da47957 - Type: Modified - [org-ui] [modal] Made the new-organization modal open in place from the UI and reset its default values consistently.
- 1 - I moved the reusable `create-org-modal` inclusion to `templates/base/footer.tmpl` so signed-in users who can create organizations have the modal available on normal pages without navigating away first.
- 2 - I updated the `New Organization` triggers in `templates/base/head_navbar.tmpl`, `templates/user/dashboard/navbar.tmpl`, `templates/admin/org/list.tmpl`, and `templates/user/settings/organization.tmpl` to use `show-modal` with `/org/create` as a non-JavaScript fallback, preserving the current page and scroll position when JavaScript is enabled.
- 3 - I added explicit reset attributes for organization name, `redirect_to`, visibility radios, and the `repo_admin_change_team_access` checkbox so the modal opened from `/user/settings/organization` now uses the same defaults as the one opened from the global create menu.
102 - [2026-05-06 10:55:13] - v1.27.0-dev-91-gba0da47957 - Type: Modified - [org-ui] [modal] Extended the in-place new-organization modal behavior to the dashboard organization list component.
- 1 - I modified `web_src/js/components/DashboardRepoList.vue` so the `New Organization` trigger in the organizations dashboard tab now also uses the shared `show-modal` flow instead of forcing navigation when JavaScript is enabled.
- 2 - I kept `/org/create` as the fallback `href` in the component so the non-JavaScript path remains available.
103 - [2026-05-06 18:03:33] - v1.27.0-dev-91-gba0da47957 - Type: Modified - [locale] [ro] Somes correction Romanian wording and grammar in `locale_ro-RO.json`.
104 - [2026-05-06 18:19:21] - v1.27.0-dev-91-gba0da47957 - Type: Modified - [ui] Fix align new-user check-boxes help text.
105 - [2026-05-06 18:47:44] - v1.27.0-dev-91-gba0da47957 - Type: Modified - [locale] [ro] Some new correction Romanian wording and grammar in `locale_ro-RO.json`.
106 - [2026-05-06 15:54:50] - v1.27.0-dev-96-g7c7357f314 - Type: Modified - [admin-invite] [auth] Reduced the resend button size on the invitation acceptance prompt.
- 1 - I modified `templates/user/auth/invite_prompt.tmpl` so the `Resend` button on `/user/invitation?email=...` now uses the smaller `ui mini button` size instead of `ui tiny button`.
- 2 - I kept the existing inline resend states, colors, and success reset behavior unchanged.
107 - [2026-05-06 18:57:49] - v1.27.0-dev-98-g5f0f52d04f - Type: Fixed - [org-ui] [modal] Prevented the new-organization modal from inheriting unrelated global success flashes from the underlying page.
- 1 - I modified `templates/org/create.tmpl` so the modal now renders only its local error flash instead of the full `base/alert` block.
- 2 - This keeps `/org/create` validation errors visible in the modal while preventing inherited success, info, or warning flash messages from the background page from appearing inside it.
108 - [2026-05-06 21:07:26] - v1.27.0-dev-99-gfc43980a5c - Type: Fixed - [admin-invite] [admin-created-user] [mailer] [locale] Made admin-created user notification and invitation emails use the current page locale.
- 1 - I modified `services/mailer/mail_user.go` to add locale-aware variants for registration-notify and admin-invite emails, while preserving the existing user-language fallback helpers for other call sites.
- 2 - I modified `routers/web/admin/users.go` and `routers/api/v1/admin/user.go` so admin-created account emails now use `ctx.Locale` from the current request instead of always rendering in the new account's empty or default language.
109 - [2026-05-06 22:11:33] - v1.27.0-dev-100-g70ef46362e - Type: Modified - [admin-created-user] [mailer] [locale] [en] [ro] Personalized the admin-created account notification email with the creator name and a direct set-password link.
- 1 - I modified `services/mailer/mail_user.go` so the registration notification email now accepts the admin user, generates a time-limited `reset_password` token URL for the new account, and passes both values into the mail template.
- 2 - I modified `routers/web/admin/users.go` and `routers/api/v1/admin/user.go` so the admin-created account notification now includes `ctx.Doer` when sending the non-invite email variant.
- 3 - I modified `templates/mail/user/auth/register_notify.tmpl`, `options/locale/locale_en-US.json`, and `options/locale/locale_ro-RO.json` so the email explicitly states that the administrator created the account and instructs the recipient to use a personal password-setup link before signing in.
110 - [2026-05-06 22:11:33] - v1.27.0-dev-100-g70ef46362e - Type: Fixed - [admin-created-user] [mailer] Corrected the admin-created account password-setup email link to use the public recovery route.
- 1 - I modified `services/mailer/mail_user.go` so the personalized password-setup link now targets `/user/recover_account?code=...`, which is the actual public route mounted for password reset token handling.
- 2 - This fixes the 404 triggered by the previous `/user/reset_password?code=...` link, because the router exposes `auth.ResetPasswd` on `/user/recover_account` instead.
111 - [2026-05-06 23:43:34] - v1.27.0-dev-102-g146013827c - Type: Modified - [admin-invite] [admin-created-user] Made the admin-created account notification link behave like an invitation by signing the user in through `/user/activate`.
- 1 - I modified `models/user/user.go` to add a dedicated `TimeLimitCodeAdminAccess` purpose that reuses the password-reset lifetime but remains separate from reset-password and invite tokens.
- 2 - I modified `services/mailer/mail_user.go` so the `Send User Registration Notification` email now points to `/user/activate?code=...` with the new admin-access token instead of sending the recipient through the recovery form flow.
- 3 - I modified `routers/web/auth/auth.go` so `auth.Activate` and `auth.ActivatePost` can consume the new token, rotate `Rands`, create the session, refresh locale, update last-login metadata, and then rely on the existing `MustChangePassword` redirect to land the user on `/user/settings/change_password`.
- 4 - I added `TestActivateAdminAccessSignsInAndInvalidatesCode` in `routers/web/auth/auth_test.go` to cover the new direct-access flow and confirm the token is invalidated after first use.
112 - [2026-05-06 23:43:34] - v1.27.0-dev-102-g146013827c - Type: Modified - [auth] [admin-created-user] [mailer] Simplified the admin-created account notification email to show only the personalized activation link.
- 1 - I modified `templates/mail/user/auth/register_notify.tmpl` so the mail no longer shows the generic `/user/login` URL and instead displays the personalized admin-access link directly under the username.
- 2 - I removed the trailing explanatory paragraph below that link to avoid repeating the same password-setup action twice in the same email.
113 - [2026-05-07 01:01:44] - v1.27.0-dev-104-g10495b7cd1 - Type: Modified - [user-settings] [sticky-layout] [appearance] [locale] [en] [ro] Reverted the global fixed-footer behavior and replaced it with a persistent per-user footer preference in `/user/settings/appearance`.
- 1 - I modified `templates/user/settings/appearance.tmpl`, `routers/web/user/setting/profile.go`, and `routers/web/web.go` to add a new footer section with a checkbox that saves whether the footer should stay visible at the bottom of the viewport for the current user.
- 2 - I modified `models/user/setting_options.go`, `routers/common/pagetmpl.go`, `templates/base/head.tmpl`, `modules/web/middleware/cookie.go`, `web_src/css/base.css`, and `web_src/css/home.css` so the preference is stored in `user_settings`, propagated into the page layout, and applied only when the `show-persistent-footer` body class is enabled.
- 3 - I modified `options/locale/locale_en-US.json`, `options/locale/locale_ro-RO.json`, and `models/user/setting_test.go` to add the new UI strings and a focused test covering the new persisted setting key.
114 - [2026-05-07 09:30:56] - v1.27.0-dev-105-gb3a7692ce9 - Type: Modified - [ui] [sticky-layout] Moved the persistent footer outside the page scroll area.
- 1 - I modified `web_src/css/base.css` so pages with `show-persistent-footer` stop scrolling the whole `body` and instead scroll the `.full.height` content container, keeping the footer in its own fixed viewport slot.
- 2 - I modified `web_src/css/home.css` so the persistent footer no longer overlays the page with `position: fixed`, but stays permanently visible as a non-scrolling sibling below the main content area.
115 - [2026-05-07 09:54:43] - v1.27.0-dev-106-g61a9e4bd06 - Type: Modified - [user-settings] [sticky-layout] [locale] [en] [ro] Added the persistent sticky side-menu preference and the finalized sidebar behavior for `/user/settings` and `/-/admin`.
- 1 - I modified `models/user/setting_options.go`, `routers/common/pagetmpl.go`, `templates/base/head.tmpl`, `routers/web/user/setting/profile.go`, `routers/web/web.go`, `templates/user/settings/appearance.tmpl`, `options/locale/locale_en-US.json`, `options/locale/locale_ro-RO.json`, and `models/user/setting_test.go` to add the persisted `ui.sticky_side_menus` preference, expose it to templates as `ShowStickySideMenus`, save it from `/user/settings/appearance`, document it in the UI, and cover it with a focused test.
- 2 - I modified `templates/user/settings/actions_general.tmpl` so `/user/settings/actions/general` passes the expected `pageClass` and participates in the same sticky-sidebar behavior as the other settings subpages.
- 3 - I modified `web_src/css/modules/flexcontainer.css` so, when the preference is enabled, the shared left menus on `/user/settings` and `/-/admin` use the current sticky layout: sticky positioning on the inner menu, `top: var(--page-spacing)`, footer-aware `max-height` handling for both persistent and non-persistent footer modes, hidden desktop scrollbars, green overflow hints, local menu scrolling, and the current `/user/settings` item padding.
- 4 - I modified `web_src/js/features/common-page.ts` so the sticky side menus update their overflow-hint classes dynamically as their scroll position, size, or expanded sections change.
116 - [2026-05-07 20:41:28] - v1.27.0-dev-106-g61a9e4bd06 - Type: Modified - [user-settings] [sticky-layout] [appearance] [locale] [en] [ro] Added a persistent navigation-bar preference in `/user/settings/appearance`.
- 1 - I modified `models/user/setting_options.go`, `models/user/setting_test.go`, `routers/common/pagetmpl.go`, `routers/web/user/setting/profile.go`, `routers/web/web.go`, `templates/base/head.tmpl`, `templates/user/settings/appearance.tmpl`, `options/locale/locale_en-US.json`, and `options/locale/locale_ro-RO.json` to add the persisted `ui.persistent_navbar` preference, expose it to templates as `ShowPersistentNavbar`, save it from `/user/settings/appearance`, and document it in the UI.
- 2 - I modified `web_src/css/modules/navbar.css` so the main `#navbar` becomes sticky at the top of the viewport when the new preference is enabled.
- 3 - I modified `web_src/css/modules/flexcontainer.css` so sticky side menus take the persistent navbar height into account on desktop, preventing the left menus from sliding underneath the navbar when both preferences are enabled.
117 - [2026-05-07 20:49:16] - v1.27.0-dev-106-g61a9e4bd06 - Type: Modified - [user-settings] [ui] [sticky-layout] Preserved the `/user/settings` left-menu scroll position across settings-page navigation.
- 1 - I modified `web_src/js/features/common-page.ts` so the sticky `/user/settings` menu saves its current `scrollTop` to `sessionStorage` while scrolling and immediately before clicking a menu link.
- 2 - I also made the same code restore that saved scroll position after the next settings page renders, keeping the left menu at the same viewport position when navigating between items and subitems.
118 - [2026-05-07 20:57:42] - v1.27.0-dev-106-g61a9e4bd06 - Type: Modified - [ui] [sticky-layout] Made the footer `Licenses` and `API` links open in a new browser tab and finalized the sticky `User Settings` header plus its top green scroll indicator.
- 1 - I modified `templates/base/footer_content.tmpl` so both footer links now use `target="_blank"` with `rel="noreferrer"`.
- 2 - I modified `web_src/css/modules/flexcontainer.css` so the `.header.item` at the top of the `/user/settings` sticky side menu now uses `position: sticky` inside the menu itself, with its own background and bottom separator.
- 3 - I modified `web_src/css/modules/flexcontainer.css` so, after making the `User Settings` header sticky, the top overflow hint is rendered on the bottom edge of that header and its gradient is drawn by a dedicated `::after` element extending into the scrollable area, while the menu container keeps only the bottom hint when both are active.
119 - [2026-05-07 21:14:11] - v1.27.0-dev-106-g61a9e4bd06 - Type: Modified - [ui] [sticky-layout] Made the `Admin Settings` menu header sticky while the admin left-menu options scroll.
- 1 - I modified `web_src/css/modules/flexcontainer.css` so the `.header.item` at the top of the `/-/admin` sticky side menu now uses the same sticky header treatment as `/user/settings`, with its own background and bottom separator.
- 2 - I modified `web_src/css/modules/flexcontainer.css` so the top green overflow indicator for `/-/admin` is also rendered on the bottom edge of the sticky header, with the gradient drawn by the same dedicated `::after` element used in `/user/settings`.
120 - [2026-05-07 21:31:18] - v1.27.0-dev-106-g61a9e4bd06 - Type: Modified - [user-settings] [ui] [sticky-layout] Preserved the `/user/settings` left-menu scroll position without the visible reset flicker during navigation.
- 1 - I modified `templates/user/settings/navbar.tmpl` to add a small inline restore hook around the menu markup, so a saved `scrollTop` is applied from `sessionStorage` before the menu becomes visible on the next settings page.
- 2 - I modified `web_src/css/modules/flexcontainer.css` so, while that inline restore is in progress, only the `/user/settings` left menu is temporarily hidden, preventing the brief flash of the menu reset at the top.
- 3 - I kept `web_src/js/features/common-page.ts` focused on saving the menu scroll position and refreshing the scroll indicators, removing the now-redundant late restore path from the global initializer.
121 - [2026-05-07 21:41:44] - v1.27.0-dev-106-g61a9e4bd06 - Type: Modified - [user-settings] [sticky-layout] Restored the agreed `/user/settings` sticky-menu item padding behavior.
- 1 - I also updated the same CSS so the `/user/settings` menu padding is applied at the item level inside `.ui.vertical.menu`, using `0.9em 1.14285714em` instead of relying on a menu-level spacing adjustment.
122 - [2026-05-07 22:11:06] - v1.27.0-dev-106-g61a9e4bd06 - Type: Modified - [user-settings] [ui] [sticky-layout] Restored the pre-`122` `/user/settings` layout baseline while keeping the current sticky-menu behavior.
- 1 - I modified `templates/user/settings/layout_head.tmpl` to return the settings page wrapper from `ui container fluid padded flex-container` to `ui container flex-container`.
- 2 - I restored the `/user/settings` menu to the same single scroll container structure used before, removing the ineffective inner-body split and keeping the inline restore hook in `templates/user/settings/navbar.tmpl`.
- 3 - I modified `web_src/css/modules/flexcontainer.css` so the `/user/settings` left menu remains temporarily hidden only during the inline scroll restore, keeps the `/user/settings`-only 24px non-persistent-footer bottom padding on the left navigation column, and supports the small `--sticky-side-menu-correction` transform without affecting admin pages.
- 4 - I kept the matching logic in `web_src/js/features/common-page.ts`, so the `/user/settings` menu still restores its saved scroll position after navigation, refreshes the green overflow indicators, and applies the modest runtime correction only when the sticky menu drifts slightly above its configured top offset.
123 - [2026-05-09 12:47:10] - v1.27.0-dev-114-gbb77e80bf5 - Type: Modified - [sticky-layout] Finalized the sticky side-menu bottom-edge behavior by compacting menu items and increasing the viewport reserve.
- 1 - I modified `web_src/css/modules/menu.css` so shared menu items now use `padding: 0.75em 1.14285714em`, reducing vertical item height across the sticky left menus.
- 2 - I modified `web_src/css/modules/flexcontainer.css` so the sticky side menus in both `/user/settings` and `/-/admin` now reserve `40px` instead of `24px` at the bottom of their `max-height` calculation for the non-persistent-footer case.
- 3 - This combination keeps the sticky menus from jumping upward at the bottom of the page scroll while preserving the current sticky headers, scroll hints, and `/user/settings` scroll-position restore behavior.
124 - [2026-05-09 15:31:52] - v1.27.0-dev-115-g06b7bd3ca1 - Type: Modified - [sticky-layout] Highlighted the active submenu entry with the standard active background color.
- 1 - I modified `web_src/css/modules/menu.css` so `.ui.vertical.menu .item .menu .active.item` now uses `background-color: var(--color-active)` instead of `transparent`.
- 2 - I kept the existing medium font weight and text color unchanged, so only the active submenu background treatment changed.
125 - [2026-05-09 15:56:47] - v1.27.0-dev-116-g8a0d319607 - Type: Added - [permissions-table] [locale] [en] [ro] Added column-wide Select all controls to the user access-token permissions table.
- 1 - I modified `templates/user/settings/applications.tmpl` to add a `Select all` row above the token-scope category rows, with per-column `All` radio buttons for No access, Read, and Write.
- 2 - I added `web_src/js/features/access-token-settings.ts` and registered it in `web_src/js/index.ts` so selecting one of those top-row radios automatically applies the matching permission choice to every category row in the same column.
- 3 - I added the `settings.select_all` locale string in both `options/locale/locale_en-US.json` and `options/locale/locale_ro-RO.json` for the new control row label.
- 4 - I extended the same `web_src/js/features/access-token-settings.ts` logic so each top-row `All` radio now becomes active only when every category row in its column is selected, becomes inactive when the column is no longer fully selected, and can still be reselected to apply that column choice to all rows again.
- 5 - I corrected the select-all synchronization fallback so no top-row radio stays selected when no permission column is fully matched, instead of incorrectly defaulting back to the `No access` column.
126 - [2026-05-09 17:16:12] - v1.27.0-dev-117-gab1135d1c6 - Type: Added - [permissions-table] Added header-level Select all controls to the shared Actions maximum-permissions table.
- 1 - I modified `templates/shared/actions/permissions_table.tmpl` to add a second header row with `Select all` on the left and per-column `All` radio controls for None, Read, and Write.
- 2 - I extended `web_src/js/features/common-actions-permissions.ts` so those header radios apply the chosen permission to every row in the table and stay synchronized bidirectionally with the current per-row selections.
- 3 - Because the change is implemented in the shared Actions permissions partial and its existing initializer, the same behavior now applies consistently to `/user/settings/actions/general` and the other pages that reuse that table.
127 - [2026-05-09 17:34:41] - v1.27.0-dev-118-g021f12509f - Type: Modified - [org-ui] [sticky-layout] Applied the shared sticky side-menu behavior to organization settings pages.
- 1 - I modified `web_src/css/modules/flexcontainer.css` so the same sticky left-menu layout, hidden scrollbar styling, sticky header behavior, and green overflow indicators used by user settings and admin pages now also apply to `.page-content.organization.settings`.
- 2 - I modified `web_src/js/features/common-page.ts` so organization settings menus participate in the shared sticky-menu overflow indicator logic.
- 3 - I modified `templates/org/settings/actions_general.tmpl` to pass `pageClass: "organization settings actions"` into the shared organization settings layout, so the Actions General page also matches the shared organization settings selectors.
128 - [2026-05-09 18:46:07] - v1.27.0-dev-120-g01e3eb1306 - Type: Added - [auth] [password-ui] [signup] [locale] [en] [ro] Added password visibility toggles to the login and signup forms.
- 1 - I modified `templates/user/auth/signin_inner.tmpl` to add an eye button beside the `/user/login` password field.
- 2 - I modified `templates/user/auth/signup_inner.tmpl` to add the same eye button beside the `/user/sign_up` password field and marked the `Confirm Password` field for toggle-aware behavior.
- 3 - I added `web_src/js/features/password-visibility.ts` and registered it in `web_src/js/index.ts` so the eye button toggles between hidden and visible password states.
- 4 - In the signup form, when password visibility is enabled, the script now hides the `Confirm Password` field, removes its `required` state, and keeps its value synchronized with the main password field; when visibility is disabled again, the field is shown and required again.
- 5 - I added `auth.show_password` and `auth.hide_password` locale strings in both `options/locale/locale_en-US.json` and `options/locale/locale_ro-RO.json` for the button tooltip and accessibility label.
- 6 - I corrected the login and signup password-toggle button templates so their `data-hide-label` attributes close the Go template expression properly, removing the template parsing error that prevented startup.
- 7 - I added `octicon-eye-closed` to `web_src/js/svg.ts`, fixing the runtime JavaScript error raised when the password toggle switched from the visible-eye icon to the hidden-eye icon.
129 - [2026-05-09 19:36:18] - v1.27.0-dev-121-gbfb584f161 - Type: Modified - [sticky-layout] [repo-settings] Applied the shared sticky side-menu behavior to repository settings pages.
- 1 - I modified `web_src/css/modules/flexcontainer.css` so the same sticky left-menu layout, hidden scrollbar styling, sticky header behavior, and green overflow indicators used by user settings, organization settings, and admin pages now also apply to `.page-content.repository.settings`.
- 2 - I modified `web_src/js/features/common-page.ts` so repository settings menus participate in the shared sticky-menu overflow indicator logic.
130 - [2026-05-09 20:07:36] - v1.27.0-dev-122-g652d3c20da - Type: Modified - [sticky-layout] [repo-actions] Applied the shared sticky side-menu behavior to repository Actions pages.
- 1 - I modified `templates/repo/actions/list.tmpl` to mark the workflow sidebar menu with a dedicated hook class for the shared sticky-menu initializer.
- 2 - I modified `web_src/css/modules/flexcontainer.css` so the same sticky left-menu layout, hidden scrollbar styling, and green overflow indicators now also apply to `.page-content.repository.actions`.
- 3 - I modified `web_src/js/features/common-page.ts` so the repository Actions sidebar participates in the shared sticky-menu overflow indicator logic.
- 4 - I refined the same CSS for repository Actions so the top green scroll hint is drawn directly on the menu container, because that sidebar has no `.header.item` for the shared header-based top-gradient treatment.
- 5 - I extended `templates/repo/actions/list.tmpl` with the same inline `sessionStorage` restore hook pattern used by `/user/settings`, so the repository Actions sidebar can restore its scroll position before becoming visible.
- 6 - I modified `web_src/css/modules/flexcontainer.css` so the repository Actions sidebar is temporarily hidden only during that inline restore step, preventing the visible reset flicker.
- 7 - I extended `web_src/js/features/common-page.ts` so the repository Actions sidebar now saves its own scroll position on scroll and before navigation clicks, using the dedicated `sticky-side-menu-scroll:repo-actions` session key.
131 - [2026-05-09 20:54:41] - v1.27.0-dev-123-g0f3876c0b1 - Type: Added - [repo-actions] Added pilot partial navigation for the repository Actions sidebar.
- 1 - I added `web_src/js/features/repo-actions-sidebar.ts` and registered it in `web_src/js/index.ts` to intercept plain left-click navigation on `/<user>/<repo>/actions` sidebar workflow links.
- 2 - The new client-side flow fetches the target page, replaces only the Actions page `.ui.container` content, updates `document.title`, and pushes the new URL into browser history instead of reloading the full page.
- 3 - The same logic also handles browser back/forward through `popstate`, keeping the pilot partial navigation limited to repository Actions pages.
- 4 - I extended the same pilot so, after each partial `.ui.container` swap, the repository Actions sidebar re-runs the shared sticky-menu indicator initializer on the new DOM, restoring the green overflow hints that disappeared after the first in-page navigation.
132 - [2026-05-09 21:10:27] - v1.27.0-dev-123-g0f3876c0b1 - Type: Modified - [scripts] [smart-build] Added an audio bell for interactive prompts in `smart-build.sh`.
- 1 - I added a small `notify_human_interaction()` helper to `smart-build.sh` that emits a terminal bell only when the script is running on an interactive terminal.
- 2 - I call that helper immediately before the build-load, architecture, and build-tags interactive menus, so the user gets an audible prompt exactly when human input is needed.
- 3 - I extended the same helper so VS Code and code-server terminals also get a high-visibility fallback banner when browser-controlled terminal bells do not produce an audible sound.
- 4 - I extended the same helper again to send a Linux desktop notification through `notify-send` before each interactive menu, while keeping the existing audio and terminal fallbacks for environments where no notification daemon is available.
133 - [2026-05-09 22:32:57] - v1.27.0-dev-125-g1525c9c8ee - Type: Modified - [auth] [password-ui] [signup] Finalized the manual-only password visibility toggle behavior for login and signup.
- 1 - I removed the static eye button from the login and signup templates and now create it from `web_src/js/features/password-visibility.ts` only when the current password value qualifies for manual reveal.
- 2 - The final reveal rules are now strict: prefilled or browser-autofilled passwords never show the eye, appending characters to an already non-empty password still keeps it hidden, and the eye appears only after a trusted manual empty-to-non-empty entry or a full manual replacement of a selected existing value.
- 3 - Once the eye has legitimately appeared, it stays visible through continued typing until the password is cleared again, preserves focus plus caret/selection on click, and keeps the signup confirm-password field synchronized while reveal mode is active.
- 4 - I converted the toggle into an overlaid control inside the password field, hid the browser-native reveal buttons, and kept the final transparent eye-button background styling that was adjusted manually in `web_src/css/user.css`.
134 - [2026-05-09 23:58:22] - v1.27.0-dev-125-g1525c9c8ee - Type: Modified - [build-artifacts] Ignored the local frontend hash artifact.
- 1 - I added `/.frontend.hash` to `.gitignore` so local frontend rebuild hash churn no longer appears in the repository working tree.
- 2 - I removed `.frontend.hash` from Git tracking with `git rm --cached`, so the ignore rule now fully suppresses future local hash churn instead of only affecting newly untracked copies.
135 - [2026-05-10 00:06:54] - v1.27.0-dev-125-g1525c9c8ee - Type: Modified - [user-settings] [appearance] Unified the persistent appearance toggles into a single settings group.
- 1 - I merged the top navigation bar, side menus, and footer persistence controls in `templates/user/settings/appearance.tmpl` into one shared `Persistent layout` section with a single Save button.
- 2 - I added `UpdatePersistentLayout` in `routers/web/user/setting/profile.go` and routed `/user/settings/appearance/layout` to save all three preferences in one request while preserving the footer cookie update.
- 3 - I added the `settings.persistent_layout` and `settings.persistent_layout_desc` locale strings and finalized the section markup so the shared description sits in its own `.field` container and each per-option help paragraph is separated with a `<br>` after the checkbox row.
136 - [2026-05-10 18:40:36] - v1.27.0-dev-125-g1525c9c8ee - Type: Added - [org-ui] [permissions-table] Added column-wide Select all controls to the organization team-units permissions table.
- 1 - I extended `templates/org/team/new.tmpl` so the team-units permissions table in `org/<team_name>/teams/new` gets the same header-level Select row used by the Actions permissions table, with `All` radios for none, read, and write.
- 2 - I extended `web_src/js/features/org-team.ts` to synchronize those header radios bidirectionally with the per-unit permission rows, while correctly ignoring globally disabled read/write cells when applying or computing a column-wide selection.
137 - [2026-05-10 19:02:14] - v1.27.0-dev-125-g1525c9c8ee - Type: Added - [installer] [password-ui] Added the password visibility toggle to the SMTP password field on the install page.
- 1 - I wrapped the `smtp_passwd` input in `templates/install.tmpl` with the same `js-password-toggle-group` used by login and signup, reusing the existing password-visibility initializer and show/hide labels so the install-page SMTP password field gets the same eye toggle behavior.
138 - [2026-05-10 19:08:32] - v1.27.0-dev-125-g1525c9c8ee - Type: Modified - [mailer] [installer] Enabled install-page email notifications by default for fresh setups.
- 1 - I updated `routers/install/install.go` so the install form defaults `mail_notify` to enabled when there is no existing mailer configuration and notify-mail was still unset, while preserving an explicit existing configuration during reinstall/edit scenarios.
139 - [2026-05-10 19:15:41] - v1.27.0-dev-125-g1525c9c8ee - Type: Added - [installer] [password-ui] Added the password visibility toggle and confirm-password behavior to the install-page super-admin password fields.
- 1 - I wrapped the install-page `admin_passwd` field in the same `js-password-toggle-group` used by signup and login, so the super-admin password now gets the same eye toggle UI and manual-entry reveal behavior.
- 2 - I wired the install-page `admin_confirm_passwd` field into the existing confirm-password flow, so revealing the admin password hides the confirm field and keeps it synchronized just like the signup form.
- 3 - I refined `web_src/js/features/password-visibility.ts` so confirm-field synchronization is opt-in per toggle group via explicit selectors, preventing the install-page SMTP password toggle from accidentally targeting the super-admin confirm field in the same form.
- 4 - I adjusted `web_src/css/install.css` so install-page password fields that use the overlaid eye wrapper keep the same 60% inline-field width as the original plain inputs instead of shrinking or stretching when the wrapper is present.
140 - [2026-05-10 19:22:04] - v1.27.0-dev-125-g1525c9c8ee - Type: Added - [installer] [password-ui] Added the password visibility toggle to the install-page database password field.
- 1 - I wrapped `db_passwd` in `templates/install.tmpl` with the same `js-password-toggle-group` used by the other install-page password fields, so the database password now gets the same eye control without changing its inline width or reusing any confirm-password logic.
141 - [2026-05-10 19:27:48] - v1.27.0-dev-125-g1525c9c8ee - Type: Added - [user-settings] [password-ui] Added the password visibility toggle and confirm-password behavior to `/user/settings/account`.
- 1 - I wrapped the `settings.new_password` field in `templates/user/settings/account.tmpl` with the shared `js-password-toggle-group`, reusing the existing eye-toggle logic and show/hide labels.
- 2 - I wired the `settings.retype_new_password` field into the existing confirm-password flow through dedicated selectors, so revealing the new password hides the confirm field and keeps it synchronized the same way as signup and the install-page super-admin password form.
142 - [2026-05-10 19:43:11] - v1.27.0-dev-125-g1525c9c8ee - Type: Added - [installer] [branding] Added optional custom branding uploads to the install page.
- 1 - I finalized the installer `Branding` section with optional uploads for `logo.svg`, `logo.png`, `loading.png`, `favicon.svg`, and `favicon.png`, including clear format/size guidance plus a shared-assets checkbox for using one SVG and one PNG upload for both logo and favicon.
- 2 - I implemented backend validation and persistence for all branding uploads in `routers/install/install.go` (expected type checks, 1 MB limit, square PNG with minimum 64x64) and save accepted overrides under `custom/public/assets/img/`.
- 3 - I completed the runtime behavior so uploaded branding files override built-in assets through layered serving, `logo.svg` is mirrored to `gitea.svg` for legacy lookups, post-install progress prefers a custom `loading.png`, and the shared-assets mode hides favicon fields while relabeling logo fields to `Logo & Favicon SVG/PNG`.
- 4 - I manually updated Romanian locale wording for the final branding texts and labels.
143 - [2026-05-12 00:02:10] - v1.27.0-dev-125-g1525c9c8ee - Type: Modified - [auth] [signup] [admin-created-user] [locale] [en] [ro] Finalized Register behavior for admin-created notification accounts without altering the invitation flow.
- 1 - I extended `POST /user/sign_up` in `routers/web/auth/auth.go` for existing active local accounts created by an admin when `username` and `email` match, while explicitly leaving pending admin invitations on their existing flow.
- 2 - If password is correct, the user is now authenticated into that existing account; when `MustChangePassword` is enabled, the flow redirects directly to `/user/settings/change_password`, otherwise it follows the normal post-auth redirect.
- 3 - If password is incorrect, the flow now redirects to `/user/forgot_password?email=<email>` and shows a warning to use account recovery plus check Spam/Junk.
- 4 - I added the locale key `auth.admin_notify_recover_password_spam_hint` in both `options/locale/locale_en-US.json` and `options/locale/locale_ro-RO.json`.
- 5 - I added regression tests in `routers/web/auth/auth_test.go` for normal sign-in, forced change-password redirect, wrong-password recovery redirect, and a guard that the admin-invitation flow still redirects to `/user/invitation`.
144 - [2026-05-12 00:47:20] - v1.27.0-dev-125-g1525c9c8ee - Type: Added - [user-settings] [password-ui] Added the password visibility toggle to `/user/settings/change_password`.
- 1 - I wrapped the forced-change password field in `templates/user/auth/change_passwd_inner.tmpl` with the shared `js-password-toggle-group`, reusing the existing eye-toggle logic and show/hide labels.
- 2 - I wired the confirm-password field into the existing toggle sync behavior so revealing the new password hides the confirm field and keeps it synchronized like the other password-update forms.
145 - [2026-05-12 01:16:50] - v1.27.0-dev-125-g1525c9c8ee - Type: Added - [installer] [app-ini-import] [locale] [en] [ro] Added installer support for importing an existing `app.ini`.
- 1 - I added an `Import Existing Configuration` section at the top of `templates/install.tmpl` with an `app.ini` upload control that imports automatically as soon as a file is selected, without a separate `Load app.ini` button.
- 2 - I kept the dedicated installer route `POST /import_app_ini` in `routers/install/routes.go`, but the page now posts to it via `fetch` and applies the imported values back into the existing form with `DOMParser`, so the browser is not visibly navigated to `/import_app_ini` and the page scripts are not re-executed.
- 3 - In `routers/install/install.go`, I factored the installer defaults into reusable helpers, added `app.ini` upload parsing with size/error handling, and mapped the imported config into the existing install form fields for database, general server paths, mailer, registration, OpenID, security, and admin policy settings.
- 4 - I added installer locale strings in both `options/locale/locale_en-US.json` and `options/locale/locale_ro-RO.json` for the new import UI, success message, and import errors, and the success flash now auto-dismisses after 5 seconds both on initial page load and after the AJAX import injects a new flash message.
- 5 - I added regression coverage in `routers/install/routes_test.go` for the new upload control and the config-to-form mapping behavior.
146 - [2026-05-12 01:30:10] - v1.27.0-dev-125-g1525c9c8ee - Type: Modified - [installer] [branding] Enabled shared branding assets by default in the installer.
- 1 - I updated `routers/install/install.go` so `BrandingUseSharedAssets` starts as enabled on the install form, making `Use the same logo files for favicon assets` checked by default.
147 - [2026-05-12 01:43:10] - v1.27.0-dev-125-g1525c9c8ee - Type: Added - [installer] [app-ini-import] [secrets] Added optional sensitive-secret import for installer `app.ini` uploads.
- 1 - I added an explicit installer checkbox for importing sensitive secrets from `app.ini` in `templates/install.tmpl`.
- 2 - I extended the installer form, submit pipeline, and final config writer so the optional import reuses `LFS_JWT_SECRET`, `INTERNAL_TOKEN`, and `oauth2.JWT_SECRET` from the uploaded `app.ini` instead of generating new values, including a submit-time fallback that re-reads the uploaded file if the checkbox was enabled after the first auto-import.
- 3 - I finalized secret resolution for both direct values and `LFS_JWT_SECRET_URI` / `INTERNAL_TOKEN_URI` / `JWT_SECRET_URI` file-based references, and added regression coverage for direct imports, URI-based imports, the real `POST /import_app_ini` flow, and the persisted `app.ini` output.
148 - [2026-05-12 22:44:38] - v1.27.0-dev-143-g512e577c3f - Type: Added - [scripts] [repo-sync] [rollback] Finalized the safe upstream update helper script as `.update-gitea.sh`.
- 1 - I renamed the updater to `.update-gitea.sh`, documented its purpose and ordered usage steps, including the explicit "dry-run has conflicts" path before any real sync, and added an interactive menu plus direct commands for `sync`, `dry-run`, `fetch`, `backup`, `status`, `list-backups`, `rollback`, `restore-stash`, `restore-snapshot`, and `clean-dry-run`.
- 2 - I hardened real update actions so they verify repository state, create or offer safety backup branches, retain the original pre-sync stash for rollback, and record the active restore metadata inside `.git`.
- 3 - I added exact worktree snapshots under `.git/.update-gitea-snapshots`, showed the latest/saved snapshot paths in `status`, and made `rollback` plus `restore-snapshot` restore the saved starting commit, the original local changes, and the exact worktree contents including untracked and ignored files while preserving a fresh safety snapshot of the state being replaced.
- 4 - I implemented a reusable dry-run workspace under `.git/.update-gitea-dry-run`, added cleanup for both that workspace and legacy temporary dry-run directories, and made dry-run collect and report all detected rebase conflict steps without modifying the real repository.
- 5 - I improved conflict reporting so package.json conflicts show the upstream scripts block, the conflicting commit side, and the current branch working-tree side, and the final dry-run summary now includes the total conflict-step count, the local commits that conflicted, and the unique conflicted files.
149 - [2026-05-13 00:05:18] - v1.27.0-dev-143-g512e577c3f - Type: Added - [scripts] [repo-sync] [cherry-pick] Added a dedicated safe upstream import helper based on `cherry-pick`.
- 1 - I added [`.import-upstream-cherry-pick.sh`](/config/workspace/gitea-dev/gitea/.import-upstream-cherry-pick.sh) as a separate helper that fetches upstream, lists importable upstream-only commits, and imports either selected commits or an inclusive upstream range through `git cherry-pick -x` so the imported commits keep a visible reference to the original upstream hashes.
- 2 - I gave the script the same safety model as the updater flow by creating a fresh backup branch, an exact worktree snapshot, and a saved tracked/untracked stash before every real import action, while recording the active restore metadata in `.git/.import-upstream-cherry-pick-state`.
- 3 - I added safe recovery commands for `continue`, `rollback`, `restore-stash`, and `restore-snapshot`, so interrupted or unwanted imports can be resumed or reverted back to the saved starting commit and exact worktree state, including untracked and ignored files.
- 4 - I added both command-line usage and an interactive menu for fetch, list, import, import-range, continue, backup, rollback, restore, and status workflows.
150 - [2026-05-13 00:18:42] - v1.27.0-dev-143-g512e577c3f - Type: Added - [scripts] [custom-release] [interactive] Added an interactive custom-release maintenance helper for stable patch lines.
- 1 - I added [`.maintain-custom-release.sh`](/config/workspace/gitea-dev/gitea/.maintain-custom-release.sh) to maintain a persistent custom branch such as `release/v1.26-custom`, starting from a base tag like `v1.26.0-rc0`, importing the missing upstream commits from the real upstream minor release branch such as `release/v1.26`, and then importing only the custom commits from a chosen local source branch.
- 2 - I made the helper interactive with a menu plus a guided `configure` step, so the base tag, upstream release branch, maintenance branch, custom source branch, upstream compare branch, and custom tag suffix can all be adjusted from prompts instead of only through environment variables, and I added automatic fallback from mistyped patch-style branch names like `release/v1.26.0` to the real upstream branch `release/v1.26` when it exists.
- 3 - I gave the script the same safety model as the other local Git helpers by creating a fresh backup branch, an exact worktree snapshot, and a saved tracked/untracked stash before every real import action, while also storing pending cherry-pick state so interrupted sequences can be continued.
- 4 - I added recovery commands for `continue`, `rollback`, `restore-stash`, and `restore-snapshot`, and a `tag` command that creates annotated custom release tags such as `v1.26.0-custom` on the maintained custom release branch.
151 - [2026-05-13 00:34:10] - v1.27.0-dev-143-g512e577c3f - Type: Modified - [scripts] [repo-sync] [fetch] Narrowed local upstream fetch scope and cleaned unused upstream tracking refs.
- 1 - I updated [`.update-gitea.sh`](/config/workspace/gitea-dev/gitea/.update-gitea.sh) and [`.import-upstream-cherry-pick.sh`](/config/workspace/gitea-dev/gitea/.import-upstream-cherry-pick.sh) so they fetch only the explicitly requested upstream branch instead of all upstream branches.
- 2 - I updated [`.maintain-custom-release.sh`](/config/workspace/gitea-dev/gitea/.maintain-custom-release.sh) so it fetches only the configured upstream release branch, the configured compare branch, and tags, while also normalizing mistaken patch-style release branch names like `release/v1.26.0` to the real upstream branch `release/v1.26`.
- 3 - I narrowed the local `remote.upstream.fetch` refspec to `upstream/main` and `upstream/release/v1.26`, then removed the other local `upstream/*` remote-tracking refs so Git Graph no longer shows the unused upstream branches by default.
152 - [2026-05-13 20:23:40] - v1.27.0-dev-143-g512e577c3f - Type: Modified - [scripts] [custom-release] [restore-points] Extended the custom-release maintenance helper with manual restore points and corrected its fetch and interactive configuration behavior.
- 1 - I updated [`.maintain-custom-release.sh`](/config/workspace/gitea-dev/gitea/.maintain-custom-release.sh) so it no longer auto-fetches upstream tags during release-branch synchronization, preventing patch tags like `v1.26.1` from being pulled in just because the release branch history was fetched.
- 2 - I added manual restore-point management commands for `create-restore-point`, `list-restore-points`, `restore-point`, and `delete-restore-point`, each backed by an exact worktree snapshot plus an associated backup branch stored under `.git/.maintain-custom-release-restore-points`.
- 3 - I integrated the new restore-point workflow into the interactive menu, the `help` text, and `status`, including support for restoring by full path or by the final restore-point directory name, automatically using the latest restore point for the current branch when no target is provided, recognizing the older manual restore points already stored under `.git/.manual-restore-points`, and fixing the interactive configuration prompts so they are shown correctly during `Edit configuration`.
153 - [2026-05-13 21:51:32] - v1.27.0-dev-143-g512e577c3f - Type: Modified - [scripts] [custom-release] [rollback] Finalized the custom-release maintenance helper workflow and recovery behavior.
- 1 - I made `bootstrap` a clean branch-creation step from `BASE_TAG`, separated fetch and sync into explicit compare/release-target/custom actions, added `UPSTREAM_RELEASE_TARGET_REF`, and updated the built-in help so the recommended workflow matches the current menu structure.
- 2 - I hardened recovery so rollback, restore-point, restore-snapshot, restore-stash, and restore-deletion correctly preserve or clean script-managed refs, maintenance branches, state files, backup branches, and snapshots, including rollback from the original entry branch after a bootstrap-created maintenance branch, cleanup of legacy restore-point leftovers, and removal of the correctly paired `backup/maint-*` Git Graph marker when a saved snapshot is deleted.
- 3 - I finalized the interactive UX by keeping a self-updating runtime copy in `/tmp`, persisting the last-used settings in `/tmp/.maintain-custom-release.env`, and reorganizing the menu into `Manual Backups >`, `Fetch upstreams >`, `Sync >`, `Rollback >`, and `Restore >` submenus, including `Delete Restore >` with numbered stash and snapshot selection, with numbered selections, `b`/`B` or `Enter` for Back, correct return-to-parent behavior from every submenu, and `0` for Exit.
154 - [2026-05-17 00:18:43] - v1.26.0-rc0-154-gfc98a14014 - Type: Fixed - [admin-users] [terminology] [locale] [en] [ro] Corrected the bootstrap-admin label from `GOOD` to `GOD`.
- 1 - I renamed the bootstrap admin actor label and the related immutable-account locale key from `good` to `god` in the admin grant helpers and admin users UI flow.
- 2 - I updated the admin API and admin-panel restriction messages, tests, and both English and Romanian locale strings so bootstrap-protected accounts are consistently labeled as `GOD`-granted.
- 3 - I updated the matching historical task descriptions in `.codex-history.md` so the earlier admin-policy entries now use the corrected `GOD` terminology.
155 - [2026-05-17 15:35:49] - v1.26.0-by-petru - Type: Fixed - [scripts] [custom-release] [release-target] Stopped release-target sync from requiring the remote release branch when an explicit target tag/ref is configured.
- 1 - I updated [`.maintain-custom-release.sh`](/config/workspace/gitea-dev/gitea/.maintain-custom-release.sh) so `Sync upstream release target commits` validates only the configured `UPSTREAM_RELEASE_TARGET_REF` when one is set, instead of still failing on a missing local `upstream/release/...` remote-tracking branch after successfully fetching a target tag such as `v1.26.1`.
156 - [2026-05-17 18:14:08] - v1.26.0-by-petru-24-gadb90b3453 - Type: Modified - [scripts] [smart-build] [artifacts] Renamed smart-build outputs to include the tag/ref and generated per-file SHA-256 checksums.
- 1 - I updated [`.smart-build.sh`](/config/workspace/gitea-dev/gitea/.smart-build.sh) so each build artifact is now written as `gitea-<tag-or-ref>-<os>-<platform><-sqlite>` with the original executable extension preserved, and each output also gets its own adjacent `.sha256` file generated with `sha256sum` or `shasum -a 256`.
157 - [2026-05-17 17:32:10] - v1.26.0-by-petru-23-g2d228475fc - Type: Fixed - [build] [versioning] Preserved custom tag names in `GITEA_VERSION` while keeping `git describe` build metadata.
- 1 - I updated `Makefile` so `GITEA_VERSION` now strips the leading `v`, preserves exact custom tag names such as `1.26.0-by-petru`, and converts only the trailing `-N-gSHA` suffix from `git describe` into `+N-gSHA` for in-between builds like `1.26.0-by-petru+3-g...` and `1.27.0-dev+143-g...`.
158 - [2026-05-17 22:20:35] - v1.26.0-by-petru - Type: Fixed - [admin-users] [delete-user] [fetch-action] Made the admin user-table trash action return fetch-compatible delete responses.
- 1 - I updated the `/-/admin/users` delete modal in the user table to submit an explicit inline fetch flag, and I changed the web admin `DeleteUser` handler so that this table-specific fetch flow now returns `JSONRedirect` on success and `JSONError` for expected validation failures, while the classic edit-page delete form keeps its normal redirect behavior; I also added integration coverage for the table delete path.
159 - [2026-05-17 00:21:37] - v1.26.0-by-petru - Type: Modified - [docs] [changelog] [github-links] Documented the custom `1.26.0-by petru & codex` release in `CHANGELOG.md`.
- 1 - I added the custom release reference and the dedicated `CUSTOM by petru & codex` release-notes block in `CHANGELOG.md`, summarizing the project-specific features and behavior changes shipped on top of upstream `1.26.0`.
- 2 - I updated `CHANGELOG.md` and `CHANGELOG-archived.md` so plain standalone references of the form `(#NNNNN)` and compound ampersand groups such as `(#NNNNN & #MMMMM)` now point directly to `https://github.com/
159 - [2026-05-17 17:13:47] - v1.26.0-by-petru - Type: Modified - [update] Added v1.26.1 original Gitea commits
160 - [2026-05-17 17:13:47] - v1.26.1-by-petru - Type: Modified - [docs] [changelog] [github-links] Added explicit GitHub links for the remaining bare PR references in `CHANGELOG.md` for the `v1.26.1-by-petru` release notes.
- 1 - I updated the remaining bare `#NNNNN` pull-request references in `CHANGELOG.md` so they now point directly to `https://github.com/go-gitea/gitea/pull/...`, without folding this tag-specific changelog cleanup into the earlier generic changelog-link conversion entry.
161 - [2026-05-19 21:31:45] - v1.27.0-dev-172-g3a6684178a - Type: Modified - [scripts] [smart-build] [darwin] Added macOS amd64/arm64 smart-build support, including SQLite-aware Docker-host handling for containerized workspaces.
- 1 - I updated `smart-build.sh` so its interactive architecture menu now offers `macos-amd64`, `macos-arm64`, and includes both Darwin targets in `All Arch`, while preserving the existing `darwin` artifact naming in `dist/`.
- 2 - I added a dedicated Darwin SQLite build path in `smart-build.sh` that routes macOS `bindata sqlite sqlite_unlock_notify` builds through `make release-darwin`, and I updated `Makefile` to make `release-darwin` configurable through `DARWIN_ARCHS` so helper scripts can request only `darwin-10.12/amd64` or `darwin-10.12/arm64`.
- 3 - I hardened the Darwin SQLite flow in `smart-build.sh` for `code-server`-style containerized workspaces by distinguishing between a missing Docker CLI and an unreachable Docker daemon, by validating that the host Docker daemon can see the same mounted repository `go.mod` path as the current workspace, and by moving the temporary release output under `dist/` instead of `/tmp`.
- 4 - I added `SMART_BUILD_DARWIN_HOST_REPO_PATH` support to `smart-build.sh` so Darwin SQLite builds can be redirected to a host-visible repository mount path when the interactive workspace path inside the container differs from the real host path used by the Docker daemon.
161 - [2026-05-19 23:43:29] - v1.27.0-dev-172-g06e5bd7f46 - Type: Modified - [scripts] [configure] [git-lfs] Added conditional Git LFS setup to `configure.sh` when repository LFS hooks are installed.
- 1 - I updated `.configure.sh` so repositories that already have Git LFS hook scripts in `.git/hooks` now treat `git-lfs` as a required dependency during verification, install the `git-lfs` system package on supported package managers, and run `git lfs install --local` during non-verify setup.
+337
View File
@@ -0,0 +1,337 @@
# Gitea Project Map for Codex
This file is the persistent implementation map for fast project orientation.
Use it after `./.codex-context.md` when a task needs architecture, flow, or extension-point context.
## 1. Fast Entry Points Index
- auth -> `routers/web/auth/`, `templates/user/auth/`, `services/auth/`
- installer -> `routers/install/`, `templates/install.tmpl`, `options/locale/`
- user settings UI -> `routers/web/user/setting/`, `templates/user/settings/`, `web_src/js/features/`, `web_src/css/modules/`
- sticky menus / persistent layout UI -> `templates/*/navbar*.tmpl`, `web_src/css/modules/menu.css`, `web_src/css/modules/flexcontainer.css`, `web_src/js/features/common-page.ts`
- repo settings / actions UI -> `routers/web/repo/`, `templates/repo/`, `templates/repo/settings/`
- admin UI -> `routers/web/admin/`, `templates/admin/`
- mail / notifications -> `services/mailer/`, `templates/mail/`, `routers/web/admin/`, `routers/web/auth/`
- custom release maintenance and repo-sync helpers -> `./.maintain-custom-release.sh`, `./.update-gitea.sh`, `./.import-upstream-cherry-pick.sh`, `./.codex-script-notes.md`
## 2. Repository Map
- Executable entry point: `main.go`
- CLI lifecycle and command startup: `cmd/`
- Installed-instance initialization and route-tree mounting: `routers/init.go`
- Web SSR routes: `routers/web/`
- API routes: `routers/api/`
- Request context, session, template data, response helpers: `services/context/`
- Business logic: `services/`
- Persistence and domain models: `models/`
- Cross-cutting infrastructure: `modules/`
- Server-side templates: `templates/`
- Browser-side frontend: `web_src/`
## 3. Bootstrap and Request Flow
### 2.1 Application Bootstrap
1. `main.go`
- Sets `setting.AppVer`, `setting.AppBuiltWith`, and `setting.AppStartTime`.
- Starts the CLI app through `cmd.NewMainApp(...)` and `cmd.RunMainApp(...)`.
2. `cmd/web.go`
- `newWebCommand()` defines the `web` command.
- `runWeb(...)` prepares graceful shutdown.
- `serveInstalled(...)` calls `routers.InitWebInstalled(...)` and then `routers.NormalRoutes()`.
3. `routers/init.go`
- `InitWebInstalled(...)` initializes Git, settings, storage, cache, DB, models, auth, indexers, webhooks, SSH, Actions, and cron.
- `NormalRoutes()` mounts:
- `/` -> `routers/web.Routes()`
- `/api/v1` -> public API
- `/api/internal` -> private API
- optional package and Actions API areas when enabled
### 2.2 Web Request Pipeline
1. `routers/web/web.go:Routes()`
- Builds the main web router.
- Exposes static assets, avatars, `robots.txt`, `metrics`, and `healthz`.
2. Core middleware
- `common.MustInitSessioner()` prepares the session.
- `context.Contexter()` builds the web context and template data.
- `newWebAuthMiddleware()` resolves optional or required authentication.
3. `services/context/`
- `NewBaseContext(...)` creates the base request context.
- `NewWebContext(...)` attaches `Doer`, `Repo`, `Org`, `Session`, `Flash`, and `PageData`.
- `Contexter()` injects global template and page data such as:
- `Link`
- `PageData`
- flash cookie
- `SystemConfig`
- shared template state
4. Auth and access validation
- `verifyAuthWithOptions(...)` enforces:
- `SignInRequired`
- `SignOutRequired`
- `AdminRequired`
- cross-origin rules
- inactive-user and forced-password-change constraints
5. Domain handler
- The request reaches `routers/web/...` or `routers/api/...`.
- Handlers should stay thin and delegate to `services/...`.
6. Business logic and persistence
- `services/...` orchestrate business rules.
- `models/...` read or write the DB and represent domain state.
- `modules/...` provide reusable infrastructure such as git, storage, cache, markup, logging, web helpers, SSH, and indexing.
7. Response
- Web:
- templates from `templates/...`
- optional page JS data for `web_src/js/...`
- API:
- JSON or file responses through helpers in `services/context/`
## 4. Authentication Map
### 3.1 Where Auth Routes Live
Auth routes are mainly declared in `routers/web/web.go`, especially around:
- `/user/login`
- `/user/sign_up`
- `/user/two_factor/...`
- `/user/webauthn/...`
- `/user/openid/...`
- `/login/oauth/...`
- `/user/settings/security/...`
- `/user/settings/applications/oauth2/...`
### 3.2 Key Auth Files
- `routers/web/auth/auth.go`
- classic login
- signup
- remember-cookie login
- post-login redirect
- branching toward 2FA or WebAuthn
- `routers/web/auth/password.go`
- forgot password
- reset password
- forced password change
- `routers/web/auth/2fa.go`
- TOTP
- scratch codes
- `routers/web/auth/webauthn.go`
- passkeys
- WebAuthn challenge/assertion flow
- `routers/web/auth/openid.go`
- OpenID sign-in
- connect
- register
- `routers/web/auth/oauth.go`
- OAuth2 / OIDC provider login start and callback
- link account
- auto-registration
- provider-data sync triggers
- `routers/web/auth/oauth_signin_sync.go`
- post-login provider-data synchronization
- `routers/web/auth/oauth2_provider.go`
- Gitea as an OAuth2 / OIDC provider
- authorize, access token, userinfo, introspection, JWKS
- `routers/web/auth/linkaccount.go`
- external-account linking to a local account
### 3.3 Classic Web Login Flow
1. Browser requests `/user/login`.
2. `context.Contexter()` prepares context and page data.
3. `newWebAuthMiddleware()` attempts authentication through available strategies:
- OAuth2 header/bearer where allowed
- Basic auth where allowed
- reverse-proxy auth if enabled
- session
- SSPI on Windows if enabled
4. `auth.SignIn` renders the page.
5. `POST /user/login` enters `auth.SignInPost`.
6. On success, the flow may:
- branch to 2FA
- branch to WebAuthn
- create a remember cookie
- redirect to `redirect_to` or the default target
7. Inactive, blocked, or forced-password-change users are stopped by auth logic or `verifyAuthWithOptions(...)`.
### 3.4 Auth Services and UI
- `services/auth/` contains reusable auth strategies such as:
- `Basic`
- `OAuth2`
- `Session`
- `ReverseProxy`
- `SSPI`
- Auth UI lives in `templates/user/auth/`
- Relevant browser-side auth code includes:
- `web_src/js/features/user-auth-webauthn.ts`
- `web_src/js/features/captcha.ts`
### 3.5 Where to Extend Auth
- New auth UI step:
- `routers/web/auth/...`
- `templates/user/auth/...`
- optional `web_src/js/features/...`
- New authentication rule or source:
- `services/auth/...`
- optionally `models/auth/...`
- integrate through `newWebAuthMiddleware()`
- New OAuth2/OIDC provider endpoint:
- `routers/web/auth/oauth2_provider.go`
- `services/oauth2_provider/...`
## 5. Change Entry Points
### 4.1 New Web Route
- Add handler in `routers/web/<domain>/`
- Register in `routers/web/web.go`
- If it has UI:
- template in `templates/...`
- optional JS/CSS in `web_src/...`
### 4.2 New API Route
- Add handler in `routers/api/v1/...` or the proper API subtree
- Mount through `routers/init.go` or the existing API router
- Use `services/context/` helpers for validation and response consistency
### 4.3 New Business Rule
- Orchestration in `services/<domain>/`
- Persistence in `models/<domain>/`
- Keep routing logic thin
### 4.4 New Template Data
- Put page-specific data in handlers or domain middleware
- Put global data there only if it is truly cross-cutting
- For data consumed by page JS, use `ctx.PageData`
### 4.5 New SSR Screen or UI Change
- Template in `templates/...`
- If client-side interaction is needed:
- logic in `web_src/js/features/...`
- styles in `web_src/css/...`
### 4.6 Global Navigation and Template Hooks
- Main top navigation:
- `templates/base/head_navbar.tmpl`
- Extra global links without rewriting the standard navbar:
- `templates/custom/`
- `custom/extra_links` hook in `templates/base/head_navbar.tmpl`
- Repository header and main repo tabs:
- `templates/repo/header.tmpl`
- Extra repo tabs without rewriting the standard header:
- `custom/extra_tabs` hook in `templates/repo/header.tmpl`
- Repo submenu areas:
- `templates/repo/navbar.tmpl`
- `templates/repo/sub_menu.tmpl`
### 4.7 User, Org, Repo, and Admin Areas
- Repo:
- `routers/web/repo/`
- `services/repository/`, `services/pull/`, `services/issue/`, `services/git/`
- `templates/repo/`
- User:
- `routers/web/user/`
- `routers/web/user/setting/`
- `services/user/`
- `templates/user/`
- `templates/user/settings/`
- Org:
- `routers/web/org/`
- `services/org/`
- `templates/org/`
- `templates/org/settings/`
- Admin:
- `routers/web/admin/`
- support often spans `models/`, `services/`, and `modules/setting/`
- `templates/admin/`
## 6. Frequent Task Shortcuts
- Login / signup / account recovery:
- `routers/web/auth/`
- `templates/user/auth/`
- `services/auth/`
- `models/auth/`
- `models/user/`
- User settings / security / applications:
- `routers/web/user/setting/`
- `templates/user/settings/`
- Repository header / tabs / page chrome:
- `templates/repo/header.tmpl`
- `templates/repo/navbar.tmpl`
- `templates/repo/sub_menu.tmpl`
- Top navigation / global links:
- `templates/base/head_navbar.tmpl`
- `templates/custom/`
- Packages:
- `routers/api/packages/`
- `services/packages/`
- `models/packages/`
- Actions:
- `routers/api/actions/`
- `routers/web/repo/actions/`
- `services/actions/`
- `models/actions/`
## 7. Technology and Validation Notes
- Backend: Go
- Server-side rendering: Go `.tmpl` templates
- Frontend: TypeScript
- Vue components exist in the repo
- Styling: CSS, Tailwind CSS, Fomantic UI
- Frontend verification tooling: Vitest, Playwright, ESLint, Stylelint
For area-specific validation:
- Go:
- `make fmt`
- `make lint-go`
- targeted Go tests
- TypeScript / frontend:
- `make lint-js`
- `make test-frontend` or targeted frontend tests when needed
- `go.mod` changes:
- `make tidy`
- targeted frontend tests when needed
- `go.mod` changes:
- `make tidy`
+62
View File
@@ -0,0 +1,62 @@
# Codex Script Notes
This file is a fast-reference companion for the large local helper scripts.
## `.maintain-custom-release.sh`
Purpose:
- maintain a custom stable branch such as `release/v1.26-custom`
- start from `BASE_TAG`
- fetch and sync upstream compare / release-target refs explicitly
- cherry-pick selected custom work from a local source branch
Current interaction model:
- interactive menu with submenus:
- `Manual Backups >`
- `Fetch upstreams >`
- `Sync >`
- `Rollback >`
- `Restore >`
- submenu navigation:
- `Enter` or `b` / `B` => Back
- `0` => Exit
Persistent runtime state:
- runtime copy: `/tmp/.maintain-custom-release.sh`
- persisted settings: `/tmp/.maintain-custom-release.env`
- restore points: `.git/.maintain-custom-release-restore-points/`
- snapshots: `.git/.maintain-custom-release-snapshots/`
- active state file: `.git/.maintain-custom-release-state`
Recommended order:
1. `Bootstrap maintenance branch`
2. `Fetch upstream/main compare ref`
3. `Fetch upstream release target ref`
4. `Show import plan`
5. `Sync` actions as needed
Important behavior:
- `bootstrap` should only create/switch the maintenance branch from `BASE_TAG`; it should not fetch automatically
- `rollback` should remove bootstrap-created maintenance branches and clean script-managed refs/artifacts
- deleting a saved exact snapshot should also remove its paired `backup/maint-*` Git Graph marker
## `.update-gitea.sh`
Purpose:
- safe upstream sync helper for the working tree
- create safety backups before real sync actions
- provide `dry-run`, `rollback`, `restore-stash`, and `restore-snapshot`
Key safety expectations:
- `dry-run` must not modify the real repository
- real sync actions must preserve enough state for exact rollback
## `.import-upstream-cherry-pick.sh`
Purpose:
- import upstream commits through `git cherry-pick -x`
- support commit-by-commit or range-based import
Key safety expectations:
- save backup branch, snapshot, and stash before real import actions
- support `continue`, `rollback`, `restore-stash`, and `restore-snapshot`
+61
View File
@@ -0,0 +1,61 @@
#!/usr/bin/env bash
set -euo pipefail
CALLBACK_URL="http://127.0.0.1:1455/auth/callback"
SUCCESS_URL="http://localhost:1455/success"
die() {
printf 'ERROR: %s\n' "$*" >&2
exit 1
}
extract_code() {
local input="$1"
case "$input" in
*code=*)
input="${input#*code=}"
input="${input%%&*}"
input="${input%%#*}"
;;
esac
printf '%s' "$input"
}
extract_id_token() {
local response_file="$1"
sed -n 's/.*id_token=\([^&[:space:]"'"'"'<>]*\).*/\1/p' "$response_file" |
tr -d '\r' |
head -n 1
}
printf 'Codex ChatGPT login helper\n'
printf 'Paste the received code, full callback URL, or query string containing code=...\n'
printf 'Received key: '
IFS= read -r received_key
[ -n "$received_key" ] || die "empty received key"
code="$(extract_code "$received_key")"
[ -n "$code" ] || die "could not extract code"
response_file="$(mktemp)"
trap 'rm -f "$response_file"' EXIT
printf '\nCalling Codex auth callback...\n'
curl -sv -H "Host: localhost" --get --data-urlencode "code=$code" "$CALLBACK_URL" >"$response_file" 2>&1 || {
cat "$response_file" >&2
die "callback request failed"
}
id_token="$(extract_id_token "$response_file")"
[ -n "$id_token" ] || {
cat "$response_file" >&2
die "could not find id_token in callback response"
}
printf 'id_token received. Completing login...\n'
curl -sv --get --data-urlencode "id_token=$id_token" "$SUCCESS_URL"
printf '\nDone.\n'
Executable
+722
View File
@@ -0,0 +1,722 @@
#!/usr/bin/env bash
set -Eeuo pipefail
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
repo_go_version() {
sed -n 's/^go //p' "$SCRIPT_DIR/go.mod" 2>/dev/null | head -n 1
}
repo_node_version() {
sed -n 's/.*"node": ">= *\([^"]*\)".*/\1/p' "$SCRIPT_DIR/package.json" 2>/dev/null | head -n 1
}
repo_pnpm_version() {
sed -n 's/.*"packageManager": "pnpm@\([^"]*\)".*/\1/p' "$SCRIPT_DIR/package.json" 2>/dev/null | head -n 1
}
GO_VERSION="${GO_VERSION:-$(repo_go_version)}"
GO_VERSION="${GO_VERSION:-1.26.2}"
NODE_VERSION="${NODE_VERSION:-$(repo_node_version)}"
NODE_VERSION="${NODE_VERSION:-22.18.0}"
PNPM_VERSION="${PNPM_VERSION:-$(repo_pnpm_version)}"
PNPM_VERSION="${PNPM_VERSION:-10.33.0}"
NVM_VERSION="${NVM_VERSION:-v0.40.3}"
INSTALL_SYSTEM=1
INSTALL_GO=1
INSTALL_NODE=1
INSTALL_FRONTEND_DEPS=1
VERIFY_ONLY=0
WITH_CROSS_CGO=0
SHOW_MENU=0
VERIFY_REPORT_ONLY=0
VERIFY_HAD_ISSUES=0
usage() {
cat <<EOF
Usage: ./configure.sh [options]
Installs and configures the local build requirements for this Gitea tree.
Options:
--with-cross-cgo Also install/configure cross-CGO toolchains for
sqlite builds targeting linux/armv7 and windows/amd64.
This is useful for "All Arch" + sqlite builds, but it
downloads noticeably larger packages.
--skip-system Do not install system packages.
--skip-go Do not install Go.
--skip-node Do not install NVM/Node/pnpm.
--skip-frontend-deps Do not run pnpm install --frozen-lockfile.
--verify-only Only check the current environment.
--menu Show the interactive run menu.
-h, --help Show this help.
Environment overrides:
GO_VERSION=$GO_VERSION
NODE_VERSION=$NODE_VERSION
PNPM_VERSION=$PNPM_VERSION
NVM_VERSION=$NVM_VERSION
EOF
}
show_description() {
cat <<EOF
Gitea build environment setup
This script prepares the local machine for the Gitea build used in this tree.
It can install or verify:
- the required system build packages, including gcc, make, git, pkg-config,
and the SQLite/PAM libraries;
- git-lfs when this repository has Git LFS hooks installed;
- Go $GO_VERSION, as required by go.mod;
- Node $NODE_VERSION and pnpm $PNPM_VERSION, as required by package.json;
- frontend dependencies with pnpm install --frozen-lockfile;
- optional cross-CGO compilers for SQLite builds targeting linux/armv7
and windows/amd64.
For automated runs, you can keep using CLI options, for example:
./configure.sh --verify-only
./configure.sh --with-cross-cgo
EOF
}
interactive_menu() {
show_description
cat <<EOF
Select install mode:
1) Normal mode
2) With cross cgo
3) Verify only
4) Quit
EOF
# Install the standard requirements: system packages, Go, Node, pnpm, and frontend deps.
# Normal mode plus cross-CGO toolchains for multi-arch SQLite builds.
# Install nothing; only check the current environment.
while true; do
printf 'Choose option [1-4]: '
if ! read -r choice; then
die "No menu option selected."
fi
case "$choice" in
1)
printf 'Selected: Normal\n'
return
;;
2)
WITH_CROSS_CGO=1
printf 'Selected: With cross cgo\n'
return
;;
3)
VERIFY_ONLY=1
INSTALL_SYSTEM=0
INSTALL_GO=0
INSTALL_NODE=0
INSTALL_FRONTEND_DEPS=0
VERIFY_REPORT_ONLY=1
printf 'Selected: Verify only\n'
return
;;
4)
printf 'Canceled.\n'
exit 0
;;
*)
printf 'Invalid option: %s\n' "$choice"
;;
esac
done
}
log() {
printf '\n==> %s\n' "$*"
}
warn() {
printf 'WARNING: %s\n' "$*" >&2
}
die() {
printf 'ERROR: %s\n' "$*" >&2
exit 1
}
command_exists() {
command -v "$1" >/dev/null 2>&1
}
repo_has_git_lfs_hooks() {
local hook
for hook in pre-push post-checkout post-commit post-merge; do
[ -f "$SCRIPT_DIR/.git/hooks/$hook" ] || continue
if grep -q 'git-lfs' "$SCRIPT_DIR/.git/hooks/$hook"; then
return 0
fi
done
return 1
}
repo_requires_git_lfs() {
repo_has_git_lfs_hooks
}
run_as_root() {
if [ "$(id -u)" -eq 0 ]; then
"$@"
elif command_exists sudo; then
sudo "$@"
else
die "This step needs root privileges. Install sudo or run the script as root."
fi
}
fetch_to() {
local url="$1"
local output="$2"
if command_exists curl; then
curl -fL --retry 3 --retry-delay 2 -o "$output" "$url"
elif command_exists wget; then
wget -O "$output" "$url"
else
die "curl or wget is required to download $url"
fi
}
version_ge() {
local actual="$1"
local required="$2"
[ "$(printf '%s\n%s\n' "$required" "$actual" | sort -V | head -n 1)" = "$required" ]
}
append_profile_line() {
local file="$1"
local line="$2"
touch "$file"
if ! grep -qxF "$line" "$file"; then
printf '\n%s\n' "$line" >>"$file"
fi
}
ensure_go_path() {
activate_go_path
append_profile_line "$HOME/.profile" 'export PATH="/usr/local/go/bin:$HOME/go/bin:$PATH"'
append_profile_line "$HOME/.bashrc" 'export PATH="/usr/local/go/bin:$HOME/go/bin:$PATH"'
}
activate_go_path() {
export PATH="/usr/local/go/bin:$HOME/go/bin:$PATH"
}
install_system_packages() {
log "Installing system packages"
if command_exists apt-get; then
local -a packages=(
bash
build-essential
ca-certificates
coreutils
curl
findutils
gawk
git
gzip
libpam0g-dev
libsqlite3-dev
make
openssh-client
perl
pkg-config
python3
sed
sqlite3
tar
unzip
wget
xz-utils
zip
)
repo_requires_git_lfs && packages+=(git-lfs)
if [ "$WITH_CROSS_CGO" -eq 1 ]; then
packages+=(
gcc-arm-linux-gnueabihf
g++-arm-linux-gnueabihf
gcc-mingw-w64-x86-64
g++-mingw-w64-x86-64
)
fi
run_as_root apt-get update
run_as_root env DEBIAN_FRONTEND=noninteractive apt-get install -y "${packages[@]}"
return
fi
if command_exists dnf; then
local -a packages=(
bash
ca-certificates
coreutils
curl
findutils
gawk
gcc
gcc-c++
git
gzip
make
openssh-clients
pam-devel
perl-core
pkgconf-pkg-config
python3
sed
sqlite
sqlite-devel
tar
unzip
wget
xz
zip
)
repo_requires_git_lfs && packages+=(git-lfs)
run_as_root dnf install -y "${packages[@]}"
[ "$WITH_CROSS_CGO" -eq 0 ] || warn "Cross-CGO package setup is only automated for apt-based systems."
return
fi
if command_exists yum; then
local -a packages=(
bash
ca-certificates
coreutils
curl
findutils
gawk
gcc
gcc-c++
git
gzip
make
openssh-clients
pam-devel
perl
pkgconfig
python3
sed
sqlite
sqlite-devel
tar
unzip
wget
xz
zip
)
repo_requires_git_lfs && packages+=(git-lfs)
run_as_root yum install -y "${packages[@]}"
[ "$WITH_CROSS_CGO" -eq 0 ] || warn "Cross-CGO package setup is only automated for apt-based systems."
return
fi
if command_exists pacman; then
local -a packages=(
base-devel
bash
ca-certificates
coreutils
curl
findutils
gawk
git
gzip
make
openssh
pam
perl
pkgconf
python
sed
sqlite
tar
unzip
wget
xz
zip
)
repo_requires_git_lfs && packages+=(git-lfs)
run_as_root pacman -Sy --needed --noconfirm "${packages[@]}"
[ "$WITH_CROSS_CGO" -eq 0 ] || warn "Cross-CGO package setup is only automated for apt-based systems."
return
fi
if command_exists zypper; then
local -a packages=(
bash
ca-certificates
coreutils
curl
findutils
gawk
gcc
gcc-c++
git
gzip
make
openssh
pam-devel
perl
pkg-config
python3
sed
sqlite3
sqlite3-devel
tar
unzip
wget
xz
zip
)
repo_requires_git_lfs && packages+=(git-lfs)
run_as_root zypper install -y "${packages[@]}"
[ "$WITH_CROSS_CGO" -eq 0 ] || warn "Cross-CGO package setup is only automated for apt-based systems."
return
fi
die "Unsupported package manager. Install git, make, gcc/g++, pkg-config, sqlite3 headers, curl/wget, tar, unzip, xz, python3, and then rerun with --skip-system."
}
go_download_arch() {
case "$(uname -m)" in
x86_64 | amd64)
printf 'amd64'
;;
aarch64 | arm64)
printf 'arm64'
;;
i386 | i686)
printf '386'
;;
armv6l | armv7l)
printf 'armv6l'
;;
*)
die "Unsupported CPU architecture for automatic Go install: $(uname -m)"
;;
esac
}
current_go_version() {
if command_exists go; then
go version | awk '{print $3}' | sed 's/^go//'
fi
}
install_go() {
log "Configuring Go $GO_VERSION"
ensure_go_path
if [ "$(current_go_version)" = "$GO_VERSION" ]; then
printf 'Go %s is already installed.\n' "$GO_VERSION"
return
fi
local arch
arch="$(go_download_arch)"
local archive="/tmp/go${GO_VERSION}.linux-${arch}.tar.gz"
local url="https://go.dev/dl/go${GO_VERSION}.linux-${arch}.tar.gz"
fetch_to "$url" "$archive"
run_as_root rm -rf /usr/local/go
run_as_root tar -C /usr/local -xzf "$archive"
ensure_go_path
[ "$(current_go_version)" = "$GO_VERSION" ] || die "Go install finished, but go version is not $GO_VERSION."
}
load_nvm() {
export NVM_DIR="${NVM_DIR:-$HOME/.nvm}"
# shellcheck disable=SC1091
[ -s "$NVM_DIR/nvm.sh" ] && . "$NVM_DIR/nvm.sh"
}
install_nvm() {
export NVM_DIR="${NVM_DIR:-$HOME/.nvm}"
if [ -s "$NVM_DIR/nvm.sh" ]; then
load_nvm
return
fi
log "Installing NVM $NVM_VERSION"
local installer="/tmp/nvm-install-${NVM_VERSION}.sh"
fetch_to "https://raw.githubusercontent.com/nvm-sh/nvm/${NVM_VERSION}/install.sh" "$installer"
bash "$installer"
load_nvm
command_exists nvm || die "NVM could not be loaded after installation."
}
current_node_version() {
if command_exists node; then
node -p 'process.versions.node'
fi
}
current_pnpm_version() {
if command_exists pnpm; then
pnpm --version
fi
}
install_node_and_pnpm() {
log "Configuring Node $NODE_VERSION and pnpm $PNPM_VERSION"
install_nvm
nvm install "$NODE_VERSION"
nvm alias default "$NODE_VERSION" >/dev/null
nvm use "$NODE_VERSION" >/dev/null
hash -r
if command_exists corepack; then
corepack enable
corepack prepare "pnpm@${PNPM_VERSION}" --activate
hash -r
fi
if ! command_exists pnpm || ! version_ge "$(current_pnpm_version)" "$PNPM_VERSION"; then
npm install -g "pnpm@${PNPM_VERSION}"
hash -r
fi
if ! version_ge "$(current_node_version)" "$NODE_VERSION"; then
die "Node $(current_node_version) is older than required $NODE_VERSION."
fi
if ! version_ge "$(current_pnpm_version)" "$PNPM_VERSION"; then
die "pnpm $(current_pnpm_version) is older than required $PNPM_VERSION."
fi
}
install_frontend_deps() {
log "Installing frontend dependencies"
cd "$SCRIPT_DIR"
pnpm install --frozen-lockfile
}
configure_git_lfs() {
repo_requires_git_lfs || return
log "Configuring Git LFS"
command_exists git-lfs || die "git-lfs is required for this repository but is not installed."
cd "$SCRIPT_DIR"
git lfs install --local >/dev/null
}
configure_cross_cgo() {
[ "$WITH_CROSS_CGO" -eq 1 ] || return
log "Configuring Makefile.local for cross-CGO sqlite builds"
cd "$SCRIPT_DIR"
if [ -f Makefile.local ] && grep -qF '# BEGIN configure.sh cross-cgo' Makefile.local; then
printf 'Makefile.local already contains configure.sh cross-CGO settings.\n'
return
fi
cat >>Makefile.local <<'EOF'
# BEGIN configure.sh cross-cgo
ifeq ($(GOOS)/$(GOARCH),windows/amd64)
CC := x86_64-w64-mingw32-gcc
CXX := x86_64-w64-mingw32-g++
export CC
export CXX
endif
ifeq ($(GOOS)/$(GOARCH)/$(GOARM),linux/arm/7)
CC := arm-linux-gnueabihf-gcc
CXX := arm-linux-gnueabihf-g++
export CC
export CXX
endif
# END configure.sh cross-cgo
EOF
}
verify_environment() {
log "Verifying build environment"
activate_go_path
load_nvm || true
hash -r
local -a missing=()
local -a problems=()
local command_name
for command_name in git make go node pnpm gcc pkg-config; do
if ! command_exists "$command_name"; then
missing+=("$command_name")
fi
done
if repo_requires_git_lfs && ! command_exists git-lfs; then
missing+=("git-lfs")
fi
if command_exists go; then
local found_go
found_go="$(current_go_version)"
[ "$found_go" = "$GO_VERSION" ] || problems+=("Go $found_go found, but $GO_VERSION is required.")
fi
if command_exists node; then
local found_node
found_node="$(current_node_version)"
version_ge "$found_node" "$NODE_VERSION" || problems+=("Node $found_node found, but >= $NODE_VERSION is required.")
fi
if command_exists pnpm; then
local found_pnpm
found_pnpm="$(current_pnpm_version)"
version_ge "$found_pnpm" "$PNPM_VERSION" || problems+=("pnpm $found_pnpm found, but >= $PNPM_VERSION is required.")
fi
cd "$SCRIPT_DIR"
if command_exists make && ! make help >/dev/null; then
problems+=("make help failed.")
fi
if [ "$WITH_CROSS_CGO" -eq 1 ]; then
for command_name in arm-linux-gnueabihf-gcc x86_64-w64-mingw32-gcc; do
if ! command_exists "$command_name"; then
missing+=("$command_name")
fi
done
fi
if [ ! -d "$SCRIPT_DIR/node_modules" ]; then
problems+=("node_modules is missing; frontend dependencies are not installed.")
fi
if [ "${#missing[@]}" -gt 0 ] || [ "${#problems[@]}" -gt 0 ]; then
VERIFY_HAD_ISSUES=1
if [ "${#missing[@]}" -gt 0 ]; then
printf '\nMissing commands:\n'
for command_name in "${missing[@]}"; do
printf ' - %s\n' "$command_name"
done
fi
if [ "${#problems[@]}" -gt 0 ]; then
printf '\nConfiguration issues:\n'
local problem
for problem in "${problems[@]}"; do
printf ' - %s\n' "$problem"
done
fi
printf '\nTo fix the standard build environment, run ./configure.sh and choose 1) Normal.\n'
printf 'For sqlite multi-arch builds, choose 2) With cross cgo.\n'
if [ "$VERIFY_REPORT_ONLY" -eq 1 ]; then
printf '\nVerify only completed; no changes were made.\n'
return 0
fi
return 1
fi
printf 'Go: %s\n' "$(go version)"
printf 'Node: %s\n' "$(node --version)"
printf 'pnpm: %s\n' "$(pnpm --version)"
printf 'gcc: %s\n' "$(gcc --version | head -n 1)"
if repo_requires_git_lfs; then
printf 'git-lfs: %s\n' "$(git lfs version)"
fi
if [ -d "$SCRIPT_DIR/node_modules" ]; then
printf 'node_modules: present\n'
else
printf 'node_modules: missing; run ./configure.sh or pnpm install --frozen-lockfile\n'
fi
}
if [ "$#" -eq 0 ] && [ -t 0 ]; then
SHOW_MENU=1
fi
while [ "$#" -gt 0 ]; do
case "$1" in
--with-cross-cgo)
WITH_CROSS_CGO=1
;;
--skip-system)
INSTALL_SYSTEM=0
;;
--skip-go)
INSTALL_GO=0
;;
--skip-node)
INSTALL_NODE=0
;;
--skip-frontend-deps)
INSTALL_FRONTEND_DEPS=0
;;
--verify-only)
VERIFY_ONLY=1
INSTALL_SYSTEM=0
INSTALL_GO=0
INSTALL_NODE=0
INSTALL_FRONTEND_DEPS=0
;;
--menu)
SHOW_MENU=1
;;
-h | --help)
usage
exit 0
;;
*)
usage
die "Unknown option: $1"
;;
esac
shift
done
if [ "$SHOW_MENU" -eq 1 ]; then
interactive_menu
fi
if [ "$(id -u)" -eq 0 ]; then
warn "You are running as root. NVM/Node will be configured for root, not for your normal user."
fi
if [ "$VERIFY_ONLY" -eq 0 ]; then
[ "$INSTALL_SYSTEM" -eq 0 ] || install_system_packages
configure_git_lfs
[ "$INSTALL_GO" -eq 0 ] || install_go
[ "$INSTALL_NODE" -eq 0 ] || install_node_and_pnpm
configure_cross_cgo
[ "$INSTALL_FRONTEND_DEPS" -eq 0 ] || install_frontend_deps
fi
verify_environment
if [ "$VERIFY_HAD_ISSUES" -eq 1 ]; then
cat <<EOF
Done. Missing requirements were reported above and no changes were made.
Run ./configure.sh again and choose:
1) Normal
For sqlite builds across all smart-build architectures, choose:
2) With cross cgo
EOF
else
cat <<EOF
Done.
Recommended next steps:
./smart-build.sh
For sqlite builds across all smart-build architectures, prepare the heavier
cross-CGO tools with:
./configure.sh --with-cross-cgo
EOF
fi
+1
View File
@@ -0,0 +1 @@
34a58393847d8354e1a401512d0e56138e53bcae
+7
View File
@@ -113,6 +113,13 @@ prime/
/.claude/
/.cursorrules
/.cursor/
# /.configure.sh
# /configure.sh
/.frontend.hash
# /.smart-build.sh
# /smart-build.sh
# /.update-gitea.sh
# /update-gitea.sh
/.goosehints
/.windsurfrules
/.github/copilot-instructions.md
+894
View File
@@ -0,0 +1,894 @@
#!/usr/bin/env bash
set -euo pipefail
# This script safely imports selected upstream commits onto the current local
# branch through cherry-pick.
# It:
# 1. checks that no conflicting git operation is already in progress;
# 2. ensures the upstream remote exists and points to the official repository;
# 3. lists upstream commits whose changes are not yet present on the current
# branch;
# 4. creates a safety backup branch and an exact worktree snapshot;
# 5. stashes tracked and untracked local changes before the import;
# 6. cherry-picks the selected upstream commits with `-x` so the original
# upstream commit hash remains visible in the imported commit message;
# 7. restores the stashed local changes only after the import completes.
# If a conflict happens, the backup branch, the exact snapshot, and the saved
# stash are all kept so the original state can be restored safely.
BRANCH="${BRANCH:-main}"
REMOTE_NAME="${REMOTE_NAME:-upstream}"
REMOTE_URL="${REMOTE_URL:-https://github.com/go-gitea/gitea.git}"
REPO_ROOT=""
GIT_DIR=""
STATE_FILE=""
SNAPSHOT_ROOT=""
CURRENT_BRANCH=""
BACKUP_BRANCH=""
STASH_REF=""
STASH_HASH=""
STATE_BRANCH=""
STATE_BACKUP_BRANCH=""
STATE_STASH_HASH=""
STATE_REMOTE_NAME=""
STATE_REMOTE_URL=""
STATE_TARGET_BRANCH=""
STATE_START_HEAD=""
STATE_SNAPSHOT_PATH=""
STATE_IMPORT_COMMITS=""
STATE_STATUS=""
STATE_UPDATED_AT=""
say() {
printf '%s\n' "$*"
}
die() {
say "ERROR: $*" >&2
exit 1
}
show_usage() {
cat <<EOF
Usage: $(basename "$0") [command]
Available commands:
fetch
Fetch the latest upstream changes only.
list
Show upstream commits whose changes are not yet present on the current branch.
import <commit> [commit...]
Cherry-pick one or more selected upstream commits with \`-x\`.
import-range <from-commit> <to-commit>
Cherry-pick an inclusive upstream commit range in upstream order.
continue
Continue an interrupted cherry-pick and restore the saved local stash once the import finishes.
backup
Create a safety backup branch from the current HEAD only.
rollback [backup-branch|snapshot-dir]
Restore the saved pre-import state, or an explicit backup branch / snapshot.
restore-stash
Re-apply the saved pre-import local stash from the last recorded import state.
restore-snapshot [snapshot-dir]
Restore the exact saved repository snapshot from the last recorded real action, or from a specific snapshot directory.
status
Show the current repository, branch, remote, local-change state, and saved import metadata.
help
Show this help text.
If no command is provided and the script is run from a terminal, an interactive
menu is shown.
Recommended order:
1. Run: ./.import-upstream-cherry-pick.sh status
2. Run: ./.import-upstream-cherry-pick.sh list
3. Choose the exact upstream commits you want to import.
4. Run: ./.import-upstream-cherry-pick.sh import <commit...>
or: ./.import-upstream-cherry-pick.sh import-range <from> <to>
5. If cherry-pick stops with conflicts:
- either resolve them and continue with: ./.import-upstream-cherry-pick.sh continue
- or return safely with: ./.import-upstream-cherry-pick.sh rollback
6. If restoring local changes after the import causes conflicts:
- either resolve them manually
- or return safely with: ./.import-upstream-cherry-pick.sh rollback
7. Use: ./.import-upstream-cherry-pick.sh restore-snapshot
when you want to restore the exact saved repository state, including
untracked and ignored files that existed at snapshot time.
EOF
}
ensure_git_repo() {
local raw_git_dir
REPO_ROOT="$(git rev-parse --show-toplevel 2>/dev/null)" || die "This script must be run inside a git repository."
raw_git_dir="$(git rev-parse --git-dir)"
case "$raw_git_dir" in
/*) GIT_DIR="$raw_git_dir" ;;
*) GIT_DIR="$REPO_ROOT/$raw_git_dir" ;;
esac
STATE_FILE="$GIT_DIR/.import-upstream-cherry-pick-state"
SNAPSHOT_ROOT="$GIT_DIR/.import-upstream-cherry-pick-snapshots"
}
write_state() {
{
printf 'STATE_BRANCH=%q\n' "$STATE_BRANCH"
printf 'STATE_BACKUP_BRANCH=%q\n' "$STATE_BACKUP_BRANCH"
printf 'STATE_STASH_HASH=%q\n' "$STATE_STASH_HASH"
printf 'STATE_REMOTE_NAME=%q\n' "$STATE_REMOTE_NAME"
printf 'STATE_REMOTE_URL=%q\n' "$STATE_REMOTE_URL"
printf 'STATE_TARGET_BRANCH=%q\n' "$STATE_TARGET_BRANCH"
printf 'STATE_START_HEAD=%q\n' "$STATE_START_HEAD"
printf 'STATE_SNAPSHOT_PATH=%q\n' "$STATE_SNAPSHOT_PATH"
printf 'STATE_IMPORT_COMMITS=%q\n' "$STATE_IMPORT_COMMITS"
printf 'STATE_STATUS=%q\n' "$STATE_STATUS"
printf 'STATE_UPDATED_AT=%q\n' "$(date +%Y-%m-%dT%H:%M:%S)"
} >"$STATE_FILE"
}
load_state() {
ensure_git_repo
[ -f "$STATE_FILE" ] || return 1
# shellcheck disable=SC1090
. "$STATE_FILE"
return 0
}
worktree_has_local_changes() {
! git diff --quiet || ! git diff --cached --quiet || [ -n "$(git ls-files --others --exclude-standard)" ]
}
has_cherry_pick_in_progress() {
[ -e "$(git rev-parse --git-path CHERRY_PICK_HEAD)" ]
}
sanitize_ref_name() {
printf '%s\n' "${1//\//-}"
}
ensure_rsync_available() {
command -v rsync >/dev/null 2>&1 || die "rsync is required for exact repository snapshots."
}
snapshot_repo_dir() {
printf '%s\n' "$1/repo"
}
is_valid_snapshot_dir() {
[ -d "$1" ] && [ -d "$(snapshot_repo_dir "$1")" ]
}
snapshot_metadata_value() {
local snapshot_dir="$1" key="$2"
[ -f "$snapshot_dir/metadata.txt" ] || return 1
sed -n "s/^${key}=//p" "$snapshot_dir/metadata.txt" | head -n 1
}
create_worktree_snapshot_for_reason() {
local reason="$1" safe_branch_name timestamp snapshot_dir snapshot_dir_repo
ensure_rsync_available
safe_branch_name="$(sanitize_ref_name "$CURRENT_BRANCH")"
timestamp="$(date +%Y%m%d-%H%M%S)"
snapshot_dir="$SNAPSHOT_ROOT/$safe_branch_name/${timestamp}-${reason}"
snapshot_dir_repo="$(snapshot_repo_dir "$snapshot_dir")"
mkdir -p "$snapshot_dir_repo"
rsync --archive --delete --exclude='.git' "$REPO_ROOT"/ "$snapshot_dir_repo"/
{
printf 'branch=%s\n' "$CURRENT_BRANCH"
printf 'head=%s\n' "$(git rev-parse HEAD)"
printf 'created_at=%s\n' "$(date +%Y-%m-%dT%H:%M:%S)"
printf 'reason=%s\n' "$reason"
} >"$snapshot_dir/metadata.txt"
printf '%s\n' "$snapshot_dir"
}
restore_worktree_snapshot() {
local snapshot_dir="$1" snapshot_dir_repo
ensure_rsync_available
is_valid_snapshot_dir "$snapshot_dir" || die "Snapshot directory '$snapshot_dir' is not valid."
snapshot_dir_repo="$(snapshot_repo_dir "$snapshot_dir")"
rsync --archive --delete --exclude='.git' "$snapshot_dir_repo"/ "$REPO_ROOT"/
}
find_latest_snapshot_for_current() {
local safe_branch_name snapshot_branch_dir
safe_branch_name="$(sanitize_ref_name "$CURRENT_BRANCH")"
snapshot_branch_dir="$SNAPSHOT_ROOT/$safe_branch_name"
[ -d "$snapshot_branch_dir" ] || return 1
find "$snapshot_branch_dir" -mindepth 1 -maxdepth 1 -type d | sort -r | head -n 1
}
ensure_no_noncherrypick_git_operation_in_progress() {
local git_path
for git_path in MERGE_HEAD REVERT_HEAD BISECT_LOG rebase-merge rebase-apply; do
if [ -e "$(git rev-parse --git-path "$git_path")" ]; then
die "A git operation is already in progress ($git_path). Finish it before running this script."
fi
done
}
ensure_no_git_operation_in_progress() {
local git_path
for git_path in CHERRY_PICK_HEAD MERGE_HEAD REVERT_HEAD BISECT_LOG rebase-merge rebase-apply; do
if [ -e "$(git rev-parse --git-path "$git_path")" ]; then
die "A git operation is already in progress ($git_path). Finish it before running this script."
fi
done
if [ -n "$(git diff --name-only --diff-filter=U)" ]; then
die "There are unmerged files in the working tree. Resolve them first."
fi
}
ensure_current_branch() {
CURRENT_BRANCH="$(git symbolic-ref --quiet --short HEAD || true)"
[ -n "$CURRENT_BRANCH" ] || die "Detached HEAD is not supported. Check out a branch first."
}
ensure_current_branch_with_state_fallback() {
CURRENT_BRANCH="$(git symbolic-ref --quiet --short HEAD || true)"
if [ -n "$CURRENT_BRANCH" ]; then
return
fi
if load_state && [ -n "${STATE_BRANCH:-}" ]; then
CURRENT_BRANCH="$STATE_BRANCH"
return
fi
die "Detached HEAD is not supported here and no saved branch state was found."
}
ensure_upstream_remote() {
local current_remote_url
if current_remote_url="$(git remote get-url "$REMOTE_NAME" 2>/dev/null)"; then
if [ "$current_remote_url" != "$REMOTE_URL" ]; then
die "Remote '$REMOTE_NAME' points to '$current_remote_url', expected '$REMOTE_URL'."
fi
return
fi
say "Adding remote '$REMOTE_NAME'..."
git remote add "$REMOTE_NAME" "$REMOTE_URL"
}
create_backup_branch_for_reason() {
local reason="$1" safe_branch_name timestamp branch_name
safe_branch_name="$(sanitize_ref_name "$CURRENT_BRANCH")"
timestamp="$(date +%Y%m%d-%H%M%S)"
branch_name="backup/cherry-pick-${safe_branch_name}-${reason}-${timestamp}"
git branch "$branch_name" HEAD >/dev/null
printf '%s\n' "$branch_name"
}
find_latest_backup_branch_for_current() {
local safe_branch_name
safe_branch_name="$(sanitize_ref_name "$CURRENT_BRANCH")"
git for-each-ref --sort=-creatordate --format='%(refname:short)' "refs/heads/backup/cherry-pick-${safe_branch_name}-*" | head -n 1
}
prepare_safety_before_real_action() {
local backup_reason="$1"
STATE_START_HEAD="$(git rev-parse HEAD)"
BACKUP_BRANCH="$(create_backup_branch_for_reason "$backup_reason")"
STATE_SNAPSHOT_PATH="$(create_worktree_snapshot_for_reason "$backup_reason")"
say "Safety backup branch created: $BACKUP_BRANCH"
say "Exact worktree snapshot created: $STATE_SNAPSHOT_PATH"
}
stash_current_changes() {
local stash_prefix="$1" timestamp stash_name
STASH_REF=""
STASH_HASH=""
if ! worktree_has_local_changes; then
say "No local tracked/untracked changes to stash."
return
fi
timestamp="$(date +%Y%m%d-%H%M%S)"
stash_name="${stash_prefix}-$(sanitize_ref_name "$CURRENT_BRANCH")-${timestamp}"
say "Stashing local tracked and untracked changes..."
git stash push --include-untracked --message "$stash_name" >/dev/null
STASH_REF="$(git stash list -1 --format='%gd')"
[ -n "$STASH_REF" ] || die "Failed to locate the created stash entry."
STASH_HASH="$(git rev-parse "$STASH_REF")"
[ -n "$STASH_HASH" ] || die "Failed to resolve the created stash hash."
say "Local changes saved in $STASH_REF"
}
fetch_upstream() {
say "Fetching latest changes from $REMOTE_NAME/$BRANCH..."
git fetch --prune "$REMOTE_NAME" "+refs/heads/$BRANCH:refs/remotes/$REMOTE_NAME/$BRANCH"
git show-ref --verify --quiet "refs/remotes/$REMOTE_NAME/$BRANCH" || die "Remote branch '$REMOTE_NAME/$BRANCH' was not found."
}
update_state() {
STATE_BRANCH="$CURRENT_BRANCH"
STATE_BACKUP_BRANCH="$BACKUP_BRANCH"
STATE_STASH_HASH="$STASH_HASH"
STATE_REMOTE_NAME="$REMOTE_NAME"
STATE_REMOTE_URL="$REMOTE_URL"
STATE_TARGET_BRANCH="$BRANCH"
write_state
}
find_stash_ref_by_hash() {
local target_hash="$1" hash ref
while read -r hash ref; do
if [ "$hash" = "$target_hash" ]; then
printf '%s\n' "$ref"
return 0
fi
done < <(git stash list --format='%H %gd')
return 1
}
drop_stash_by_hash_if_present() {
local target_hash="$1" stash_ref
[ -n "$target_hash" ] || return 0
if stash_ref="$(find_stash_ref_by_hash "$target_hash")"; then
git stash drop "$stash_ref" >/dev/null
fi
}
restore_stash() {
local keep_saved_copy="${1:-0}" restore_target
if [ -z "$STASH_HASH" ] && [ -z "$STASH_REF" ]; then
return
fi
restore_target="${STASH_HASH:-$STASH_REF}"
say "Restoring stashed local changes from $restore_target..."
if git stash apply --index "$restore_target"; then
STASH_REF=""
if [ "$keep_saved_copy" -eq 0 ]; then
drop_stash_by_hash_if_present "$STASH_HASH"
STASH_HASH=""
STATE_STASH_HASH=""
else
STATE_STASH_HASH="${STASH_HASH:-$restore_target}"
fi
STATE_STATUS="completed"
update_state
if [ "$keep_saved_copy" -eq 0 ]; then
say "Local changes restored successfully."
else
say "Local changes restored successfully. The original stash was kept for rollback safety."
fi
return
fi
STATE_STATUS="restore_conflict"
update_state
say "Conflicts occurred while restoring local changes."
say "Backup branch kept at: $BACKUP_BRANCH"
say "Stash kept at: $restore_target"
say "Resolve the conflicts manually, or return safely with: ./.import-upstream-cherry-pick.sh rollback"
exit 1
}
ordered_available_upstream_commits() {
local available_commit_shas="" commit
available_commit_shas="$(git cherry -v HEAD "$REMOTE_NAME/$BRANCH" | awk '$1=="+"{print $2}')"
[ -n "$available_commit_shas" ] || return 0
while IFS= read -r commit; do
[ -n "$commit" ] || continue
if printf '%s\n' "$available_commit_shas" | grep -Fxq "$commit"; then
printf '%s\n' "$commit"
fi
done < <(git rev-list --reverse HEAD.."$REMOTE_NAME/$BRANCH")
}
commit_is_available_for_import() {
local commit="$1"
ordered_available_upstream_commits | grep -Fxq "$commit"
}
resolve_import_commit() {
local commit="$1"
git rev-parse --verify "${commit}^{commit}" 2>/dev/null || die "Commit '$commit' could not be resolved."
}
validate_importable_commit() {
local commit="$1"
git merge-base --is-ancestor "$commit" "$REMOTE_NAME/$BRANCH" || die "Commit '$commit' is not reachable from $REMOTE_NAME/$BRANCH."
commit_is_available_for_import "$commit" || die "Commit '$commit' is not currently available for import into '$CURRENT_BRANCH'."
}
show_available_commits() {
local found_any=0 commit
while IFS= read -r commit; do
[ -n "$commit" ] || continue
found_any=1
git show --no-patch --date=short --format=' - %h | %ad | %s' "$commit"
done < <(ordered_available_upstream_commits)
if [ "$found_any" -eq 0 ]; then
say "No upstream commits are currently available for cherry-pick import."
fi
}
run_status() {
local stash_count latest_backup latest_snapshot
ensure_git_repo
ensure_current_branch_with_state_fallback
ensure_upstream_remote
stash_count="$(git stash list | wc -l | tr -d ' ')"
latest_backup="$(find_latest_backup_branch_for_current || true)"
latest_snapshot="$(find_latest_snapshot_for_current || true)"
say "Repository: $(git rev-parse --show-toplevel)"
say "Current branch: $CURRENT_BRANCH"
say "Upstream remote: $REMOTE_NAME -> $REMOTE_URL"
say "Working tree:"
if ! worktree_has_local_changes; then
say " clean"
else
git status --short
fi
say "Stash entries: $stash_count"
say "Latest backup for current branch: ${latest_backup:-none}"
say "Latest snapshot for current branch: ${latest_snapshot:-none}"
if load_state; then
say "Saved import state: $STATE_STATUS"
say "Saved backup branch: ${STATE_BACKUP_BRANCH:-none}"
say "Saved starting commit: ${STATE_START_HEAD:-none}"
say "Saved exact snapshot: ${STATE_SNAPSHOT_PATH:-none}"
say "Saved original stash: ${STATE_STASH_HASH:-none}"
say "Saved import commits: ${STATE_IMPORT_COMMITS:-none}"
else
say "Saved import state: none"
fi
}
run_fetch_only() {
ensure_git_repo
ensure_no_git_operation_in_progress
ensure_current_branch
ensure_upstream_remote
fetch_upstream
say "Latest changes fetched from $REMOTE_NAME/$BRANCH."
}
run_list() {
ensure_git_repo
ensure_no_git_operation_in_progress
ensure_current_branch
ensure_upstream_remote
fetch_upstream
show_available_commits
}
run_backup_only() {
ensure_git_repo
ensure_no_git_operation_in_progress
ensure_current_branch
ensure_upstream_remote
BACKUP_BRANCH="$(create_backup_branch_for_reason "manual-backup")"
say "Safety backup branch created: $BACKUP_BRANCH"
}
run_import_commits() {
local requested_commits=("$@") commit resolved_commit
local -a selected_commits=()
[ "${#requested_commits[@]}" -gt 0 ] || die "Provide at least one upstream commit to import."
ensure_git_repo
ensure_no_git_operation_in_progress
ensure_current_branch
ensure_upstream_remote
fetch_upstream
for commit in "${requested_commits[@]}"; do
resolved_commit="$(resolve_import_commit "$commit")"
validate_importable_commit "$resolved_commit"
selected_commits+=("$resolved_commit")
done
STATE_IMPORT_COMMITS="${selected_commits[*]}"
prepare_safety_before_real_action "before-cherry-pick-import"
stash_current_changes "pre-cherry-pick-import"
STATE_STATUS="prepared"
update_state
for commit in "${selected_commits[@]}"; do
say "Cherry-picking upstream commit: $(git show --no-patch --format='%h %s' "$commit")"
if ! git cherry-pick -x "$commit"; then
STATE_STATUS="cherry_pick_conflict"
update_state
say "Cherry-pick stopped because of conflicts."
say "Conflicting upstream commit: $(git show --no-patch --format='%h %s' CHERRY_PICK_HEAD)"
say "Resolve conflicts and continue with: ./.import-upstream-cherry-pick.sh continue"
say "Or return safely with: ./.import-upstream-cherry-pick.sh rollback"
exit 1
fi
done
restore_stash 1
say "Imported ${#selected_commits[@]} upstream commit(s) by cherry-pick."
say "Safety backup branch available at: $BACKUP_BRANCH"
say "Safety snapshot available at: $STATE_SNAPSHOT_PATH"
if [ -n "$STATE_STASH_HASH" ]; then
say "Original pre-import stash retained for rollback at: $STATE_STASH_HASH"
fi
}
run_import_range() {
local from_commit="${1:-}" to_commit="${2:-}" from_resolved to_resolved commit
local -a selected_commits=()
[ -n "$from_commit" ] || die "Provide the start commit for import-range."
[ -n "$to_commit" ] || die "Provide the end commit for import-range."
ensure_git_repo
ensure_no_git_operation_in_progress
ensure_current_branch
ensure_upstream_remote
fetch_upstream
from_resolved="$(resolve_import_commit "$from_commit")"
to_resolved="$(resolve_import_commit "$to_commit")"
git merge-base --is-ancestor "$from_resolved" "$REMOTE_NAME/$BRANCH" || die "Start commit '$from_commit' is not reachable from $REMOTE_NAME/$BRANCH."
git merge-base --is-ancestor "$to_resolved" "$REMOTE_NAME/$BRANCH" || die "End commit '$to_commit' is not reachable from $REMOTE_NAME/$BRANCH."
git merge-base --is-ancestor "$from_resolved" "$to_resolved" || die "Start commit '$from_commit' must be an ancestor of end commit '$to_commit' on $REMOTE_NAME/$BRANCH."
while IFS= read -r commit; do
[ -n "$commit" ] || continue
if commit_is_available_for_import "$commit"; then
selected_commits+=("$commit")
fi
done < <(git rev-list --reverse "${from_resolved}^..${to_resolved}")
[ "${#selected_commits[@]}" -gt 0 ] || die "No importable commits were found in the requested range."
run_import_commits "${selected_commits[@]}"
}
run_continue() {
ensure_git_repo
ensure_current_branch_with_state_fallback
ensure_upstream_remote
load_state || die "No saved cherry-pick state was found."
[ "$CURRENT_BRANCH" = "${STATE_BRANCH:-$CURRENT_BRANCH}" ] || die "Saved cherry-pick state belongs to branch '$STATE_BRANCH'. Check out that branch first."
has_cherry_pick_in_progress || die "There is no in-progress cherry-pick to continue."
say "Continuing cherry-pick..."
GIT_EDITOR=: git cherry-pick --continue
if has_cherry_pick_in_progress; then
STATE_STATUS="cherry_pick_conflict"
update_state
say "Cherry-pick hit another conflict."
say "Current conflicting upstream commit: $(git show --no-patch --format='%h %s' CHERRY_PICK_HEAD)"
say "Resolve conflicts and run: ./.import-upstream-cherry-pick.sh continue"
say "Or return safely with: ./.import-upstream-cherry-pick.sh rollback"
exit 1
fi
STASH_HASH="${STATE_STASH_HASH:-}"
STASH_REF=""
BACKUP_BRANCH="${STATE_BACKUP_BRANCH:-}"
restore_stash 1
say "Cherry-pick import completed."
}
run_restore_saved_stash() {
ensure_git_repo
ensure_no_git_operation_in_progress
ensure_current_branch_with_state_fallback
load_state || die "No saved import state was found."
[ "$CURRENT_BRANCH" = "${STATE_BRANCH:-$CURRENT_BRANCH}" ] || die "Saved import state belongs to branch '$STATE_BRANCH'. Check out that branch first."
[ -n "${STATE_STASH_HASH:-}" ] || die "There is no saved pre-import stash to restore."
if worktree_has_local_changes; then
die "The working tree is not clean. Commit, stash, or discard current changes before restoring the saved stash."
fi
prepare_safety_before_real_action "before-restore-stash"
STASH_HASH="$STATE_STASH_HASH"
STASH_REF=""
restore_stash 1
say "Saved pre-import local changes restored."
}
run_rollback() {
local explicit_target="${1:-}" reset_target="" reset_snapshot=""
local original_restore_stash_hash="" original_restore_start_head=""
local rollback_safety_snapshot="" rollback_safety_backup="" rollback_safety_start_head=""
local preserve_stash_hash=""
ensure_git_repo
ensure_no_noncherrypick_git_operation_in_progress
load_state || true
ensure_current_branch_with_state_fallback
ensure_upstream_remote
if [ -n "$explicit_target" ] && is_valid_snapshot_dir "$explicit_target"; then
reset_snapshot="$explicit_target"
elif [ -n "$explicit_target" ]; then
git show-ref --verify --quiet "refs/heads/$explicit_target" || die "Backup branch '$explicit_target' does not exist."
reset_target="$explicit_target"
else
if [ -n "${STATE_BRANCH:-}" ] && [ "$CURRENT_BRANCH" != "$STATE_BRANCH" ]; then
die "Saved import state belongs to branch '$STATE_BRANCH'. Check out that branch or pass an explicit backup branch or snapshot."
fi
if [ -n "${STATE_SNAPSHOT_PATH:-}" ] && is_valid_snapshot_dir "$STATE_SNAPSHOT_PATH"; then
reset_snapshot="$STATE_SNAPSHOT_PATH"
fi
if [ -n "${STATE_START_HEAD:-}" ]; then
reset_target="$STATE_START_HEAD"
elif [ -n "${STATE_BACKUP_BRANCH:-}" ]; then
reset_target="$STATE_BACKUP_BRANCH"
else
reset_target="$(find_latest_backup_branch_for_current || true)"
fi
fi
if [ -z "$reset_target" ] && [ -n "$reset_snapshot" ]; then
reset_target="$(snapshot_metadata_value "$reset_snapshot" head || true)"
fi
[ -n "$reset_target" ] || [ -n "$reset_snapshot" ] || die "No saved rollback target was found."
original_restore_stash_hash="${STATE_STASH_HASH:-}"
original_restore_start_head="${STATE_START_HEAD:-}"
if [ -z "$original_restore_start_head" ] && [ -n "$reset_snapshot" ]; then
original_restore_start_head="$(snapshot_metadata_value "$reset_snapshot" head || true)"
fi
if has_cherry_pick_in_progress; then
say "Aborting in-progress cherry-pick before rollback..."
git cherry-pick --abort || die "Failed to abort the in-progress cherry-pick."
fi
if [ -n "$(git diff --name-only --diff-filter=U)" ]; then
die "There are still unmerged files in the working tree. Resolve or discard them before rollback."
fi
prepare_safety_before_real_action "before-rollback"
rollback_safety_backup="$BACKUP_BRANCH"
rollback_safety_snapshot="$STATE_SNAPSHOT_PATH"
rollback_safety_start_head="$STATE_START_HEAD"
preserve_stash_hash=""
if worktree_has_local_changes; then
stash_current_changes "pre-rollback-preserve"
preserve_stash_hash="$STASH_HASH"
fi
if [ -n "$reset_target" ]; then
say "Resetting '$CURRENT_BRANCH' to '$reset_target'..."
git reset --hard "$reset_target" >/dev/null
fi
if [ -n "$original_restore_stash_hash" ]; then
STASH_HASH="$original_restore_stash_hash"
STASH_REF=""
BACKUP_BRANCH="$rollback_safety_backup"
say "Restoring original pre-import local changes..."
restore_stash 1
fi
if [ -n "$reset_snapshot" ]; then
say "Restoring exact worktree snapshot from: $reset_snapshot"
restore_worktree_snapshot "$reset_snapshot"
fi
STATE_BRANCH="$CURRENT_BRANCH"
STATE_BACKUP_BRANCH="$rollback_safety_backup"
STATE_STASH_HASH="$preserve_stash_hash"
STATE_REMOTE_NAME="$REMOTE_NAME"
STATE_REMOTE_URL="$REMOTE_URL"
STATE_TARGET_BRANCH="$BRANCH"
STATE_START_HEAD="$rollback_safety_start_head"
STATE_SNAPSHOT_PATH="$rollback_safety_snapshot"
STATE_IMPORT_COMMITS=""
STATE_STATUS="rollback_completed"
write_state
say "Rollback completed."
say "Restored starting commit: ${original_restore_start_head:-$reset_target}"
if [ -n "$reset_snapshot" ]; then
say "Restored snapshot: $reset_snapshot"
fi
say "Safety backup of the pre-rollback state kept at: $rollback_safety_backup"
say "Safety snapshot of the pre-rollback state kept at: $rollback_safety_snapshot"
if [ -n "$preserve_stash_hash" ]; then
say "Safety stash of the pre-rollback local changes kept at: $preserve_stash_hash"
fi
}
run_restore_snapshot() {
local target_snapshot="${1:-}" restore_safety_backup="" restore_safety_snapshot=""
local restore_safety_start_head="" restore_start_head="" preserve_stash_hash=""
ensure_git_repo
ensure_no_noncherrypick_git_operation_in_progress
load_state || die "No saved import state was found."
ensure_current_branch_with_state_fallback
ensure_upstream_remote
if [ -z "$target_snapshot" ]; then
target_snapshot="${STATE_SNAPSHOT_PATH:-}"
fi
is_valid_snapshot_dir "$target_snapshot" || die "No valid saved snapshot was found to restore."
restore_start_head="${STATE_START_HEAD:-}"
if [ -z "$restore_start_head" ]; then
restore_start_head="$(snapshot_metadata_value "$target_snapshot" head || true)"
fi
[ -n "$restore_start_head" ] || die "No saved starting commit was found for the snapshot restore."
if has_cherry_pick_in_progress; then
say "Aborting in-progress cherry-pick before snapshot restore..."
git cherry-pick --abort || die "Failed to abort the in-progress cherry-pick."
fi
if [ -n "$(git diff --name-only --diff-filter=U)" ]; then
die "There are still unmerged files in the working tree. Resolve or discard them before restoring the snapshot."
fi
prepare_safety_before_real_action "before-restore-snapshot"
restore_safety_backup="$BACKUP_BRANCH"
restore_safety_snapshot="$STATE_SNAPSHOT_PATH"
restore_safety_start_head="$STATE_START_HEAD"
if worktree_has_local_changes; then
stash_current_changes "pre-restore-snapshot-preserve"
preserve_stash_hash="$STASH_HASH"
fi
say "Resetting '$CURRENT_BRANCH' to '$restore_start_head' before snapshot restore..."
git reset --hard "$restore_start_head" >/dev/null
if [ -n "${STATE_STASH_HASH:-}" ]; then
STASH_HASH="$STATE_STASH_HASH"
STASH_REF=""
BACKUP_BRANCH="$restore_safety_backup"
say "Restoring saved pre-import local changes..."
restore_stash 1
fi
say "Restoring exact worktree snapshot from: $target_snapshot"
restore_worktree_snapshot "$target_snapshot"
STATE_BRANCH="$CURRENT_BRANCH"
STATE_BACKUP_BRANCH="$restore_safety_backup"
STATE_STASH_HASH="$preserve_stash_hash"
STATE_REMOTE_NAME="$REMOTE_NAME"
STATE_REMOTE_URL="$REMOTE_URL"
STATE_TARGET_BRANCH="$BRANCH"
STATE_START_HEAD="$restore_safety_start_head"
STATE_SNAPSHOT_PATH="$restore_safety_snapshot"
STATE_IMPORT_COMMITS=""
STATE_STATUS="snapshot_restored"
write_state
say "Snapshot restore completed."
say "Safety backup of the pre-restore state kept at: $restore_safety_backup"
say "Safety snapshot of the pre-restore state kept at: $restore_safety_snapshot"
if [ -n "$preserve_stash_hash" ]; then
say "Safety stash of the pre-restore local changes kept at: $preserve_stash_hash"
fi
}
show_menu() {
local choice import_commits range_from range_to snapshot_target rollback_target
while true; do
cat <<EOF
Available actions:
1) Fetch upstream only
2) List available upstream commits
3) Import selected commit(s)
4) Import an inclusive commit range
5) Continue in-progress cherry-pick
6) Rollback last import
7) Restore saved stash
8) Restore exact snapshot
9) Create backup branch only
10) Show repository status
11) Help
0) Exit
EOF
printf 'Choose an action: '
read -r choice
case "$choice" in
1) run_fetch_only ;;
2) run_list ;;
3)
printf 'Enter upstream commit hash(es), separated by spaces: '
read -r -a import_commits
run_import_commits "${import_commits[@]}"
return
;;
4)
printf 'Enter the start commit hash: '
read -r range_from
printf 'Enter the end commit hash: '
read -r range_to
run_import_range "$range_from" "$range_to"
return
;;
5)
run_continue
return
;;
6)
printf 'Optional backup branch or snapshot path (leave empty for saved state): '
read -r rollback_target
run_rollback "$rollback_target"
return
;;
7)
run_restore_saved_stash
return
;;
8)
printf 'Optional snapshot path (leave empty for saved state): '
read -r snapshot_target
run_restore_snapshot "$snapshot_target"
return
;;
9) run_backup_only ;;
10) run_status ;;
11) show_usage ;;
0) exit 0 ;;
*) say "Invalid menu selection: $choice" ;;
esac
done
}
main() {
case "${1:-menu}" in
fetch) run_fetch_only ;;
list) run_list ;;
import)
shift
run_import_commits "$@"
;;
import-range) run_import_range "${2:-}" "${3:-}" ;;
continue) run_continue ;;
backup) run_backup_only ;;
rollback) run_rollback "${2:-}" ;;
restore-stash) run_restore_saved_stash ;;
restore-snapshot) run_restore_snapshot "${2:-}" ;;
status) run_status ;;
help|-h|--help) show_usage ;;
menu)
if [ -t 0 ] && [ -t 1 ]; then
show_menu
else
show_usage
fi
;;
*)
die "Unknown command: $1. Run with 'help' to see available options."
;;
esac
}
main "$@"
+2440
View File
File diff suppressed because it is too large Load Diff
+435
View File
@@ -0,0 +1,435 @@
#!/bin/bash
# Folosește instalarea Go standard dacă există, chiar dacă nu este în PATH.
if [ -x "/usr/local/go/bin/go" ]; then
export PATH="/usr/local/go/bin:$PATH"
fi
# Încarcă NVM dacă este disponibil
export NVM_DIR="$HOME/.nvm"
[ -s "$NVM_DIR/nvm.sh" ] && \. "$NVM_DIR/nvm.sh"
# Forțează folosirea versiunii 22
nvm use 22 > /dev/null 2>&1 || echo "⚠️ NVM nu a putut activa Node 22 automatically."
resolve_build_ref() {
git describe --tags --exact-match 2>/dev/null || git describe --tags --always
}
require_docker_for_darwin_sqlite() {
if ! command -v docker > /dev/null 2>&1; then
echo "❌ Docker is required for macOS SQLite cross-builds."
echo " Install the Docker CLI in this environment, or use the non-SQLite macOS build option."
echo " If you are running inside a code-server container, also mount the host Docker socket."
exit 1
fi
if ! docker info > /dev/null 2>&1; then
echo "❌ Docker is installed but the daemon is not reachable."
echo " Start Docker, or expose the host Docker daemon to this container."
echo " For a code-server container, mount /var/run/docker.sock from the host."
if [ -n "${DOCKER_HOST:-}" ]; then
echo " Current DOCKER_HOST: ${DOCKER_HOST}"
else
echo " Current DOCKER_HOST is unset."
fi
exit 1
fi
}
resolve_xgo_image() {
local xgo_version
xgo_version="$(awk '$1 == "XGO_VERSION" { print $3; exit }' Makefile 2>/dev/null)"
if [ -z "$xgo_version" ]; then
xgo_version="go-1.25.x"
fi
printf 'ghcr.io/techknowlogick/xgo:%s' "$xgo_version"
}
resolve_darwin_sqlite_repo_root() {
local override_path
override_path="${SMART_BUILD_DARWIN_HOST_REPO_PATH:-}"
if [ -z "$override_path" ]; then
pwd -P
return
fi
if [ ! -d "$override_path" ] || [ ! -f "$override_path/go.mod" ]; then
echo "❌ SMART_BUILD_DARWIN_HOST_REPO_PATH is set, but the path is not usable in this container:"
echo " $override_path"
echo " Mount the host repository path into the container at the same absolute path, then retry."
exit 1
fi
printf '%s' "$override_path"
}
validate_repo_bind_mount_for_darwin_sqlite() {
local repo_path="$1"
local xgo_image
xgo_image="$(resolve_xgo_image)"
if ! docker run --rm -v "$repo_path":/probe:ro --entrypoint sh "$xgo_image" -lc 'test -f /probe/go.mod'; then
echo "❌ Docker can reach the daemon, but the daemon cannot mount this repository path correctly:"
echo " $repo_path"
echo " The xgo container only sees an empty or different host path, so /source/go.mod is missing there."
echo " If smart-build runs inside a code-server container with the host Docker socket,"
echo " the repository must be mounted from a host bind path that exists at the same absolute path."
exit 1
fi
}
write_sha256_file() {
local artifact_path="$1"
local artifact_dir artifact_name
artifact_dir="$(dirname "$artifact_path")"
artifact_name="$(basename "$artifact_path")"
if command -v sha256sum > /dev/null 2>&1; then
(
cd "$artifact_dir" || exit 1
sha256sum "$artifact_name" > "$artifact_name.sha256"
)
return
fi
if command -v shasum > /dev/null 2>&1; then
(
cd "$artifact_dir" || exit 1
shasum -a 256 "$artifact_name" > "$artifact_name.sha256"
)
return
fi
echo "❌ Neither sha256sum nor shasum is available for checksum generation."
exit 1
}
# --- 1. VERIFICARE INTEGRITATE ȘI CURĂȚARE CACHE INIȚIALĂ ---
echo "🔍 Initialization checks..."
if ! command -v go > /dev/null 2>&1; then
echo "❌ Go nu este disponibil în PATH. Instalează Go 1.26.2 sau adaugă binarul go în PATH."
exit 1
fi
notify_human_interaction() {
local bell_oga="/usr/share/sounds/freedesktop/stereo/bell.oga"
local bell_wav="/usr/share/sounds/alsa/Front_Center.wav"
local in_vscode_terminal=0
local notification_sent=0
if [ "${TERM_PROGRAM:-}" = "vscode" ] || [ -n "${VSCODE_IPC_HOOK_CLI:-}" ] || [ -n "${VSCODE_GIT_IPC_HANDLE:-}" ]; then
in_vscode_terminal=1
fi
if command -v notify-send > /dev/null 2>&1; then
notify-send "Gitea smart-build" "Human input required in smart-build.sh" > /dev/null 2>&1 && notification_sent=1
fi
if command -v canberra-gtk-play > /dev/null 2>&1; then
canberra-gtk-play -i bell > /dev/null 2>&1 && return
fi
if [ -f "$bell_oga" ] && command -v paplay > /dev/null 2>&1; then
paplay "$bell_oga" > /dev/null 2>&1 && return
fi
if [ -f "$bell_wav" ] && command -v aplay > /dev/null 2>&1; then
aplay -q "$bell_wav" > /dev/null 2>&1 && return
fi
if [ -f "$bell_wav" ] && command -v play > /dev/null 2>&1; then
play -q "$bell_wav" > /dev/null 2>&1 && return
fi
if [ -t 1 ]; then
printf '\a'
fi
if [ "$notification_sent" -eq 0 ] && [ "$in_vscode_terminal" -eq 1 ]; then
printf '\033[1;33m%s\033[0m\n' ">>> Human input required below <<<"
fi
}
apply_moderate_build_limits() {
local go_procs="$1"
local node_memory="$2"
export GOMAXPROCS="$go_procs"
export MAKEFLAGS="-j1"
if [[ "$NODE_OPTIONS" != *"--max-old-space-size="* ]]; then
export NODE_OPTIONS="${NODE_OPTIONS:+$NODE_OPTIONS }--max-old-space-size=$node_memory"
fi
}
echo ""
echo "⚙️ Select Build Load Profile:"
echo " Normal keeps the default build behavior."
echo " Moderate limits parallel jobs and keeps CPU/RAM usage lower."
echo " Low Resource is slower, but safest for weaker machines."
notify_human_interaction
load_options=("Normal" "Moderate (GOMAXPROCS=2, make -j1)" "Low Resource (GOMAXPROCS=1, make -j1)" "Quit")
select opt in "${load_options[@]}"
do
case $opt in
"Normal")
echo "✅ Selected: Normal build profile."
break
;;
"Moderate (GOMAXPROCS=2, make -j1)")
apply_moderate_build_limits 2 2048
echo "✅ Selected: Moderate build profile."
echo " GOMAXPROCS=$GOMAXPROCS MAKEFLAGS=\"$MAKEFLAGS\" NODE_OPTIONS=\"$NODE_OPTIONS\""
break
;;
"Low Resource (GOMAXPROCS=1, make -j1)")
apply_moderate_build_limits 1 2048
echo "✅ Selected: Low Resource build profile."
echo " GOMAXPROCS=$GOMAXPROCS MAKEFLAGS=\"$MAKEFLAGS\" NODE_OPTIONS=\"$NODE_OPTIONS\""
break
;;
"Quit")
exit 0
;;
*) echo "Opțiune invalidă $REPLY";;
esac
done
# Dacă compilarea anterioară a fost întreruptă, ștergem binarul parțial
if [ -f "gitea" ] || [ -f "gitea.exe" ]; then
echo "🧹 Garbages found. Cleanning..."
rm -f gitea gitea.exe
fi
# Verificăm dacă node_modules există. Dacă nu, forțăm pnpm install
if [ ! -d "node_modules" ]; then
echo "⚠️ node_modules missing. Instaling..."
if ! pnpm install --frozen-lockfile; then
echo "❌ Fail to install frontend dependencies."
exit 1
fi
fi
# --- 2. LOGICĂ FRONTEND (CHECKSUM) ---
CHECKSUM_FILE=".frontend.hash"
CURRENT_HASH=$(find web_src package.json tailwind.config.js -type f -print0 2>/dev/null | xargs -0 sha1sum | sha1sum | awk '{print $1}')
if [ -f "$CHECKSUM_FILE" ] && [ "$CURRENT_HASH" == "$(cat $CHECKSUM_FILE)" ]; then
echo "✅ Frontend is unchanged."
else
echo "🚀 Code changes detected. Running frontend build..."
if ! make frontend; then
echo "❌ Fail to build frontend assets."
exit 1
fi
echo "$CURRENT_HASH" > "$CHECKSUM_FILE"
fi
# --- 3. MENIU INTERACTIV PENTRU ARHITECTURĂ ---
echo ""
echo "🎯 Select Arch to build:"
notify_human_interaction
arch_options=("linux-amd64" "linux-armv7" "windows-amd64" "macos-amd64" "macos-arm64" "All Arch" "Quit")
select opt in "${arch_options[@]}"
do
case $opt in
"linux-amd64")
TARGETS=("linux/amd64")
break
;;
"linux-armv7")
TARGETS=("linux/arm/7")
break
;;
"windows-amd64")
TARGETS=("windows/amd64")
break
;;
"macos-amd64")
TARGETS=("darwin/amd64")
break
;;
"macos-arm64")
TARGETS=("darwin/arm64")
break
;;
"All Arch")
TARGETS=("linux/amd64" "linux/arm/7" "windows/amd64" "darwin/amd64" "darwin/arm64")
break
;;
"Quit")
exit 0
;;
*) echo "Opțiune invalidă $REPLY";;
esac
done
echo ""
echo "🏷️ Select Build Tags:"
notify_human_interaction
tag_options=("bindata" "bindata sqlite sqlite_unlock_notify" "Quit")
select opt in "${tag_options[@]}"
do
case $opt in
"bindata")
BUILD_TAGS="bindata"
break
;;
"bindata sqlite sqlite_unlock_notify")
BUILD_TAGS="bindata sqlite sqlite_unlock_notify"
BUILD_VARIANT="sqlite"
break
;;
"Quit")
exit 0
;;
*) echo "Opțiune invalidă $REPLY";;
esac
done
if [ -z "$BUILD_VARIANT" ]; then
BUILD_VARIANT="default"
fi
BUILD_REF="$(resolve_build_ref)"
BUILD_REF="${BUILD_REF//\//-}"
echo "🏷️ Build tag/reference: $BUILD_REF"
bindata_needs_update() {
local source_dir="$1"
local bindata_file="$2"
if [ ! -f "$bindata_file" ]; then
return 0
fi
find "$source_dir" -type f -newer "$bindata_file" -print -quit 2>/dev/null | grep -q .
}
ensure_bindata_asset() {
local label="$1"
local source_dir="$2"
local go_package="$3"
local bindata_file="$4"
if bindata_needs_update "$source_dir" "$bindata_file"; then
echo "♻️ Regenerating $label bindata..."
if ! CC= GOOS= GOARCH= CGO_ENABLED=0 go generate -tags bindata "$go_package"; then
echo "❌ Failed to regenerate $label bindata."
exit 1
fi
else
echo "$label bindata is up to date."
fi
}
ensure_bindata_assets() {
if [[ " $BUILD_TAGS " != *" bindata "* ]]; then
return
fi
echo "🔎 Checking embedded bindata assets..."
ensure_bindata_asset "templates" "templates" "./modules/templates" "modules/templates/bindata.dat"
ensure_bindata_asset "options" "options" "./modules/options" "modules/options/bindata.dat"
ensure_bindata_asset "public" "public" "./modules/public" "modules/public/bindata.dat"
ensure_bindata_asset "migration schemas" "modules/migration/schemas" "./modules/migration" "modules/migration/bindata.dat"
}
ensure_bindata_assets
build_darwin_sqlite_target() {
local arch="$1"
local output="$2"
local repo_root temp_dist built_file output_abs
local built_files=()
require_docker_for_darwin_sqlite
repo_root="$(resolve_darwin_sqlite_repo_root)"
validate_repo_bind_mount_for_darwin_sqlite "$repo_root"
output_abs="$(pwd -P)/$output"
temp_dist="$repo_root/dist/.smart-build-darwin-${arch}-$$"
rm -rf "$temp_dist"
if ! mkdir -p "$temp_dist"; then
echo "❌ Failed to create a temporary macOS release directory in dist/."
exit 1
fi
echo "📦 Building for darwin/$arch with TAGS=\"$BUILD_TAGS\" via release-darwin..."
if ! make -C "$repo_root" release-darwin TAGS="$BUILD_TAGS" DARWIN_ARCHS="darwin-10.12/$arch" DIST="$temp_dist"; then
rm -rf "$temp_dist"
echo "❌ Fail to build for darwin/$arch with SQLite"
exit 1
fi
mapfile -t built_files < <(find "$temp_dist/binaries" -maxdepth 1 -type f | sort)
if [ "${#built_files[@]}" -ne 1 ]; then
rm -rf "$temp_dist"
echo "❌ Unexpected macOS artifact count for darwin/$arch: ${#built_files[@]}"
exit 1
fi
built_file="${built_files[0]}"
mv "$built_file" "$output_abs"
rm -rf "$temp_dist"
write_sha256_file "$output_abs"
echo "✅ Created: $output_abs"
echo "✅ Created: $output_abs.sha256"
}
build_standard_target() {
local os="$1"
local arch="$2"
local arm_ver="$3"
local output="$4"
local ext="$5"
export GOOS=$os
export GOARCH=$arch
export GOARM=$arm_ver
export CGO_ENABLED=0
if [ "$BUILD_VARIANT" == "sqlite" ]; then
export CGO_ENABLED=1
fi
if make build TAGS="$BUILD_TAGS"; then
mv "gitea$ext" "$output"
write_sha256_file "$output"
echo "✅ Created: $output"
echo "✅ Created: $output.sha256"
else
echo "❌ Fail to build for $os/$arch${arm_ver:+/v$arm_ver}"
exit 1
fi
}
# --- 4. COMPILARE ---
mkdir -p dist
for TARGET in "${TARGETS[@]}"; do
IFS="/" read -r OS ARCH ARM_VER <<< "$TARGET"
EXT="" && [ "$OS" == "windows" ] && EXT=".exe"
PLATFORM="$ARCH" && [ ! -z "$ARM_VER" ] && PLATFORM="armv$ARM_VER"
VARIANT_SUFFIX="" && [ "$BUILD_VARIANT" == "sqlite" ] && VARIANT_SUFFIX="-sqlite"
OUTPUT="dist/gitea-$BUILD_REF-$OS-$PLATFORM$VARIANT_SUFFIX$EXT"
if [ "$OS" == "darwin" ] && [ "$BUILD_VARIANT" == "sqlite" ]; then
build_darwin_sqlite_target "$ARCH" "$OUTPUT"
else
echo "📦 Building for $OS/$ARCH ${ARM_VER:+(v$ARM_VER) }with TAGS=\"$BUILD_TAGS\"..."
build_standard_target "$OS" "$ARCH" "$ARM_VER" "$OUTPUT" "$EXT"
fi
unset GOOS GOARCH GOARM CGO_ENABLED
done
echo "✨ Buid finished. Get file(s) from /dist"
go clean -cache # || true
+1091
View File
File diff suppressed because it is too large Load Diff
+25
View File
@@ -1,3 +1,5 @@
## Core Repository Rules
- Use `make help` to find available development targets
- Run `make fmt` to format `.go` files, and run `make lint-go` to lint them
- Run `make lint-js` to lint `.ts` files
@@ -9,3 +11,26 @@
- In TypeScript, use `!` (non-null assertion) instead of `?.`/`??` when a value is known to always exist
- Include authorship attribution in issue and pull request comments
- Add `Co-Authored-By` lines to all commits, indicating name and model used
## Execution Rules (Token Optimization)
- DO NOT read full files unless they are explicitly targeted with `@filename`, referenced from instruction `*.md` files, or required to complete the user's task.
- Assume the workspace structure described in `./.codex-context.md` and `./.codex-project-map.md` is the current baseline unless the user indicates otherwise.
- DO NOT read `./.codex-history.md` end-to-end by default; search by keyword, subsystem, tag, or read only the latest relevant entries first.
## Project Context
- Read and follow `./.codex-context.md` as the persistent repository context before starting work and when validating final changes.
- Use `./.codex-project-map.md` for the persistent structural and architectural map of the repository.
## Routing Rules for Tasks (Multi-Model Delegation)
Apply these routing preferences when the environment supports model selection. If the preferred model is unavailable, use the closest available model and note the fallback.
Priority for mixed tasks:
Architecture & Orchestration > Go & Database Coding > Frontend & Template Tasks > DevOps & Terminal Execution
1. Architecture & Orchestration Tasks: Prefer `gpt-5.4` (Reasoning: High/Extra High). Use for complex requirement breakdown, solution design, and validation of large structural updates.
2. Go & Database Coding Tasks: Prefer `gpt-5.3-codex` (Reasoning: Medium). This includes writing HTTP handlers, database queries, internal Go business logic, and server-side integration work.
3. Frontend & Template Tasks: Prefer `gpt-5.3-codex` (Reasoning: Medium). This includes `templates/`, `web_src/`, CSS, and TypeScript changes.
4. DevOps & Terminal Commands: Prefer `gpt-5.4-mini` (Reasoning: Low). Use for `pnpm`, `git`, `go mod`, `npm`, `make`, or `bash` execution flows and shell-oriented maintenance tasks.
+4496 -4496
View File
File diff suppressed because it is too large Load Diff
+5205 -4766
View File
File diff suppressed because it is too large Load Diff
+3 -2
View File
@@ -95,7 +95,7 @@ else
ifneq ($(STORED_VERSION),)
GITEA_VERSION ?= $(STORED_VERSION)
else
GITEA_VERSION ?= $(shell git describe --tags --always | sed 's/-/+/' | sed 's/^v//')
GITEA_VERSION ?= $(shell git describe --tags --always | sed -E 's/^v//; s/^(.*)-([0-9]+-g[0-9a-f]+)$$/\1+\2/')
endif
endif
@@ -107,6 +107,7 @@ endif
LDFLAGS := $(LDFLAGS) -X "main.Version=$(GITEA_VERSION)" -X "main.Tags=$(TAGS)"
LINUX_ARCHS ?= linux/amd64,linux/386,linux/arm-5,linux/arm-6,linux/arm64,linux/riscv64
DARWIN_ARCHS ?= darwin-10.12/amd64,darwin-10.12/arm64
GO_TEST_PACKAGES ?= $(filter-out $(shell $(GO) list code.gitea.io/gitea/models/migrations/...) code.gitea.io/gitea/tests/integration/migration-test code.gitea.io/gitea/tests code.gitea.io/gitea/tests/integration,$(shell $(GO) list ./... | grep -v /vendor/))
MIGRATE_TEST_PACKAGES ?= $(shell $(GO) list code.gitea.io/gitea/models/migrations/...)
@@ -685,7 +686,7 @@ release-linux: | $(DIST_DIRS)
.PHONY: release-darwin
release-darwin: | $(DIST_DIRS)
CGO_CFLAGS="$(CGO_CFLAGS)" $(GO) run $(XGO_PACKAGE) -go $(XGO_VERSION) -dest $(DIST)/binaries -tags 'netgo osusergo $(TAGS)' -ldflags '-s -w $(LDFLAGS)' -targets 'darwin-10.12/amd64,darwin-10.12/arm64' -out gitea-$(VERSION) .
CGO_CFLAGS="$(CGO_CFLAGS)" $(GO) run $(XGO_PACKAGE) -go $(XGO_VERSION) -dest $(DIST)/binaries -tags 'netgo osusergo $(TAGS)' -ldflags '-s -w $(LDFLAGS)' -targets '$(DARWIN_ARCHS)' -out gitea-$(VERSION) .
.PHONY: release-freebsd
release-freebsd: | $(DIST_DIRS)
+1
View File
@@ -19,6 +19,7 @@ import (
// regexp is based on go-license, excluding README and NOTICE
// https://github.com/google/go-licenses/blob/master/licenses/find.go
// also defined in vite.config.ts
var licenseRe = regexp.MustCompile(`^(?i)((UN)?LICEN(S|C)E|COPYING).*$`)
// primaryLicenseRe matches exact primary license filenames without suffixes.
+24 -4
View File
@@ -41,10 +41,10 @@
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;;
;; App name that shows in every page title
APP_NAME = ; Gitea: Git with a cup of tea
;APP_NAME = Gitea: Git with a cup of tea
;;
;; RUN_USER will automatically detect the current user - but you can set it here change it if you run locally
RUN_USER = ; git
;RUN_USER =
;;
;; Application run mode, affects performance and debugging: "dev" or "prod", default is "prod"
;; Mode "dev" makes Gitea easier to develop and debug, values other than "dev" are treated as "prod" which is for production use.
@@ -461,6 +461,11 @@ INTERNAL_TOKEN =
;; Name of cookie used to store authentication information.
;COOKIE_REMEMBER_NAME = gitea_incredible
;;
;; URL or path that Gitea should redirect users to *after* performing its own logout.
;; Use this, if needed, when authentication is handled by a reverse proxy or SSO.
;; For example: "/my-sso/logout?return=/my-sso/home"
;REVERSE_PROXY_LOGOUT_REDIRECT =
;;
;; Reverse proxy authentication header name of user name, email, and full name
;REVERSE_PROXY_AUTHENTICATION_USER = X-WEBAUTH-USER
;REVERSE_PROXY_AUTHENTICATION_EMAIL = X-WEBAUTH-EMAIL
@@ -778,6 +783,11 @@ LEVEL = Info
;; Disallow registration, only allow admins to create accounts.
;DISABLE_REGISTRATION = false
;;
;; When DISABLE_REGISTRATION is true, choose how administrator-created accounts are provisioned.
;; - local: create active local accounts immediately
;; - invite: create inactive accounts that require the emailed invitation link before sign-in is enabled
;ADMIN_CREATED_ACCOUNT_MODE = invite
;;
;; Allow registration only using gitea itself, it works only when DISABLE_REGISTRATION is false
;ALLOW_ONLY_INTERNAL_REGISTRATION = false
;;
@@ -1608,6 +1618,16 @@ LEVEL = Info
;;
;; Default configuration for email notifications for users (user configurable). Options: enabled, onmention, disabled
;DEFAULT_EMAIL_NOTIFICATIONS = enabled
;;
;; Enable the persistent Super Administrator role for protecting administrator management.
;SUPER_ADMIN_ENABLED = true
;;
;; Controls who can change administrator and super administrator permissions.
;; Options:
;; - super_admin_only: only super administrators can modify or delete administrator accounts and manage all administrator privilege changes.
;; - grantor_only: administrators can promote regular users to administrator and later manage only the administrator accounts they directly promoted.
;; - grantor_inheritance: like grantor_only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible administrator is found.
;ADMIN_MANAGEMENT_POLICY = grantor_only
;; Disabled features for users could be "deletion", "manage_ssh_keys", "manage_gpg_keys", "manage_mfa", "manage_credentials" more features can be disabled in future
;; - deletion: a user cannot delete their own account
;; - manage_ssh_keys: a user cannot configure ssh keys
@@ -2580,8 +2600,8 @@ LEVEL = Info
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; The first locale will be used as the default if user browser's language doesn't match any locale in the list.
;LANGS = en-US,zh-CN,zh-HK,zh-TW,de-DE,fr-FR,nl-NL,lv-LV,ru-RU,uk-UA,ja-JP,es-ES,pt-BR,pt-PT,pl-PL,bg-BG,it-IT,fi-FI,tr-TR,cs-CZ,sv-SE,ko-KR,el-GR,fa-IR,hu-HU,id-ID,ml-IN
;NAMES = English,简体中文,繁體中文(香港),繁體中文(台灣),Deutsch,Français,Nederlands,Latviešu,Русский,Українська,日本語,Español,Português do Brasil,Português de Portugal,Polski,Български,Italiano,Suomi,Türkçe,Čeština,Српски,Svenska,한국어,Ελληνικά,فارسی,Magyar nyelv,Bahasa Indonesia,മലയാളം
;LANGS = en-US,ro-RO,zh-CN,zh-HK,zh-TW,de-DE,fr-FR,nl-NL,lv-LV,ru-RU,uk-UA,ja-JP,es-ES,pt-BR,pt-PT,pl-PL,bg-BG,it-IT,fi-FI,tr-TR,cs-CZ,sv-SE,ko-KR,el-GR,fa-IR,hu-HU,id-ID,ml-IN
;NAMES = English,Română,简体中文,繁體中文(香港),繁體中文(台灣),Deutsch,Français,Nederlands,Latviešu,Русский,Українська,日本語,Español,Português do Brasil,Português de Portugal,Polski,Български,Italiano,Suomi,Türkçe,Čeština,Српски,Svenska,한국어,Ελληνικά,فارسی,Magyar nyelv,Bahasa Indonesia,മലയാളം
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
+1
View File
@@ -926,6 +926,7 @@ export default defineConfig([
{
...playwright.configs['flat/recommended'],
files: ['tests/e2e/**/*.test.ts'],
languageOptions: {globals: {...globals.nodeBuiltin, ...globals.browser}},
rules: {
...playwright.configs['flat/recommended'].rules,
'playwright/expect-expect': [0],
+4 -4
View File
@@ -1,6 +1,6 @@
module code.gitea.io/gitea
go 1.26.1
go 1.26.2
// rfc5280 said: "The serial number is an integer assigned by the CA to each certificate."
// But some CAs use negative serial number, just relax the check. related:
@@ -12,7 +12,7 @@ require (
code.gitea.io/sdk/gitea v0.24.1
codeberg.org/gusted/mcaptcha v0.0.0-20220723083913-4f3072e1d570
connectrpc.com/connect v1.19.1
gitea.com/go-chi/binding v0.0.0-20240430071103-39a851e106ed
gitea.com/go-chi/binding v0.0.0-20260414111559-654cea7ac60a
gitea.com/go-chi/cache v0.2.1
gitea.com/go-chi/captcha v0.0.0-20240315150714-fb487f629098
gitea.com/go-chi/session v0.0.0-20251124165456-68e0254e989e
@@ -52,12 +52,11 @@ require (
github.com/go-co-op/gocron/v2 v2.19.1
github.com/go-enry/go-enry/v2 v2.9.5
github.com/go-git/go-billy/v5 v5.8.0
github.com/go-git/go-git/v5 v5.17.2
github.com/go-git/go-git/v5 v5.18.0
github.com/go-ldap/ldap/v3 v3.4.13
github.com/go-redsync/redsync/v4 v4.16.0
github.com/go-sql-driver/mysql v1.9.3
github.com/go-webauthn/webauthn v0.16.1
github.com/goccy/go-json v0.10.6
github.com/gogs/chardet v0.0.0-20211120154057-b7413eaefb8f
github.com/gogs/go-gogs-client v0.0.0-20210131175652-1d7215cd8d85
github.com/golang-jwt/jwt/v5 v5.3.1
@@ -196,6 +195,7 @@ require (
github.com/go-ini/ini v1.67.0 // indirect
github.com/go-viper/mapstructure/v2 v2.5.0 // indirect
github.com/go-webauthn/x v0.2.2 // indirect
github.com/goccy/go-json v0.10.6 // indirect
github.com/golang-sql/civil v0.0.0-20220223132316-b832511892a9 // indirect
github.com/golang-sql/sqlexp v0.1.0 // indirect
github.com/golang/groupcache v0.0.0-20241129210726-2c02b8208cf8 // indirect
+4 -4
View File
@@ -18,8 +18,8 @@ filippo.io/edwards25519 v1.2.0 h1:crnVqOiS4jqYleHd9vaKZ+HKtHfllngJIiOpNpoJsjo=
filippo.io/edwards25519 v1.2.0/go.mod h1:xzAOLCNug/yB62zG1bQ8uziwrIqIuxhctzJT18Q77mc=
gitea.com/gitea/act v0.261.10 h1:ndwbtuMXXz1dpYF2iwY1/PkgKNETo4jmPXfinTZt8cs=
gitea.com/gitea/act v0.261.10/go.mod h1:oIkqQHvU0lfuIWwcpqa4FmU+t3prA89tgkuHUTsrI2c=
gitea.com/go-chi/binding v0.0.0-20240430071103-39a851e106ed h1:EZZBtilMLSZNWtHHcgq2mt6NSGhJSZBuduAlinMEmso=
gitea.com/go-chi/binding v0.0.0-20240430071103-39a851e106ed/go.mod h1:E3i3cgB04dDx0v3CytCgRTTn9Z/9x891aet3r456RVw=
gitea.com/go-chi/binding v0.0.0-20260414111559-654cea7ac60a h1:JHoBrfuTSF9Ke9aNfSYj1XRPBHjKPgCApVprnt2Am0M=
gitea.com/go-chi/binding v0.0.0-20260414111559-654cea7ac60a/go.mod h1:FOsLJIMdpiHzBp3Vby6Wfkdw2ppGscrjgU1IC7E4/zQ=
gitea.com/go-chi/cache v0.2.1 h1:bfAPkvXlbcZxPCpcmDVCWoHgiBSBmZN/QosnZvEC0+g=
gitea.com/go-chi/cache v0.2.1/go.mod h1:Qic0HZ8hOHW62ETGbonpwz8WYypj9NieU9659wFUJ8Q=
gitea.com/go-chi/captcha v0.0.0-20240315150714-fb487f629098 h1:p2ki+WK0cIeNQuqjR98IP2KZQKRzJJiV7aTeMAFwaWo=
@@ -304,8 +304,8 @@ github.com/go-git/go-billy/v5 v5.8.0 h1:I8hjc3LbBlXTtVuFNJuwYuMiHvQJDq1AT6u4DwDz
github.com/go-git/go-billy/v5 v5.8.0/go.mod h1:RpvI/rw4Vr5QA+Z60c6d6LXH0rYJo0uD5SqfmrrheCY=
github.com/go-git/go-git-fixtures/v4 v4.3.2-0.20231010084843-55a94097c399 h1:eMje31YglSBqCdIqdhKBW8lokaMrL3uTkpGYlE2OOT4=
github.com/go-git/go-git-fixtures/v4 v4.3.2-0.20231010084843-55a94097c399/go.mod h1:1OCfN199q1Jm3HZlxleg+Dw/mwps2Wbk9frAWm+4FII=
github.com/go-git/go-git/v5 v5.17.2 h1:B+nkdlxdYrvyFK4GPXVU8w1U+YkbsgciIR7f2sZJ104=
github.com/go-git/go-git/v5 v5.17.2/go.mod h1:pW/VmeqkanRFqR6AljLcs7EA7FbZaN5MQqO7oZADXpo=
github.com/go-git/go-git/v5 v5.18.0 h1:O831KI+0PR51hM2kep6T8k+w0/LIAD490gvqMCvL5hM=
github.com/go-git/go-git/v5 v5.18.0/go.mod h1:pW/VmeqkanRFqR6AljLcs7EA7FbZaN5MQqO7oZADXpo=
github.com/go-ini/ini v1.67.0 h1:z6ZrTEZqSWOTyH2FlglNbNgARyHG8oLW9gMELqKr06A=
github.com/go-ini/ini v1.67.0/go.mod h1:ByCAeIL28uOIIG0E3PJtZPDL8WnHpFKFOtgjp+3Ies8=
github.com/go-jose/go-jose/v4 v4.1.3 h1:CVLmWDhDVRa6Mi/IgCgaopNosCaHz7zrMeF9MlZRkrs=
+7 -1
View File
@@ -15,6 +15,7 @@ import (
"code.gitea.io/gitea/models/perm"
user_model "code.gitea.io/gitea/models/user"
"code.gitea.io/gitea/modules/log"
"code.gitea.io/gitea/modules/setting"
"code.gitea.io/gitea/modules/timeutil"
"code.gitea.io/gitea/modules/util"
@@ -64,7 +65,12 @@ func (key *PublicKey) AfterLoad() {
// OmitEmail returns content of public key without email address.
func (key *PublicKey) OmitEmail() string {
return strings.Join(strings.Split(key.Content, " ")[:2], " ")
fields := strings.Split(key.Content, " ") // format: ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQC... comment
if len(fields) < 2 {
setting.PanicInDevOrTesting("invalid public key %d content: %s", key.ID, key.Content)
return "" // not a valid public key, it shouldn't really happen, the value is managed internally
}
return strings.Join(fields[:2], " ")
}
func addKey(ctx context.Context, key *PublicKey) (err error) {
+1 -1
View File
@@ -633,7 +633,7 @@ func GetActiveOAuth2SourceByAuthName(ctx context.Context, name string) (*Source,
}
if !has {
return nil, fmt.Errorf("oauth2 source not found, name: %q", name)
return nil, util.NewNotExistErrorf("oauth2 source not found, name: %q", name)
}
return authSource, nil
+1 -1
View File
@@ -89,7 +89,7 @@
ref: "refs/heads/test"
commit_sha: "c2d72f548424103f01ee1dc02889c1e2bff816b0"
event: "push"
trigger_event: "push"
trigger_event: "schedule"
is_fork_pull_request: 0
status: 1
started: 1683636528
+6 -1
View File
@@ -877,7 +877,12 @@ func ParseCodeOwnersLine(ctx context.Context, tokens []string) (*CodeOwnerRule,
warnings := make([]string, 0)
expr := fmt.Sprintf("^%s$", strings.TrimPrefix(tokens[0], "!"))
// Strip leading "!" for negative rules, then strip leading "/" since
// git returns relative paths (e.g. "docs/foo.md" not "/docs/foo.md")
// and the regex is already anchored with ^...$, so the "/" is redundant.
pattern := strings.TrimPrefix(tokens[0], "!")
pattern = strings.TrimPrefix(pattern, "/")
expr := fmt.Sprintf("^%s$", pattern)
rule.Rule, err = regexp2.Compile(expr, regexp2.None)
if err != nil {
warnings = append(warnings, fmt.Sprintf("incorrect codeowner regexp: %s", err))
+83 -49
View File
@@ -17,16 +17,43 @@ import (
"github.com/stretchr/testify/require"
)
func TestPullRequest_LoadAttributes(t *testing.T) {
func TestPullRequest(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
t.Run("LoadAttributes", testPullRequestLoadAttributes)
t.Run("LoadIssue", testPullRequestLoadIssue)
t.Run("LoadBaseRepo", testPullRequestLoadBaseRepo)
t.Run("LoadHeadRepo", testPullRequestLoadHeadRepo)
t.Run("PullRequestsNewest", testPullRequestsNewest)
t.Run("PullRequestsOldest", testPullRequestsOldest)
t.Run("GetUnmergedPullRequest", testGetUnmergedPullRequest)
t.Run("HasUnmergedPullRequestsByHeadInfo", testHasUnmergedPullRequestsByHeadInfo)
t.Run("GetUnmergedPullRequestsByHeadInfo", testGetUnmergedPullRequestsByHeadInfo)
t.Run("GetUnmergedPullRequestsByBaseInfo", testGetUnmergedPullRequestsByBaseInfo)
t.Run("GetPullRequestByIndex", testGetPullRequestByIndex)
t.Run("GetPullRequestByID", testGetPullRequestByID)
t.Run("GetPullRequestByIssueID", testGetPullRequestByIssueID)
t.Run("PullRequest_UpdateCols", testPullRequestUpdateCols)
t.Run("PullRequest_IsWorkInProgress", testPullRequestIsWorkInProgress)
t.Run("PullRequest_GetWorkInProgressPrefixWorkInProgress", testPullRequestGetWorkInProgressPrefixWorkInProgress)
t.Run("DeleteOrphanedObjects", testDeleteOrphanedObjects)
t.Run("ParseCodeOwnersLine", testParseCodeOwnersLine)
t.Run("CodeOwnerAbsolutePathPatterns", testCodeOwnerAbsolutePathPatterns)
t.Run("GetApprovers", testGetApprovers)
t.Run("GetPullRequestByMergedCommit", testGetPullRequestByMergedCommit)
t.Run("Migrate_InsertPullRequests", testMigrateInsertPullRequests)
t.Run("PullRequestsClosedRecentSortType", testPullRequestsClosedRecentSortType)
t.Run("LoadRequestedReviewers", testLoadRequestedReviewers)
}
func testPullRequestLoadAttributes(t *testing.T) {
pr := unittest.AssertExistsAndLoadBean(t, &issues_model.PullRequest{ID: 1})
assert.NoError(t, pr.LoadAttributes(t.Context()))
assert.NotNil(t, pr.Merger)
assert.Equal(t, pr.MergerID, pr.Merger.ID)
}
func TestPullRequest_LoadIssue(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testPullRequestLoadIssue(t *testing.T) {
pr := unittest.AssertExistsAndLoadBean(t, &issues_model.PullRequest{ID: 1})
assert.NoError(t, pr.LoadIssue(t.Context()))
assert.NotNil(t, pr.Issue)
@@ -36,8 +63,7 @@ func TestPullRequest_LoadIssue(t *testing.T) {
assert.Equal(t, int64(2), pr.Issue.ID)
}
func TestPullRequest_LoadBaseRepo(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testPullRequestLoadBaseRepo(t *testing.T) {
pr := unittest.AssertExistsAndLoadBean(t, &issues_model.PullRequest{ID: 1})
assert.NoError(t, pr.LoadBaseRepo(t.Context()))
assert.NotNil(t, pr.BaseRepo)
@@ -47,8 +73,7 @@ func TestPullRequest_LoadBaseRepo(t *testing.T) {
assert.Equal(t, pr.BaseRepoID, pr.BaseRepo.ID)
}
func TestPullRequest_LoadHeadRepo(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testPullRequestLoadHeadRepo(t *testing.T) {
pr := unittest.AssertExistsAndLoadBean(t, &issues_model.PullRequest{ID: 1})
assert.NoError(t, pr.LoadHeadRepo(t.Context()))
assert.NotNil(t, pr.HeadRepo)
@@ -59,8 +84,7 @@ func TestPullRequest_LoadHeadRepo(t *testing.T) {
// TODO TestNewPullRequest
func TestPullRequestsNewest(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testPullRequestsNewest(t *testing.T) {
prs, count, err := issues_model.PullRequests(t.Context(), 1, &issues_model.PullRequestsOptions{
ListOptions: db.ListOptions{
Page: 1,
@@ -77,7 +101,7 @@ func TestPullRequestsNewest(t *testing.T) {
}
}
func TestPullRequests_Closed_RecentSortType(t *testing.T) {
func testPullRequestsClosedRecentSortType(t *testing.T) {
// Issue ID | Closed At. | Updated At
// 2 | 1707270001 | 1707270001
// 3 | 1707271000 | 1707279999
@@ -90,7 +114,6 @@ func TestPullRequests_Closed_RecentSortType(t *testing.T) {
{"recentclose", []int64{11, 3, 2}},
}
assert.NoError(t, unittest.PrepareTestDatabase())
_, err := db.Exec(t.Context(), "UPDATE issue SET closed_unix = 1707270001, updated_unix = 1707270001, is_closed = true WHERE id = 2")
require.NoError(t, err)
_, err = db.Exec(t.Context(), "UPDATE issue SET closed_unix = 1707271000, updated_unix = 1707279999, is_closed = true WHERE id = 3")
@@ -118,9 +141,7 @@ func TestPullRequests_Closed_RecentSortType(t *testing.T) {
}
}
func TestLoadRequestedReviewers(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testLoadRequestedReviewers(t *testing.T) {
pull := unittest.AssertExistsAndLoadBean(t, &issues_model.PullRequest{ID: 2})
assert.NoError(t, pull.LoadIssue(t.Context()))
issue := pull.Issue
@@ -146,8 +167,7 @@ func TestLoadRequestedReviewers(t *testing.T) {
assert.Empty(t, pull.RequestedReviewers)
}
func TestPullRequestsOldest(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testPullRequestsOldest(t *testing.T) {
prs, count, err := issues_model.PullRequests(t.Context(), 1, &issues_model.PullRequestsOptions{
ListOptions: db.ListOptions{
Page: 1,
@@ -164,8 +184,7 @@ func TestPullRequestsOldest(t *testing.T) {
}
}
func TestGetUnmergedPullRequest(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testGetUnmergedPullRequest(t *testing.T) {
pr, err := issues_model.GetUnmergedPullRequest(t.Context(), 1, 1, "branch2", "master", issues_model.PullRequestFlowGithub)
assert.NoError(t, err)
assert.Equal(t, int64(2), pr.ID)
@@ -175,9 +194,7 @@ func TestGetUnmergedPullRequest(t *testing.T) {
assert.True(t, issues_model.IsErrPullRequestNotExist(err))
}
func TestHasUnmergedPullRequestsByHeadInfo(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testHasUnmergedPullRequestsByHeadInfo(t *testing.T) {
exist, err := issues_model.HasUnmergedPullRequestsByHeadInfo(t.Context(), 1, "branch2")
assert.NoError(t, err)
assert.True(t, exist)
@@ -187,8 +204,7 @@ func TestHasUnmergedPullRequestsByHeadInfo(t *testing.T) {
assert.False(t, exist)
}
func TestGetUnmergedPullRequestsByHeadInfo(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testGetUnmergedPullRequestsByHeadInfo(t *testing.T) {
prs, err := issues_model.GetUnmergedPullRequestsByHeadInfo(t.Context(), 1, "branch2")
assert.NoError(t, err)
assert.Len(t, prs, 1)
@@ -198,8 +214,7 @@ func TestGetUnmergedPullRequestsByHeadInfo(t *testing.T) {
}
}
func TestGetUnmergedPullRequestsByBaseInfo(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testGetUnmergedPullRequestsByBaseInfo(t *testing.T) {
prs, err := issues_model.GetUnmergedPullRequestsByBaseInfo(t.Context(), 1, "master")
assert.NoError(t, err)
assert.Len(t, prs, 1)
@@ -209,8 +224,7 @@ func TestGetUnmergedPullRequestsByBaseInfo(t *testing.T) {
assert.Equal(t, "master", pr.BaseBranch)
}
func TestGetPullRequestByIndex(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testGetPullRequestByIndex(t *testing.T) {
pr, err := issues_model.GetPullRequestByIndex(t.Context(), 1, 2)
assert.NoError(t, err)
assert.Equal(t, int64(1), pr.BaseRepoID)
@@ -225,8 +239,7 @@ func TestGetPullRequestByIndex(t *testing.T) {
assert.True(t, issues_model.IsErrPullRequestNotExist(err))
}
func TestGetPullRequestByID(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testGetPullRequestByID(t *testing.T) {
pr, err := issues_model.GetPullRequestByID(t.Context(), 1)
assert.NoError(t, err)
assert.Equal(t, int64(1), pr.ID)
@@ -237,8 +250,7 @@ func TestGetPullRequestByID(t *testing.T) {
assert.True(t, issues_model.IsErrPullRequestNotExist(err))
}
func TestGetPullRequestByIssueID(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testGetPullRequestByIssueID(t *testing.T) {
pr, err := issues_model.GetPullRequestByIssueID(t.Context(), 2)
assert.NoError(t, err)
assert.Equal(t, int64(2), pr.IssueID)
@@ -248,8 +260,7 @@ func TestGetPullRequestByIssueID(t *testing.T) {
assert.True(t, issues_model.IsErrPullRequestNotExist(err))
}
func TestPullRequest_UpdateCols(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testPullRequestUpdateCols(t *testing.T) {
pr := &issues_model.PullRequest{
ID: 1,
BaseBranch: "baseBranch",
@@ -265,9 +276,7 @@ func TestPullRequest_UpdateCols(t *testing.T) {
// TODO TestAddTestPullRequestTask
func TestPullRequest_IsWorkInProgress(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testPullRequestIsWorkInProgress(t *testing.T) {
pr := unittest.AssertExistsAndLoadBean(t, &issues_model.PullRequest{ID: 2})
pr.LoadIssue(t.Context())
@@ -280,9 +289,7 @@ func TestPullRequest_IsWorkInProgress(t *testing.T) {
assert.True(t, pr.IsWorkInProgress(t.Context()))
}
func TestPullRequest_GetWorkInProgressPrefixWorkInProgress(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testPullRequestGetWorkInProgressPrefixWorkInProgress(t *testing.T) {
pr := unittest.AssertExistsAndLoadBean(t, &issues_model.PullRequest{ID: 2})
pr.LoadIssue(t.Context())
@@ -296,9 +303,7 @@ func TestPullRequest_GetWorkInProgressPrefixWorkInProgress(t *testing.T) {
assert.Equal(t, "[wip]", pr.GetWorkInProgressPrefix(t.Context()))
}
func TestDeleteOrphanedObjects(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testDeleteOrphanedObjects(t *testing.T) {
countBefore, err := db.GetEngine(t.Context()).Count(&issues_model.PullRequest{})
assert.NoError(t, err)
@@ -317,7 +322,7 @@ func TestDeleteOrphanedObjects(t *testing.T) {
assert.Equal(t, countBefore, countAfter)
}
func TestParseCodeOwnersLine(t *testing.T) {
func testParseCodeOwnersLine(t *testing.T) {
type CodeOwnerTest struct {
Line string
Tokens []string
@@ -331,6 +336,8 @@ func TestParseCodeOwnersLine(t *testing.T) {
{Line: `docs/(aws|google|azure)/[^/]*\\.(md|txt) @org3 @org2/team2`, Tokens: []string{`docs/(aws|google|azure)/[^/]*\.(md|txt)`, "@org3", "@org2/team2"}},
{Line: `\#path @org3`, Tokens: []string{`#path`, "@org3"}},
{Line: `path\ with\ spaces/ @org3`, Tokens: []string{`path with spaces/`, "@org3"}},
{Line: `/docs/.*\\.md @user1`, Tokens: []string{`/docs/.*\.md`, "@user1"}},
{Line: `!/assets/.*\\.(bin|exe|msi) @user1`, Tokens: []string{`!/assets/.*\.(bin|exe|msi)`, "@user1"}},
}
for _, g := range given {
@@ -339,8 +346,37 @@ func TestParseCodeOwnersLine(t *testing.T) {
}
}
func TestGetApprovers(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testCodeOwnerAbsolutePathPatterns(t *testing.T) {
type testCase struct {
content string
file string
expected bool
}
cases := []testCase{
// Absolute path pattern should match (leading "/" stripped)
{content: "/README.md @user5\n", file: "README.md", expected: true},
// Absolute path pattern in subdirectory
{content: "/docs/.* @user5\n", file: "docs/foo.md", expected: true},
// Absolute path should not match nested paths it shouldn't
{content: "/docs/.* @user5\n", file: "other/docs/foo.md", expected: false},
// Relative path still works
{content: "README.md @user5\n", file: "README.md", expected: true},
// Negated absolute path pattern
{content: "!/.* @user5\n", file: "README.md", expected: false},
}
for _, c := range cases {
rules, _ := issues_model.GetCodeOwnersFromContent(t.Context(), c.content)
require.NotEmpty(t, rules)
rule := rules[0]
regexpMatched, _ := rule.Rule.MatchString(c.file)
ruleMatched := regexpMatched == !rule.Negative
assert.Equal(t, c.expected, ruleMatched, "pattern %q against file %q", c.content, c.file)
}
}
func testGetApprovers(t *testing.T) {
pr := unittest.AssertExistsAndLoadBean(t, &issues_model.PullRequest{ID: 5})
// Official reviews are already deduplicated. Allow unofficial reviews
// to assert that there are no duplicated approvers.
@@ -350,8 +386,7 @@ func TestGetApprovers(t *testing.T) {
assert.Equal(t, expected, approvers)
}
func TestGetPullRequestByMergedCommit(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testGetPullRequestByMergedCommit(t *testing.T) {
pr, err := issues_model.GetPullRequestByMergedCommit(t.Context(), 1, "1a8823cd1a9549fde083f992f6b9b87a7ab74fb3")
assert.NoError(t, err)
assert.EqualValues(t, 1, pr.ID)
@@ -362,8 +397,7 @@ func TestGetPullRequestByMergedCommit(t *testing.T) {
assert.ErrorAs(t, err, &issues_model.ErrPullRequestNotExist{})
}
func TestMigrate_InsertPullRequests(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testMigrateInsertPullRequests(t *testing.T) {
reponame := "repo1"
repo := unittest.AssertExistsAndLoadBean(t, &repo_model.Repository{Name: reponame})
owner := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: repo.OwnerID})
-46
View File
@@ -8,10 +8,7 @@ import (
"fmt"
"code.gitea.io/gitea/models/db"
"code.gitea.io/gitea/models/perm"
"code.gitea.io/gitea/models/unit"
user_model "code.gitea.io/gitea/models/user"
"code.gitea.io/gitea/modules/container"
"code.gitea.io/gitea/modules/log"
"xorm.io/builder"
@@ -129,49 +126,6 @@ func IsUserOrgOwner(ctx context.Context, users user_model.UserList, orgID int64)
return results
}
// GetOrgAssignees returns all users that have write access and can be assigned to issues
// of the any repository in the organization.
func GetOrgAssignees(ctx context.Context, orgID int64) (_ []*user_model.User, err error) {
e := db.GetEngine(ctx)
userIDs := make([]int64, 0, 10)
if err = e.Table("access").
Join("INNER", "repository", "`repository`.id = `access`.repo_id").
Where("`repository`.owner_id = ? AND `access`.mode >= ?", orgID, perm.AccessModeWrite).
Select("user_id").
Find(&userIDs); err != nil {
return nil, err
}
additionalUserIDs := make([]int64, 0, 10)
if err = e.Table("team_user").
Join("INNER", "team_repo", "`team_repo`.team_id = `team_user`.team_id").
Join("INNER", "team_unit", "`team_unit`.team_id = `team_user`.team_id").
Join("INNER", "repository", "`repository`.id = `team_repo`.repo_id").
Where("`repository`.owner_id = ? AND (`team_unit`.access_mode >= ? OR (`team_unit`.access_mode = ? AND `team_unit`.`type` = ?))",
orgID, perm.AccessModeWrite, perm.AccessModeRead, unit.TypePullRequests).
Distinct("`team_user`.uid").
Select("`team_user`.uid").
Find(&additionalUserIDs); err != nil {
return nil, err
}
uniqueUserIDs := make(container.Set[int64])
uniqueUserIDs.AddMultiple(userIDs...)
uniqueUserIDs.AddMultiple(additionalUserIDs...)
users := make([]*user_model.User, 0, len(uniqueUserIDs))
if len(userIDs) > 0 {
if err = e.In("id", uniqueUserIDs.Values()).
Where(builder.Eq{"`user`.is_active": true}).
OrderBy(user_model.GetOrderByName()).
Find(&users); err != nil {
return nil, err
}
}
return users, nil
}
func loadOrganizationOwners(ctx context.Context, users user_model.UserList, orgID int64) (map[int64]*TeamUser, error) {
if len(users) == 0 {
return nil, nil //nolint:nilnil // return nil when there are no users
+2 -2
View File
@@ -52,13 +52,13 @@ func InsertProperty(ctx context.Context, refType PropertyType, refID int64, name
// GetProperties gets all properties
func GetProperties(ctx context.Context, refType PropertyType, refID int64) ([]*PackageProperty, error) {
pps := make([]*PackageProperty, 0, 10)
return pps, db.GetEngine(ctx).Where("ref_type = ? AND ref_id = ?", refType, refID).Find(&pps)
return pps, db.GetEngine(ctx).Where("ref_type = ? AND ref_id = ?", refType, refID).OrderBy("id").Find(&pps)
}
// GetPropertiesByName gets all properties with a specific name
func GetPropertiesByName(ctx context.Context, refType PropertyType, refID int64, name string) ([]*PackageProperty, error) {
pps := make([]*PackageProperty, 0, 10)
return pps, db.GetEngine(ctx).Where("ref_type = ? AND ref_id = ? AND name = ?", refType, refID, name).Find(&pps)
return pps, db.GetEngine(ctx).Where("ref_type = ? AND ref_id = ? AND name = ?", refType, refID, name).OrderBy("id").Find(&pps)
}
// UpdateProperty updates a property
+6 -2
View File
@@ -50,8 +50,8 @@ type RepoFileOptions struct {
DeprecatedRepoName string // it is only a patch for the non-standard "markup" api
DeprecatedOwnerName string // it is only a patch for the non-standard "markup" api
CurrentRefPath string // eg: "branch/main"
CurrentTreePath string // eg: "path/to/file" in the repo
CurrentRefPath string // eg: "branch/main", it is a sub URL path escaped by callers, TODO: rename to CurrentRefSubURL
CurrentTreePath string // eg: "path/to/file" in the repo, it is the tree path without URL path escaping
}
func NewRenderContextRepoFile(ctx context.Context, repo *repo_model.Repository, opts ...RepoFileOptions) *markup.RenderContext {
@@ -70,6 +70,10 @@ func NewRenderContextRepoFile(ctx context.Context, repo *repo_model.Repository,
"repo": helper.opts.DeprecatedRepoName,
})
}
// External render's iframe needs this to generate correct links
// TODO: maybe need to make it access "CurrentRefPath" directly (but impossible at the moment due to cycle-import)
// CurrentRefPath is already path-escaped by callers
rctx.RenderOptions.Metas["RefTypeNameSubURL"] = helper.opts.CurrentRefPath
rctx = rctx.WithHelper(helper).WithEnableHeadingIDGeneration(true)
return rctx
}
+5 -11
View File
@@ -8,6 +8,7 @@ import (
"strings"
"code.gitea.io/gitea/models/db"
"code.gitea.io/gitea/models/organization"
"code.gitea.io/gitea/models/perm"
"code.gitea.io/gitea/models/unit"
user_model "code.gitea.io/gitea/models/user"
@@ -94,8 +95,7 @@ func GetWatchedRepos(ctx context.Context, opts *WatchedReposOptions) ([]*Reposit
return db.FindAndCount[Repository](ctx, opts)
}
// GetRepoAssignees returns all users that have write access and can be assigned to issues
// of the repository,
// GetRepoAssignees returns all users that have write access and can be assigned to issues or pull-requests of the repository,
func GetRepoAssignees(ctx context.Context, repo *Repository) (_ []*user_model.User, err error) {
if err = repo.LoadOwner(ctx); err != nil {
return nil, err
@@ -114,15 +114,9 @@ func GetRepoAssignees(ctx context.Context, repo *Repository) (_ []*user_model.Us
uniqueUserIDs.AddMultiple(userIDs...)
if repo.Owner.IsOrganization() {
additionalUserIDs := make([]int64, 0, 10)
if err = e.Table("team_user").
Join("INNER", "team_repo", "`team_repo`.team_id = `team_user`.team_id").
Join("INNER", "team_unit", "`team_unit`.team_id = `team_user`.team_id").
Where("`team_repo`.repo_id = ? AND (`team_unit`.access_mode >= ? OR (`team_unit`.access_mode = ? AND `team_unit`.`type` = ?))",
repo.ID, perm.AccessModeWrite, perm.AccessModeRead, unit.TypePullRequests).
Distinct("`team_user`.uid").
Select("`team_user`.uid").
Find(&additionalUserIDs); err != nil {
// issues and pull requests both need "assignee list"
additionalUserIDs, err := organization.GetTeamUserIDsWithAccessToAnyRepoUnit(ctx, repo.OwnerID, repo.ID, perm.AccessModeRead, unit.TypeIssues, unit.TypePullRequests)
if err != nil {
return nil, err
}
uniqueUserIDs.AddMultiple(additionalUserIDs...)
+34 -4
View File
@@ -6,7 +6,12 @@ package repo_test
import (
"testing"
"code.gitea.io/gitea/models/db"
"code.gitea.io/gitea/models/organization"
perm_model "code.gitea.io/gitea/models/perm"
access_model "code.gitea.io/gitea/models/perm/access"
repo_model "code.gitea.io/gitea/models/repo"
"code.gitea.io/gitea/models/unit"
"code.gitea.io/gitea/models/unittest"
user_model "code.gitea.io/gitea/models/user"
@@ -14,9 +19,14 @@ import (
"github.com/stretchr/testify/require"
)
func TestRepoAssignees(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func TestUserRepo(t *testing.T) {
require.NoError(t, unittest.PrepareTestDatabase())
t.Run("GetIssuePostersWithSearch", testUserRepoGetIssuePostersWithSearch)
t.Run("Assignees", testUserRepoAssignees)
t.Run("AssigneesNoTeamUnit", testRepoAssigneesNoTeamUnit)
}
func testUserRepoAssignees(t *testing.T) {
repo2 := unittest.AssertExistsAndLoadBean(t, &repo_model.Repository{ID: 2})
users, err := repo_model.GetRepoAssignees(t.Context(), repo2)
assert.NoError(t, err)
@@ -39,9 +49,29 @@ func TestRepoAssignees(t *testing.T) {
}
}
func TestGetIssuePostersWithSearch(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
func testRepoAssigneesNoTeamUnit(t *testing.T) {
ctx := t.Context()
repo := unittest.AssertExistsAndLoadBean(t, &repo_model.Repository{ID: 32})
require.NoError(t, repo.LoadOwner(ctx))
require.True(t, repo.Owner.IsOrganization())
require.NoError(t, db.TruncateBeans(ctx, &organization.Team{}, &organization.TeamUser{}, &organization.TeamRepo{}, &organization.TeamUnit{}, &access_model.Access{}))
user := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: 4})
team := &organization.Team{OrgID: repo.OwnerID, LowerName: "admin-team", AccessMode: perm_model.AccessModeAdmin}
require.NoError(t, db.Insert(ctx, team))
require.NoError(t, db.Insert(ctx, &organization.TeamUser{OrgID: repo.OwnerID, TeamID: team.ID, UID: user.ID}))
require.NoError(t, db.Insert(ctx, &organization.TeamRepo{OrgID: repo.OwnerID, TeamID: team.ID, RepoID: repo.ID}))
require.NoError(t, db.Insert(ctx, &organization.TeamUnit{OrgID: repo.OwnerID, TeamID: team.ID, Type: unit.TypePullRequests, AccessMode: perm_model.AccessModeNone}))
users, err := repo_model.GetRepoAssignees(ctx, repo)
require.NoError(t, err)
require.Len(t, users, 1)
assert.ElementsMatch(t, []int64{4}, []int64{users[0].ID})
}
func testUserRepoGetIssuePostersWithSearch(t *testing.T) {
repo2 := unittest.AssertExistsAndLoadBean(t, &repo_model.Repository{ID: 2})
users, err := repo_model.GetIssuePostersWithSearch(t.Context(), repo2, false, "USER")
+535
View File
@@ -0,0 +1,535 @@
// Copyright 2026 The Gitea Authors. All rights reserved.
// SPDX-License-Identifier: MIT
package user
import (
"context"
"encoding/hex"
"fmt"
"strconv"
"strings"
"time"
"code.gitea.io/gitea/models/db"
"code.gitea.io/gitea/modules/base"
"code.gitea.io/gitea/modules/optional"
"xorm.io/builder"
)
const (
SettingsKeyAccountRequestStatus = "account_request.status"
SettingsKeyAccountRequestExpiresUnix = "account_request.expires_unix"
SettingsKeyAccountRequestSignupAttempts = "account_request.signup_attempts"
SettingsKeyAccountRequestEmailValidatedUnix = "account_request.email_validated_unix"
SettingsKeyAccountRequestReviewedUnix = "account_request.reviewed_unix"
SettingsKeyAccountRequestReviewedBy = "account_request.reviewed_by"
SettingsKeyAccountRequestValidationMailStatus = "account_request.validation_mail_status"
SettingsKeyAccountRequestValidationMailUnix = "account_request.validation_mail_unix"
SettingsKeyAccountRequestValidationResendHits = "account_request.validation_resend_hits"
SettingsKeyAccountRequestValidationCodeHash = "account_request.validation_code_hash"
SettingsKeyActivationMailStatus = "activation.mail_status"
SettingsKeyActivationMailUnix = "activation.mail_unix"
SettingsKeyActivationResendHits = "activation.resend_hits"
SettingsKeyAdminInvitePending = "admin_invite.pending"
SettingsKeyAdminInviteMailStatus = "admin_invite.mail_status"
SettingsKeyAdminInviteMailUnix = "admin_invite.mail_unix"
SettingsKeyAdminInviteResendHits = "admin_invite.resend_hits"
AccountRequestStatusPendingEmailValidation = "pending_email_validation"
AccountRequestStatusPendingAdminReview = "pending_admin_review"
AccountRequestStatusRejected = "rejected"
AccountRequestStatusBlocked = "blocked"
AccountRequestValidationHours = 48
AccountRequestMaxAttempts = 5
AccountRequestMaxResendHits = 5
ActivationMaxResendHits = 5
AdminInviteMaxResendHits = 5
AccountRequestValidationMailStatusSucceeded = "succeeded"
AccountRequestValidationMailStatusFailed = "failed"
)
func GetAccountRequestStatus(ctx context.Context, user *User) (string, error) {
status, err := GetUserSetting(ctx, user.ID, SettingsKeyAccountRequestStatus)
if err != nil || status != "" {
return status, err
}
hasValidationState, err := HasAccountRequestValidationState(ctx, user)
if err != nil || !hasValidationState {
return "", err
}
return AccountRequestStatusPendingEmailValidation, nil
}
func SetAccountRequestStatus(ctx context.Context, userID int64, status string) error {
if status == "" {
return DeleteUserSetting(ctx, userID, SettingsKeyAccountRequestStatus)
}
return SetUserSetting(ctx, userID, SettingsKeyAccountRequestStatus, status)
}
func HasAccountRequestValidationState(ctx context.Context, user *User) (bool, error) {
if user == nil || user.IsActive {
return false, nil
}
for _, key := range []string{
SettingsKeyAccountRequestStatus,
SettingsKeyAccountRequestExpiresUnix,
SettingsKeyAccountRequestValidationMailStatus,
SettingsKeyAccountRequestValidationCodeHash,
} {
value, err := GetUserSetting(ctx, user.ID, key)
if err != nil || value != "" {
return value != "", err
}
}
return false, nil
}
func getAccountRequestInt64(ctx context.Context, userID int64, key string) (int64, error) {
value, err := GetUserSetting(ctx, userID, key)
if err != nil || value == "" {
return 0, err
}
return strconv.ParseInt(value, 10, 64)
}
func setAccountRequestInt64(ctx context.Context, userID int64, key string, value int64) error {
if value == 0 {
return DeleteUserSetting(ctx, userID, key)
}
return SetUserSetting(ctx, userID, key, strconv.FormatInt(value, 10))
}
func GetAccountRequestExpiry(ctx context.Context, user *User) (time.Time, error) {
unix, err := getAccountRequestInt64(ctx, user.ID, SettingsKeyAccountRequestExpiresUnix)
if err != nil || unix == 0 {
return time.Time{}, err
}
return time.Unix(unix, 0), nil
}
func RefreshAccountRequestValidationWindow(ctx context.Context, user *User) error {
return setAccountRequestInt64(ctx, user.ID, SettingsKeyAccountRequestExpiresUnix, time.Now().Add(AccountRequestValidationHours*time.Hour).Unix())
}
func GetAccountRequestSignupAttempts(ctx context.Context, user *User) (int, error) {
value, err := getAccountRequestInt64(ctx, user.ID, SettingsKeyAccountRequestSignupAttempts)
return int(value), err
}
func SetAccountRequestSignupAttempts(ctx context.Context, userID int64, attempts int) error {
return setAccountRequestInt64(ctx, userID, SettingsKeyAccountRequestSignupAttempts, int64(attempts))
}
func GetAccountRequestValidationMailAttemptStatus(ctx context.Context, user *User) (string, error) {
return GetUserSetting(ctx, user.ID, SettingsKeyAccountRequestValidationMailStatus)
}
func GetAccountRequestValidationMailAttemptUnix(ctx context.Context, user *User) (int64, error) {
return getAccountRequestInt64(ctx, user.ID, SettingsKeyAccountRequestValidationMailUnix)
}
func GetAccountRequestValidationResendHits(ctx context.Context, user *User) (int, error) {
value, err := getAccountRequestInt64(ctx, user.ID, SettingsKeyAccountRequestValidationResendHits)
return int(value), err
}
func SetAccountRequestValidationResendHits(ctx context.Context, userID int64, hits int) error {
return setAccountRequestInt64(ctx, userID, SettingsKeyAccountRequestValidationResendHits, int64(hits))
}
func SetAccountRequestValidationCode(ctx context.Context, userID int64, code string) error {
if code == "" {
return DeleteUserSetting(ctx, userID, SettingsKeyAccountRequestValidationCodeHash)
}
return SetUserSetting(ctx, userID, SettingsKeyAccountRequestValidationCodeHash, base.EncodeSha256(code))
}
func IncrementAccountRequestValidationResendHits(ctx context.Context, user *User) (int, error) {
hits, err := GetAccountRequestValidationResendHits(ctx, user)
if err != nil {
return 0, err
}
hits++
if err := SetAccountRequestValidationResendHits(ctx, user.ID, hits); err != nil {
return 0, err
}
return hits, nil
}
func RecordAccountRequestValidationMailAttempt(ctx context.Context, userID int64, success bool) error {
status := AccountRequestValidationMailStatusFailed
if success {
status = AccountRequestValidationMailStatusSucceeded
}
if err := SetUserSetting(ctx, userID, SettingsKeyAccountRequestValidationMailStatus, status); err != nil {
return err
}
return setAccountRequestInt64(ctx, userID, SettingsKeyAccountRequestValidationMailUnix, time.Now().Unix())
}
func GetActivationMailAttemptStatus(ctx context.Context, user *User) (string, error) {
return GetUserSetting(ctx, user.ID, SettingsKeyActivationMailStatus)
}
func GetActivationMailAttemptUnix(ctx context.Context, user *User) (int64, error) {
return getAccountRequestInt64(ctx, user.ID, SettingsKeyActivationMailUnix)
}
func GetActivationResendHits(ctx context.Context, user *User) (int, error) {
value, err := getAccountRequestInt64(ctx, user.ID, SettingsKeyActivationResendHits)
return int(value), err
}
func SetActivationResendHits(ctx context.Context, userID int64, hits int) error {
return setAccountRequestInt64(ctx, userID, SettingsKeyActivationResendHits, int64(hits))
}
func IncrementActivationResendHits(ctx context.Context, user *User) (int, error) {
hits, err := GetActivationResendHits(ctx, user)
if err != nil {
return 0, err
}
hits++
if err := SetActivationResendHits(ctx, user.ID, hits); err != nil {
return 0, err
}
return hits, nil
}
func RecordActivationMailAttempt(ctx context.Context, userID int64, success bool) error {
status := AccountRequestValidationMailStatusFailed
if success {
status = AccountRequestValidationMailStatusSucceeded
}
if err := SetUserSetting(ctx, userID, SettingsKeyActivationMailStatus, status); err != nil {
return err
}
return setAccountRequestInt64(ctx, userID, SettingsKeyActivationMailUnix, time.Now().Unix())
}
func SetAdminInvitePending(ctx context.Context, userID int64, pending bool) error {
if !pending {
return DeleteUserSetting(ctx, userID, SettingsKeyAdminInvitePending)
}
return SetUserSetting(ctx, userID, SettingsKeyAdminInvitePending, "true")
}
func hasStoredAdminInviteCreator(ctx context.Context, userID int64) (bool, error) {
for _, key := range []string{
SettingsKeyAdminInviteCreatedBy,
SettingsKeyAdminInviteCreatedByName,
SettingsKeyAdminInviteCreatedByEmail,
} {
value, err := GetUserSetting(ctx, userID, key)
if err == nil && value != "" {
return true, nil
}
if err != nil && !IsErrUserSettingIsNotExist(err) {
return false, err
}
}
return false, nil
}
func IsPendingAdminInvite(ctx context.Context, user *User) (bool, error) {
if user == nil || user.IsActive {
return false, nil
}
pending, err := GetUserSetting(ctx, user.ID, SettingsKeyAdminInvitePending)
if err == nil && pending == "true" {
return true, nil
}
if err != nil && !IsErrUserSettingIsNotExist(err) {
return false, err
}
if !user.ProhibitLogin {
return false, nil
}
return hasStoredAdminInviteCreator(ctx, user.ID)
}
func GetAdminInviteMailAttemptStatus(ctx context.Context, user *User) (string, error) {
return GetUserSetting(ctx, user.ID, SettingsKeyAdminInviteMailStatus)
}
func GetAdminInviteMailAttemptUnix(ctx context.Context, user *User) (int64, error) {
return getAccountRequestInt64(ctx, user.ID, SettingsKeyAdminInviteMailUnix)
}
func GetAdminInviteResendHits(ctx context.Context, user *User) (int, error) {
value, err := getAccountRequestInt64(ctx, user.ID, SettingsKeyAdminInviteResendHits)
return int(value), err
}
func SetAdminInviteResendHits(ctx context.Context, userID int64, hits int) error {
return setAccountRequestInt64(ctx, userID, SettingsKeyAdminInviteResendHits, int64(hits))
}
func IncrementAdminInviteResendHits(ctx context.Context, user *User) (int, error) {
hits, err := GetAdminInviteResendHits(ctx, user)
if err != nil {
return 0, err
}
hits++
if err := SetAdminInviteResendHits(ctx, user.ID, hits); err != nil {
return 0, err
}
return hits, nil
}
func RecordAdminInviteMailAttempt(ctx context.Context, userID int64, success bool) error {
status := AccountRequestValidationMailStatusFailed
if success {
status = AccountRequestValidationMailStatusSucceeded
}
if err := SetUserSetting(ctx, userID, SettingsKeyAdminInviteMailStatus, status); err != nil {
return err
}
return setAccountRequestInt64(ctx, userID, SettingsKeyAdminInviteMailUnix, time.Now().Unix())
}
func ClearAdminInviteState(ctx context.Context, userID int64) error {
for _, key := range []string{
SettingsKeyAdminInvitePending,
SettingsKeyAdminInviteMailStatus,
SettingsKeyAdminInviteMailUnix,
SettingsKeyAdminInviteResendHits,
} {
if err := DeleteUserSetting(ctx, userID, key); err != nil {
return err
}
}
return nil
}
func ClearActivationResendState(ctx context.Context, userID int64) error {
for _, key := range []string{
SettingsKeyActivationMailStatus,
SettingsKeyActivationMailUnix,
SettingsKeyActivationResendHits,
} {
if err := DeleteUserSetting(ctx, userID, key); err != nil {
return err
}
}
return nil
}
func IsAccountRequestExpired(ctx context.Context, user *User) (bool, error) {
status, err := GetAccountRequestStatus(ctx, user)
if err != nil || status != AccountRequestStatusPendingEmailValidation {
return false, err
}
expiresAt, err := GetAccountRequestExpiry(ctx, user)
if err != nil || expiresAt.IsZero() {
return false, err
}
return time.Now().After(expiresAt), nil
}
func ActivateAccountRequestPrimaryEmail(ctx context.Context, user *User) error {
return db.WithTx(ctx, func(ctx context.Context) error {
addr, exist, err := db.Get[EmailAddress](ctx, builder.Eq{"uid": user.ID, "lower_email": strings.ToLower(user.Email)})
if err != nil {
return err
}
if !exist {
return fmt.Errorf("no such email: %d (%s)", user.ID, user.Email)
}
if addr.IsActivated {
return nil
}
return updateActivation(ctx, addr, true)
})
}
func ResetAccountRequestToPendingEmailValidation(ctx context.Context, user *User) error {
if err := SetAccountRequestStatus(ctx, user.ID, AccountRequestStatusPendingEmailValidation); err != nil {
return err
}
if err := RefreshAccountRequestValidationWindow(ctx, user); err != nil {
return err
}
if err := SetAccountRequestSignupAttempts(ctx, user.ID, 1); err != nil {
return err
}
if err := SetAccountRequestValidationResendHits(ctx, user.ID, 0); err != nil {
return err
}
_ = DeleteUserSetting(ctx, user.ID, SettingsKeyAccountRequestEmailValidatedUnix)
_ = DeleteUserSetting(ctx, user.ID, SettingsKeyAccountRequestReviewedUnix)
_ = DeleteUserSetting(ctx, user.ID, SettingsKeyAccountRequestReviewedBy)
_ = DeleteUserSetting(ctx, user.ID, SettingsKeyAccountRequestValidationCodeHash)
user.ProhibitLogin = false
_, err := db.GetEngine(ctx).ID(user.ID).Cols("prohibit_login").Update(user)
return err
}
func IncrementAccountRequestSignupAttempts(ctx context.Context, user *User) (attempts int, blocked bool, _ error) {
attempts, err := GetAccountRequestSignupAttempts(ctx, user)
if err != nil {
return 0, false, err
}
attempts++
if err := SetAccountRequestSignupAttempts(ctx, user.ID, attempts); err != nil {
return 0, false, err
}
if attempts < AccountRequestMaxAttempts {
return attempts, false, nil
}
if err := SetAccountRequestStatus(ctx, user.ID, AccountRequestStatusBlocked); err != nil {
return 0, false, err
}
user.ProhibitLogin = true
_, err = db.GetEngine(ctx).ID(user.ID).Cols("prohibit_login").Update(user)
return attempts, true, err
}
func MarkAccountRequestPendingAdminReview(ctx context.Context, user *User) error {
if err := ActivateAccountRequestPrimaryEmail(ctx, user); err != nil {
return err
}
if err := SetAccountRequestStatus(ctx, user.ID, AccountRequestStatusPendingAdminReview); err != nil {
return err
}
if err := setAccountRequestInt64(ctx, user.ID, SettingsKeyAccountRequestEmailValidatedUnix, time.Now().Unix()); err != nil {
return err
}
_ = DeleteUserSetting(ctx, user.ID, SettingsKeyAccountRequestExpiresUnix)
_ = DeleteUserSetting(ctx, user.ID, SettingsKeyAccountRequestValidationResendHits)
_ = DeleteUserSetting(ctx, user.ID, SettingsKeyAccountRequestValidationCodeHash)
return nil
}
func RejectAccountRequest(ctx context.Context, user *User, reviewerID int64) error {
if err := SetAccountRequestStatus(ctx, user.ID, AccountRequestStatusRejected); err != nil {
return err
}
if err := setAccountRequestInt64(ctx, user.ID, SettingsKeyAccountRequestReviewedUnix, time.Now().Unix()); err != nil {
return err
}
if err := setAccountRequestInt64(ctx, user.ID, SettingsKeyAccountRequestReviewedBy, reviewerID); err != nil {
return err
}
user.ProhibitLogin = true
_, err := db.GetEngine(ctx).ID(user.ID).Cols("prohibit_login").Update(user)
return err
}
func ApproveAccountRequest(ctx context.Context, user *User, reviewerID int64) error {
if err := ActivateAccountRequestPrimaryEmail(ctx, user); err != nil {
return err
}
var err error
user.IsActive = true
user.ProhibitLogin = false
if user.Rands, err = GetUserSalt(); err != nil {
return err
}
if err := UpdateUserCols(ctx, user, "is_active", "prohibit_login", "rands"); err != nil {
return err
}
if err := setAccountRequestInt64(ctx, user.ID, SettingsKeyAccountRequestReviewedUnix, time.Now().Unix()); err != nil {
return err
}
if err := setAccountRequestInt64(ctx, user.ID, SettingsKeyAccountRequestReviewedBy, reviewerID); err != nil {
return err
}
_ = DeleteUserSetting(ctx, user.ID, SettingsKeyAccountRequestStatus)
_ = DeleteUserSetting(ctx, user.ID, SettingsKeyAccountRequestExpiresUnix)
_ = DeleteUserSetting(ctx, user.ID, SettingsKeyAccountRequestSignupAttempts)
_ = DeleteUserSetting(ctx, user.ID, SettingsKeyAccountRequestValidationResendHits)
_ = DeleteUserSetting(ctx, user.ID, SettingsKeyAccountRequestValidationCodeHash)
return nil
}
func UnblockAccountRequest(ctx context.Context, user *User) error {
return ResetAccountRequestToPendingEmailValidation(ctx, user)
}
func GenerateAccountRequestValidationCode(user *User) string {
data := makeTimeLimitCodeHashData(&TimeLimitCodeOptions{Purpose: TimeLimitCodeAccountRequest}, user)
code := base.CreateTimeLimitCode(data, AccountRequestValidationHours*60, time.Now(), nil)
code += hex.EncodeToString([]byte(user.LowerName))
return code
}
func VerifyAccountRequestValidationCode(ctx context.Context, code string) (user *User) {
if user = GetVerifyUser(ctx, code); user != nil {
prefix := code[:base.TimeLimitCodeLength]
hasValidationState, err := HasAccountRequestValidationState(ctx, user)
if err != nil || !hasValidationState {
return nil
}
for _, purpose := range []TimeLimitCodePurpose{TimeLimitCodeAccountRequest, TimeLimitCodeActivateAccount} {
data := makeTimeLimitCodeHashData(&TimeLimitCodeOptions{Purpose: purpose}, user)
if base.VerifyTimeLimitCode(time.Now(), data, AccountRequestValidationHours*60, prefix) {
return user
}
}
storedHash, err := GetUserSetting(ctx, user.ID, SettingsKeyAccountRequestValidationCodeHash)
if err == nil && storedHash != "" && storedHash == base.EncodeSha256(code) {
return user
}
}
return nil
}
func GetUserByAnyEmail(ctx context.Context, email string) (*User, error) {
email = strings.TrimSpace(email)
if err := validateEmailBasic(email); err != nil {
return nil, err
}
addr := &EmailAddress{LowerEmail: strings.ToLower(email)}
has, err := db.GetEngine(ctx).Get(addr)
if err != nil {
return nil, err
}
if !has {
return nil, ErrUserNotExist{Name: email}
}
return GetUserByID(ctx, addr.UID)
}
func DeleteExpiredPendingAccountRequests(ctx context.Context) error {
users, _, err := SearchUsers(ctx, SearchUserOptions{
Types: []UserType{UserTypeIndividual, UserTypeUserReserved},
IsActive: optional.Some(false),
ListOptions: db.ListOptionsAll,
})
if err != nil {
return err
}
for _, user := range users {
status, err := GetAccountRequestStatus(ctx, user)
if err != nil || status != AccountRequestStatusPendingEmailValidation {
if err != nil {
return err
}
continue
}
expired, err := IsAccountRequestExpired(ctx, user)
if err != nil {
return err
}
if !expired {
continue
}
if _, err := db.GetEngine(ctx).Where("uid=?", user.ID).Delete(&EmailAddress{}); err != nil {
return err
}
if _, err := db.GetEngine(ctx).Where("uid=?", user.ID).Delete(&Setting{}); err != nil {
return err
}
if _, err := db.GetEngine(ctx).ID(user.ID).Delete(&User{}); err != nil {
return err
}
}
return nil
}
+95
View File
@@ -0,0 +1,95 @@
// Copyright 2026 The Gitea Authors. All rights reserved.
// SPDX-License-Identifier: MIT
package user_test
import (
"testing"
"code.gitea.io/gitea/models/unittest"
user_model "code.gitea.io/gitea/models/user"
"code.gitea.io/gitea/modules/setting"
"code.gitea.io/gitea/modules/test"
"github.com/stretchr/testify/require"
)
func TestAccountRequestValidationCode(t *testing.T) {
require.NoError(t, unittest.PrepareTestDatabase())
defer test.MockVariableValue(&setting.Service.RegisterManualConfirm, true)()
user := &user_model.User{
Name: "account-request-code-user",
Email: "account-request-code-user@example.com",
Passwd: "password",
}
require.NoError(t, user_model.CreateUser(t.Context(), user, &user_model.Meta{}))
require.NoError(t, user_model.ResetAccountRequestToPendingEmailValidation(t.Context(), user))
code := user_model.GenerateAccountRequestValidationCode(user)
verifiedUser := user_model.VerifyAccountRequestValidationCode(t.Context(), code)
require.NotNil(t, verifiedUser)
require.Equal(t, user.ID, verifiedUser.ID)
}
func TestAccountRequestValidationCodeStoredFallback(t *testing.T) {
require.NoError(t, unittest.PrepareTestDatabase())
defer test.MockVariableValue(&setting.Service.RegisterManualConfirm, true)()
user := &user_model.User{
Name: "account-request-stored-code-user",
Email: "account-request-stored-code-user@example.com",
Passwd: "password",
}
require.NoError(t, user_model.CreateUser(t.Context(), user, &user_model.Meta{}))
require.NoError(t, user_model.ResetAccountRequestToPendingEmailValidation(t.Context(), user))
code := user_model.GenerateAccountRequestValidationCode(user)
require.NoError(t, user_model.SetAccountRequestValidationCode(t.Context(), user.ID, code))
user.Rands = "changed-rands-after-email"
require.NoError(t, user_model.UpdateUserCols(t.Context(), user, "rands"))
verifiedUser := user_model.VerifyAccountRequestValidationCode(t.Context(), code)
require.NotNil(t, verifiedUser)
require.Equal(t, user.ID, verifiedUser.ID)
}
func TestAccountRequestValidationCodeMissingStatusFallback(t *testing.T) {
require.NoError(t, unittest.PrepareTestDatabase())
defer test.MockVariableValue(&setting.Service.RegisterManualConfirm, true)()
user := &user_model.User{
Name: "account-request-missing-status-user",
Email: "account-request-missing-status-user@example.com",
Passwd: "password",
}
require.NoError(t, user_model.CreateUser(t.Context(), user, &user_model.Meta{}))
require.NoError(t, user_model.ResetAccountRequestToPendingEmailValidation(t.Context(), user))
require.NoError(t, user_model.DeleteUserSetting(t.Context(), user.ID, user_model.SettingsKeyAccountRequestStatus))
status, err := user_model.GetAccountRequestStatus(t.Context(), user)
require.NoError(t, err)
require.Equal(t, user_model.AccountRequestStatusPendingEmailValidation, status)
code := user_model.GenerateAccountRequestValidationCode(user)
verifiedUser := user_model.VerifyAccountRequestValidationCode(t.Context(), code)
require.NotNil(t, verifiedUser)
require.Equal(t, user.ID, verifiedUser.ID)
}
func TestAccountRequestValidationCodeIgnoresClassicActivation(t *testing.T) {
require.NoError(t, unittest.PrepareTestDatabase())
defer test.MockVariableValue(&setting.Service.RegisterEmailConfirm, true)()
defer test.MockVariableValue(&setting.Service.RegisterManualConfirm, false)()
user := &user_model.User{
Name: "classic-activation-user",
Email: "classic-activation-user@example.com",
Passwd: "password",
}
require.NoError(t, user_model.CreateUser(t.Context(), user, &user_model.Meta{}))
code := user_model.GenerateUserTimeLimitCode(&user_model.TimeLimitCodeOptions{Purpose: user_model.TimeLimitCodeActivateAccount}, user)
require.Nil(t, user_model.VerifyAccountRequestValidationCode(t.Context(), code))
}
+106
View File
@@ -0,0 +1,106 @@
// Copyright 2026 The Gitea Authors. All rights reserved.
// SPDX-License-Identifier: MIT
package user
import (
"context"
"strconv"
)
const BootstrapAdminActorName = "GOD"
func getUserSettingInt64(ctx context.Context, userID int64, key string) (int64, bool, error) {
value, err := GetUserSetting(ctx, userID, key)
if err != nil {
if IsErrUserSettingIsNotExist(err) {
return 0, false, nil
}
return 0, false, err
}
if value == "" {
return 0, false, nil
}
parsed, err := strconv.ParseInt(value, 10, 64)
if err != nil {
return 0, false, err
}
return parsed, true, nil
}
func GetAdminGrantorID(ctx context.Context, userID int64) (int64, bool, error) {
return getUserSettingInt64(ctx, userID, SettingsKeyAdminGrantedBy)
}
func GetSuperAdminGrantorID(ctx context.Context, userID int64) (int64, bool, error) {
return getUserSettingInt64(ctx, userID, SettingsKeySuperAdminGrantedBy)
}
func HasBootstrapAdminGrant(ctx context.Context, userID int64) (bool, error) {
for _, key := range []string{SettingsKeyAdminGrantedByName, SettingsKeySuperAdminGrantedByName} {
value, err := GetUserSetting(ctx, userID, key)
if err != nil {
if IsErrUserSettingIsNotExist(err) {
continue
}
return false, err
}
if value == BootstrapAdminActorName {
return true, nil
}
}
return false, nil
}
func IsGrantorOf(ctx context.Context, grantedUserID, possibleGrantorID int64) (bool, error) {
for _, getter := range []func(context.Context, int64) (int64, bool, error){GetAdminGrantorID, GetSuperAdminGrantorID} {
grantorID, has, err := getter(ctx, grantedUserID)
if err != nil {
return false, err
}
if has && grantorID == possibleGrantorID {
return true, nil
}
}
return false, nil
}
func IsEligibleAdminGrantor(ctx context.Context, userID int64) (bool, error) {
u, err := GetUserByID(ctx, userID)
if err != nil {
if IsErrUserNotExist(err) {
return false, nil
}
return false, err
}
return u.IsAdmin && u.IsActive && !u.ProhibitLogin, nil
}
func GetEffectiveAdminGrantorID(ctx context.Context, userID int64) (int64, bool, error) {
visited := map[int64]struct{}{userID: {}}
currentUserID := userID
for {
grantorID, has, err := GetAdminGrantorID(ctx, currentUserID)
if err != nil {
return 0, false, err
}
if !has {
return 0, false, nil
}
if _, ok := visited[grantorID]; ok {
return 0, false, nil
}
visited[grantorID] = struct{}{}
eligible, err := IsEligibleAdminGrantor(ctx, grantorID)
if err != nil {
return 0, false, err
}
if eligible {
return grantorID, true, nil
}
currentUserID = grantorID
}
}
+1 -1
View File
@@ -64,7 +64,7 @@ type GetBadgeUsersOptions struct {
func GetBadgeUsers(ctx context.Context, opts *GetBadgeUsersOptions) ([]*User, int64, error) {
sess := db.GetEngine(ctx).
Select("`user`.*").
Join("INNER", "user_badge", "`user_badge`.user_id=user.id").
Join("INNER", "user_badge", "`user_badge`.user_id=`user`.id").
Join("INNER", "badge", "`user_badge`.badge_id=badge.id").
Where("badge.slug=?", opts.BadgeSlug)
+108 -4
View File
@@ -3,9 +3,22 @@
package user
import (
"context"
"code.gitea.io/gitea/models/db"
"code.gitea.io/gitea/modules/optional"
)
const (
// SettingsKeyHiddenCommentTypes is the setting key for hidden comment types
SettingsKeyHiddenCommentTypes = "issue.hidden_comment_types"
// SettingsKeyPersistentFooter is the setting key for whether the footer remains visible in the viewport
SettingsKeyPersistentFooter = "ui.persistent_footer"
// SettingsKeyPersistentNavbar is the setting key for whether the navigation bar remains visible in the viewport
SettingsKeyPersistentNavbar = "ui.persistent_navbar"
// SettingsKeyStickySideMenus is the setting key for whether settings/admin side menus remain visible while scrolling
SettingsKeyStickySideMenus = "ui.sticky_side_menus"
// SettingsKeyDiffWhitespaceBehavior is the setting key for whitespace behavior of diff
SettingsKeyDiffWhitespaceBehavior = "diff.whitespace_behaviour"
// SettingsKeyShowOutdatedComments is the setting key whether or not to show outdated comments in PRs
@@ -18,10 +31,101 @@ const (
SettingsKeyCodeViewShowFileTree = "code_view.show_file_tree"
SettingsKeyEmailNotificationGiteaActions = "email_notification.gitea_actions"
SettingEmailNotificationGiteaActionsAll = "all"
SettingEmailNotificationGiteaActionsFailureOnly = "failure-only" // Default for actions email preference
SettingEmailNotificationGiteaActionsDisabled = "disabled"
SettingsKeyEmailNotificationNewAccountRequests = "email_notification.new_account_requests"
SettingEmailNotificationNewAccountRequestsEnabled = "enabled"
SettingEmailNotificationNewAccountRequestsDisabled = "disabled"
SettingsKeyEmailNotificationGiteaActions = "email_notification.gitea_actions"
SettingEmailNotificationGiteaActionsAll = "all"
SettingEmailNotificationGiteaActionsFailureOnly = "failure-only" // Default for actions email preference
SettingEmailNotificationGiteaActionsDisabled = "disabled"
SettingsKeyActionsConfig = "actions.config"
)
func GetEmailNotificationNewAccountRequestsPreference(ctx context.Context, user *User) (string, error) {
def := SettingEmailNotificationNewAccountRequestsDisabled
if user.IsAdmin {
def = SettingEmailNotificationNewAccountRequestsEnabled
}
return GetUserSetting(ctx, user.ID, SettingsKeyEmailNotificationNewAccountRequests, def)
}
func IsEmailNotificationNewAccountRequestsEnabled(ctx context.Context, user *User) (bool, error) {
preference, err := GetEmailNotificationNewAccountRequestsPreference(ctx, user)
if err != nil {
return false, err
}
return preference == SettingEmailNotificationNewAccountRequestsEnabled, nil
}
func CountAdminsWithNewAccountRequestNotificationsEnabled(ctx context.Context) (int, error) {
admins, _, err := SearchUsers(ctx, SearchUserOptions{
Types: []UserType{UserTypeIndividual},
IsAdmin: optional.Some(true),
IsActive: optional.Some(true),
ListOptions: db.ListOptionsAll,
})
if err != nil {
return 0, err
}
count := 0
for _, admin := range admins {
enabled, err := IsEmailNotificationNewAccountRequestsEnabled(ctx, admin)
if err != nil {
return 0, err
}
if enabled {
count++
}
}
return count, nil
}
func IsLastAdminWithNewAccountRequestNotificationsEnabled(ctx context.Context, user *User) (bool, error) {
if !user.IsAdmin || !user.IsActive {
return false, nil
}
enabled, err := IsEmailNotificationNewAccountRequestsEnabled(ctx, user)
if err != nil {
return false, err
}
if !enabled {
return false, nil
}
count, err := CountAdminsWithNewAccountRequestNotificationsEnabled(ctx)
if err != nil {
return false, err
}
return count <= 1, nil
}
func ShouldEnableNewAccountRequestNotificationsFallback(ctx context.Context, actor, target *User) (bool, error) {
if actor == nil || target == nil || actor.ID == target.ID {
return false, nil
}
if !actor.IsAdmin || !actor.IsActive {
return false, nil
}
targetIsLastNotifier, err := IsLastAdminWithNewAccountRequestNotificationsEnabled(ctx, target)
if err != nil {
return false, err
}
if !targetIsLastNotifier {
return false, nil
}
actorEnabled, err := IsEmailNotificationNewAccountRequestsEnabled(ctx, actor)
if err != nil {
return false, err
}
return !actorEnabled, nil
}
+40
View File
@@ -4,6 +4,7 @@
package user_test
import (
"strconv"
"testing"
"code.gitea.io/gitea/models/unittest"
@@ -57,3 +58,42 @@ func TestSettings(t *testing.T) {
assert.NoError(t, err)
assert.Empty(t, settings)
}
func TestPersistentFooterSetting(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
assert.NoError(t, user_model.SetUserSetting(t.Context(), 99, user_model.SettingsKeyPersistentFooter, "true"))
val, err := user_model.GetUserSetting(t.Context(), 99, user_model.SettingsKeyPersistentFooter, "false")
assert.NoError(t, err)
enabled, err := strconv.ParseBool(val)
assert.NoError(t, err)
assert.True(t, enabled)
}
func TestPersistentNavbarSetting(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
assert.NoError(t, user_model.SetUserSetting(t.Context(), 99, user_model.SettingsKeyPersistentNavbar, "true"))
val, err := user_model.GetUserSetting(t.Context(), 99, user_model.SettingsKeyPersistentNavbar, "false")
assert.NoError(t, err)
enabled, err := strconv.ParseBool(val)
assert.NoError(t, err)
assert.True(t, enabled)
}
func TestStickySideMenusSetting(t *testing.T) {
assert.NoError(t, unittest.PrepareTestDatabase())
assert.NoError(t, user_model.SetUserSetting(t.Context(), 99, user_model.SettingsKeyStickySideMenus, "true"))
val, err := user_model.GetUserSetting(t.Context(), 99, user_model.SettingsKeyStickySideMenus, "false")
assert.NoError(t, err)
enabled, err := strconv.ParseBool(val)
assert.NoError(t, err)
assert.True(t, enabled)
}
+40
View File
@@ -0,0 +1,40 @@
// Copyright 2026 The Gitea Authors. All rights reserved.
// SPDX-License-Identifier: MIT
package user_test
import (
"testing"
"code.gitea.io/gitea/models/unittest"
user_model "code.gitea.io/gitea/models/user"
"code.gitea.io/gitea/modules/setting"
"code.gitea.io/gitea/modules/test"
"github.com/stretchr/testify/require"
)
func TestResetPasswordTimeLimitCodeUsesResetPasswordLifetime(t *testing.T) {
require.NoError(t, unittest.PrepareTestDatabase())
defer test.MockVariableValue(&setting.Service.ActiveCodeLives, 0)()
defer test.MockVariableValue(&setting.Service.ResetPwdCodeLives, 180)()
user := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: 2})
opts := &user_model.TimeLimitCodeOptions{Purpose: user_model.TimeLimitCodeResetPassword}
code := user_model.GenerateUserTimeLimitCode(opts, user)
require.Equal(t, "000180", code[12:18])
require.NotNil(t, user_model.VerifyUserTimeLimitCode(t.Context(), opts, code))
}
func TestAdminInviteTimeLimitCodeUsesInvitationLifetime(t *testing.T) {
require.NoError(t, unittest.PrepareTestDatabase())
defer test.MockVariableValue(&setting.Service.ActiveCodeLives, 0)()
user := unittest.AssertExistsAndLoadBean(t, &user_model.User{ID: 2})
opts := &user_model.TimeLimitCodeOptions{Purpose: user_model.TimeLimitCodeAdminInvite}
code := user_model.GenerateUserTimeLimitCode(opts, user)
require.Equal(t, "001440", code[12:18])
require.NotNil(t, user_model.VerifyUserTimeLimitCode(t.Context(), opts, code))
}
+57 -3
View File
@@ -819,7 +819,7 @@ func (err ErrDeleteLastAdminUser) Error() string {
// IsLastAdminUser check whether user is the last admin
func IsLastAdminUser(ctx context.Context, user *User) bool {
if user.IsAdmin && CountUsers(ctx, &CountUserFilter{IsAdmin: optional.Some(true)}) <= 1 {
if user.IsAdmin && user.IsActive && CountUsers(ctx, &CountUserFilter{IsAdmin: optional.Some(true), IsActive: optional.Some(true)}) <= 1 {
return true
}
return false
@@ -900,8 +900,52 @@ type TimeLimitCodePurpose string
const (
TimeLimitCodeActivateAccount TimeLimitCodePurpose = "activate_account"
TimeLimitCodeAccountRequest TimeLimitCodePurpose = "account_request"
TimeLimitCodeActivateEmail TimeLimitCodePurpose = "activate_email"
TimeLimitCodeResetPassword TimeLimitCodePurpose = "reset_password"
TimeLimitCodeAdminAccess TimeLimitCodePurpose = "admin_access"
TimeLimitCodeAdminInvite TimeLimitCodePurpose = "admin_invite"
)
const AdminInviteCodeLives = 24 * 60
const (
SettingsKeyAdminInviteCreatedBy = "admin_invite.created_by"
SettingsKeyAdminInviteCreatedByName = "admin_invite.created_by_name"
SettingsKeyAdminInviteCreatedByEmail = "admin_invite.created_by_email"
SettingsKeyAdminGrantedUnix = "admin_grant.granted_unix"
SettingsKeyAdminGrantedBy = "admin_grant.granted_by"
SettingsKeyAdminGrantedByName = "admin_grant.granted_by_name"
SettingsKeyAdminGrantedByEmail = "admin_grant.granted_by_email"
SettingsKeyAdminGrantedReason = "admin_grant.reason"
SettingsKeyAdminActivatedBy = "admin_activation.activated_by"
SettingsKeyAdminActivatedByName = "admin_activation.activated_by_name"
SettingsKeyAdminActivatedByEmail = "admin_activation.activated_by_email"
SettingsKeyAdminDeactivatedUnix = "admin_deactivation.deactivated_unix"
SettingsKeyAdminDeactivatedBy = "admin_deactivation.deactivated_by"
SettingsKeyAdminDeactivatedByName = "admin_deactivation.deactivated_by_name"
SettingsKeyAdminDeactivatedByEmail = "admin_deactivation.deactivated_by_email"
SettingsKeyAdminDeactivatedReason = "admin_deactivation.reason"
SettingsKeyAdminProhibitLoginUnix = "admin_prohibit_login.prohibited_unix"
SettingsKeyAdminProhibitLoginBy = "admin_prohibit_login.prohibited_by"
SettingsKeyAdminProhibitLoginByName = "admin_prohibit_login.prohibited_by_name"
SettingsKeyAdminProhibitLoginByEmail = "admin_prohibit_login.prohibited_by_email"
SettingsKeyAdminProhibitLoginReason = "admin_prohibit_login.reason"
SettingsKeyAdminRestrictedUnix = "admin_restriction.restricted_unix"
SettingsKeyAdminRestrictedBy = "admin_restriction.restricted_by"
SettingsKeyAdminRestrictedByName = "admin_restriction.restricted_by_name"
SettingsKeyAdminRestrictedByEmail = "admin_restriction.restricted_by_email"
SettingsKeyAdminRestrictedReason = "admin_restriction.reason"
SettingsKeySuperAdminEnabled = "super_admin.enabled"
SettingsKeySuperAdminGrantedUnix = "super_admin.granted_unix"
SettingsKeySuperAdminGrantedBy = "super_admin.granted_by"
SettingsKeySuperAdminGrantedByName = "super_admin.granted_by_name"
SettingsKeySuperAdminGrantedByEmail = "super_admin.granted_by_email"
SettingsKeySuperAdminRevokedUnix = "super_admin.revoked_unix"
SettingsKeySuperAdminRevokedBy = "super_admin.revoked_by"
SettingsKeySuperAdminRevokedByName = "super_admin.revoked_by_name"
SettingsKeySuperAdminRevokedByEmail = "super_admin.revoked_by_email"
SettingsKeySuperAdminRevokedReason = "super_admin.revoked_reason"
)
type TimeLimitCodeOptions struct {
@@ -913,11 +957,21 @@ func makeTimeLimitCodeHashData(opts *TimeLimitCodeOptions, u *User) string {
return fmt.Sprintf("%s|%d|%s|%s|%s|%s", opts.Purpose, u.ID, strings.ToLower(util.IfZero(opts.NewEmail, u.Email)), u.LowerName, u.Passwd, u.Rands)
}
func timeLimitCodeLives(opts *TimeLimitCodeOptions) int {
if opts.Purpose == TimeLimitCodeResetPassword || opts.Purpose == TimeLimitCodeAdminAccess {
return setting.Service.ResetPwdCodeLives
}
if opts.Purpose == TimeLimitCodeAdminInvite {
return AdminInviteCodeLives
}
return setting.Service.ActiveCodeLives
}
// GenerateUserTimeLimitCode generates a time-limit code based on user information and given e-mail.
// TODO: need to use cache or db to store it to make sure a code can only be consumed once
func GenerateUserTimeLimitCode(opts *TimeLimitCodeOptions, u *User) string {
data := makeTimeLimitCodeHashData(opts, u)
code := base.CreateTimeLimitCode(data, setting.Service.ActiveCodeLives, time.Now(), nil)
code := base.CreateTimeLimitCode(data, timeLimitCodeLives(opts), time.Now(), nil)
code += hex.EncodeToString([]byte(u.LowerName)) // Add tail hex username
return code
}
@@ -928,7 +982,7 @@ func VerifyUserTimeLimitCode(ctx context.Context, opts *TimeLimitCodeOptions, co
// time limit code
prefix := code[:base.TimeLimitCodeLength]
data := makeTimeLimitCodeHashData(opts, user)
if base.VerifyTimeLimitCode(time.Now(), data, setting.Service.ActiveCodeLives, prefix) {
if base.VerifyTimeLimitCode(time.Now(), data, timeLimitCodeLives(opts), prefix) {
return user
}
}
+10
View File
@@ -103,10 +103,20 @@ func GetEventsFromContent(content []byte) ([]*jobparser.Event, error) {
if err != nil {
return nil, err
}
if err := ValidateWorkflowContent(content); err != nil {
return nil, err
}
return events, nil
}
// ValidateWorkflowContent catches structural errors (e.g. blank lines in run: | blocks)
// that model.ReadWorkflow alone does not detect.
func ValidateWorkflowContent(content []byte) error {
_, err := jobparser.Parse(content)
return err
}
func DetectWorkflows(
gitRepo *git.Repository,
commit *git.Commit,
+16 -6
View File
@@ -9,16 +9,26 @@ import (
"code.gitea.io/gitea/modules/git"
"code.gitea.io/gitea/modules/setting"
api "code.gitea.io/gitea/modules/structs"
"code.gitea.io/gitea/modules/test"
webhook_module "code.gitea.io/gitea/modules/webhook"
"github.com/stretchr/testify/assert"
)
func fullWorkflowContent(part string) []byte {
return []byte(`
name: test
` + part + `
jobs:
test:
runs-on: ubuntu-latest
steps:
- run: echo hello
`)
}
func TestIsWorkflow(t *testing.T) {
oldDirs := setting.Actions.WorkflowDirs
defer func() {
setting.Actions.WorkflowDirs = oldDirs
}()
defer test.MockVariableValue(&setting.Actions.WorkflowDirs)()
tests := []struct {
name string
@@ -218,7 +228,7 @@ func TestDetectMatched(t *testing.T) {
for _, tc := range testCases {
t.Run(tc.desc, func(t *testing.T) {
evts, err := GetEventsFromContent([]byte(tc.yamlOn))
evts, err := GetEventsFromContent(fullWorkflowContent(tc.yamlOn))
assert.NoError(t, err)
assert.Len(t, evts, 1)
assert.Equal(t, tc.expected, detectMatched(nil, tc.commit, tc.triggedEvent, tc.payload, evts[0]))
@@ -373,7 +383,7 @@ func TestMatchIssuesEvent(t *testing.T) {
for _, tc := range testCases {
t.Run(tc.desc, func(t *testing.T) {
evts, err := GetEventsFromContent([]byte(tc.yamlOn))
evts, err := GetEventsFromContent(fullWorkflowContent(tc.yamlOn))
assert.NoError(t, err)
assert.Len(t, evts, 1)
+2 -1
View File
@@ -4,6 +4,7 @@
package dump
import (
"archive/zip"
"context"
"errors"
"fmt"
@@ -85,7 +86,7 @@ func NewDumper(ctx context.Context, format string, output io.Writer) (*Dumper, e
var comp archives.ArchiverAsync
switch format {
case "zip":
comp = archives.Zip{}
comp = archives.Zip{Compression: zip.Deflate}
case "tar":
comp = archives.Tar{}
case "tar.sz":
+34 -31
View File
@@ -13,63 +13,45 @@ import (
"strconv"
"strings"
"sync/atomic"
"time"
"code.gitea.io/gitea/modules/git/gitcmd"
"code.gitea.io/gitea/modules/log"
"code.gitea.io/gitea/modules/util"
)
var catFileBatchDebugWaitClose atomic.Int64
type catFileBatchCommunicator struct {
closeFunc func(err error)
closeFunc atomic.Pointer[func(err error)]
reqWriter io.Writer
respReader *bufio.Reader
debugGitCmd *gitcmd.Command
}
func (b *catFileBatchCommunicator) Close() {
if b.closeFunc != nil {
b.closeFunc(nil)
b.closeFunc = nil
func (b *catFileBatchCommunicator) Close(err ...error) {
if fn := b.closeFunc.Swap(nil); fn != nil {
(*fn)(util.OptionalArg(err))
}
}
// newCatFileBatch opens git cat-file --batch in the provided repo and returns a stdin pipe, a stdout reader and cancel function
func newCatFileBatch(ctx context.Context, repoPath string, cmdCatFile *gitcmd.Command) (ret *catFileBatchCommunicator) {
// newCatFileBatch opens git cat-file --batch/--batch-check/--batch-command command and prepares the stdin/stdout pipes for communication.
func newCatFileBatch(ctx context.Context, repoPath string, cmdCatFile *gitcmd.Command) *catFileBatchCommunicator {
ctx, ctxCancel := context.WithCancelCause(ctx)
// We often want to feed the commits in order into cat-file --batch, followed by their trees and subtrees as necessary.
stdinWriter, stdoutReader, stdPipeClose := cmdCatFile.MakeStdinStdoutPipe()
pipeClose := func() {
if delay := catFileBatchDebugWaitClose.Load(); delay > 0 {
time.Sleep(time.Duration(delay)) // for testing purpose only
}
stdPipeClose()
}
closeFunc := func(err error) {
ctxCancel(err)
pipeClose()
}
return newCatFileBatchWithCloseFunc(ctx, repoPath, cmdCatFile, stdinWriter, stdoutReader, closeFunc)
}
func newCatFileBatchWithCloseFunc(ctx context.Context, repoPath string, cmdCatFile *gitcmd.Command,
stdinWriter gitcmd.PipeWriter, stdoutReader gitcmd.PipeReader, closeFunc func(err error),
) *catFileBatchCommunicator {
ret := &catFileBatchCommunicator{
debugGitCmd: cmdCatFile,
closeFunc: closeFunc,
reqWriter: stdinWriter,
respReader: bufio.NewReaderSize(stdoutReader, 32*1024), // use a buffered reader for rich operations
}
ret.closeFunc.Store(new(func(err error) {
ctxCancel(err)
stdPipeClose()
}))
err := cmdCatFile.WithDir(repoPath).StartWithStderr(ctx)
if err != nil {
log.Error("Unable to start git command %v: %v", cmdCatFile.LogString(), err)
// ideally here it should return the error, but it would require refactoring all callers
// so just return a dummy communicator that does nothing, almost the same behavior as before, not bad
closeFunc(err)
ret.Close(err)
return ret
}
@@ -78,12 +60,33 @@ func newCatFileBatchWithCloseFunc(ctx context.Context, repoPath string, cmdCatFi
if err != nil && !errors.Is(err, context.Canceled) {
log.Error("cat-file --batch command failed in repo %s, error: %v", repoPath, err)
}
closeFunc(err)
ret.Close(err)
}()
return ret
}
func (b *catFileBatchCommunicator) debugKill() (ret struct {
beforeClose chan struct{}
blockClose chan struct{}
afterClose chan struct{}
},
) {
ret.beforeClose = make(chan struct{})
ret.blockClose = make(chan struct{})
ret.afterClose = make(chan struct{})
oldCloseFunc := b.closeFunc.Load()
b.closeFunc.Store(new(func(err error) {
b.closeFunc.Store(nil)
close(ret.beforeClose)
<-ret.blockClose
(*oldCloseFunc)(err)
close(ret.afterClose)
}))
b.debugGitCmd.DebugKill()
return ret
}
// catFileBatchParseInfoLine reads the header line from cat-file --batch
// We expect: <oid> SP <type> SP <size> LF
// then leaving the rest of the stream "<contents> LF" to be read
+23 -22
View File
@@ -7,9 +7,7 @@ import (
"io"
"os"
"path/filepath"
"sync"
"testing"
"time"
"code.gitea.io/gitea/modules/test"
@@ -39,13 +37,22 @@ func testCatFileBatch(t *testing.T) {
require.Error(t, err)
})
simulateQueryTerminated := func(pipeCloseDelay, pipeReadDelay time.Duration) (errRead error) {
catFileBatchDebugWaitClose.Store(int64(pipeCloseDelay))
defer catFileBatchDebugWaitClose.Store(0)
simulateQueryTerminated := func(t *testing.T, errBeforePipeClose, errAfterPipeClose error) {
readError := func(t *testing.T, r io.Reader, expectedErr error) {
if expectedErr == nil {
return // expectedErr == nil means this read should be skipped
}
n, err := r.Read(make([]byte, 100))
assert.Zero(t, n)
assert.ErrorIs(t, err, expectedErr)
}
batch, err := NewBatch(t.Context(), filepath.Join(testReposDir, "repo1_bare"))
require.NoError(t, err)
defer batch.Close()
_, _ = batch.QueryInfo("e2129701f1a4d54dc44f03c93bca0a2aec7c5449")
_, err = batch.QueryInfo("e2129701f1a4d54dc44f03c93bca0a2aec7c5449")
require.NoError(t, err)
var c *catFileBatchCommunicator
switch b := batch.(type) {
case *catFileBatchLegacy:
@@ -58,24 +65,18 @@ func testCatFileBatch(t *testing.T) {
t.FailNow()
}
wg := sync.WaitGroup{}
wg.Go(func() {
time.Sleep(pipeReadDelay)
var n int
n, errRead = c.respReader.Read(make([]byte, 100))
assert.Zero(t, n)
})
time.Sleep(10 * time.Millisecond)
c.debugGitCmd.DebugKill()
wg.Wait()
return errRead
}
require.NotEqual(t, errBeforePipeClose == nil, errAfterPipeClose == nil, "must set exactly one of the expected errors")
inceptor := c.debugKill()
<-inceptor.beforeClose // wait for the command's Close to be called, the pipe is not closed yet
readError(t, c.respReader, errBeforePipeClose) // then caller will read on an open pipe which will be closed soon
close(inceptor.blockClose) // continue to close the pipe
<-inceptor.afterClose // wait for the pipe to be closed
readError(t, c.respReader, errAfterPipeClose) // then caller will read on a closed pipe
}
t.Run("QueryTerminated", func(t *testing.T) {
err := simulateQueryTerminated(0, 20*time.Millisecond)
assert.ErrorIs(t, err, os.ErrClosed) // pipes are closed faster
err = simulateQueryTerminated(40*time.Millisecond, 20*time.Millisecond)
assert.ErrorIs(t, err, io.EOF) // reader is faster
simulateQueryTerminated(t, io.EOF, nil) // reader is faster
simulateQueryTerminated(t, nil, os.ErrClosed) // pipes are closed faster
})
batch, err := NewBatch(t.Context(), filepath.Join(testReposDir, "repo1_bare"))
-35
View File
@@ -1,35 +0,0 @@
// Copyright 2025 The Gitea Authors. All rights reserved.
// SPDX-License-Identifier: MIT
package json
import (
"bytes"
"io"
"github.com/goccy/go-json"
)
var _ Interface = jsonGoccy{}
type jsonGoccy struct{}
func (jsonGoccy) Marshal(v any) ([]byte, error) {
return json.Marshal(v)
}
func (jsonGoccy) Unmarshal(data []byte, v any) error {
return json.Unmarshal(data, v)
}
func (jsonGoccy) NewEncoder(writer io.Writer) Encoder {
return json.NewEncoder(writer)
}
func (jsonGoccy) NewDecoder(reader io.Reader) Decoder {
return json.NewDecoder(reader)
}
func (jsonGoccy) Indent(dst *bytes.Buffer, src []byte, prefix, indent string) error {
return json.Indent(dst, src, prefix, indent)
}
+2 -2
View File
@@ -6,12 +6,12 @@
package json
import (
"encoding/json"
"encoding/json" //nolint:depguard // this package wraps it
"io"
)
func getDefaultJSONHandler() Interface {
return jsonGoccy{}
return jsonV1{}
}
func MarshalKeepOptionalEmpty(v any) ([]byte, error) {
+27 -1
View File
@@ -21,7 +21,33 @@ import (
// RegisterRenderers registers all supported third part renderers according settings
func RegisterRenderers() {
markup.RegisterRenderer(&openAPIRenderer{})
markup.RegisterRenderer(&frontendRenderer{
name: "openapi-swagger",
patterns: []string{
"openapi.yaml",
"openapi.yml",
"openapi.json",
"swagger.yaml",
"swagger.yml",
"swagger.json",
},
})
markup.RegisterRenderer(&frontendRenderer{
name: "viewer-3d",
patterns: []string{
// It needs more logic to make it overall right (render a text 3D model automatically):
// we need to distinguish the ambiguous filename extensions.
// For example: "*.amf, *.obj, *.off, *.step" might be or not be a 3D model file.
// So when it is a text file, we can't assume that "we only render it by 3D plugin",
// otherwise the end users would be impossible to view its real content when the file is not a 3D model.
"*.3dm", "*.3ds", "*.3mf", "*.amf", "*.bim", "*.brep",
"*.dae", "*.fbx", "*.fcstd", "*.glb", "*.gltf",
"*.ifc", "*.igs", "*.iges", "*.stp", "*.step",
"*.stl", "*.obj", "*.off", "*.ply", "*.wrl",
},
})
for _, renderer := range setting.ExternalMarkupRenderers {
markup.RegisterRenderer(&Renderer{renderer})
}
+95
View File
@@ -0,0 +1,95 @@
// Copyright 2026 The Gitea Authors. All rights reserved.
// SPDX-License-Identifier: MIT
package external
import (
"encoding/base64"
"io"
"unicode/utf8"
"code.gitea.io/gitea/modules/htmlutil"
"code.gitea.io/gitea/modules/markup"
"code.gitea.io/gitea/modules/public"
"code.gitea.io/gitea/modules/setting"
"code.gitea.io/gitea/modules/util"
)
type frontendRenderer struct {
name string
patterns []string
}
var (
_ markup.PostProcessRenderer = (*frontendRenderer)(nil)
_ markup.ExternalRenderer = (*frontendRenderer)(nil)
)
func (p *frontendRenderer) Name() string {
return p.name
}
func (p *frontendRenderer) NeedPostProcess() bool {
return false
}
func (p *frontendRenderer) FileNamePatterns() []string {
// TODO: the file extensions are ambiguous, even if the file name matches, it doesn't mean that the file is a 3D model
// There are some approaches to make it more accurate, but they are all complicated:
// A. Make backend know everything (detect a file is a 3D model or not)
// B. Let frontend renders to try render one by one
//
// If there would be more frontend renders in the future, we need to implement the "frontend" approach:
// 1. Make backend or parent window collect the supported extensions of frontend renders (done: backend external render framework)
// 2. If the current file matches any extension, start the general iframe embedded render (done: this renderer)
// 3. The iframe window calls the frontend renders one by one (done: frontend external render)
// 4. Report the render result to parent by postMessage (TODO: when needed)
return p.patterns
}
func (p *frontendRenderer) SanitizerRules() []setting.MarkupSanitizerRule {
return nil
}
func (p *frontendRenderer) GetExternalRendererOptions() (ret markup.ExternalRendererOptions) {
ret.SanitizerDisabled = true
ret.DisplayInIframe = true
ret.ContentSandbox = "allow-scripts allow-forms allow-modals allow-popups allow-downloads"
return ret
}
func (p *frontendRenderer) Render(ctx *markup.RenderContext, input io.Reader, output io.Writer) error {
if ctx.RenderOptions.StandalonePageOptions == nil {
opts := p.GetExternalRendererOptions()
return markup.RenderIFrame(ctx, &opts, output)
}
content, err := util.ReadWithLimit(input, int(setting.UI.MaxDisplayFileSize))
if err != nil {
return err
}
contentEncoding, contentString := "text", util.UnsafeBytesToString(content)
if !utf8.Valid(content) {
contentEncoding = "base64"
contentString = base64.StdEncoding.EncodeToString(content)
}
_, err = htmlutil.HTMLPrintf(output,
`<!DOCTYPE html>
<html>
<head>
<!-- external-render-helper will be injected here by the markup render -->
<meta name="viewport" content="width=device-width, initial-scale=1">
</head>
<body>
<div id="frontend-render-viewer" data-frontend-renders="%s" data-file-tree-path="%s"></div>
<textarea id="frontend-render-data" data-content-encoding="%s" hidden>%s</textarea>
<script nonce type="module" src="%s"></script>
</body>
</html>`,
p.name, ctx.RenderOptions.RelativePath,
contentEncoding, contentString,
public.AssetURI("js/external-render-frontend.js"))
return err
}
-84
View File
@@ -1,84 +0,0 @@
// Copyright 2026 The Gitea Authors. All rights reserved.
// SPDX-License-Identifier: MIT
package external
import (
"fmt"
"html"
"io"
"code.gitea.io/gitea/modules/markup"
"code.gitea.io/gitea/modules/public"
"code.gitea.io/gitea/modules/setting"
"code.gitea.io/gitea/modules/util"
)
type openAPIRenderer struct{}
var (
_ markup.PostProcessRenderer = (*openAPIRenderer)(nil)
_ markup.ExternalRenderer = (*openAPIRenderer)(nil)
)
func (p *openAPIRenderer) Name() string {
return "openapi"
}
func (p *openAPIRenderer) NeedPostProcess() bool {
return false
}
func (p *openAPIRenderer) FileNamePatterns() []string {
return []string{
"openapi.yaml",
"openapi.yml",
"openapi.json",
"swagger.yaml",
"swagger.yml",
"swagger.json",
}
}
func (p *openAPIRenderer) SanitizerRules() []setting.MarkupSanitizerRule {
return nil
}
func (p *openAPIRenderer) GetExternalRendererOptions() (ret markup.ExternalRendererOptions) {
ret.SanitizerDisabled = true
ret.DisplayInIframe = true
ret.ContentSandbox = "allow-scripts allow-forms allow-modals allow-popups allow-downloads"
return ret
}
func (p *openAPIRenderer) Render(ctx *markup.RenderContext, input io.Reader, output io.Writer) error {
if ctx.RenderOptions.StandalonePageOptions == nil {
opts := p.GetExternalRendererOptions()
return markup.RenderIFrame(ctx, &opts, output)
}
content, err := util.ReadWithLimit(input, int(setting.UI.MaxDisplayFileSize))
if err != nil {
return err
}
// HINT: SWAGGER-OPENAPI-VIEWER: another place "templates/swagger/openapi-viewer.tmpl"
_, err = io.WriteString(output, fmt.Sprintf(
`<!DOCTYPE html>
<html>
<head>
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="stylesheet" href="%s">
</head>
<body>
<div id="swagger-ui"><textarea class="swagger-spec-content" data-spec-filename="%s">%s</textarea></div>
<script type="module" src="%s"></script>
</body>
</html>`,
public.AssetURI("css/swagger.css"),
html.EscapeString(ctx.RenderOptions.RelativePath),
html.EscapeString(util.UnsafeBytesToString(content)),
public.AssetURI("js/swagger.js"),
))
return err
}
+21 -8
View File
@@ -6,6 +6,7 @@ package markup
import (
"bytes"
"context"
"errors"
"fmt"
"html/template"
"io"
@@ -43,7 +44,8 @@ type WebThemeInterface interface {
}
type StandalonePageOptions struct {
CurrentWebTheme WebThemeInterface
CurrentWebTheme WebThemeInterface
RenderQueryString string
}
type RenderOptions struct {
@@ -206,17 +208,23 @@ func RenderString(ctx *RenderContext, content string) (string, error) {
}
func RenderIFrame(ctx *RenderContext, opts *ExternalRendererOptions, output io.Writer) error {
ownerName, repoName := ctx.RenderOptions.Metas["user"], ctx.RenderOptions.Metas["repo"]
refSubURL := ctx.RenderOptions.Metas["RefTypeNameSubURL"]
if ownerName == "" || repoName == "" || refSubURL == "" {
setting.PanicInDevOrTesting("RenderIFrame requires user, repo and RefTypeNameSubURL metas")
return errors.New("RenderIFrame requires user, repo and RefTypeNameSubURL metas")
}
src := fmt.Sprintf("%s/%s/%s/render/%s/%s", setting.AppSubURL,
url.PathEscape(ctx.RenderOptions.Metas["user"]),
url.PathEscape(ctx.RenderOptions.Metas["repo"]),
util.PathEscapeSegments(ctx.RenderOptions.Metas["RefTypeNameSubURL"]),
url.PathEscape(ownerName),
url.PathEscape(repoName),
ctx.RenderOptions.Metas["RefTypeNameSubURL"],
util.PathEscapeSegments(ctx.RenderOptions.RelativePath),
)
var extraAttrs template.HTML
if opts.ContentSandbox != "" {
extraAttrs = htmlutil.HTMLFormat(` sandbox="%s"`, opts.ContentSandbox)
}
_, err := htmlutil.HTMLPrintf(output, `<iframe data-src="%s" class="external-render-iframe"%s></iframe>`, src, extraAttrs)
_, err := htmlutil.HTMLPrintf(output, `<iframe data-src="%s" data-global-init="initExternalRenderIframe" class="external-render-iframe"%s></iframe>`, src, extraAttrs)
return err
}
@@ -228,7 +236,7 @@ func pipes() (io.ReadCloser, io.WriteCloser, func()) {
}
}
func getExternalRendererOptions(renderer Renderer) (ret ExternalRendererOptions, _ bool) {
func GetExternalRendererOptions(renderer Renderer) (ret ExternalRendererOptions, _ bool) {
if externalRender, ok := renderer.(ExternalRenderer); ok {
return externalRender.GetExternalRendererOptions(), true
}
@@ -237,7 +245,7 @@ func getExternalRendererOptions(renderer Renderer) (ret ExternalRendererOptions,
func RenderWithRenderer(ctx *RenderContext, renderer Renderer, input io.Reader, output io.Writer) error {
var extraHeadHTML template.HTML
if extOpts, ok := getExternalRendererOptions(renderer); ok && extOpts.DisplayInIframe {
if extOpts, ok := GetExternalRendererOptions(renderer); ok && extOpts.DisplayInIframe {
if ctx.RenderOptions.StandalonePageOptions == nil {
// for an external "DisplayInIFrame" render, it could only output its content in a standalone page
// otherwise, a <iframe> should be outputted to embed the external rendered page
@@ -248,7 +256,12 @@ func RenderWithRenderer(ctx *RenderContext, renderer Renderer, input io.Reader,
extraLinkHref := ctx.RenderOptions.StandalonePageOptions.CurrentWebTheme.PublicAssetURI()
// "<script>" must go before "<link>", to make Golang's http.DetectContentType() can still recognize the content as "text/html"
// DO NOT use "type=module", the script must run as early as possible, to set up the environment in the iframe
extraHeadHTML = htmlutil.HTMLFormat(`<script crossorigin src="%s"></script><link rel="stylesheet" href="%s">`, extraScriptSrc, extraLinkHref)
extraHeadHTML = htmlutil.HTMLFormat(
`<script nonce crossorigin src="%s" id="gitea-external-render-helper" data-render-query-string="%s"></script>`+
`<link rel="stylesheet" href="%s">`,
extraScriptSrc, ctx.RenderOptions.StandalonePageOptions.RenderQueryString,
extraLinkHref,
)
}
ctx.usedByRender = true
+2 -2
View File
@@ -24,8 +24,8 @@ func TestRenderIFrame(t *testing.T) {
// the value is read from config RENDER_CONTENT_SANDBOX, empty means "disabled"
ret := render(ctx, ExternalRendererOptions{ContentSandbox: ""})
assert.Equal(t, `<iframe data-src="/test-owner/test-repo/render/src/branch/master/tree-path" class="external-render-iframe"></iframe>`, ret)
assert.Equal(t, `<iframe data-src="/test-owner/test-repo/render/src/branch/master/tree-path" data-global-init="initExternalRenderIframe" class="external-render-iframe"></iframe>`, ret)
ret = render(ctx, ExternalRendererOptions{ContentSandbox: "allow"})
assert.Equal(t, `<iframe data-src="/test-owner/test-repo/render/src/branch/master/tree-path" class="external-render-iframe" sandbox="allow"></iframe>`, ret)
assert.Equal(t, `<iframe data-src="/test-owner/test-repo/render/src/branch/master/tree-path" data-global-init="initExternalRenderIframe" class="external-render-iframe" sandbox="allow"></iframe>`, ret)
}
+19 -12
View File
@@ -47,6 +47,7 @@ type Metadata struct {
Keywords []string `json:"keywords,omitempty"`
RepositoryURL string `json:"repository_url,omitempty"`
License string `json:"license,omitempty"`
LicenseURL string `json:"license_url,omitempty"`
Author Person `json:"author"`
Manifests map[string]*Manifest `json:"manifests,omitempty"`
}
@@ -67,7 +68,8 @@ type SoftwareSourceCode struct {
Keywords []string `json:"keywords,omitempty"`
CodeRepository string `json:"codeRepository,omitempty"`
License string `json:"license,omitempty"`
Author Person `json:"author"`
LicenseURL string `json:"licenseURL,omitempty"`
Author *Person `json:"author,omitempty"`
ProgrammingLanguage ProgrammingLanguage `json:"programmingLanguage"`
RepositoryURLs []string `json:"repositoryURLs,omitempty"`
}
@@ -181,26 +183,31 @@ func ParsePackage(sr io.ReaderAt, size int64, mr io.Reader) (*Package, error) {
if err := json.NewDecoder(mr).Decode(&ssc); err != nil {
return nil, err
}
p.Metadata.Description = ssc.Description
p.Metadata.Keywords = ssc.Keywords
p.Metadata.License = ssc.License
author := Person{
Name: ssc.Author.Name,
GivenName: ssc.Author.GivenName,
MiddleName: ssc.Author.MiddleName,
FamilyName: ssc.Author.FamilyName,
p.Metadata.LicenseURL = ssc.LicenseURL
if ssc.Author != nil {
author := Person{
Name: ssc.Author.Name,
GivenName: ssc.Author.GivenName,
MiddleName: ssc.Author.MiddleName,
FamilyName: ssc.Author.FamilyName,
}
// If Name is not provided, generate it from individual name components
if author.Name == "" {
author.Name = author.String()
}
p.Metadata.Author = author
}
// If Name is not provided, generate it from individual name components
if author.Name == "" {
author.Name = author.String()
}
p.Metadata.Author = author
p.Metadata.RepositoryURL = ssc.CodeRepository
if !validation.IsValidURL(p.Metadata.RepositoryURL) {
p.Metadata.RepositoryURL = ""
}
if !validation.IsValidURL(p.Metadata.LicenseURL) {
p.Metadata.LicenseURL = ""
}
p.RepositoryURLs = ssc.RepositoryURLs
}
+39 -36
View File
@@ -4,11 +4,12 @@
package swift
import (
"archive/zip"
"bytes"
"strings"
"testing"
"code.gitea.io/gitea/modules/test"
"github.com/hashicorp/go-version"
"github.com/stretchr/testify/assert"
)
@@ -18,36 +19,24 @@ const (
packageVersion = "1.0.1"
packageDescription = "Package Description"
packageRepositoryURL = "https://gitea.io/gitea/gitea"
packageLicenseURL = "https://opensource.org/license/mit"
packageAuthor = "KN4CK3R"
packageLicense = "MIT"
)
func TestParsePackage(t *testing.T) {
createArchive := func(files map[string][]byte) *bytes.Reader {
var buf bytes.Buffer
zw := zip.NewWriter(&buf)
for filename, content := range files {
w, _ := zw.Create(filename)
w.Write(content)
}
zw.Close()
return bytes.NewReader(buf.Bytes())
}
t.Run("MissingManifestFile", func(t *testing.T) {
data := createArchive(map[string][]byte{"dummy.txt": {}})
p, err := ParsePackage(data, data.Size(), nil)
data := test.WriteZipArchive(map[string]string{"dummy.txt": ""})
p, err := ParsePackage(bytes.NewReader(data.Bytes()), int64(data.Len()), nil)
assert.Nil(t, p)
assert.ErrorIs(t, err, ErrMissingManifestFile)
})
t.Run("ManifestFileTooLarge", func(t *testing.T) {
data := createArchive(map[string][]byte{
"Package.swift": make([]byte, maxManifestFileSize+1),
data := test.WriteZipArchive(map[string]string{
"Package.swift": strings.Repeat("a", maxManifestFileSize+1),
})
p, err := ParsePackage(data, data.Size(), nil)
p, err := ParsePackage(bytes.NewReader(data.Bytes()), int64(data.Len()), nil)
assert.Nil(t, p)
assert.ErrorIs(t, err, ErrManifestFileTooLarge)
})
@@ -56,12 +45,12 @@ func TestParsePackage(t *testing.T) {
content1 := "// swift-tools-version:5.7\n//\n// Package.swift"
content2 := "// swift-tools-version:5.6\n//\n// Package@swift-5.6.swift"
data := createArchive(map[string][]byte{
"Package.swift": []byte(content1),
"Package@swift-5.5.swift": []byte(content2),
data := test.WriteZipArchive(map[string]string{
"Package.swift": content1,
"Package@swift-5.5.swift": content2,
})
p, err := ParsePackage(data, data.Size(), nil)
p, err := ParsePackage(bytes.NewReader(data.Bytes()), int64(data.Len()), nil)
assert.NotNil(t, p)
assert.NoError(t, err)
@@ -77,14 +66,13 @@ func TestParsePackage(t *testing.T) {
})
t.Run("WithMetadata", func(t *testing.T) {
data := createArchive(map[string][]byte{
"Package.swift": []byte("// swift-tools-version:5.7\n//\n// Package.swift"),
data := test.WriteZipArchive(map[string]string{
"Package.swift": "// swift-tools-version:5.7\n//\n// Package.swift",
})
p, err := ParsePackage(
data,
data.Size(),
strings.NewReader(`{"name":"`+packageName+`","version":"`+packageVersion+`","description":"`+packageDescription+`","keywords":["swift","package"],"license":"`+packageLicense+`","codeRepository":"`+packageRepositoryURL+`","author":{"givenName":"`+packageAuthor+`"},"repositoryURLs":["`+packageRepositoryURL+`"]}`),
bytes.NewReader(data.Bytes()), int64(data.Len()),
strings.NewReader(`{"name":"`+packageName+`","version":"`+packageVersion+`","description":"`+packageDescription+`","keywords":["swift","package"],"license":"`+packageLicense+`","licenseURL":"`+packageLicenseURL+`","codeRepository":"`+packageRepositoryURL+`","author":{"givenName":"`+packageAuthor+`"},"repositoryURLs":["`+packageRepositoryURL+`"]}`),
)
assert.NotNil(t, p)
assert.NoError(t, err)
@@ -97,6 +85,7 @@ func TestParsePackage(t *testing.T) {
assert.Equal(t, packageDescription, p.Metadata.Description)
assert.ElementsMatch(t, []string{"swift", "package"}, p.Metadata.Keywords)
assert.Equal(t, packageLicense, p.Metadata.License)
assert.Equal(t, packageLicenseURL, p.Metadata.LicenseURL)
assert.Equal(t, packageAuthor, p.Metadata.Author.Name)
assert.Equal(t, packageAuthor, p.Metadata.Author.GivenName)
assert.Equal(t, packageRepositoryURL, p.Metadata.RepositoryURL)
@@ -104,14 +93,13 @@ func TestParsePackage(t *testing.T) {
})
t.Run("WithExplicitNameField", func(t *testing.T) {
data := createArchive(map[string][]byte{
"Package.swift": []byte("// swift-tools-version:5.7\n//\n// Package.swift"),
data := test.WriteZipArchive(map[string]string{
"Package.swift": "// swift-tools-version:5.7\n//\n// Package.swift",
})
authorName := "John Doe"
p, err := ParsePackage(
data,
data.Size(),
bytes.NewReader(data.Bytes()), int64(data.Len()),
strings.NewReader(`{"name":"`+packageName+`","version":"`+packageVersion+`","description":"`+packageDescription+`","author":{"name":"`+authorName+`","givenName":"John","familyName":"Doe"}}`),
)
assert.NotNil(t, p)
@@ -122,15 +110,30 @@ func TestParsePackage(t *testing.T) {
assert.Equal(t, "Doe", p.Metadata.Author.FamilyName)
})
t.Run("WithEmptyJSONMetadata", func(t *testing.T) {
data := test.WriteZipArchive(map[string]string{
"Package.swift": "// swift-tools-version:5.7\n//\n// Package.swift",
})
p, err := ParsePackage(
bytes.NewReader(data.Bytes()), int64(data.Len()),
strings.NewReader(`{}`),
)
assert.NotNil(t, p)
assert.NoError(t, err)
assert.NotNil(t, p.Metadata)
assert.Empty(t, p.Metadata.Author.Name)
assert.Empty(t, p.RepositoryURLs)
})
t.Run("NameFieldGeneration", func(t *testing.T) {
data := createArchive(map[string][]byte{
"Package.swift": []byte("// swift-tools-version:5.7\n//\n// Package.swift"),
data := test.WriteZipArchive(map[string]string{
"Package.swift": "// swift-tools-version:5.7\n//\n// Package.swift",
})
// Test with only individual name components - Name should be auto-generated
p, err := ParsePackage(
data,
data.Size(),
bytes.NewReader(data.Bytes()), int64(data.Len()),
strings.NewReader(`{"author":{"givenName":"John","middleName":"Q","familyName":"Doe"}}`),
)
assert.NotNil(t, p)
+2
View File
@@ -56,6 +56,8 @@ func parseManifest(data []byte) (map[string]string, map[string]string) {
paths[key] = entry.File
names[entry.File] = entry.Name
// Map associated CSS files, e.g. "css/index.css" -> "css/index.B3zrQPqD.css"
// FIXME: INCORRECT-VITE-MANIFEST-PARSER: the logic is wrong, Vite manifest doesn't work this way
// It just happens to be correct for the current modules dependencies
for _, css := range entry.CSS {
cssKey := path.Dir(css) + "/" + entry.Name + path.Ext(css)
paths[cssKey] = css
+37
View File
@@ -12,10 +12,29 @@ import (
var Admin struct {
DisableRegularOrgCreation bool
DefaultEmailNotification string
SuperAdminEnabled bool
AdminManagementPolicy string
UserDisabledFeatures container.Set[string]
ExternalUserDisableFeatures container.Set[string]
}
const (
AdminManagementPolicySuperAdminOnly = "super_admin_only"
AdminManagementPolicyGrantorOnly = "grantor_only"
AdminManagementPolicyGrantorInheritance = "grantor_inheritance"
AdminManagementPolicyAdminsCanPromote = "admins_can_promote_users"
AdminManagementPolicySuperAdminApproval = "super_admin_approval"
defaultAdminManagementPolicy = AdminManagementPolicyGrantorOnly
)
var validAdminManagementPolicies = container.SetOf(
AdminManagementPolicySuperAdminOnly,
AdminManagementPolicyGrantorOnly,
AdminManagementPolicyGrantorInheritance,
AdminManagementPolicyAdminsCanPromote,
AdminManagementPolicySuperAdminApproval,
)
var validUserFeatures = container.SetOf(
UserFeatureDeletion,
UserFeatureManageSSHKeys,
@@ -30,9 +49,16 @@ func loadAdminFrom(rootCfg ConfigProvider) {
sec := rootCfg.Section("admin")
Admin.DisableRegularOrgCreation = sec.Key("DISABLE_REGULAR_ORG_CREATION").MustBool(false)
Admin.DefaultEmailNotification = sec.Key("DEFAULT_EMAIL_NOTIFICATIONS").MustString("enabled")
Admin.SuperAdminEnabled = sec.Key("SUPER_ADMIN_ENABLED").MustBool(true)
Admin.AdminManagementPolicy = normalizeAdminManagementPolicy(sec.Key("ADMIN_MANAGEMENT_POLICY").MustString(defaultAdminManagementPolicy))
Admin.UserDisabledFeatures = container.SetOf(sec.Key("USER_DISABLED_FEATURES").Strings(",")...)
Admin.ExternalUserDisableFeatures = container.SetOf(sec.Key("EXTERNAL_USER_DISABLE_FEATURES").Strings(",")...).Union(Admin.UserDisabledFeatures)
if !validAdminManagementPolicies.Contains(Admin.AdminManagementPolicy) {
log.Warn("ADMIN_MANAGEMENT_POLICY contains unknown policy %q, using %q", Admin.AdminManagementPolicy, defaultAdminManagementPolicy)
Admin.AdminManagementPolicy = defaultAdminManagementPolicy
}
for feature := range Admin.UserDisabledFeatures {
if !validUserFeatures.Contains(feature) {
log.Warn("USER_DISABLED_FEATURES contains unknown feature %q", feature)
@@ -45,6 +71,17 @@ func loadAdminFrom(rootCfg ConfigProvider) {
}
}
func normalizeAdminManagementPolicy(policy string) string {
switch policy {
case AdminManagementPolicyAdminsCanPromote:
return AdminManagementPolicyGrantorOnly
case AdminManagementPolicySuperAdminApproval:
return AdminManagementPolicySuperAdminOnly
default:
return policy
}
}
const (
UserFeatureDeletion = "deletion"
UserFeatureManageSSHKeys = "manage_ssh_keys"
+1
View File
@@ -6,6 +6,7 @@ package setting
// defaultI18nLangNames must be a slice, we need the order
var defaultI18nLangNames = []string{
"en-US", "English",
"ro-RO", "Română",
"zh-CN", "简体中文",
"zh-HK", "繁體中文(香港)",
"zh-TW", "繁體中文(台灣)",
+2
View File
@@ -31,6 +31,7 @@ var (
ReverseProxyAuthEmail string
ReverseProxyAuthFullName string
ReverseProxyLimit int
ReverseProxyLogoutRedirect string
ReverseProxyTrustedProxies []string
MinPasswordLength int
ImportLocalPaths bool
@@ -124,6 +125,7 @@ func loadSecurityFrom(rootCfg ConfigProvider) {
ReverseProxyAuthFullName = sec.Key("REVERSE_PROXY_AUTHENTICATION_FULL_NAME").MustString("X-WEBAUTH-FULLNAME")
ReverseProxyLimit = sec.Key("REVERSE_PROXY_LIMIT").MustInt(1)
ReverseProxyLogoutRedirect = sec.Key("REVERSE_PROXY_LOGOUT_REDIRECT").String()
ReverseProxyTrustedProxies = sec.Key("REVERSE_PROXY_TRUSTED_PROXIES").Strings(",")
if len(ReverseProxyTrustedProxies) == 0 {
ReverseProxyTrustedProxies = []string{"127.0.0.0/8", "::1/128"}
+9
View File
@@ -21,6 +21,9 @@ const (
HCaptcha = "hcaptcha"
MCaptcha = "mcaptcha"
CfTurnstile = "cfturnstile"
AdminCreatedAccountModeLocal = "local"
AdminCreatedAccountModeInvite = "invite"
)
// Service settings
@@ -38,6 +41,7 @@ var Service = struct {
EmailDomainAllowList []glob.Glob
EmailDomainBlockList []glob.Glob
DisableRegistration bool
AdminCreatedAccountMode string
AllowOnlyInternalRegistration bool
AllowOnlyExternalRegistration bool
ShowRegistrationButton bool
@@ -149,6 +153,11 @@ func loadServiceFrom(rootCfg ConfigProvider) {
Service.ActiveCodeLives = sec.Key("ACTIVE_CODE_LIVE_MINUTES").MustInt(180)
Service.ResetPwdCodeLives = sec.Key("RESET_PASSWD_CODE_LIVE_MINUTES").MustInt(180)
Service.DisableRegistration = sec.Key("DISABLE_REGISTRATION").MustBool()
defaultAdminCreatedAccountMode := AdminCreatedAccountModeLocal
if Service.DisableRegistration {
defaultAdminCreatedAccountMode = AdminCreatedAccountModeInvite
}
Service.AdminCreatedAccountMode = sec.Key("ADMIN_CREATED_ACCOUNT_MODE").In(defaultAdminCreatedAccountMode, []string{AdminCreatedAccountModeLocal, AdminCreatedAccountModeInvite})
Service.AllowOnlyInternalRegistration = sec.Key("ALLOW_ONLY_INTERNAL_REGISTRATION").MustBool()
Service.AllowOnlyExternalRegistration = sec.Key("ALLOW_ONLY_EXTERNAL_REGISTRATION").MustBool()
if Service.AllowOnlyExternalRegistration && Service.AllowOnlyInternalRegistration {
+1 -1
View File
@@ -201,7 +201,7 @@ func mustCurrentRunUserMatch(rootCfg ConfigProvider) {
if HasInstallLock(rootCfg) {
currentUser, match := IsRunUserMatchCurrentUser(RunUser)
if !match {
log.Fatal("Expect user '%s' but current user is: %s", RunUser, currentUser)
log.Fatal("Expect user '%s' (RUN_USER in app.ini) but current user is: %s", RunUser, currentUser)
}
}
}
+16 -3
View File
@@ -5,6 +5,7 @@ package templates
import (
"html/template"
"net/url"
"strings"
"testing"
@@ -169,9 +170,21 @@ func TestQueryBuild(t *testing.T) {
})
}
const queryNonASCII = " !\"#$%&'()*+,-./:;<=>?@[\\]^_`{|}~" // all non-letter & non-number chars
func TestQueryEscape(t *testing.T) {
// this test is a reference for "urlQueryEscape" in JS
in := "!\"#$%&'()*+,-./:;<=>?@[\\]^_`{|}~" // all non-letter & non-number chars
expected := "%21%22%23%24%25%26%27%28%29%2A%2B%2C-.%2F%3A%3B%3C%3D%3E%3F%40%5B%5C%5D%5E_%60%7B%7C%7D~"
assert.Equal(t, expected, string(queryEscape(in)))
// Special case for space encoding:
// * RFC 3986: Uniform Resource Identifier (URI): %20
// * WHATWG HTML: application/x-www-form-urlencoded: +
// * JavaScript: encodeURIComponent() uses "%20". URLSearchParams uses "+"
// * Golang: QueryEscape uses "+"
expected := "+%21%22%23%24%25%26%27%28%29%2A%2B%2C-.%2F%3A%3B%3C%3D%3E%3F%40%5B%5C%5D%5E_%60%7B%7C%7D~"
assert.Equal(t, expected, url.QueryEscape(queryNonASCII))
}
func TestPathEscape(t *testing.T) {
// this test is a reference for "pathEscape" in JS
expected := "%20%21%22%23$%25&%27%28%29%2A+%2C-.%2F:%3B%3C=%3E%3F@%5B%5C%5D%5E_%60%7B%7C%7D~"
assert.Equal(t, expected, url.PathEscape(queryNonASCII))
}
+12
View File
@@ -5,6 +5,7 @@ package test
import (
"archive/tar"
"archive/zip"
"bytes"
"compress/gzip"
"io"
@@ -97,6 +98,17 @@ func WriteTarArchive(files map[string]string) *bytes.Buffer {
return WriteTarCompression(func(w io.Writer) io.WriteCloser { return util.NopCloser{Writer: w} }, files)
}
func WriteZipArchive(files map[string]string) *bytes.Buffer {
buf := &bytes.Buffer{}
zw := zip.NewWriter(buf)
for name, content := range files {
w, _ := zw.Create(name)
_, _ = w.Write([]byte(content))
}
_ = zw.Close()
return buf
}
func WriteTarCompression[F func(io.Writer) io.WriteCloser | func(io.Writer) (io.WriteCloser, error)](compression F, files map[string]string) *bytes.Buffer {
buf := &bytes.Buffer{}
var cw io.WriteCloser
+6 -4
View File
@@ -255,11 +255,13 @@ func EnumValue[T comparable](val EnumConst[T]) (ret T, valid bool) {
return enums[0], false
}
func ReserveLineBreakForTextarea(input string) string {
func NormalizeStringEOL(input string) string {
// Since the content is from a form which is a textarea, the line endings are \r\n.
// It's a standard behavior of HTML.
// But we want to store them as \n like what GitHub does.
// And users are unlikely to really need to keep the \r.
// But in most cases, we only want "\n" for EOL
// * Text files: use "\n" by default because "\r\n" sometimes doesn't work in POSIX
// * Actions values: store them as "\n" like what GitHub does.
// And users are unlikely to really need the "\r".
// Other than this, we should respect the original content, even leading or trailing spaces.
return strings.ReplaceAll(input, "\r\n", "\n")
return UnsafeBytesToString(NormalizeEOL(UnsafeStringToBytes(input)))
}
+10 -3
View File
@@ -175,9 +175,9 @@ func TestToTitleCase(t *testing.T) {
assert.Equal(t, `Foo Bar Baz`, ToTitleCase(`FOO BAR BAZ`))
}
func TestReserveLineBreakForTextarea(t *testing.T) {
assert.Equal(t, "test\ndata", ReserveLineBreakForTextarea("test\r\ndata"))
assert.Equal(t, "test\ndata\n", ReserveLineBreakForTextarea("test\r\ndata\r\n"))
func TestNormalizeStringEOL(t *testing.T) {
assert.Equal(t, "test\ndata", NormalizeStringEOL("test\r\ndata"))
assert.Equal(t, " test\ndata\n ", NormalizeStringEOL(" test\rdata\r "))
}
func TestOptionalArg(t *testing.T) {
@@ -192,3 +192,10 @@ func TestOptionalArg(t *testing.T) {
assert.Equal(t, 42, bar(nil))
assert.Equal(t, 100, bar(nil, 100))
}
func TestPathEscapeSegments(t *testing.T) {
assert.Equal(t, "a", PathEscapeSegments("a"))
assert.Equal(t, "a/b", PathEscapeSegments("a/b"))
assert.Equal(t, "a/b%20c", PathEscapeSegments("a/b c"))
assert.Equal(t, "a/b+c", PathEscapeSegments("a/b+c"))
}
+17
View File
@@ -5,12 +5,14 @@ package validation
import (
"fmt"
"io"
"regexp"
"strings"
"code.gitea.io/gitea/modules/auth"
"code.gitea.io/gitea/modules/git"
"code.gitea.io/gitea/modules/glob"
"code.gitea.io/gitea/modules/json"
"code.gitea.io/gitea/modules/util"
"gitea.com/go-chi/binding"
@@ -31,8 +33,23 @@ const (
ErrInvalidBadgeSlug = "InvalidBadgeSlug"
)
type jsonProvider struct{}
func (j jsonProvider) Marshal(v any) ([]byte, error) { return json.Marshal(v) }
func (j jsonProvider) Unmarshal(data []byte, v any) error { return json.Unmarshal(data, v) }
func (j jsonProvider) NewDecoder(reader io.Reader) binding.JSONDecoder {
return json.NewDecoder(reader)
}
func (j jsonProvider) NewEncoder(writer io.Writer) binding.JSONEncoder {
return json.NewEncoder(writer)
}
// AddBindingRules adds additional binding rules
func AddBindingRules() {
binding.JSONProvider = jsonProvider{}
addGitRefNameBindingRule()
addValidURLListBindingRule()
addValidURLBindingRule()
+1
View File
@@ -17,6 +17,7 @@ import (
const (
CookieWebBannerDismissed = "gitea_disbnr"
CookieTheme = "gitea_theme"
CookiePersistentFooter = "gitea_persistent_footer"
cookieRedirectTo = "redirect_to"
)
+61 -8
View File
@@ -183,8 +183,10 @@
"startpage.lightweight_desc": "Gitea má minimální požadavky a může běžet na Raspberry Pi. Šetřete energii vašeho stroje!",
"startpage.license_desc": "Vše je na <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%[1]s\">%[2]s</a>! Připojte se tím, že <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%[3]s\">přispějete</a> a uděláte tento projekt ještě lepší. Nestyďte se být přispěvatel!",
"install.install": "Instalace",
"install.installing_desc": "Installing now, please wait…",
"install.title": "Výchozí konfigurace",
"install.docker_helper": "Pokud spouštíte Gitea v Dockeru, přečtěte si <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">dokumentaci</a>, než budete měnit jakákoliv nastavení.",
"install.require_db_desc": "Gitea requires MySQL, PostgreSQL, MSSQL, SQLite3 or TiDB (MySQL protocol).",
"install.db_title": "Nastavení databáze",
"install.db_type": "Typ databáze",
"install.host": "Hostitel",
@@ -193,17 +195,26 @@
"install.db_name": "Název databáze",
"install.db_schema": "Schéma",
"install.db_schema_helper": "Ponechte prázdné pro výchozí nastavení databáze („public“).",
"install.ssl_mode": "SSL",
"install.path": "Cesta",
"install.sqlite_helper": "Cesta k souboru SQLite3 databáze.<br>Pokud spouštíte Gitea jako službu, zadejte absolutní cestu.",
"install.reinstall_error": "Pokoušíte se nainstalovat do existující databáze Gitea",
"install.reinstall_confirm_message": "Přeinstalování s existující databází Gitea může způsobit více problémů. Ve většině případů byste měli použít existující „app.ini“ pro spuštění Gitea. Pokud víte, co děláte, potvrďte následující:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "Potvrzujete, že jste si naprosto jisti, že tato Gitea je spuštěna se správným umístěním souboru app.ini a že jste si jisti, že musíte provést novou instalaci. Potvrzujete, že berete na vědomí výše uvedená rizika.",
"install.err_empty_db_path": "Cesta k SQLite3 databázi nemůže být prázdná.",
"install.no_admin_and_disable_registration": "Nemůžete vypnout registraci účtů bez vytvoření účtu správce.",
"install.err_empty_admin_password": "Heslo administrátora nemůže být prázdné.",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "Obecná nastavení",
"install.app_name": "Název stránky",
"install.app_name_helper": "Zde můžete zadat název vaší společnosti.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Kořenový adresář repozitářů",
"install.repo_path_helper": "Všechny vzdálené repozitáře Gitu budou uloženy do tohoto adresáře.",
"install.lfs_path": "Kořenový adresář Git LFS",
@@ -215,6 +226,7 @@
"install.ssh_port": "Port SSH serveru",
"install.ssh_port_helper": "Číslo portu, na kterém SSH server naslouchá. Když ponecháte prázdné, SSH server zakážete.",
"install.http_port": "Port, na kterém Gitea naslouchá HTTP protokolu",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "Základní URL Gitea",
"install.app_url_helper": "Základní adresa pro HTTP(S) URL adresy pro klonování a e-mailová oznámení.",
"install.log_root_path": "Adresář logů",
@@ -228,15 +240,33 @@
"install.smtp_from_helper": "E-mailová adresa, kterou bude Gitea používat. Zadejte běžnou e-mailovou adresu, nebo použijte formát \"Jméno\"<email@example.com>.",
"install.mailer_user": "Uživatelské jméno SMTP",
"install.mailer_password": "Heslo pro SMTP",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Pro registraci vyžadovat potvrzení e-mailu",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Povolit e-mailová oznámení",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Nastavení serveru a dalších služeb",
"install.offline_mode": "Povolit místní režim",
"install.offline_mode_popup": "Zakázat sítě pro doručování obsahu a poskytovat veškerý obsah lokálně.",
"install.disable_gravatar": "Zakázat Gravatar",
"install.disable_gravatar_popup": "Zakážete Gravatar a jiné cizí zdroje avatarů. Pokud uživatel nenahraje avatar, bude použit výchozí.",
"install.federated_avatar_lookup": "Povolit avatary z veřejných zdrojů",
"install.federated_avatar_lookup_popup": "Povolte vyhledání avatarů z veřejných zdrojů pro využití služeb založených na libravatar.",
"install.disable_registration": "Vypnout možnost uživatelské registrace",
"install.disable_registration_popup": "Vypnout možnost registrace. Pouze správci budou moci vytvářet účty.",
"install.allow_only_external_registration_popup": "Povolit registraci pouze prostřednictvím externích služeb",
@@ -244,6 +274,8 @@
"install.openid_signin_popup": "Umožňuje uživateli přihlásit se pomocí OpenID.",
"install.openid_signup": "Povolit automatickou registraci pomocí OpenID",
"install.openid_signup_popup": "Umožňuje uživateli automaticky se registrovat pomocí OpenID.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Povolit CAPTCHA při registraci",
"install.enable_captcha_popup": "Vyžadovat správně zadaný text CAPTCHA při registraci.",
"install.require_sign_in_view": "Vyžadovat přihlášení k zobrazení stránek",
@@ -254,6 +286,13 @@
"install.admin_password": "Heslo",
"install.confirm_password": "Potvrdit heslo",
"install.admin_email": "E-mailová adresa",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Nainstalovat Gitea",
"install.test_git_failed": "Chyba při testu příkazu 'git': %v",
"install.sqlite3_not_available": "Tato verze Gitea nepodporuje SQLite3. Stáhněte si oficiální binární verzi od %s (nikoli verzi „gobuild“).",
@@ -261,7 +300,6 @@
"install.invalid_db_table": "Databázová tabulka „%s“ je neplatná: %v",
"install.invalid_repo_path": "Kořenový adresář repozitářů není správný: %v",
"install.invalid_app_data_path": "Cesta k datům aplikace je neplatná: %v",
"install.run_user_not_match": "\"Run as\" uživatelské jméno není aktuální uživatelské jméno: %s -> %s",
"install.internal_token_failed": "Nepodařilo se vytvořit interní token: %v",
"install.secret_key_failed": "Nepodařilo se vytvořit tajný klíč: %v",
"install.save_config_failed": "Uložení konfigurace se nezdařilo: %v",
@@ -277,6 +315,7 @@
"install.no_reply_address_helper": "Název domény pro uživatele se skrytou e-mailovou adresou. Příklad: Pokud je název skryté e-mailové domény nastaven na „noreply.example.org“, uživatelské jméno „joe“ bude zaznamenáno v Gitu jako „joe@noreply.example.org“.",
"install.password_algorithm": "Hash algoritmus hesla",
"install.invalid_password_algorithm": "Neplatný algoritmus hash hesla",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "Povolit kontrolu aktualizací",
"install.enable_update_checker_helper": "Kontroluje vydání nových verzí pravidelně připojením ke gitea.io.",
"install.env_config_keys": "Konfigurace prostředí",
@@ -326,6 +365,9 @@
"auth.sign_up_now": "Zaregistruj se nyní.",
"auth.sign_up_successful": "Účet byl úspěšně vytvořen. Vítejte!",
"auth.confirmation_mail_sent_prompt_ex": "Nový potvrzovací e-mail byl odeslán na <b>%s</b>. Zkontrolujte prosím svou doručenou poštu během následujících %s a dokončete proces registrace. Pokud je Vaše registrační e-mailová adresa nesprávná, můžete se znovu přihlásit a změnit ji.",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.must_change_password": "Aktualizujte své heslo",
"auth.allow_password_change": "Vyžádat od uživatele změnu hesla (doporučeno)",
"auth.reset_password_mail_sent_prompt": "Na adresu <b>%s</b> byl zaslán potvrzovací e-mail. Zkontrolujte prosím vaši doručenou poštu během následujících %s, abyste dokončili proces obnovení účtu.",
@@ -2615,6 +2657,7 @@
"admin.users.created": "Vytvořen",
"admin.users.last_login": "Poslední přihlášení",
"admin.users.send_register_notify": "Odeslat upozornění při registraci uživatele",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.new_success": "Uživatelský účet „%s“ byl vytvořen.",
"admin.users.edit": "Upravit",
"admin.users.auth_source": "Zdroj ověřování",
@@ -3306,5 +3349,15 @@
"git.filemode.normal_file": "Normální soubor",
"git.filemode.executable_file": "Spustitelný soubor",
"git.filemode.symbolic_link": "Symbolický odkaz",
"git.filemode.submodule": "Submodul"
"git.filemode.submodule": "Submodul",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+63 -8
View File
@@ -174,26 +174,39 @@
"startpage.lightweight_desc": "Gitea hat minimale Systemanforderungen und kann selbst auf einem günstigen und stromsparenden Raspberry Pi betrieben werden!",
"startpage.license": "Quelloffen",
"startpage.license_desc": "Hol dir den Code unter <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%[1]s\">%[2]s</a>! Leiste deinen <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%[3]s\">Beitrag</a> bei der Verbesserung dieses Projekts. Trau dich!",
"install.install": "Installation",
"install.installing_desc": "Installing now, please wait…",
"install.title": "Erstkonfiguration",
"install.docker_helper": "Wenn du Gitea in einem Docker-Container nutzt, lies bitte die <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">Dokumentation</a>, bevor du irgendwelche Einstellungen veränderst.",
"install.require_db_desc": "Gitea benötigt MySQL, PostgreSQL, MSSQL, SQLite3 oder TiDB (MySQL-Protokoll).",
"install.db_title": "Datenbankeinstellungen",
"install.db_type": "Datenbanktyp",
"install.host": "Host",
"install.user": "Benutzername",
"install.password": "Passwort",
"install.db_name": "Datenbankname",
"install.db_schema": "Schema",
"install.db_schema_helper": "Leer lassen, um das Standard-Schema (\"public\") zu verwenden.",
"install.ssl_mode": "SSL",
"install.path": "Pfad",
"install.sqlite_helper": "Dateipfad zur SQLite3 Datenbank.<br>Gebe einen absoluten Pfad an, wenn Gitea als Service gestartet wird.",
"install.reinstall_error": "Du versuchst, in eine bereits existierende Gitea Datenbank zu installieren",
"install.reinstall_confirm_message": "Eine Neuinstallation mit einer bestehenden Gitea-Datenbank kann mehrere Probleme verursachen. In den meisten Fällen solltest du deine vorhandene \"app.ini\" verwenden, um Gitea auszuführen. Wenn du weist, was du tust, bestätigen die folgenden Angaben:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "Du bestätigst, dass du absolut sicher bist, dass diese Gitea mit der richtigen app.ini läuft, und du sicher bist, dass du neu installieren musst. Du bestätigst, dass du die oben genannten Risiken anerkennst.",
"install.err_empty_db_path": "Der SQLite3 Datenbankpfad darf nicht leer sein.",
"install.no_admin_and_disable_registration": "Du kannst Selbst-Registrierungen nicht deaktivieren, ohne ein Administratorkonto zu erstellen.",
"install.err_empty_admin_password": "Das Administrator-Passwort darf nicht leer sein.",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "Allgemeine Einstellungen",
"install.app_name": "Seitentitel",
"install.app_name_helper": "Du kannst hier den Namen deines Unternehmens eingeben.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Repository-Verzeichnis",
"install.repo_path_helper": "Remote-Git-Repositories werden in diesem Verzeichnis gespeichert.",
"install.lfs_path": "Git-LFS-Wurzelpfad",
@@ -205,6 +218,7 @@
"install.ssh_port": "SSH-Server-Port",
"install.ssh_port_helper": "Der Port deines SSH-Servers. Leer lassen, um SSH zu deaktivieren.",
"install.http_port": "Gitea-HTTP-Listen-Port",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "Gitea-Basis-URL",
"install.app_url_helper": "Adresse für HTTP(S)-Klon-URLs und E-Mail-Benachrichtigungen.",
"install.log_root_path": "Logdateipfad",
@@ -218,15 +232,33 @@
"install.smtp_from_helper": "E-Mail-Adresse, die von Gitea genutzt werden soll. Bitte gib die E-Mail-Adresse im Format „\"Name\" <email@example.com>“ ein.",
"install.mailer_user": "SMTP-Benutzername",
"install.mailer_password": "SMTP-Passwort",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "E-Mail-Bestätigung benötigt zum Registrieren",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "E-Mail-Benachrichtigungen aktivieren",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Sonstige Server- und Drittserviceeinstellungen",
"install.offline_mode": "Offline-Modus aktivieren",
"install.offline_mode_popup": "Drittanbieter-CDNs deaktivieren und alle Ressourcen lokal zur Verfügung stellen.",
"install.disable_gravatar": "Gravatar deaktivieren",
"install.disable_gravatar_popup": "Gravatar und Drittanbieter-Avatar-Quellen deaktivieren. Ein Standardavatar wird verwendet, bis der Nutzer einen eigenen Avatar hochlädt.",
"install.federated_avatar_lookup": "Föderierte Profilbilder einschalten",
"install.federated_avatar_lookup_popup": "Föderierte Profilbilder via Libravatar aktivieren.",
"install.disable_registration": "Registrierung deaktivieren",
"install.disable_registration_popup": "Registrierung neuer Benutzer deaktivieren. Nur Administratoren werden neue Benutzerkonten anlegen können.",
"install.allow_only_external_registration_popup": "Registrierung nur über externe Services erlauben",
@@ -234,6 +266,8 @@
"install.openid_signin_popup": "Benutzeranmeldung via OpenID aktivieren.",
"install.openid_signup": "OpenID-Selbstregistrierung aktivieren",
"install.openid_signup_popup": "OpenID-basierte Selbstregistrierung aktivieren.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Registrierungs-Captcha aktivieren",
"install.enable_captcha_popup": "Captcha-Eingabe bei der Registrierung erforderlich.",
"install.require_sign_in_view": "Ansehen erfordert Anmeldung",
@@ -244,6 +278,13 @@
"install.admin_password": "Passwort",
"install.confirm_password": "Passwort bestätigen",
"install.admin_email": "E-Mail-Adresse",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Gitea installieren",
"install.test_git_failed": "Fehler beim Test des „git“-Befehls: %v",
"install.sqlite3_not_available": "Diese Gitea-Version unterstützt SQLite3 nicht. Bitte lade die offizielle binäre Version von %s herunter (nicht die „gobuild“-Version).",
@@ -251,7 +292,6 @@
"install.invalid_db_table": "Die Datenbanktabelle \"%s\" ist ungültig: %v",
"install.invalid_repo_path": "Repository-Verzeichnis ist ungültig: %v",
"install.invalid_app_data_path": "Der App-Daten-Pfad ist ungültig: %v",
"install.run_user_not_match": "Der „Ausführen als“-Benutzername ist nicht der aktuelle Benutzername: %s -> %s",
"install.internal_token_failed": "Fehler beim Generieren des internen Tokens: %v",
"install.secret_key_failed": "Fehler beim Generieren des geheimen Schlüssels: %v",
"install.save_config_failed": "Fehler beim Speichern der Konfiguration: %v",
@@ -267,6 +307,7 @@
"install.no_reply_address_helper": "Domain-Name für Benutzer mit einer versteckten Emailadresse. Zum Beispiel wird der Benutzername „Joe“ in Git als „joe@noreply.example.org“ protokolliert, wenn die versteckte E-Mail-Domain „noreply.example.org“ festgelegt ist.",
"install.password_algorithm": "Passwort Hashing Algorithmus",
"install.invalid_password_algorithm": "Ungültiger Passwort-Hash-Algorithmus",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "Aktualisierungsprüfung aktivieren",
"install.enable_update_checker_helper": "Stellt regelmäßig eine Verbindung zu gitea.io her, um nach neuen Versionen zu prüfen.",
"install.env_config_keys": "Umgebungskonfiguration",
@@ -319,6 +360,9 @@
"auth.sign_up_now": "Jetzt registrieren.",
"auth.sign_up_successful": "Konto wurde erfolgreich erstellt. Willkommen!",
"auth.confirmation_mail_sent_prompt_ex": "Eine neue Bestätigungs-E-Mail wurde an <b>%s</b>gesendet. Bitte überprüfe deinen Posteingang innerhalb der nächsten %s, um den Registrierungsprozess abzuschließen. Wenn deine Registrierungs-E-Mail-Adresse falsch ist, kannst du dich erneut anmelden und diese ändern.",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.must_change_password": "Aktualisiere dein Passwort",
"auth.allow_password_change": "Verlange vom Benutzer das Passwort zu ändern (empfohlen)",
"auth.reset_password_mail_sent_prompt": "Eine Bestätigungs-E-Mail wurde an <b>%s</b> gesendet. Bitte überprüfe dein Postfach innerhalb von %s, um den Wiederherstellungsprozess abzuschließen.",
@@ -2584,6 +2628,7 @@
"admin.users.created": "Registriert am",
"admin.users.last_login": "Letzte Anmeldung",
"admin.users.send_register_notify": "Benutzer-Registrierungsbenachrichtigung senden",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.new_success": "Der Account \"%s\" wurde erstellt.",
"admin.users.edit": "Bearbeiten",
"admin.users.auth_source": "Authentifizierungsquelle",
@@ -3248,5 +3293,15 @@
"git.filemode.normal_file": "Normale Datei",
"git.filemode.executable_file": "Ausführbare Datei",
"git.filemode.symbolic_link": "Softlink",
"git.filemode.submodule": "Submodul"
"git.filemode.submodule": "Submodul",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+62 -8
View File
@@ -156,6 +156,7 @@
"startpage.lightweight_desc": "Gitea έχει χαμηλές ελάχιστες απαιτήσεις και μπορεί να τρέξει σε ένα οικονομικό Raspberry Pi. Εξοικονομήστε ενέργεια!",
"startpage.license": "Ανοικτού κώδικα",
"install.install": "Εγκατάσταση",
"install.installing_desc": "Installing now, please wait…",
"install.title": "Αρχικές Ρυθμίσεις",
"install.docker_helper": "Αν εκτελέσετε το Gitea μέσα στο Docker, παρακαλώ διαβάστε την <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">τεκμηρίωση</a> πριν αλλάξετε τις ρυθμίσεις.",
"install.require_db_desc": "Το Gitea απαιτεί MySQL, PostgreSQL, MSSQL, SQLite3 ή TiDB (με πρωτόκολλο MySQL).",
@@ -167,17 +168,26 @@
"install.db_name": "Όνομα Βάσης Δεδομένων",
"install.db_schema": "Σχήμα",
"install.db_schema_helper": "Αφήστε κενό για την προεπιλογή της βάσης δεδομένων (\"public\").",
"install.ssl_mode": "SSL",
"install.path": "Διαδρομή",
"install.sqlite_helper": "Διαδρομή αρχείου για τη βάση δεδομένων SQLite3.<br>Εισάγετε μια απόλυτη διαδρομή αν εκτελείτε το Gitea ως υπηρεσία.",
"install.reinstall_error": "Προσπαθείτε να εγκαταστήσετε σε μια υπάρχουσα βάση δεδομένων Gitea",
"install.reinstall_confirm_message": "Η επανεγκατάσταση με μια υπάρχουσα βάση δεδομένων Gitea μπορεί να προκαλέσει πολλαπλά προβλήματα. Στις περισσότερες περιπτώσεις, θα πρέπει να χρησιμοποιήσετε το υπάρχον \"app.ini\" για να εκτελέσετε το Gitea. Αν γνωρίζετε τι κάνετε, επιβεβαιώστε τα εξής:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "Επιβεβαιώνετε ότι είστε απολύτως σίγουροι ότι αυτό το Gitea τρέχει στη σωστή τοποθεσία στο app.ini και ότι είστε σίγουροι ότι θα πρέπει να επανεγκαταστήσετε. Επιβεβαιώνετε ότι αναγνωρίζετε τους παραπάνω κινδύνους.",
"install.err_empty_db_path": "Η διαδρομή της βάσης δεδομένων SQLite3 δεν μπορεί να είναι κενή.",
"install.no_admin_and_disable_registration": "Δεν μπορείτε να απενεργοποιήσετε την ιδιο-εγγραφή χρήστη χωρίς να έχετε δημιουργήσει διαχειριστικό λογαριασμό.",
"install.err_empty_admin_password": "Ο κωδικός πρόσβασης του διαχειριστή δεν μπορεί να είναι κενός.",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "Γενικές Ρυθμίσεις",
"install.app_name": "Τίτλος Ιστοτόπου",
"install.app_name_helper": "Μπορείτε να εισάγετε το όνομα της εταιρείας σας εδώ.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Ριζική Διαδρομή Αποθετηρίου",
"install.repo_path_helper": "Τα απομακρυσμένα αποθετήρια Git θα αποθηκεύονται σε αυτόν τον κατάλογο.",
"install.lfs_path": "Ριζική Διαδρομή Git LFS",
@@ -189,6 +199,7 @@
"install.ssh_port": "Θύρα της υπηρεσίας SSH",
"install.ssh_port_helper": "Αριθμός θύρας που ακούει η υπηρεσία SSH. Αφήστε κενό για να το απενεργοποιήσετε.",
"install.http_port": "Η HTTP θύρα που ακούει το Gitea",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "Βασικό URL του Gitea",
"install.app_url_helper": "Βασική Διεύθυνση για τα URL κλωνοποίησης μέσω HTTP(S) και για τις ειδοποιήσεις μέσω email.",
"install.log_root_path": "Διαδρομή Αρχείων Καταγραφής",
@@ -198,18 +209,37 @@
"install.smtp_addr": "Διακομιστής SMTP",
"install.smtp_port": "Θύρα SMTP",
"install.smtp_from": "Αποστολή Email Ως",
"install.smtp_from_invalid": "The \"Send Email As\" address is invalid",
"install.smtp_from_helper": "Η διεύθυνση email που θα χρησιμοποιεί το Gitea. Εισάγετε μια απλή διεύθυνση ηλεκτρονικού ταχυδρομείου ή χρησιμοποιήστε τη μορφή \"Όνομα\" <email@example.com>.",
"install.mailer_user": "Όνομα Χρήστη SMTP",
"install.mailer_password": "Κωδικός SMTP",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Απαιτείται Επιβεβαίωση της Διεύθυνσης Εmail για Εγγραφή",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Ενεργοποίηση Ειδοποιήσεων με Email",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Ρυθμίσεις Διακομιστή και Υπηρεσιών Τρίτων",
"install.offline_mode": "Ενεργοποίηση Τοπικής Λειτουργίας",
"install.offline_mode_popup": "Απενεργοποιήση των δικτύων διανομής περιεχομένου τρίτων και σερβίρετε όλων των πόρων τοπικά.",
"install.disable_gravatar": "Απενεργοποίηση Gravatar",
"install.disable_gravatar_popup": "Απενεργοποιήση του Gravatar και των εξωτερικών πηγών avatar. Θα χρησιμοποιηθεί ένα προεπιλεγμένο avatar εκτός αν ένας χρήστης ανεβάσει τοπικά ένα avatar.",
"install.federated_avatar_lookup": "Ενεργοποίηση Ομόσπονδων Avatars",
"install.federated_avatar_lookup_popup": "Ενεργοποίηση ομόσπονδης αναζήτησης avatar χρησιμοποιώντας το Libravatar.",
"install.disable_registration": "Απενεργοποίηση Αυτοεγγραφής",
"install.disable_registration_popup": "Απενεργοποίηση αυτοεγγραφής χρήστη. Μόνο οι διαχειριστές θα μπορούν να δημιουργήσουν νέους λογαριασμούς χρηστών.",
"install.allow_only_external_registration_popup": "Να Επιτρέπεται Η Εγγραφή Μόνο Μέσω Εξωτερικών Υπηρεσιών",
@@ -217,6 +247,8 @@
"install.openid_signin_popup": "Ενεργοποίηση σύνδεσης χρήστη μέσω OpenID.",
"install.openid_signup": "Ενεργοποίηση Ιδιοεγγραφής μέσω OpenID",
"install.openid_signup_popup": "Ενεργοποίηση ιδιοεγγραφής χρηστών με βάση το OpenID.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Ενεργοποίηση CAPTCHA στην εγγραφή",
"install.enable_captcha_popup": "Απαιτείται ένα CAPTCHA για τη ιδιοεγγραφή του χρήστη.",
"install.require_sign_in_view": "Απαιτείται Είσοδος για τη Προβολή Σελίδων",
@@ -227,6 +259,13 @@
"install.admin_password": "Κωδικός Πρόσβασης",
"install.confirm_password": "Επιβεβαίωση Κωδικού Πρόσβασης",
"install.admin_email": "Διεύθυνση Email",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Εγκατάσταση Gitea",
"install.test_git_failed": "Αδυναμία δοκιμής της εντολής 'git': %v",
"install.sqlite3_not_available": "Αυτή η έκδοση Gitea δεν υποστηρίζει την SQLite3. Παρακαλώ κατεβάστε την επίσημη δυαδική έκδοση από το %s (όχι την έκδοση 'gobuild').",
@@ -234,7 +273,6 @@
"install.invalid_db_table": "Ο πίνακας βάσης δεδομένων \"%s\" δεν είναι έγκυρος: %v",
"install.invalid_repo_path": "Η αρχική διαδρομή των αποθετηρίων δεν είναι έγκυρη: %v",
"install.invalid_app_data_path": "Η διαδρομή δεδομένων εφαρμογής (app data) δεν είναι έγκυρη: %v",
"install.run_user_not_match": "Το όνομα χρήστη 'εκτέλεση ως' δεν είναι το τρέχον όνομα χρήστη: %s -> %s",
"install.internal_token_failed": "Αποτυχία δημιουργίας εσωτερικού διακριτικού: %v",
"install.secret_key_failed": "Αποτυχία δημιουργίας μυστικού κλειδιού: %v",
"install.save_config_failed": "Αποτυχία αποθήκευσης ρυθμίσεων: %v",
@@ -250,10 +288,12 @@
"install.no_reply_address_helper": "Όνομα τομέα για χρήστες με μια κρυφή διεύθυνση email. Για παράδειγμα, το όνομα χρήστη 'nikos' θα συνδεθεί στο Git ως 'nikos@noreply.example.org' αν ο κρυφός τομέας email έχει οριστεί ως 'noreply.example.org'.",
"install.password_algorithm": "Αλγόριθμος Hash Κωδικού Πρόσβασης",
"install.invalid_password_algorithm": "Μη έγκυρος αλγόριθμος κωδικού πρόσβασης",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "Ενεργοποίηση Ελεγκτή Ενημερώσεων",
"install.enable_update_checker_helper": "Ελέγχει περιοδικά για νέες εκδόσεις κάνοντας σύνδεση στο gitea.io.",
"install.env_config_keys": "Ρυθμίσεις Περιβάλλοντος",
"install.env_config_keys_prompt": "Οι ακόλουθες μεταβλητές περιβάλλοντος θα εφαρμοστούν επίσης στο αρχείο ρυθμίσεων σας:",
"install.config_write_file_prompt": "These configuration options will be written into: %s",
"home.uname_holder": "Όνομα Χρήστη ή Διεύθυνση Email",
"home.password_holder": "Κωδικός Πρόσβασης",
"home.switch_dashboard_context": "Εναλλαγή Περιεχομένων Αρχικού Πίνακα",
@@ -293,6 +333,9 @@
"auth.forgot_password": "Ξεχάσατε τον κωδικό πρόσβασης;",
"auth.sign_up_successful": "Ο λογαριασμός δημιουργήθηκε επιτυχώς. Καλώς ορίσατε!",
"auth.must_change_password": "Ενημερώστε τον κωδικό πρόσβασης σας",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.allow_password_change": "Απαιτείται από το χρήστη να αλλάξει τον κωδικό πρόσβασης (συνιστόμενο)",
"auth.reset_password_mail_sent_prompt": "Ένα email επιβεβαίωσης έχει σταλεί στο <b>%s</b>. Παρακαλώ ελέγξτε τα εισερχόμενα σας στις επόμενες %s για να ολοκληρώσετε τη διαδικασία ανάκτησης λογαριασμού.",
"auth.active_your_account": "Ενεργοποιήστε Το Λογαριασμό Σας",
@@ -2356,6 +2399,7 @@
"admin.users.created": "Δημιουργήθηκε",
"admin.users.last_login": "Τελευταία Σύνδεση",
"admin.users.send_register_notify": "Αποστολή Ειδοποίησης Εγγραφής Χρήστη",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.new_success": "Ο λογαριασμός χρήστη \"%s\" δημιουργήθηκε.",
"admin.users.edit": "Επεξεργασία",
"admin.users.auth_source": "Πηγή Ταυτοποίησης",
@@ -3000,5 +3044,15 @@
"git.filemode.directory": "Φάκελος",
"git.filemode.normal_file": "Κανονικό αρχείο",
"git.filemode.executable_file": "Εκτελέσιμο αρχείο",
"git.filemode.submodule": "Υπομονάδα"
"git.filemode.submodule": "Υπομονάδα",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+193 -16
View File
@@ -236,7 +236,20 @@
"install.install": "Installation",
"install.installing_desc": "Installing now, please wait…",
"install.title": "Initial Configuration",
"install.language_balloon": "Choose a language",
"install.docker_helper": "If you run Gitea inside Docker, please read the <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">documentation</a> before changing any settings.",
"install.import_app_ini_title": "Import Existing Configuration",
"install.import_app_ini_desc": "Upload an existing app.ini file to prefill this installer form with the configuration values it already contains.",
"install.import_app_ini_file": "app.ini File",
"install.import_app_ini_helper": "Optional. INI file only, up to %d KB. The imported values are copied into the installer form so you can review and adjust them before saving.",
"install.import_app_ini_sensitive_secrets": "Import sensitive secrets from app.ini",
"install.import_app_ini_sensitive_secrets_helper": "Optional. Also import LFS_JWT_SECRET, INTERNAL_TOKEN, and JWT_SECRET from the uploaded configuration. Use this for restores or migrations where existing signed tokens must continue working.",
"install.import_app_ini_button": "Load app.ini",
"install.import_app_ini_missing": "Please choose an app.ini file to import.",
"install.import_app_ini_read_failed": "Could not read the uploaded app.ini file: %v",
"install.import_app_ini_too_big": "The uploaded app.ini file exceeds the maximum size of %d KB.",
"install.import_app_ini_invalid": "The uploaded app.ini file could not be parsed: %v",
"install.import_app_ini_success": "Configuration values were loaded from app.ini. Review the imported settings before continuing.",
"install.require_db_desc": "Gitea requires MySQL, PostgreSQL, MSSQL, SQLite3 or TiDB (MySQL protocol).",
"install.db_title": "Database Settings",
"install.db_type": "Database Type",
@@ -264,12 +277,14 @@
"install.general_title": "General Settings",
"install.app_name": "Site Title",
"install.app_name_helper": "You can enter your company name here.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Repository Root Path",
"install.repo_path_helper": "Remote Git repositories will be saved to this directory.",
"install.lfs_path": "Git LFS Root Path",
"install.lfs_path_helper": "Files tracked by Git LFS will be stored in this directory. Leave empty to disable.",
"install.run_user": "Run As Username",
"install.run_user_helper": "The operating system username that Gitea runs as. Note that this user must have access to the repository root path.",
"install.run_user_helper": "The operating system username that Gitea runs as, it must have write access to the data paths. This value is auto-detected and cannot be changed here. To use a different user, restart Gitea under that account.",
"install.domain": "Server Domain",
"install.domain_helper": "Domain or host address for the server.",
"install.ssh_port": "SSH Server Port",
@@ -281,6 +296,28 @@
"install.log_root_path": "Log Path",
"install.log_root_path_helper": "Log files will be written to this directory.",
"install.optional_title": "Optional Settings",
"install.branding_title": "Branding",
"install.branding_desc": "Upload optional custom logo and favicon files. If you leave any field empty, Gitea will continue using the built-in asset for that file.",
"install.branding.shared_assets": "Use the same logo files for favicon assets",
"install.branding.shared_assets_helper": "When enabled, the uploaded logo SVG and logo PNG will also be reused as the favicon SVG and favicon PNG, so you only need one upload per format.",
"install.branding.logo_svg": "Logo SVG",
"install.branding.logo_and_favicon_svg": "Logo & Favicon SVG",
"install.branding.logo_svg_helper": "Optional. SVG only, up to %d KB. Recommended for scalable UI branding.",
"install.branding.logo_png": "Logo PNG",
"install.branding.logo_and_favicon_png": "Logo & Favicon PNG",
"install.branding.logo_png_helper": "Optional. PNG only, up to %d KB. Must be square and at least %dx%d pixels. 512x512 is recommended for manifest and social preview fallbacks.",
"install.branding.loading_png": "Install Progress PNG",
"install.branding.loading_png_helper": "Optional. PNG or animated PNG only, up to %d KB. Must be square and at least %dx%d pixels. Use this to replace the post-install progress graphic.",
"install.branding.favicon_svg": "Favicon SVG",
"install.branding.favicon_svg_helper": "Optional. SVG only, up to %d KB. Use a simple square icon for best browser compatibility.",
"install.branding.favicon_png": "Favicon PNG",
"install.branding.favicon_png_helper": "Optional. PNG only, up to %d KB. Must be square and at least %dx%d pixels. 512x512 is recommended; browsers will downscale as needed.",
"install.branding.upload_read_failed": "Could not read %s: %v",
"install.branding.upload_too_big": "%s exceeds the maximum size of %d KB.",
"install.branding.upload_invalid_type": "%s must be a %s file.",
"install.branding.upload_png_square": "%s must be a square PNG image.",
"install.branding.upload_png_too_small": "%s must be at least %dx%d pixels.",
"install.branding.upload_save_failed": "Could not save branding files: %v",
"install.email_title": "Email Settings",
"install.smtp_addr": "SMTP Host",
"install.smtp_port": "SMTP Port",
@@ -289,8 +326,32 @@
"install.smtp_from_helper": "Email address Gitea will use. Enter a plain email address or use the \"Name\" <email@example.com> format.",
"install.mailer_user": "SMTP Username",
"install.mailer_password": "SMTP Password",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Require Email Confirmation to Register",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Enable Email Notifications",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Server and Third-Party Service Settings",
"install.disable_registration": "Disable Self-Registration",
"install.disable_registration_popup": "Disable user self-registration. Only administrators will be able to create new user accounts.",
@@ -299,16 +360,25 @@
"install.openid_signin_popup": "Enable user sign-in via OpenID.",
"install.openid_signup": "Enable OpenID Self-Registration",
"install.openid_signup_popup": "Enable OpenID-based user self-registration.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Enable registration CAPTCHA",
"install.enable_captcha_popup": "Require a CAPTCHA for user self-registration.",
"install.require_sign_in_view": "Require Sign-In to View Pages",
"install.require_sign_in_view_popup": "Limit page access to signed-in users. Visitors will only see the sign-in and registration pages.",
"install.admin_setting_desc": "Creating an administrator account is optional. The first registered user will automatically become an administrator.",
"install.admin_title": "Administrator Account Settings",
"install.admin_name": "Administrator Username",
"install.admin_setting_desc": "Creating a super administrator account is optional. The first registered user will automatically become a super administrator.",
"install.admin_title": "Super Administrator Account Settings",
"install.admin_name": "Super Administrator Username",
"install.admin_password": "Password",
"install.confirm_password": "Confirm Password",
"install.admin_email": "Email Address",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Install Gitea",
"install.test_git_failed": "Could not test 'git' command: %v",
"install.sqlite3_not_available": "This Gitea version does not support SQLite3. Please download the official binary version from %s (not the 'gobuild' version).",
@@ -316,7 +386,6 @@
"install.invalid_db_table": "The database table \"%s\" is invalid: %v",
"install.invalid_repo_path": "The repository root path is invalid: %v",
"install.invalid_app_data_path": "The app data path is invalid: %v",
"install.run_user_not_match": "The 'run as' username is not the current username: %s -> %s",
"install.internal_token_failed": "Failed to generate internal token: %v",
"install.secret_key_failed": "Failed to generate secret key: %v",
"install.save_config_failed": "Failed to save configuration: %v",
@@ -380,15 +449,44 @@
"auth.disable_register_prompt": "Registration is disabled. Please contact your site administrator.",
"auth.disable_register_mail": "Email confirmation for registration is disabled.",
"auth.manual_activation_only": "Contact your site administrator to complete activation.",
"auth.account_request_validation_sent": "We sent you a validation email for this account request. The link is valid for 48 hours.",
"auth.account_request_validation_pending_login": "A validation email has already been sent to %s for this account request. Please validate it before signing in.",
"auth.account_request_validation_pending_signup": "A validation email has already been sent to %s for this account request. Please validate it before creating another account.",
"auth.account_request_validation_resent": "We sent a new validation email for this account request.",
"auth.account_request_validation_resend_failed": "The validation email could not be sent. Please try again later or contact an administrator.",
"auth.account_request_validation_expired": "This account request validation link has expired. Please register again.",
"auth.account_request_admin_review_pending": "Your email address has been validated. An administrator will now review your account request.",
"auth.account_request_validated_waiting_admin": "Your account request was validated successfully. Please wait for an administrator to review it.",
"auth.account_request_resend": "Resend",
"auth.account_request_resend_prompt": "Did not receive the email?",
"auth.account_request_resend_button": "Resend",
"auth.account_request_spam_hint": "Please also check your Spam/Junk folder.",
"auth.account_request_resend_not_available": "This account request can no longer receive a validation email.",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"auth.admin_notify_recover_password_spam_hint": "We couldn't verify your password. Please use account recovery and also check your Spam/Junk folder.",
"auth.account_request_blocked": "This account request has been blocked after %d unconfirmed attempts. An administrator must unblock it.",
"auth.account_request_rejected_signup": "This account request was rejected. An administrator must unblock it before the same email address can be used again.",
"auth.remember_me": "Remember This Device",
"auth.remember_me.compromised": "The login token is not valid anymore which may indicate a compromised account. Please check your account for unusual activities.",
"auth.forgot_password_title": "Forgot Password",
"auth.forgot_password": "Forgot password?",
"auth.show_password": "Show password",
"auth.hide_password": "Hide password",
"auth.need_account": "Need an account?",
"auth.sign_up_tip": "You are registering the first account in the system, which has administrator privileges. Please carefully remember your username and password. If you forget the username or password, please refer to the Gitea documentation to recover the account.",
"auth.sign_up_now": "Register now.",
"auth.sign_up_successful": "Account was successfully created. Welcome!",
"auth.confirmation_mail_failed": "We could not send a confirmation email to %s, so the account was not created. Please verify the email address and try again.",
"auth.confirmation_mail_sent_prompt_ex": "A new confirmation email has been sent to <b>%s</b>. Please check your inbox within the next %s to complete the registration process. If your registration email address is incorrect, you can sign in again and change it.",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.must_change_password": "Update your password",
"auth.allow_password_change": "Require user to change password (recommended)",
"auth.reset_password_mail_sent_prompt": "A confirmation email has been sent to <b>%s</b>. Please check your inbox within the next %s to complete the account recovery process.",
@@ -463,11 +561,42 @@
"mail.activate_email": "Verify your email address",
"mail.activate_email.title": "%s, please verify your email address",
"mail.activate_email.text": "Please click the following link to verify your email address within <b>%s</b>:",
"mail.new_account_request": "New account request on %s",
"mail.new_account_request.title": "New account request on %s",
"mail.new_account_request.text_1": "A new user account request is awaiting administrator review on %s.",
"mail.new_account_request.text_2": "Requested account: <b>%[1]s</b> (%[2]s).",
"mail.new_account_request.text_3": "Review and activate the account here:",
"mail.account_request.validate": "Validate your account request",
"mail.account_request.validate.title": "%s, validate your account request",
"mail.account_request.validate.text_1": "Hi <b>%[1]s</b>, please validate your account request for %[2]s.",
"mail.account_request.validate.text_2": "Click the following link within <b>%s</b> to validate your email address and submit the request for administrator review:",
"mail.account_request.approved": "Your account request for %s was approved",
"mail.account_request.approved.title": "Your account request for %s was approved",
"mail.account_request.approved.text_1": "Hi <b>%[1]s</b>, your account request for %[2]s was approved.",
"mail.account_request.approved.text_2": "You can now sign in with your account.",
"mail.account_request.rejected": "Your account request for %s was rejected",
"mail.account_request.rejected.title": "Your account request for %s was rejected",
"mail.account_request.rejected.text_1": "Hi <b>%[1]s</b>, your account request for %[2]s was rejected.",
"mail.account_request.rejected.text_2": "The account remains blocked until an administrator unblocks it.",
"mail.register_notify": "Welcome to %s",
"mail.register_notify.title": "%[1]s, welcome to %[2]s",
"mail.register_notify.text_1": "This is your registration confirmation email for %s!",
"mail.register_notify.text_2": "You can now log in via username: %s.",
"mail.register_notify.text_3": "If this account has been created for you, please <a href=\"%s\">set your password</a> first.",
"mail.register_notify.text_1": "Administrator \"%[1]s\" created an account for you on %s.",
"mail.register_notify.text_1_no_admin": "An account was created for you on %s.",
"mail.register_notify.text_2": "You can sign in with username: %s.",
"mail.register_notify.text_3": "Before signing in, please use your personal link to <a href=\"%s\">set your password</a>.",
"mail.admin_invite": "You are invited to join %s",
"mail.admin_invite.title": "Invitation to join %s",
"mail.admin_invite.text_1": "Administrator \"%[1]s\" created an account for you and invites you to join %[2]s.",
"mail.admin_invite.text_2": "If you accept our invitation, please use the link below:",
"mail.admin_invite.note": "Note: This link is valid for %s.",
"mail.admin_invite.accepted": "%[1]s accepted your invitation to join %[2]s",
"mail.admin_invite.accepted.title": "Invitation accepted for %s",
"mail.admin_invite.accepted.text_1": "%[1]s (@%[2]s) accepted your invitation and joined %[3]s.",
"mail.admin_status_changed": "Your account status on %s was changed",
"mail.admin_status_changed.title": "Your account status on %s was changed",
"mail.admin_status_changed.text_1": "Hi <b>%[1]s</b>, your account status on %[2]s was changed.",
"mail.admin_status_changed.text_2": "This action was performed by administrator <b>%s</b>.",
"mail.admin_status_changed.reason": "Reason:",
"mail.reset_password": "Recover your account",
"mail.reset_password.title": "%s, you have requested to recover your account",
"mail.reset_password.text": "Please click the following link to recover your account within <b>%s</b>:",
@@ -638,14 +767,8 @@
"user.block.unblock.failure": "Failed to unblock user: %s",
"user.block.blocked": "You have blocked this user.",
"user.block.title": "Block a user",
"user.block.info": "Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.",
"user.block.info_1": "Blocking a user prevents the following actions on your account and your repositories:",
"user.block.info_2": "following your account",
"user.block.info_3": "send you notifications by @mentioning your username",
"user.block.info_4": "inviting you as a collaborator to their repositories",
"user.block.info_5": "starring, forking or watching on repositories",
"user.block.info_6": "opening and commenting on issues or pull requests",
"user.block.info_7": "reacting to your comments in issues or pull requests",
"user.block.info": "Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues.",
"user.block.info.docs": "Learn more about blocking a user.",
"user.block.user_to_block": "User to block",
"user.block.note": "Note",
"user.block.note.title": "Optional note:",
@@ -697,6 +820,7 @@
"settings.hidden_comment_types_description": "Comment types checked here will not be shown on issue pages. Checking \"Label\", for example, removes all \"{user} added/removed {label}\" comments.",
"settings.hidden_comment_types.ref_tooltip": "Comments where this issue was referenced from another issue/commit/…",
"settings.hidden_comment_types.issue_ref_tooltip": "Comments where the user changes the branch/tag associated with the issue",
"settings.select_all": "Select",
"settings.comment_type_group_reference": "Reference",
"settings.comment_type_group_label": "Label",
"settings.comment_type_group_milestone": "Milestone",
@@ -712,6 +836,17 @@
"settings.comment_type_group_project": "Project",
"settings.comment_type_group_issue_ref": "Issue reference",
"settings.saved_successfully": "Your settings were saved successfully.",
"settings.persistent_layout": "Persistent layout",
"settings.persistent_layout_desc": "Choose which interface regions should remain visible while the page scrolls.",
"settings.footer": "Footer",
"settings.footer_desc": "Choose whether the site footer should remain visible at the bottom of the viewport.",
"settings.show_persistent_footer": "Keep the footer visible on screen",
"settings.navigation_bar": "Navigation bar",
"settings.navigation_bar_desc": "Choose whether the top navigation bar should remain visible while the page scrolls.",
"settings.show_persistent_navbar": "Keep the navigation bar visible while scrolling",
"settings.side_menus": "Side menus",
"settings.side_menus_desc": "Choose whether the left menus in user settings and the admin area should remain visible while the page content scrolls.",
"settings.show_sticky_side_menus": "Keep the left menus visible while scrolling",
"settings.privacy": "Privacy",
"settings.keep_activity_private": "Hide Activity from profile page",
"settings.keep_activity_private_popup": "Makes the activity visible only for you and the admins",
@@ -949,6 +1084,9 @@
"settings.email_notifications.disable": "Disable Email Notifications",
"settings.email_notifications.submit": "Set Email Preference",
"settings.email_notifications.andyourown": "And Your Own Notifications",
"settings.email_notifications.new_account_requests": "New account request notifications",
"settings.email_notifications.new_account_requests.desc": "Email me when a new user account is waiting for administrator approval.",
"settings.email_notifications.new_account_requests.last_admin": "At least one admin must keep new account request notifications enabled.",
"settings.email_notifications.actions.desc": "Notifications for workflow runs on repositories set up with <a target=\"_blank\" href=\"%s\">Gitea Actions</a>.",
"settings.email_notifications.actions.failure_only": "Only notify for failed workflow runs",
"settings.visibility": "User visibility",
@@ -2937,6 +3075,8 @@
"admin.dashboard.cron.finished": "Cron: %[1]s has finished",
"admin.dashboard.delete_inactive_accounts": "Delete all unactivated accounts",
"admin.dashboard.delete_inactive_accounts.started": "Task to delete all unactivated accounts started",
"admin.dashboard.delete_expired_account_requests": "Delete expired account requests awaiting email validation",
"admin.dashboard.delete_expired_account_requests.started": "Task to delete expired account requests awaiting email validation started",
"admin.dashboard.delete_repo_archives": "Delete all repositories' archives (ZIP, TAR.GZ, etc..)",
"admin.dashboard.delete_repo_archives.started": "Task to delete all repository archives started",
"admin.dashboard.delete_missing_repos": "Delete all repositories missing their Git files",
@@ -3017,6 +3157,9 @@
"admin.users.last_login": "Last Sign-In",
"admin.users.never_login": "Never Signed In",
"admin.users.send_register_notify": "Send User Registration Notification",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"admin.users.new_success": "The user account \"%s\" has been created.",
"admin.users.edit": "Edit",
"admin.users.auth_source": "Authentication Source",
@@ -3030,6 +3173,8 @@
"admin.users.is_activated": "User Account Is Activated",
"admin.users.prohibit_login": "Disable Sign-In",
"admin.users.is_admin": "Is Administrator",
"admin.users.is_super_admin": "Is Super Administrator",
"admin.users.super_admin": "Super Admin",
"admin.users.is_restricted": "Is Restricted",
"admin.users.allow_git_hook": "May Create Git Hooks",
"admin.users.allow_git_hook_tooltip": "Git Hooks are executed as the OS user running Gitea and will have the same level of host access. As a result, users with this special Git Hook privilege can access and modify all Gitea repositories as well as the database used by Gitea. Consequently they are also able to gain Gitea administrator privileges.",
@@ -3038,12 +3183,44 @@
"admin.users.update_profile": "Update User Account",
"admin.users.delete_account": "Delete User Account",
"admin.users.cannot_delete_self": "You cannot delete yourself",
"admin.users.cannot_delete_grantor": "You cannot delete the administrator who granted your privileges.",
"admin.users.admin_grantor.required": "You can only manage administrator accounts that belong to your grant chain.",
"admin.users.god_immutable": "Accounts granted by GOD cannot be modified or deleted.",
"admin.users.still_own_repo": "This user still owns one or more repositories. Delete or transfer these repositories first.",
"admin.users.still_has_org": "This user is a member of an organization. Remove the user from any organizations first.",
"admin.users.purge": "Purge User",
"admin.users.purge_help": "Forcibly delete user and any repositories, organizations, and packages owned by the user. All comments will be deleted too.",
"admin.users.still_own_packages": "This user still owns one or more packages. Delete these packages first.",
"admin.users.deletion_success": "The user account has been deleted.",
"admin.users.account_request.status": "Account request status",
"admin.users.account_request.attempts": "Unconfirmed attempts: %d",
"admin.users.account_request.validation_mail": "Validation email attempt",
"admin.users.account_request.activate": "Activate Request",
"admin.users.account_request.reject": "Reject Request",
"admin.users.account_request.unblock": "Unblock Request",
"admin.users.account_request.approved": "The account request has been approved.",
"admin.users.account_request.rejected": "The account request has been rejected.",
"admin.users.account_request.unblocked": "The account request has been unblocked and a new validation email was sent.",
"admin.users.account_request.invalid_action": "This account request action is not available for the current request state.",
"admin.users.account_request.active_managed_externally": "Activation for this account is currently managed by the account request workflow.",
"admin.users.status_change.reason": "Reason:",
"admin.users.status_change.reason_required": "Please provide a reason for this account status change.",
"admin.users.status_change.admin_granted": "Congratulations, your account has been promoted to administrator.",
"admin.users.status_change.admin_revoked": "Administrator privileges have been removed from your account.",
"admin.users.status_change.super_admin_granted": "Congratulations, your account has been promoted to super administrator.",
"admin.users.status_change.super_admin_revoked": "Super administrator privileges have been removed from your account.",
"admin.users.status_change.deactivated": "Your account has been invalidated and can no longer be accessed.",
"admin.users.status_change.reactivated": "Your account has been reactivated and can be accessed again.",
"admin.users.status_change.prohibit_login": "Sign-in has been disabled for your account.",
"admin.users.status_change.allow_login": "Sign-in has been enabled again for your account.",
"admin.users.status_change.restricted": "Your account has been restricted and can only access resources explicitly granted to it.",
"admin.users.status_change.unrestricted": "The restricted status has been removed from your account.",
"admin.users.super_admin.required": "Only a super administrator can manage administrator accounts.",
"admin.users.super_admin.last": "You cannot remove the last super administrator. There must be at least one super administrator.",
"admin.users.account_request.status.pending_email_validation": "Waiting for email validation",
"admin.users.account_request.status.pending_admin_review": "Waiting for administrator review",
"admin.users.account_request.status.rejected": "Rejected",
"admin.users.account_request.status.blocked": "Blocked",
"admin.users.reset_2fa": "Reset 2FA",
"admin.users.list_status_filter.menu_text": "Filter",
"admin.users.list_status_filter.reset": "Reset",
+62 -8
View File
@@ -151,6 +151,7 @@
"startpage.lightweight_desc": "Gitea tiene pocos requisitos y puede funcionar en una Raspberry Pi barata. ¡Ahorra energía!",
"startpage.license": "Código abierto",
"install.install": "Instalación",
"install.installing_desc": "Installing now, please wait…",
"install.title": "Configuración inicial",
"install.docker_helper": "Si está ejecutando Gitea dentro de un contenedor Docker, por favor lea la <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">documentación</a> antes de realizar cambios en la configuración.",
"install.require_db_desc": "Gitea requiere una base de datos MySQL, PostgreSQL, MSSQL, SQLite3 o TiDB (usar el protocolo MySQL).",
@@ -162,17 +163,26 @@
"install.db_name": "Nombre de la base de datos",
"install.db_schema": "Esquema",
"install.db_schema_helper": "Dejar en blanco para la base de datos por defecto (\"public\").",
"install.ssl_mode": "SSL",
"install.path": "Ruta",
"install.sqlite_helper": "Ruta del archivo de la base de datos SQLite3.<br>Escriba una ruta de acceso absoluta si ejecuta Gitea como servicio.",
"install.reinstall_error": "Usted está intentando instalar en una base de datos de Gitea existente",
"install.reinstall_confirm_message": "Reinstalar con una base de datos de Gitea existente puede causar múltiples problemas. En la mayoría de los casos, debería utilizar su actual \"app.ini\" para ejecutar Gitea. Si sabe lo que está haciendo, confirme lo siguiente:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "Confirma que está absolutamente seguro de que este Gitea se está ejecutando con el app.ini correcto y que está seguro de que tiene que volver a instalar. Confirma que reconoce los riesgos anteriores.",
"install.err_empty_db_path": "La ruta a la base de datos SQLite3 no puede estar vacía.",
"install.no_admin_and_disable_registration": "No puede deshabilitar el auto-registro sin crear una cuenta de administrador.",
"install.err_empty_admin_password": "La contraseña del administrador no puede estar vacía.",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "Configuración general",
"install.app_name": "Título del sitio",
"install.app_name_helper": "Puede colocar aquí el nombre de su empresa.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Ruta de la raiz del repositorio",
"install.repo_path_helper": "Los repositorios Git se guardarán en este directorio.",
"install.lfs_path": "Ruta raíz de Git LFS",
@@ -184,6 +194,7 @@
"install.ssh_port": "Puerto de servidor SSH",
"install.ssh_port_helper": "Número de puerto en el que está escuchando su servidor SSH. Déjelo vacío para deshabilitarlo.",
"install.http_port": "Puerto de escucha HTTP de Gitea",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "URL base de Gitea",
"install.app_url_helper": "Dirección base para URLs de clonación HTTP(S) y notificaciones de correo electrónico.",
"install.log_root_path": "Ruta del registro",
@@ -193,18 +204,37 @@
"install.smtp_addr": "Servidor SMTP",
"install.smtp_port": "Puerto SMTP",
"install.smtp_from": "Enviar correos electrónicos como",
"install.smtp_from_invalid": "The \"Send Email As\" address is invalid",
"install.smtp_from_helper": "Dirección de correo electrónico que utilizará Gitea. Introduzca una dirección de correo electrónico normal o utilice el formato \"Nombre\" <email@example.com>.",
"install.mailer_user": "Nombre de usuario SMTP",
"install.mailer_password": "Contraseña SMTP",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Requerir confirmación de correo electrónico para registrarse",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Habilitar las notificaciones por correo electrónico",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Configuración del servidor y de servicios de terceros",
"install.offline_mode": "Habilitar autenticación Local",
"install.offline_mode_popup": "Deshabilitar redes de distribución de contenido de terceros y servir todos los recursos localmente.",
"install.disable_gravatar": "Desactivar Gravatar",
"install.disable_gravatar_popup": "Desactivar el Gravatar y fuentes de avatares de terceros. Se utilizará un avatar por defecto a menos que un usuario suba un avatar localmente.",
"install.federated_avatar_lookup": "Habilitar avatares federados",
"install.federated_avatar_lookup_popup": "Habilitar búsqueda de avatares federador para usar el servicio federado de código abierto basado en libravatar.",
"install.disable_registration": "Deshabilitar auto-registro",
"install.disable_registration_popup": "Deshabilitar auto-registro de usuarios. Sólo los administradores podrán crear nuevas cuentas de usuario.",
"install.allow_only_external_registration_popup": "Permitir el registro únicamente a través de servicios externos",
@@ -212,6 +242,8 @@
"install.openid_signin_popup": "Habilitar el inicio de sesión de usuarios con OpenID.",
"install.openid_signup": "Habilitar el auto-registro con OpenID",
"install.openid_signup_popup": "Habilitar autorregistro de usuario basado en OpenID.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Requerir CAPTCHA durante el registro",
"install.enable_captcha_popup": "Requerir CAPTCHA para auto-registro de usuario.",
"install.require_sign_in_view": "Requerir inicio de sesión para ver páginas",
@@ -222,6 +254,13 @@
"install.admin_password": "Contraseña",
"install.confirm_password": "Confirmar Contraseña",
"install.admin_email": "Correo electrónico",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Instalar Gitea",
"install.test_git_failed": "Fallo al probar el comando 'git': %v",
"install.sqlite3_not_available": "Esta versión de Gitea no soporta SQLite3. Por favor, descarga la versión binaria oficial de %s (no la versión 'gobuild').",
@@ -229,7 +268,6 @@
"install.invalid_db_table": "La tabla \"%s\" de la base de datos no es válida: %v",
"install.invalid_repo_path": "La ruta de la raíz del repositorio no es válida: %v",
"install.invalid_app_data_path": "La ruta de datos de la aplicación (APP_DATA_PATH) no es válida: %v",
"install.run_user_not_match": "El nombre de usuario 'ejecutar como' no es el nombre actual de usuario: %s -> %s",
"install.internal_token_failed": "Fallo al generar el INTERNAL_TOKEN: %v",
"install.secret_key_failed": "Fallo al generar el SECRET_KEY: %v",
"install.save_config_failed": "Error al guardar la configuración: %v",
@@ -245,10 +283,12 @@
"install.no_reply_address_helper": "Nombre de dominio para usuarios con dirección de correo electrónico oculta. Por ejemplo, el usuario 'joe' quedará registrado en Git como 'joe@noreply.example.org' si el dominio de correo electrónico oculto se establece a 'noreply.example.org'.",
"install.password_algorithm": "Algoritmo Hash de Contraseña",
"install.invalid_password_algorithm": "Algoritmo hash de contraseña no válido",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "Activar comprobador de actualizaciones",
"install.enable_update_checker_helper": "Comprueba el lanzamiento de nuevas versiones periódicamente en gitea.io.",
"install.env_config_keys": "Configuración del entorno",
"install.env_config_keys_prompt": "Las siguientes variables de entorno también se aplicarán a su archivo de configuración:",
"install.config_write_file_prompt": "These configuration options will be written into: %s",
"home.uname_holder": "Nombre de usuario o correo electrónico",
"home.password_holder": "Contraseña",
"home.switch_dashboard_context": "Cambiar el contexto del Dashboard",
@@ -287,6 +327,9 @@
"auth.forgot_password": "¿Has olvidado tu contraseña?",
"auth.sign_up_successful": "La cuenta se ha creado correctamente. ¡Bienvenido!",
"auth.must_change_password": "Actualizar su contraseña",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.allow_password_change": "Obligar al usuario a cambiar la contraseña (recomendado)",
"auth.reset_password_mail_sent_prompt": "Un correo de confirmación se ha enviado a <b>%s</b>. Compruebe su bandeja de entrada en las siguientes %s para completar el proceso de recuperación de la cuenta.",
"auth.active_your_account": "Activa tu cuenta",
@@ -2322,6 +2365,7 @@
"admin.users.created": "Creado",
"admin.users.last_login": "Último registro",
"admin.users.send_register_notify": "Enviar notificación de registro de usuario",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.new_success": "Se ha creado la cuenta de usuario \"%s\".",
"admin.users.edit": "Editar",
"admin.users.auth_source": "Origen de Autenticación",
@@ -2959,5 +3003,15 @@
"git.filemode.normal_file": "Archivo normal",
"git.filemode.executable_file": "Archivo ejecutable",
"git.filemode.symbolic_link": "Enlace simbólico",
"git.filemode.submodule": "Submódulo"
"git.filemode.submodule": "Submódulo",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+71 -8
View File
@@ -94,8 +94,10 @@
"startpage.lightweight_desc": "گیتی با حداقل منابع میتوانید برای روی دستگاه Raspberry Pi اجرا شود و مصرف انرژی شما را کاهش دهد!",
"startpage.license": "متن باز",
"install.install": "نصب و راه اندازی",
"install.installing_desc": "Installing now, please wait…",
"install.title": "تنظیمات اولیه",
"install.docker_helper": "اگر گیتی را با داکر اجرا کرده‌اید، لطفا قبل از هر تغییری <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">مستندات</a> را مطالعه نمایید.",
"install.require_db_desc": "Gitea requires MySQL, PostgreSQL, MSSQL, SQLite3 or TiDB (MySQL protocol).",
"install.db_title": "تنظیمات پایگاه داده",
"install.db_type": "نوع پایگاه داده",
"install.host": "میزبان",
@@ -104,27 +106,38 @@
"install.db_name": "نام پایگاه داده",
"install.db_schema": "قالب",
"install.db_schema_helper": "برای مقدار پیش فرض پایگاه داده خالی بگذارید (\"public\").",
"install.ssl_mode": "SSL",
"install.path": "مسیر",
"install.sqlite_helper": "مسیر فایل برای دیتابیس SQLite3. <br>اگر گیتی را به عنوان یک سرویس اجرا میکنید، یک مسیر کامل وارد کنید.",
"install.reinstall_error": "شما در حال تلاش هستید برای نصب روی یک پایگاه داده Gitea که موجود است",
"install.reinstall_confirm_message": "نصب مجدد با پایگاه داده Gitea موجود می تواند مشکلات متعددی ایجاد کند. در بیشتر موارد، باید از \"app.ini\" موجود خود برای اجرای Gitea استفاده کنید. اگر می دانید چه کاری انجام می دهید، موارد زیر را تأیید کنید:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "شما تأیید می کنید که کاملاً مطمئن هستید که این Gitea با مکان صحیح app.ini اجرا می شود و مطمئن هستید که باید دوباره نصب کنید. شما تأیید می کنید که خطرات فوق را تأیید می کنید.",
"install.err_empty_db_path": "مسیر دیتابیس SQLite3 نمیتواند خالی باشد.",
"install.no_admin_and_disable_registration": "شما بدون ایجاد حساب‌ کاربری مدیر نمی‌توانید عضویت را غیر فعال کنید.",
"install.err_empty_admin_password": "کلمه عبور حساب مدیر نمی تواند خالی باشد.",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "تنظیمات عمومی",
"install.app_name": "عنوان سایت",
"install.app_name_helper": "شما می توانید نام شرکت خود را در اینجا وارد کنید.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "مسیر ریشه مخزن",
"install.repo_path_helper": "تمام مخازن کد راه دور در این پوشه ذخیره می‌شوند.",
"install.lfs_path": "مسیر Git LFS",
"install.lfs_path_helper": "فایل هایی که توسط Git LFS دنبال میشوند در این پوشه ذخیره خواهند شد. درصورت خالی بودن فیلد این قابلیت غیرفعال خواهد بود.",
"install.run_user": "اجرا به عنوان نام کاربری",
"install.run_user_helper": "The operating system username that Gitea runs as, it must have write access to the data paths. This value is auto-detected and cannot be changed here. To use a different user, restart Gitea under that account.",
"install.domain": "دامنه سرور",
"install.domain_helper": "آدرس میزبان یا دامنه برای سرور.",
"install.ssh_port": "پورت SSH سرور",
"install.ssh_port_helper": "شماره درگاهی که سرور SSH گوش می دهد. برای غیر فعال کردن خالی بگذارید.",
"install.http_port": "پورت HTTP گیتی",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "آدرس پایه گیتی",
"install.app_url_helper": "آدرس پایه برای URLهای اجماع HTTP(S) و هشدار های رایانامه (ایمیل).",
"install.log_root_path": "مسیر گزارش‌ها",
@@ -134,18 +147,37 @@
"install.smtp_addr": "میزبان SMTP",
"install.smtp_port": "گذرگاه(پورت) SMTP",
"install.smtp_from": "ارسال ایمیل به عنوان",
"install.smtp_from_invalid": "The \"Send Email As\" address is invalid",
"install.smtp_from_helper": "آدرس ایمیلی که گیتی استفاده میکند. یک ایمیل وارد کنید یا به \"Name\" <email@example.com> شکل استفاده کنید.",
"install.mailer_user": "نام کاربری SMTP",
"install.mailer_password": "گذرواژه SMTP",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "نیاز به تایید ایمیل ثبت نام",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "فعال‌سازی اعلان‌های ایمیل",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "تنظیمات سرور و سرویس‌های شخص ثالث",
"install.offline_mode": "فعال کردن حالت محلی",
"install.offline_mode_popup": "غیر فعال کردن شبکه های شخص ثالث تحویل محتوا و استفاده از تمام منابع به صورت محلی.",
"install.disable_gravatar": "غیر فعال کردن Gravatar",
"install.disable_gravatar_popup": "غیر فعال کردن کلیک و منابع آواتار شخص ثالث. مگر در مواردی که کاربر محلی بارگزاری آواتار پیش فرض استفاده خواهد شد.",
"install.federated_avatar_lookup": "فعال سازی آواتار مشترک",
"install.federated_avatar_lookup_popup": "مراجعه مشترک آواتار با استفاده از Libravatar را قادر می سازد.",
"install.disable_registration": "غیرفعال‌کردن خود ثبت نامی",
"install.disable_registration_popup": "غیرفعال کردن ثبت نام کاربر. تنها مدیر ها قادر خواهند بود حساب کاربری جدید اضافه کنند.",
"install.allow_only_external_registration_popup": "اجازه ثبت نام فقط از طریق خدمات خارجی",
@@ -153,22 +185,32 @@
"install.openid_signin_popup": "فعالسازی ورود کاربر با OpenID.",
"install.openid_signup": "فعالسازی ثبت نام با OpenID",
"install.openid_signup_popup": "فعال سازی ثبت نام با استفاده از OpenID.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "فعالسازی CAPTCHA برای ثبت نام",
"install.enable_captcha_popup": "عضویت افراد نیازمند کپچا است.",
"install.require_sign_in_view": "فعال‌سازی نیازمند به ورود در هنگام مشاهده صفحات",
"install.require_sign_in_view_popup": "Limit page access to signed-in users. Visitors will only see the sign-in and registration pages.",
"install.admin_setting_desc": "ساخت حساب مدیر اختیاری است. اولین کاربری که ثبت‌نام میکنید مدیر خواهد بود.",
"install.admin_title": "تنظیمات حساب مدیر",
"install.admin_name": "نام کاربری مدیر",
"install.admin_password": "گذرواژه",
"install.confirm_password": "تکرارگذواژه",
"install.admin_email": "نشانی رایانامه (ایمیل)",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "نصب گیتی",
"install.test_git_failed": "عدم توانایی در آزمایش دستور 'git' توضیح بیشتر: %v",
"install.sqlite3_not_available": "نسخه مورد استفاده شما از SQLite3 پشتیبانی نمی کند. لطفا نسخه باینری رسمی را از s% دانلود کنید و از ورژن gobuild هم استفاده نکنید.",
"install.invalid_db_setting": "تنظیمات پایگاه داده معتبر نیست: %v",
"install.invalid_db_table": "The database table \"%s\" is invalid: %v",
"install.invalid_repo_path": "مسیر ریشه مخزن نامعتبر است: %v",
"install.invalid_app_data_path": "مسیر داده برنامه نامعتبر است: %v",
"install.run_user_not_match": "نام کاربری 'اجرا به عنوان' نام کاربری فعلی نیست: %s -> %s",
"install.internal_token_failed": "کد داخلی ایجاد نشد: %v",
"install.secret_key_failed": "کلید مخفی ایجاد نشد: %v",
"install.save_config_failed": "تنظیمات ذخیره نشد: %v",
@@ -183,6 +225,13 @@
"install.no_reply_address": "مخفی کردن دامنه ایمیل",
"install.no_reply_address_helper": "نام دامنه برای کاربران دارای آدرس ایمیل پنهان است. به عنوان مثال ، اگر نام دامنه ایمیل مخفی روی \"noreply.example.org\" تنظیم شده باشد ، نام کاربری \"joe\" در Git به عنوان \"joe@noreply.example.org\" وارد می شود",
"install.password_algorithm": "الگوریتم درهم‌ساز گذرواژه",
"install.invalid_password_algorithm": "Invalid password hash algorithm",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "Enable Update Checker",
"install.enable_update_checker_helper": "Checks for new version releases periodically by connecting to gitea.io.",
"install.env_config_keys": "Environment Configuration",
"install.env_config_keys_prompt": "The following environment variables will also be applied to your configuration file:",
"install.config_write_file_prompt": "These configuration options will be written into: %s",
"home.uname_holder": "نام کاربری یا نشانی ایمیل",
"home.password_holder": "گذرواژه",
"home.switch_dashboard_context": "تغییر محتوای پیشخوان",
@@ -216,6 +265,9 @@
"auth.forgot_password_title": "گذرواژه خود را فراموش کرده ام",
"auth.forgot_password": "گذرواژه خود را فراموش کرده‌اید؟",
"auth.must_change_password": "گذرواژه خود را به روز کنید",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.allow_password_change": "نیاز به کاربر برای تغییرگذرواژه (توصیه می شود)",
"auth.reset_password_mail_sent_prompt": "ایمیل تاییدیه جدیدی به <b>%s</b> ارسال شد. لطفا صندوق ورودی خود را در %s آینده برای فرآیند بازیابی حساب کاربری خود بررسی کنید.",
"auth.active_your_account": "حساب خود را فعال کنید",
@@ -1838,6 +1890,7 @@
"admin.users.created": "ایجاد شده",
"admin.users.last_login": "آخرین ورود",
"admin.users.send_register_notify": "ارسال اعلان ثبت نام کاربر",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.edit": "ویرایش",
"admin.users.auth_source": "منبع احراز هویت",
"admin.users.local": "محلی",
@@ -2228,5 +2281,15 @@
"actions.runners.status.active": "فعال",
"actions.runners.version": "نسخه",
"actions.runs.commit": "کامیت",
"git.filemode.symbolic_link": "پیوند نمادین"
"git.filemode.symbolic_link": "پیوند نمادین",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+77 -7
View File
@@ -108,6 +108,7 @@
"startpage.lightweight_desc": "Gitealla on vähäiset vähimmäisvaatimukset, joten se toimii jopa halvassa Raspberry Pi:ssä. Säästä koneesi energiaa!",
"startpage.license": "Avoin lähdekoodi",
"install.install": "Asennus",
"install.installing_desc": "Installing now, please wait…",
"install.title": "Alkuperäiset asetukset",
"install.docker_helper": "Jos ajat Giteaa Dockerin sisällä, lue <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">ohjeet</a> ennen minkään asetuksen muuttamista.",
"install.require_db_desc": "Gitea tarvitsee toimiakseen MySQL, PostgreSQL, MSSQL, SQLite3 tai TiDB (MySQL protokolla) tietokannan.",
@@ -118,26 +119,39 @@
"install.password": "Salasana",
"install.db_name": "Tietokannan nimi",
"install.db_schema": "Skeema",
"install.db_schema_helper": "Leave blank for database default (\"public\").",
"install.ssl_mode": "SSL",
"install.path": "Polku",
"install.sqlite_helper": "SQLite3-tietokannan tiedostopolku.<br>Syötä absoluuttinen polku, jos ajat Giteaa palveluna.",
"install.reinstall_error": "Yrität asentaa olemassa olevaan Gitea tietokantaan",
"install.reinstall_confirm_message": "Asentaminen uudelleen olemassa olevalla Gitea-tietokannalla voi aiheuttaa useita ongelmia. Useimmissa tapauksissa sinun pitäisi käyttää olemassa olevia \"app.ini\" asetuksia Gitean käyttöön. Jos tiedät mitä teet, vahvista seuraavat seikat:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "Vahvistat, että olet täysin varma siitä, että tämä Gitea toimii oikealla app.ini sijainnilla ja että olet varma, että sinun täytyy asentaa uudelleen. Vahvistat, että tunnustat edellä mainitut riskit.",
"install.err_empty_db_path": "SQLite3-tietokannan polku ei voi olla tyhjä.",
"install.no_admin_and_disable_registration": "Et voi kytkeä rekisteröintiä pois luomatta sitä ennen ylläpitotiliä.",
"install.err_empty_admin_password": "Ylläpitäjän salasana ei voi olla tyhjä.",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "Yleiset asetukset",
"install.app_name": "Sivuston otsikko",
"install.app_name_helper": "Voit syöttää yrityksesi nimen tähän.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Repon juuren polku",
"install.repo_path_helper": "Muualla olevat git-repositoriot tullaan tallentamaan tähän kansioon.",
"install.lfs_path": "Git LFS -juuripolku",
"install.lfs_path_helper": "Git LFS:n ylläpitämät tiedostot tullaan tallentamaan tähän hakemistoon. Jätä tyhjäksi kytkeäksesi toiminnon pois.",
"install.run_user": "Aja käyttäjänä",
"install.run_user_helper": "The operating system username that Gitea runs as, it must have write access to the data paths. This value is auto-detected and cannot be changed here. To use a different user, restart Gitea under that account.",
"install.domain": "Palvelimen verkkotunnus",
"install.domain_helper": "Domain or host address for the server.",
"install.ssh_port": "SSH-palvelimen portti",
"install.ssh_port_helper": "Porttinumero, jossa SSH-palvelimesi kuuntelee. Jätä tyhjäksi kytkeäksesi pois.",
"install.http_port": "Gitean HTTP-kuunteluportti",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "Gitean juuriosoite",
"install.app_url_helper": "Juuriosoite HTTP(S)-klooniosoitteille ja sähköpostimuistutuksille.",
"install.log_root_path": "Lokin polku",
@@ -147,18 +161,37 @@
"install.smtp_addr": "SMTP isäntä",
"install.smtp_port": "SMTP portti",
"install.smtp_from": "Lähetä sähköpostit osoitteella",
"install.smtp_from_invalid": "The \"Send Email As\" address is invalid",
"install.smtp_from_helper": "Sähköpostiosoite, jota Gitea käyttää. Kirjoita osoite ”nimi” <email@example.com> -muodossa.",
"install.mailer_user": "SMTP-käyttäjätunnus",
"install.mailer_password": "SMTP-salasana",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Vaadi sähköpostin vahvistaminen rekisteröintiin",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Ota käyttöön sähköpostiilmoitukset",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Palvelin ja kolmansien osapuolten palveluiden asetukset",
"install.offline_mode": "Ota käyttöön lokaali tila",
"install.offline_mode_popup": "Poista kolmannen osapuolen sisällöstä jakeluverkot ja tarjoa kaikki resurssit paikallisesti.",
"install.disable_gravatar": "Poista Gravatar käytöstä",
"install.disable_gravatar_popup": "Poista Gravatar ja kolmannen osapuolen avaratir käytöstä. Oletus-avatar näytetään, ellei käyttäjä ole ladannut omaansa.",
"install.federated_avatar_lookup": "Käytä ulkopuolisia profiilikuvia",
"install.federated_avatar_lookup_popup": "Enable federated avatars lookup to use federated open source service based on libravatar.",
"install.disable_registration": "Poista rekisteröinti käytöstä",
"install.disable_registration_popup": "Poista käyttäjän itse-rekisteröinti, vain ylläpito voi luoda tilejä.",
"install.allow_only_external_registration_popup": "Salli rekisteröinti vain ulkopuolisista palveluista",
@@ -166,30 +199,53 @@
"install.openid_signin_popup": "Ota käyttöön kirjautuminen OpenID:n kautta.",
"install.openid_signup": "Ota käyttöön OpenID itse-rekisteröinti",
"install.openid_signup_popup": "Ota käyttöön OpenID-pohjainen käyttäjän itse-rekisteröinti.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Ota käyttöön CAPTCHA rekisteröityessä",
"install.enable_captcha_popup": "Pakollinen captcha käyttäjän itse rekisteröityessä.",
"install.require_sign_in_view": "Vaadi sisäänkirjautuminen sivujen näkemiseksi",
"install.require_sign_in_view_popup": "Limit page access to signed-in users. Visitors will only see the sign-in and registration pages.",
"install.admin_setting_desc": "Ylläpitotilin luominen on valinnaista. Ensimmäisestä rekisteröityneestä käyttäjästä tulee automaattisesti ylläpitäjä.",
"install.admin_title": "Ylläpitotilin asetukset",
"install.admin_name": "Ylläpitäjän käyttäjätunnus",
"install.admin_password": "Salasana",
"install.confirm_password": "Varmista salasana",
"install.admin_email": "Sähköpostiosoite",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Asenna Gitea",
"install.test_git_failed": "Epäonnistui testata 'git' komentoa: %v",
"install.sqlite3_not_available": "Tämä Gitea versio ei tue SQLite3. Lataa virallinen binääriversio kohteesta %s (ei 'gobuild' versio).",
"install.invalid_db_setting": "Tietokanta-asetukset ovat väärin: %v",
"install.invalid_db_table": "The database table \"%s\" is invalid: %v",
"install.invalid_repo_path": "Repojen juuri polku on virheellinen: %v",
"install.invalid_app_data_path": "Sovelluksen datapolku on virheellinen: %v",
"install.internal_token_failed": "Sisäisen pääsymerkin luonti epäonnistui: %v",
"install.secret_key_failed": "Failed to generate secret key: %v",
"install.save_config_failed": "Asetusten tallentaminen epäonnistui: %v",
"install.invalid_admin_setting": "Administrator account setting is invalid: %v",
"install.invalid_log_root_path": "The log path is invalid: %v",
"install.default_keep_email_private": "Piilota sähköpostiosoitteet oletuksena",
"install.default_keep_email_private_popup": "Piilota oletusarvoisesti uusien käyttäjätilien sähköpostiosoitteet.",
"install.default_allow_create_organization": "Allow Creation of Organizations by Default",
"install.default_allow_create_organization_popup": "Allow new user accounts to create organizations by default.",
"install.default_enable_timetracking": "Ota ajan seuranta oletusarvoisesti käyttöön",
"install.default_enable_timetracking_popup": "Ota käyttöön uusien repojen aikaseuranta oletusarvoisesti.",
"install.no_reply_address": "Piilotettu sähköpostin verkkotunnus",
"install.no_reply_address_helper": "Verkkotunnuksen nimi käyttäjille, joilla on piilotettu sähköpostiosoite. Esimerkiksi käyttäjätunnus 'joe' kirjataan Git nimellä 'joe@noreply.example.org' jos piilotettu sähköpostiosoite on asetettu 'noreply.example.org'.",
"install.password_algorithm": "Salasanan hajautusalgoritmi",
"install.invalid_password_algorithm": "Invalid password hash algorithm",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "Enable Update Checker",
"install.enable_update_checker_helper": "Checks for new version releases periodically by connecting to gitea.io.",
"install.env_config_keys": "Environment Configuration",
"install.env_config_keys_prompt": "The following environment variables will also be applied to your configuration file:",
"install.config_write_file_prompt": "These configuration options will be written into: %s",
"home.uname_holder": "Käyttäjätunnus tai sähköpostiosoite",
"home.password_holder": "Salasana",
"home.switch_dashboard_context": "Vaihda kojelaudan kontekstia",
@@ -223,6 +279,9 @@
"auth.forgot_password_title": "Unohtuiko salasana",
"auth.forgot_password": "Unohtuiko salasana?",
"auth.must_change_password": "Vaihda salasanasi",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.allow_password_change": "Vaadi käyttäjää vaihtamaan salasanansa (suositeltava)",
"auth.reset_password_mail_sent_prompt": "Varmistussähköposti on lähetetty osoitteeseen <b>%s</b>. Tarkista saapuneet seuraavan %s tunnin sisällä saadaksesi tilin palauttamisen valmiiksi.",
"auth.active_your_account": "Aktivoi tilisi",
@@ -1237,6 +1296,7 @@
"admin.users.allow_create_organization": "Voi luoda organisaatioita",
"admin.users.update_profile": "Päivitä käyttäjän tili",
"admin.users.delete_account": "Poista käyttäjän tili",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.list_status_filter.menu_text": "Suodata",
"admin.users.list_status_filter.reset": "Tyhjennä",
"admin.users.list_status_filter.is_active": "Aktiivinen",
@@ -1474,5 +1534,15 @@
"actions.runners.labels": "Tunnisteet",
"actions.runners.task_list.run": "Suorita",
"actions.runners.task_list.repository": "Repo",
"actions.runners.version": "Versio"
"actions.runners.version": "Versio",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+50 -2
View File
@@ -262,6 +262,8 @@
"install.general_title": "Configuration générale",
"install.app_name": "Titre du site",
"install.app_name_helper": "Entrez ici le nom de votre société.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Emplacement racine des dépôts",
"install.repo_path_helper": "Les dépôts Git distants seront stockés dans ce répertoire.",
"install.lfs_path": "Répertoire racine Git LFS",
@@ -287,8 +289,32 @@
"install.smtp_from_helper": "Adresse courriel utilisée par Gitea. Utilisez directement votre adresse ou la forme « Nom <email@example.com> ».",
"install.mailer_user": "Utilisateur SMTP",
"install.mailer_password": "Mot de passe SMTP",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Exiger la confirmation du courriel lors de linscription",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Activer les notifications par courriel",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Paramètres Serveur et Tierce Parties",
"install.disable_registration": "Désactiver le formulaire d'inscription",
"install.disable_registration_popup": "Désactiver les nouvelles inscriptions. Seuls les administrateurs pourront créer de nouveaux comptes utilisateurs.",
@@ -297,6 +323,8 @@
"install.openid_signin_popup": "Activer l'authentification via OpenID.",
"install.openid_signup": "Activer l'inscription OpenID",
"install.openid_signup_popup": "Activer l'inscription avec OpenID.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Activer le CAPTCHA d'inscription",
"install.enable_captcha_popup": "Demander un CAPTCHA à l'inscription.",
"install.require_sign_in_view": "Exiger la connexion à un compte pour afficher les pages",
@@ -307,6 +335,13 @@
"install.admin_password": "Mot de passe",
"install.confirm_password": "Confirmez le mot de passe",
"install.admin_email": "Courriel",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Installer Gitea",
"install.test_git_failed": "Le test de la commande \"git\" a échoué : %v",
"install.sqlite3_not_available": "Cette version de Gitea ne supporte pas SQLite3. Veuillez télécharger la version binaire officielle de %s (pas la version 'gobuild').",
@@ -314,7 +349,6 @@
"install.invalid_db_table": "La table \"%s\" de la base de données est invalide : %v",
"install.invalid_repo_path": "Le chemin racine du dépôt est invalide : %v",
"install.invalid_app_data_path": "Le chemin des données de l'application est invalide : %v",
"install.run_user_not_match": "Le nom d'utilisateur sous lequel Gitea est configuré n'est pas le nom d'utilisateur actuel: %s -> %s",
"install.internal_token_failed": "Impossible de générer le jeton interne : %v",
"install.secret_key_failed": "Impossible de générer la clé secrète : %v",
"install.save_config_failed": "L'enregistrement de la configuration %v a échoué",
@@ -387,6 +421,9 @@
"auth.sign_up_now": "Inscrivez-vous dès maintenant !",
"auth.sign_up_successful": "Le compte a été créé avec succès. Bienvenue !",
"auth.confirmation_mail_sent_prompt_ex": "Un nouveau courriel de confirmation a été envoyé à <b>%s</b>. Veuillez vérifier votre boîte de réception dans la prochaine %s pour terminer le processus dinscription. Si votre adresse courriel est incorrecte, vous pouvez vous reconnecter et la modifier.",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.must_change_password": "Réinitialisez votre mot de passe",
"auth.allow_password_change": "Demande à l'utilisateur de changer son mot de passe (recommandé)",
"auth.reset_password_mail_sent_prompt": "Un mail de confirmation a été envoyé à <b>%s</b>. Veuillez vérifier votre boîte de réception dans les prochaines %s pour terminer la procédure de récupération du compte.",
@@ -3006,6 +3043,7 @@
"admin.users.last_login": "Dernière connexion",
"admin.users.never_login": "Jamais connecté",
"admin.users.send_register_notify": "Envoyer une notification d'inscription",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.new_success": "Le compte \"%s\" a bien été créé.",
"admin.users.edit": "Éditer",
"admin.users.auth_source": "Sources d'authentification",
@@ -3819,5 +3857,15 @@
"actions.general.cross_repo_desc": "Permet aux dépôts sélectionnés d’être visible en lecture-seule par tous les dépôts de ce propriétaire à laide de GITEA_TOKEN lors de lexécution des tâches dactions.",
"actions.general.cross_repo_selected": "Dépôts sélectionnés",
"actions.general.cross_repo_target_repos": "Dépôts cibles",
"actions.general.cross_repo_add": "Ajouter un dépôt cible"
"actions.general.cross_repo_add": "Ajouter un dépôt cible",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+50 -2
View File
@@ -262,6 +262,8 @@
"install.general_title": "Socruithe Ginearálta",
"install.app_name": "Teideal an tSuímh",
"install.app_name_helper": "Is féidir leat ainm do chuideachta a iontráil anseo.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Cosán Fréimhe an Stór",
"install.repo_path_helper": "Sábhálfar stórais iargúlta Git chuig an eolaire seo.",
"install.lfs_path": "Cosán Fréamh Git LFS",
@@ -287,8 +289,32 @@
"install.smtp_from_helper": "Seoladh ríomhphoist a úsáidfidh Gitea. Cuir isteach seoladh ríomhphoist simplí nó úsáid an fhormáid \"Ainm\" <email@example.com>.",
"install.mailer_user": "SMTP Ainm úsáideora",
"install.mailer_password": "Pasfhocal SMTP",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Deimhniú Ríomhphoist a cheangal le Clárú",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Cumasaigh Fógraí Ríomhphoist",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Socruithe Freastalaí agus Seirbhíse Tríú Páirtí",
"install.disable_registration": "Díchumasaigh Féin-Chlárú",
"install.disable_registration_popup": "Díchumasaigh féinchlárú úsáideora. Ní bheidh ach riarthóirí in ann cuntais úsáideora nua a chruthú.",
@@ -297,6 +323,8 @@
"install.openid_signin_popup": "Cumasaigh síniú isteach úsáideora trí OpenID.",
"install.openid_signup": "Cumasaigh Féinchlárú OpenID",
"install.openid_signup_popup": "Cumasaigh féinchlárú úsáideora bunaithe ar OpenID.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Cumasaigh clárú CAPTCHA",
"install.enable_captcha_popup": "Teastaíonn CAPTCHA le haghaidh féinchlárú úsáideora.",
"install.require_sign_in_view": "Teastaíonn Sínigh isteach chun Leathanaigh Amharc",
@@ -307,6 +335,13 @@
"install.admin_password": "Pasfhocal",
"install.confirm_password": "Deimhnigh Pasfhocal",
"install.admin_email": "Seoladh ríomhphoist",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Suiteáil Gitea",
"install.test_git_failed": "Ní féidir ordú 'git' a thástáil: %v",
"install.sqlite3_not_available": "Ní thacaíonn an leagan Gitea seo le SQLite3. Íoslódáil an leagan dénártha oifigiúil ó %s (ní an leagan 'gobuild').",
@@ -314,7 +349,6 @@
"install.invalid_db_table": "Tá an tábla bunachar sonraí \"%s\" neamhbhailí: %v",
"install.invalid_repo_path": "Tá cosán fréimhe an stór neamhbhailí:%v",
"install.invalid_app_data_path": "Tá cosán sonraí an aip neamhbhailí:%v",
"install.run_user_not_match": "Ní hé an t-ainm úsáideora 'rith mar' an t-ainm úsáideora reatha: %s -> %s",
"install.internal_token_failed": "Theip ar chomhartha inmheánach a ghiniúint:%v",
"install.secret_key_failed": "Theip ar an eochair rúnda a ghiniúint:%v",
"install.save_config_failed": "Theip ar chumraíocht a shábháil:%v",
@@ -387,6 +421,9 @@
"auth.sign_up_now": "Cláraigh anois.",
"auth.sign_up_successful": "Cruthaíodh cuntas go rathúil. Fáilte romhat!",
"auth.confirmation_mail_sent_prompt_ex": "Tá ríomhphost dearbhaithe nua seolta chuig <b>%s</b>. Seiceáil do bhosca isteach laistigh den chéad %s eile chun an próiseas clárúcháin a chur i gcrích. Má tá do sheoladh ríomhphoist clárúcháin mícheart, is féidir leat síniú isteach arís agus é a athrú.",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.must_change_password": "Nuashonraigh do phasfhocal",
"auth.allow_password_change": "A cheangal ar an úsáideoir pasfhocal a athrú (molta)",
"auth.reset_password_mail_sent_prompt": "Seoladh ríomhphost deimhnithe chu <b>ig %s</b>. Seiceáil do bhosca isteach laistigh den chéad %s eile chun an próiseas aisghabhála cuntais a chríochnú.",
@@ -3008,6 +3045,7 @@
"admin.users.last_login": "Sínigh Isteach Deiridh",
"admin.users.never_login": "Ná Sínigh Isteach riamh",
"admin.users.send_register_notify": "Seol Fógra um Chlárú Úsáideora",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.new_success": "Tá an cuntas úsáideora \"%s\" cruthaithe.",
"admin.users.edit": "Eagar",
"admin.users.auth_source": "Foinse Fíordheimhnithe",
@@ -3819,5 +3857,15 @@
"actions.general.cross_repo_desc": "Ceadaigh rochtain (léamh amháin) a bheith ag na stórtha uile san úinéir seo ar na stórtha roghnaithe le GITEA_TOKEN agus poist Gníomhartha á reáchtáil.",
"actions.general.cross_repo_selected": "Stórtha roghnaithe",
"actions.general.cross_repo_target_repos": "Stórtha Spriocdhírithe",
"actions.general.cross_repo_add": "Cuir Stór Sprioc leis"
"actions.general.cross_repo_add": "Cuir Stór Sprioc leis",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+81 -8
View File
@@ -81,8 +81,10 @@
"startpage.lightweight": "Könnyűsúlyú",
"startpage.license": "Nyílt forráskódú",
"install.install": "Telepítés",
"install.installing_desc": "Installing now, please wait…",
"install.title": "Kezdeti konfiguráció",
"install.docker_helper": "Ha ön a Gitea-t Docker-ből futtatja, kérem olvassa el a <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">dokumentációt</a> a beállítások megváltoztatása előtt.",
"install.require_db_desc": "Gitea requires MySQL, PostgreSQL, MSSQL, SQLite3 or TiDB (MySQL protocol).",
"install.db_title": "Adatbázis beállítások",
"install.db_type": "Adatbázis típusa",
"install.host": "Kiszolgáló",
@@ -91,22 +93,38 @@
"install.db_name": "Adatbázis neve",
"install.db_schema": "Séma",
"install.db_schema_helper": "Az adatbázis alapértelmezett beállításához (\"public\") üresen kell hagyni.",
"install.ssl_mode": "SSL",
"install.path": "Elérési út",
"install.sqlite_helper": "A SQLite3 adatbázis elérési útvonala.<br>Kérjük adjon meg egy abszolút elérési útvonalat, ha a Gitea-t szolgáltatásként futtatja.",
"install.reinstall_error": "You are trying to install into an existing Gitea database",
"install.reinstall_confirm_message": "Re-installing with an existing Gitea database can cause multiple problems. In most cases, you should use your existing \"app.ini\" to run Gitea. If you know what you are doing, confirm the following:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "You confirm that you are absolutely sure that this Gitea is running with the correct app.ini location and that you are sure that you have to re-install. You confirm that you acknowledge the above risks.",
"install.err_empty_db_path": "SQLite3 adatbázis elérési útvonala nem lehet üres.",
"install.no_admin_and_disable_registration": "Nem tilthatja le a regisztrációt, amíg nem hoz létre egy rendszergazdai fiókot.",
"install.err_empty_admin_password": "A rendszergazdai jelszó nem lehet üres.",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "Általános beállítások",
"install.app_name": "Webhely címe",
"install.app_name_helper": "Itt megadhatja a vállalata nevét.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Tárolók gyökérkönyvtára",
"install.repo_path_helper": "Minden távoli Git tároló ebbe a mappába lesz mentve.",
"install.lfs_path": "LFS Gyökérkönyvtár",
"install.lfs_path_helper": "A fájlok amiket Git LFS-el elmentesz ebbe a könyvtárba kerülnek. Hagyd üresen az LFS kikapcsolásához.",
"install.run_user": "Futtatás mint",
"install.run_user_helper": "The operating system username that Gitea runs as, it must have write access to the data paths. This value is auto-detected and cannot be changed here. To use a different user, restart Gitea under that account.",
"install.domain": "Server Domain",
"install.domain_helper": "Domain or host address for the server.",
"install.ssh_port": "SSH szerver port",
"install.ssh_port_helper": "SSH port amit az ön szervere használni fog. Hagyja üresen a kikapcsoláshoz.",
"install.http_port": "Gitea HTTP Figyelő Port",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "Az oldal alapértelmezett címe",
"install.app_url_helper": "Alapcím HTTP(S) klón címekhez és e-mail értesítésekhez.",
"install.log_root_path": "Naplófájl elérési útja",
@@ -116,18 +134,37 @@
"install.smtp_addr": "SMTP kiszolgáló",
"install.smtp_port": "SMTP port",
"install.smtp_from": "E-mail küldése mint",
"install.smtp_from_invalid": "The \"Send Email As\" address is invalid",
"install.smtp_from_helper": "Az E-mail cím a mit a Gitea használni fog. Megadhatja sima email címként vagy \"Név<email@példa.hu>\" formátumban.",
"install.mailer_user": "SMTP-felhasználónév",
"install.mailer_password": "SMTP-jelszó",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "A regisztrációhoz e-mail visszaigazolás szükséges",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Email értesítés engedélyezése",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Szerver és egyéb szolgáltatások beállítása",
"install.offline_mode": "Helyi mód bekapcsolása",
"install.offline_mode_popup": "Gravatar és egyedi források kikapcsolása, minden avatárt a felhasználók töltenek fel.",
"install.disable_gravatar": "Gravatar Kikapcsolása",
"install.disable_gravatar_popup": "Gravatar és a harmadik féltől származó avatar források letoltása. Alapértelmezett avatárt fog használni, kivéve, ha a felhasználó helyileg tölt fel avatárt.",
"install.federated_avatar_lookup": "Összevont profilkép lekérés engedélyezése",
"install.federated_avatar_lookup_popup": "Összevont profilkép lekérés engedélyezése a libravatar használatával.",
"install.disable_registration": "Ön-regisztráció kikapcsolása",
"install.disable_registration_popup": "Regisztráció kikapcsolása, csak a rendszergazda hozhat létre fiókokat.",
"install.allow_only_external_registration_popup": "Regisztráció engedélyezése csak külső forrásokból",
@@ -135,20 +172,34 @@
"install.openid_signin_popup": "Felhasználói bejelentkezés engedélyezése OpenID-val.",
"install.openid_signup": "Regisztráció engedélyezése OpenID alapon",
"install.openid_signup_popup": "Regisztráció engedélyezése OpenID alapon.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Enable registration CAPTCHA",
"install.enable_captcha_popup": "CAPTCHA megkövetelése amikor egy felhasználó regisztrál.",
"install.require_sign_in_view": "Bejelentkezés megkövetelése az oldalak megtekintéséhez",
"install.require_sign_in_view_popup": "Limit page access to signed-in users. Visitors will only see the sign-in and registration pages.",
"install.admin_setting_desc": "Nem szükséges most beállítania rendszergazdai fiókot, mert az első felhasználó automatikusan rendszergazdai jogokat kap.",
"install.admin_title": "Rendszergazda fiók beállításai",
"install.admin_name": "Rendszergazda felhasználóneve",
"install.admin_password": "Jelszó",
"install.confirm_password": "Jelszó megerősítése",
"install.admin_email": "E-mail cím",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Gitea telepítése",
"install.test_git_failed": "Nem sikerült a 'git' parancs kipróbálása: %v",
"install.sqlite3_not_available": "Ez a verzió nem támogatja az SQLite3-at, kérlek töltsd le a hivatalos bináris verziót: %s (NE a gobuild változatot).",
"install.invalid_db_setting": "Az adatbázis-beállítások érvénytelenek: %v",
"install.invalid_db_table": "The database table \"%s\" is invalid: %v",
"install.invalid_repo_path": "Repository gyökérkönyvtára helytelen: %v",
"install.run_user_not_match": "Futtató felhasználó más, mint az aktuális felhasználó: %s -> %s",
"install.invalid_app_data_path": "The app data path is invalid: %v",
"install.internal_token_failed": "Failed to generate internal token: %v",
"install.secret_key_failed": "Failed to generate secret key: %v",
"install.save_config_failed": "Hiba történt a konfiguráció mentése közben: %v",
"install.invalid_admin_setting": "Hibás a rendszergazdai fiók beállítása: %v",
"install.invalid_log_root_path": "Naplózás gyökérmappa érvénytelen: %v",
@@ -160,6 +211,14 @@
"install.default_enable_timetracking_popup": "Időmérés bekapcsolása az új tárolókra alapértelmezetten.",
"install.no_reply_address": "Rejtett e-mail tartomány",
"install.no_reply_address_helper": "Domain név a rejtett email címmel rendelkező felhasználók számára.Például: Ha a felhasználóneve \"jani\" akkor bejelentkezhet a \"jani@noreply.example.org\" email címmel,ha a rejtett email domain \"noreply.example.org\"-ra van állítva.",
"install.password_algorithm": "Password Hash Algorithm",
"install.invalid_password_algorithm": "Invalid password hash algorithm",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "Enable Update Checker",
"install.enable_update_checker_helper": "Checks for new version releases periodically by connecting to gitea.io.",
"install.env_config_keys": "Environment Configuration",
"install.env_config_keys_prompt": "The following environment variables will also be applied to your configuration file:",
"install.config_write_file_prompt": "These configuration options will be written into: %s",
"home.uname_holder": "Felhasználónév vagy e-mail cím",
"home.password_holder": "Jelszó",
"home.switch_dashboard_context": "Műszerfal nézőpont váltás",
@@ -187,6 +246,9 @@
"auth.forgot_password_title": "Elfelejtett jelszó",
"auth.forgot_password": "Elfelejtette a jelszavát?",
"auth.must_change_password": "Jelszó módosítása",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.allow_password_change": "A felhasználóknak meg kell változtatniuk a jelszavukat(ajánlott)",
"auth.reset_password_mail_sent_prompt": "Megerősítő email lett küldve ide: <b>%s</b>. Ellenőrizze postafiókját az elkövetkező %s a jelszó visszaállítási folyamat befejezéséhez.",
"auth.active_your_account": "Aktiválja a fiókját",
@@ -1109,6 +1171,7 @@
"admin.users.created": "Létrehozva",
"admin.users.last_login": "Utolsó bejelentkezés",
"admin.users.send_register_notify": "Felhasználó regisztráció értesítés küldése",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.edit": "Szerkesztés",
"admin.users.auth_source": "Hitelesítési forrás",
"admin.users.local": "Helyi",
@@ -1383,5 +1446,15 @@
"actions.runners.task_list.repository": "Tároló",
"actions.runners.status.active": "Aktív",
"actions.runners.version": "Verzió",
"git.filemode.symbolic_link": "Szimbolikus hivatkozás"
"git.filemode.symbolic_link": "Szimbolikus hivatkozás",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+138 -3
View File
@@ -153,24 +153,145 @@
"startpage.lightweight": "Ringan",
"startpage.lightweight_desc": "Gitea hanya membutuhkan persyaratan minimal dan bisa berjalan pada Raspberry Pi yang murah. Bisa menghemat listrik!",
"startpage.license": "Sumber Terbuka",
"install.install": "Installation",
"install.installing_desc": "Installing now, please wait…",
"install.title": "Konfigurasi Awal",
"install.docker_helper": "If you run Gitea inside Docker, please read the <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">documentation</a> before changing any settings.",
"install.require_db_desc": "Gitea requires MySQL, PostgreSQL, MSSQL, SQLite3 or TiDB (MySQL protocol).",
"install.db_title": "Database Settings",
"install.db_type": "Database Type",
"install.host": "Host",
"install.user": "Nama Pengguna",
"install.password": "Kata Sandi",
"install.db_name": "Database Name",
"install.db_schema": "Schema",
"install.db_schema_helper": "Leave blank for database default (\"public\").",
"install.ssl_mode": "SSL",
"install.path": "Jalur",
"install.sqlite_helper": "File path for the SQLite3 database.<br>Enter an absolute path if you run Gitea as a service.",
"install.reinstall_error": "You are trying to install into an existing Gitea database",
"install.reinstall_confirm_message": "Re-installing with an existing Gitea database can cause multiple problems. In most cases, you should use your existing \"app.ini\" to run Gitea. If you know what you are doing, confirm the following:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "You confirm that you are absolutely sure that this Gitea is running with the correct app.ini location and that you are sure that you have to re-install. You confirm that you acknowledge the above risks.",
"install.err_empty_db_path": "The SQLite3 database path cannot be empty.",
"install.no_admin_and_disable_registration": "You cannot disable user self-registration without creating an administrator account.",
"install.err_empty_admin_password": "The administrator password cannot be empty.",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "General Settings",
"install.app_name": "Site Title",
"install.app_name_helper": "You can enter your company name here.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Jalur akar repositori",
"install.repo_path_helper": "Remote Git repositories will be saved to this directory.",
"install.lfs_path": "Git LFS Root Path",
"install.lfs_path_helper": "Files tracked by Git LFS will be stored in this directory. Leave empty to disable.",
"install.run_user": "Run As Username",
"install.run_user_helper": "The operating system username that Gitea runs as, it must have write access to the data paths. This value is auto-detected and cannot be changed here. To use a different user, restart Gitea under that account.",
"install.domain": "Server Domain",
"install.domain_helper": "Domain or host address for the server.",
"install.ssh_port": "SSH Server Port",
"install.ssh_port_helper": "Port number your SSH server listens on. Leave empty to disable.",
"install.http_port": "Gitea HTTP Listen Port",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "Gitea Base URL",
"install.app_url_helper": "Base address for HTTP(S) clone URLs and email notifications.",
"install.log_root_path": "Log Path",
"install.log_root_path_helper": "Log files will be written to this directory.",
"install.optional_title": "Optional Settings",
"install.email_title": "Pengaturan email",
"install.smtp_addr": "Host SMTP",
"install.smtp_port": "Port SMTP",
"install.smtp_from": "Kirim Email Sebagai",
"install.smtp_from_invalid": "The \"Send Email As\" address is invalid",
"install.smtp_from_helper": "Email address Gitea will use. Enter a plain email address or use the \"Name\" <email@example.com> format.",
"install.mailer_user": "SMTP Username",
"install.mailer_password": "SMTP Password",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Perlu Konfirmasi Email Saat Pendaftaran",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Aktifkan Notifikasi Email",
"install.disable_gravatar": "Menonaktifkan Gravatar",
"install.federated_avatar_lookup": "Aktifkan pencarian avatar",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Server and Third-Party Service Settings",
"install.disable_registration": "Disable Self-Registration",
"install.disable_registration_popup": "Disable user self-registration. Only administrators will be able to create new user accounts.",
"install.allow_only_external_registration_popup": "Allow Registration Only Through External Services",
"install.openid_signin": "Aktifkan Login OpenID",
"install.openid_signin_popup": "Enable user sign-in via OpenID.",
"install.openid_signup": "Enable OpenID Self-Registration",
"install.openid_signup_popup": "Enable OpenID-based user self-registration.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Enable registration CAPTCHA",
"install.enable_captcha_popup": "Require a CAPTCHA for user self-registration.",
"install.require_sign_in_view": "Harus Login Untuk Melihat Halaman",
"install.require_sign_in_view_popup": "Limit page access to signed-in users. Visitors will only see the sign-in and registration pages.",
"install.admin_setting_desc": "Creating a super administrator account is optional. The first registered user will automatically become a super administrator.",
"install.admin_title": "Super Administrator Account Settings",
"install.admin_name": "Super Administrator Username",
"install.admin_password": "Kata Sandi",
"install.confirm_password": "Konfirmasi Kata Sandi",
"install.admin_email": "Alamat Email",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Install Gitea",
"install.test_git_failed": "Could not test 'git' command: %v",
"install.sqlite3_not_available": "This Gitea version does not support SQLite3. Please download the official binary version from %s (not the 'gobuild' version).",
"install.invalid_db_setting": "The database settings are invalid: %v",
"install.invalid_db_table": "The database table \"%s\" is invalid: %v",
"install.invalid_repo_path": "The repository root path is invalid: %v",
"install.invalid_app_data_path": "The app data path is invalid: %v",
"install.internal_token_failed": "Failed to generate internal token: %v",
"install.secret_key_failed": "Failed to generate secret key: %v",
"install.save_config_failed": "Failed to save configuration: %v",
"install.invalid_admin_setting": "Administrator account setting is invalid: %v",
"install.invalid_log_root_path": "The log path is invalid: %v",
"install.default_keep_email_private": "Hide Email Addresses by Default",
"install.default_keep_email_private_popup": "Hide email addresses of new user accounts by default.",
"install.default_allow_create_organization": "Allow Creation of Organizations by Default",
"install.default_allow_create_organization_popup": "Allow new user accounts to create organizations by default.",
"install.default_enable_timetracking": "Enable Time Tracking by Default",
"install.default_enable_timetracking_popup": "Enable time tracking for new repositories by default.",
"install.no_reply_address": "Hidden Email Domain",
"install.no_reply_address_helper": "Domain name for users with a hidden email address. For example, the username 'joe' will be logged in Git as 'joe@noreply.example.org' if the hidden email domain is set to 'noreply.example.org'.",
"install.password_algorithm": "Password Hash Algorithm",
"install.invalid_password_algorithm": "Invalid password hash algorithm",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "Enable Update Checker",
"install.enable_update_checker_helper": "Checks for new version releases periodically by connecting to gitea.io.",
"install.env_config_keys": "Environment Configuration",
"install.env_config_keys_prompt": "The following environment variables will also be applied to your configuration file:",
"install.config_write_file_prompt": "These configuration options will be written into: %s",
"home.uname_holder": "Nama Pengguna atau Alamat Surel",
"home.password_holder": "Kata Sandi",
"home.switch_dashboard_context": "Alihkan Dasbor Konteks",
@@ -193,6 +314,9 @@
"auth.forgot_password_title": "Lupa Kata Sandi",
"auth.forgot_password": "Lupa kata sandi?",
"auth.must_change_password": "Perbarui kata sandi Anda",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.allow_password_change": "Wajibkan pengguna untuk mengganti kata sandi (disarankan)",
"auth.reset_password_mail_sent_prompt": "Surel konfirmasi berhasil dikirim ke <b>%s</b>. Silahkan cek akun email Anda dalam %s jam untuk menyelesaikan proses pemulihan akun.",
"auth.active_your_account": "Aktifkan Akun Anda",
@@ -940,6 +1064,7 @@
"admin.users.auth_source": "Sumber Otentikasi",
"admin.users.local": "Lokal",
"admin.users.delete_account": "Hapus Akun Pengguna",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.list_status_filter.menu_text": "Saring",
"admin.users.list_status_filter.is_admin": "Pengelola",
"admin.emails.primary": "Utama",
@@ -1198,5 +1323,15 @@
"actions.variables.update.success": "Variabel telah diedit.",
"projects.type-1.display_name": "Proyek Individu",
"projects.type-2.display_name": "Proyek Repositori",
"projects.type-3.display_name": "Proyek Organisasi"
"projects.type-3.display_name": "Proyek Organisasi",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+91 -6
View File
@@ -107,6 +107,7 @@
"startpage.lightweight_desc": "Gitea hefur lágar lágmarkskröfur og getur keyrt á ódýrum Raspberry Pi. Sparaðu orku!",
"startpage.license": "Frjáls Hugbúnaður",
"install.install": "Uppsetning",
"install.installing_desc": "Installing now, please wait…",
"install.title": "Upphafleg Uppsetning",
"install.docker_helper": "Ef þú keyrir Gitea inni í Docker þá viltu vinsamlegast lesa <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">leiðbeiningaritið</a> áður en þú breytir stillingum.",
"install.require_db_desc": "Gitea krefst MySQL, PostgreSQL, MSSQL, SQLite3 eða TiDB (MySQL samskiptareglur).",
@@ -118,27 +119,38 @@
"install.db_name": "Gagnagrunnsheiti",
"install.db_schema": "Uppdráttur",
"install.db_schema_helper": "Skildu eftir autt fyrir sjálfgefinn gagnagrunn („public“).",
"install.ssl_mode": "SSL",
"install.path": "Slóð",
"install.sqlite_helper": "Skráarslóð fyrir SQLite3 gagnagrunninn.<br>Sláðu inn algjöra slóð ef þú keyrir Gitea sem þjónustu.",
"install.reinstall_error": "Þú ert að reyna að setja upp í núverandi Gitea gagnagrunn",
"install.reinstall_confirm_message": "Enduruppsetning með núverandi Gitea gagnagrunni getur valdið mörgum vandamálum. Í flestum tilfellum ættir þú að nota núverandi \"app.ini\" til að keyra Gitea. Ef þú veist hvað þú ert að gera skaltu staðfesta eftirfarandi:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "Þú staðfestir að þú sért alveg viss um að þetta Gitea sé í gangi með réttri app.ini staðsetningu og að þú sért viss um að þú þurfir að setja það upp aftur. Þú staðfestir að þú viðurkennir ofangreindar áhættur.",
"install.err_empty_db_path": "SQLite3 gagnagrunnsslóðin má ekki vera tóm.",
"install.no_admin_and_disable_registration": "Þú getur ekki slökkt á sjálfsskráningu notenda án þess að búa til stjórnandanotanda.",
"install.err_empty_admin_password": "Lykilorð stjórnanda má ekki vera tómt.",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "Almennar Stillingar",
"install.app_name": "Heiti vefsvæðis",
"install.app_name_helper": "Þú getur slegið inn nafn fyrirtækis þíns hér.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Grunnsslóð Hugbúnaðarsafns",
"install.repo_path_helper": "Fjarlægar Git hugbúnaðarsöfn verða vistaðar í þessari möppu.",
"install.lfs_path": "Git LFS Grunnsslóð",
"install.lfs_path_helper": "Skrár sem Git LFS rekur verða geymdar í þessari möppu. Skildu eftir tómt til að slökkva á.",
"install.run_user": "Keyra Sem Notandanafn",
"install.run_user_helper": "The operating system username that Gitea runs as, it must have write access to the data paths. This value is auto-detected and cannot be changed here. To use a different user, restart Gitea under that account.",
"install.domain": "Lén Netþjóns",
"install.domain_helper": "Lén eða hýsilfang fyrir netþjóninn.",
"install.ssh_port": "SSH Netþjónsgátt",
"install.ssh_port_helper": "Gátt sem SSH þjónninn þinn hlustar á. Skildu eftir tómt til að slökkva á.",
"install.http_port": "Gitea HTTP Hlustunargátt",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "Grunnvefslóð Gitea",
"install.app_url_helper": "Grunnvistfang fyrir HTTP(S) afrit slóð og tölvupósttilkynningar.",
"install.log_root_path": "Slóð Annáls",
@@ -148,32 +160,91 @@
"install.smtp_addr": "SMTP Hýsill",
"install.smtp_port": "SMTP Gátt",
"install.smtp_from": "Senda Tölvupóst Sem",
"install.smtp_from_invalid": "The \"Send Email As\" address is invalid",
"install.smtp_from_helper": "Netfang sem Gitea mun nota. Sláðu inn venjulegt netfang eða notaðu „Nafn“ <email@example.com> sniðið.",
"install.mailer_user": "SMTP Notandanafn",
"install.mailer_password": "SMTP Lykilorð",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Krefjast Staðfestingar Tölvupósts Til Að Nýskrá",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Virkja Tölvupósttilkynningar",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Stillingar Netþjóns og Þriðja Aðila",
"install.offline_mode": "Virkjaðu Staðbundin Ham",
"install.offline_mode_popup": "Slökktu á efnisafhendingarnetum þriðja aðila og þjónaðu öllum gögnum á staðnum.",
"install.disable_gravatar": "Óvirkja Gravatar",
"install.disable_gravatar_popup": "Slökkva á Gravatar og notandamyndar þjónustum. Sjálfgefin notandamynd verður notuð ef notandi hleður ekki upp sína eigin.",
"install.federated_avatar_lookup": "Virkja Samtök Notandamyndar",
"install.disable_registration": "Disable Self-Registration",
"install.disable_registration_popup": "Disable user self-registration. Only administrators will be able to create new user accounts.",
"install.allow_only_external_registration_popup": "Allow Registration Only Through External Services",
"install.openid_signin": "Virkja OpenID Innskráningu",
"install.openid_signin_popup": "Virkja OpenID innskráningu notenda.",
"install.openid_signup": "Enable OpenID Self-Registration",
"install.openid_signup_popup": "Enable OpenID-based user self-registration.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Virkja CAPTCHA innskráningu",
"install.enable_captcha_popup": "Require a CAPTCHA for user self-registration.",
"install.require_sign_in_view": "Require Sign-In to View Pages",
"install.require_sign_in_view_popup": "Limit page access to signed-in users. Visitors will only see the sign-in and registration pages.",
"install.admin_setting_desc": "Creating a super administrator account is optional. The first registered user will automatically become a super administrator.",
"install.admin_title": "Super Administrator Account Settings",
"install.admin_name": "Notandanafn Stjórnanda",
"install.admin_password": "Lykilorð",
"install.confirm_password": "Staðfestu Lykilorðið",
"install.admin_email": "Netfang",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Setja upp Gitea",
"install.test_git_failed": "Gat ekki prófað „git“ skipunina: %v",
"install.sqlite3_not_available": "Þessi Gitea útgáfa styður ekki SQLite3. Vinsamlegast sæktu útgáfunni okkar frá %s (ekki „gobuild“ útgáfunna).",
"install.invalid_db_setting": "Gagnagrunnsstillingarnar eru ógildar: %v",
"install.invalid_db_table": "The database table \"%s\" is invalid: %v",
"install.invalid_repo_path": "Grunnsslóð hugbúnaðarsafns er ógild: %v",
"install.invalid_app_data_path": "The app data path is invalid: %v",
"install.internal_token_failed": "Failed to generate internal token: %v",
"install.secret_key_failed": "Failed to generate secret key: %v",
"install.save_config_failed": "Failed to save configuration: %v",
"install.invalid_admin_setting": "Administrator account setting is invalid: %v",
"install.invalid_log_root_path": "Slóð annáls er ógild: %v",
"install.default_keep_email_private": "Hide Email Addresses by Default",
"install.default_keep_email_private_popup": "Fela sjálfgefið netföng nýrra notendareikninga.",
"install.default_allow_create_organization": "Allow Creation of Organizations by Default",
"install.default_allow_create_organization_popup": "Allow new user accounts to create organizations by default.",
"install.default_enable_timetracking": "Enable Time Tracking by Default",
"install.default_enable_timetracking_popup": "Enable time tracking for new repositories by default.",
"install.no_reply_address": "Hidden Email Domain",
"install.no_reply_address_helper": "Lén fyrir notendur með falið netfang. Til dæmis notandanafnið „joe“ verður skráð í Git sem „joe@noreply.example.org“ ef falið tölvupóstlén er stillt á „noreply.example.org“.",
"install.password_algorithm": "Password Hash Algorithm",
"install.invalid_password_algorithm": "Invalid password hash algorithm",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "Enable Update Checker",
"install.enable_update_checker_helper": "Checks for new version releases periodically by connecting to gitea.io.",
"install.env_config_keys": "Environment Configuration",
"install.env_config_keys_prompt": "The following environment variables will also be applied to your configuration file:",
"install.config_write_file_prompt": "These configuration options will be written into: %s",
"home.uname_holder": "Notandanafn eða Netfang",
"home.password_holder": "Lykilorð",
"home.my_repos": "Hugbúnaðarsöfn",
@@ -197,6 +268,9 @@
"auth.forgot_password_title": "Gleymt Lykilorð",
"auth.forgot_password": "Gleymdirðu Lykilorðinu?",
"auth.must_change_password": "Uppfærðu lykilorðið þitt",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.active_your_account": "Virkjaðu Aðganginn Þinn",
"auth.account_activated": "Aðgangur hefur verið virkjaður",
"auth.has_unconfirmed_mail": "Halló, %s, þú ert með óstaðfest netfang (<b>%s</b>). Ef þú hefur ekki fengið staðfestingarpóst eða þarft nýjan, vinsamlegast smelltu á hnappinn hér að neðan.",
@@ -975,6 +1049,7 @@
"admin.users.created": "Búið til",
"admin.users.edit": "Breyta",
"admin.users.local": "Staðbundið",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.list_status_filter.menu_text": "Sía",
"admin.users.list_status_filter.reset": "Endurstilla",
"admin.users.list_status_filter.is_active": "Virkt",
@@ -1116,5 +1191,15 @@
"actions.runners.task_list.commit": "Framlag",
"actions.runners.status.active": "Virkt",
"actions.runners.version": "Útgáfa",
"actions.runs.commit": "Framlag"
"actions.runs.commit": "Framlag",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+75 -8
View File
@@ -101,34 +101,50 @@
"startpage.lightweight": "Leggero",
"startpage.lightweight_desc": "Gitea ha requisiti minimi bassi e può funzionare su un economico Raspberry Pi. Risparmia l'energia della tua macchina!",
"install.install": "Installazione",
"install.installing_desc": "Installing now, please wait…",
"install.title": "Configurazione Iniziale",
"install.docker_helper": "Se stai usando Gitea con Docker, leggi <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">la documentazione</a> prima di cambiare qualsiasi impostazione.",
"install.require_db_desc": "Gitea requires MySQL, PostgreSQL, MSSQL, SQLite3 or TiDB (MySQL protocol).",
"install.db_title": "Impostazioni Database",
"install.db_type": "Tipo di database",
"install.host": "Host",
"install.user": "Nome utente",
"install.password": "Password",
"install.db_name": "Nome del database",
"install.db_schema": "Schema",
"install.db_schema_helper": "Lascia vuoto per il valore predefinito del database (\"public\").",
"install.ssl_mode": "SSL",
"install.path": "Percorso",
"install.sqlite_helper": "Percorso file del database SQLite3.<br>Inserisci un percorso assoluto se stai usando Gitea come servizio.",
"install.reinstall_error": "Stai cercando di installare in un database Gitea esistente",
"install.reinstall_confirm_message": "La reinstallazione con un database Gitea esistente può causare problemi multipli. Nella maggior parte dei casi, dovresti usare il tuo \"app.ini\" esistente per eseguire Gitea. Se sai cosa stai facendo, confermi quanto segue:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "Confermi di essere assolutamente sicuro che questo Gitea è in esecuzione con l'app corretta. ni posizione e che sei sicuro di dover reinstallare. Confermi di aver riconosciuto i rischi di cui sopra.",
"install.err_empty_db_path": "Il percorso del database SQLite3 non può essere vuoto.",
"install.no_admin_and_disable_registration": "Non puoi disabilitare l'auto-registrazione degli utenti senza creare un account amministratore.",
"install.err_empty_admin_password": "La password dell'amministratore non può essere vuota.",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "Impostazioni Generali",
"install.app_name": "Titolo del Sito",
"install.app_name_helper": "Qui puoi inserire il nome della tua società.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Percorso Root del Repository",
"install.repo_path_helper": "Le Remote Git repositories saranno salvate in questa directory.",
"install.lfs_path": "Percorso radice di Git LFS",
"install.lfs_path_helper": "I file trovati da Git LFS saranno salvati in questa directory. Lasciare vuoto per disattivare.",
"install.run_user": "Esegui come Nome utente",
"install.run_user_helper": "The operating system username that Gitea runs as, it must have write access to the data paths. This value is auto-detected and cannot be changed here. To use a different user, restart Gitea under that account.",
"install.domain": "Dominio Server",
"install.domain_helper": "Dominio o indirizzo host per il server.",
"install.ssh_port": "Porta Server SSH",
"install.ssh_port_helper": "Numero di porta in ascolto sul server SSH. Lasciare vuoto per disattivare.",
"install.http_port": "Porta in ascolto HTTP Gitea",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "URL di base di Gitea",
"install.app_url_helper": "URL di base per gli HTTP(S) clone URLs e notifiche email.",
"install.log_root_path": "Percorso dei log",
@@ -138,18 +154,37 @@
"install.smtp_addr": "Host SMTP",
"install.smtp_port": "Porta SMTP",
"install.smtp_from": "Invia Email come",
"install.smtp_from_invalid": "The \"Send Email As\" address is invalid",
"install.smtp_from_helper": "Indirizzo Email che Gitea utilizzerà. Inserisci un indirizzo email o usa il formato \"Name\" <email@example.com>.",
"install.mailer_user": "Nome utente SMTP",
"install.mailer_password": "Password SMTP",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Richiedere la conferma Email per registrarsi",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Attiva le notifiche Email",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Impostazioni Server e Servizi di Terza Parte",
"install.offline_mode": "Attiva la Modalità in Locale",
"install.offline_mode_popup": "Disattiva le reti di distribuzione dei contenuti di terze parti e fornisci tutte le risorse localmente.",
"install.disable_gravatar": "Disattiva Gravatar",
"install.disable_gravatar_popup": "Disattiva Gravatar e le fonti di avatar di terze parti. Verrà usato un avatar predefinito almeno che un utente non carichi un avatar in locale.",
"install.federated_avatar_lookup": "Attiva i Federated Avatar",
"install.federated_avatar_lookup_popup": "Enable federated avatars lookup to use federated open source service based on libravatar.",
"install.disable_registration": "Disattiva Self-Registration",
"install.disable_registration_popup": "Disattiva la user self-registration. Solo gli amministratori saranno in grado di creare account.",
"install.allow_only_external_registration_popup": "Attiva la registrazione solo tramite servizi esterni",
@@ -157,21 +192,32 @@
"install.openid_signin_popup": "Attiva registrazione utente via OpenID.",
"install.openid_signup": "Attiva OpenID Self-Registration",
"install.openid_signup_popup": "Attiva OpenID-based user self-registration.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Abilita CAPTCHA per registrazione",
"install.enable_captcha_popup": "Richiedi convalida captcha per i nuovi utenti.",
"install.require_sign_in_view": "Richiedi l'accesso per visualizzare le pagine",
"install.require_sign_in_view_popup": "Limit page access to signed-in users. Visitors will only see the sign-in and registration pages.",
"install.admin_setting_desc": "Creare un account amministratore è opzionale. Il primo utente registrato sarà automaticamente un amministratore.",
"install.admin_title": "Impostazioni Account Amministratore",
"install.admin_name": "Nome utente dell'Amministratore",
"install.admin_password": "Password",
"install.confirm_password": "Conferma Password",
"install.admin_email": "Indirizzo Email",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Installare Gitea",
"install.test_git_failed": "Fallito il test del comando git: %v",
"install.sqlite3_not_available": "Questa versione di Gitea non supporta SQLite3. Si prega di scaricare la versione binaria ufficiale da %s (not the 'gobuild' version).",
"install.invalid_db_setting": "Le impostazioni del database sono invalide: %v",
"install.invalid_db_table": "The database table \"%s\" is invalid: %v",
"install.invalid_repo_path": "Il percorso radice del Repository è invalido: %v",
"install.invalid_app_data_path": "Il percorso dati dell'app non è valido: %v",
"install.run_user_not_match": "Il nome utente 'esegui come' non è il nome utente attuale: %s -> %s",
"install.internal_token_failed": "Generazione del token interno non riuscita: %v",
"install.secret_key_failed": "Generazione della chiave segreta non riuscita: %v",
"install.save_config_failed": "Salvataggio della configurazione non riuscito: %v",
@@ -186,6 +232,13 @@
"install.no_reply_address": "Dominio email nascosto",
"install.no_reply_address_helper": "Nome dominio per utenti con un indirizzo email nascosto. Ad esempio, il nome utente 'joe' accederà a Git come 'joe@noreply.example.org' se il dominio email nascosto è impostato a 'noreply.example.org'.",
"install.password_algorithm": "Algoritmo Password Hash",
"install.invalid_password_algorithm": "Invalid password hash algorithm",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "Enable Update Checker",
"install.enable_update_checker_helper": "Checks for new version releases periodically by connecting to gitea.io.",
"install.env_config_keys": "Environment Configuration",
"install.env_config_keys_prompt": "The following environment variables will also be applied to your configuration file:",
"install.config_write_file_prompt": "These configuration options will be written into: %s",
"home.uname_holder": "Nome utente o Indirizzo Email",
"home.switch_dashboard_context": "Cambia Dashboard Context",
"home.show_more_repos": "Mostra altre repositories…",
@@ -218,6 +271,9 @@
"auth.forgot_password_title": "Password Dimenticata",
"auth.forgot_password": "Password dimenticata?",
"auth.must_change_password": "Aggiorna la tua password",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.allow_password_change": "Richiede all'utente di cambiare la password (scelta consigliata)",
"auth.reset_password_mail_sent_prompt": "Una email di conferma è stata inviata a <b>%s</b>. Per favore controlla la tua posta in arrivo nelle prossime %s per completare il processo di reset della password.",
"auth.active_your_account": "Attiva il tuo Account",
@@ -1920,6 +1976,7 @@
"admin.users.created": "Creato",
"admin.users.last_login": "Ultimo accesso",
"admin.users.send_register_notify": "Invia notifica di registrazione utente",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.edit": "Modifica",
"admin.users.auth_source": "Fonte di autenticazione",
"admin.users.local": "Locale",
@@ -2377,5 +2434,15 @@
"actions.runners.task_list.run": "Esegui",
"actions.runners.status.active": "Attivo",
"actions.runners.version": "Versione",
"git.filemode.symbolic_link": "Link Simbolico"
"git.filemode.symbolic_link": "Link Simbolico",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+50 -8
View File
@@ -256,6 +256,8 @@
"install.general_title": "基本設定",
"install.app_name": "サイトタイトル",
"install.app_name_helper": "企業名をここに入れることができます。",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "リポジトリのルートパス",
"install.repo_path_helper": "リモートGitリポジトリはこのディレクトリに保存されます。",
"install.lfs_path": "Git LFSルートパス",
@@ -281,15 +283,33 @@
"install.smtp_from_helper": "Giteaが使用するメールアドレス。 メールアドレスのみ、または、 \"名前\" <email@example.com> の形式で入力してください。",
"install.mailer_user": "SMTPユーザー名",
"install.mailer_password": "SMTPパスワード",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "登録にはメールによる確認が必要",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "メール通知を有効にする",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "サーバーと外部サービスの設定",
"install.offline_mode": "ローカルモードを有効にする",
"install.offline_mode_popup": "外のCDNサービスを使わず、すべてのリソースを自前で提供します。",
"install.disable_gravatar": "Gravatarを無効にする",
"install.disable_gravatar_popup": "Gravatarと外のアバターソースを無効にします。 アバターをローカルにアップロードしていないユーザーには、デフォルトのアバターが使用されます。",
"install.federated_avatar_lookup": "フェデレーテッド・アバターを有効にする",
"install.federated_avatar_lookup_popup": "Libravatarを使用したフェデレーテッド・アバター検索を有効にします。",
"install.disable_registration": "セルフ登録を無効にする",
"install.disable_registration_popup": "ユーザーのセルフ登録を無効にします。 新しいユーザーアカウントを作成できるのは管理者だけとなります。",
"install.allow_only_external_registration_popup": "外部サービスを使用した登録のみを許可",
@@ -297,6 +317,8 @@
"install.openid_signin_popup": "OpenIDを使ったユーザーのサインインを有効にします。",
"install.openid_signup": "OpenIDを使ったセルフ登録を有効にする",
"install.openid_signup_popup": "OpenIDベースでのユーザーのセルフ登録を有効にします。",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "登録時のCAPTCHAを有効にする",
"install.enable_captcha_popup": "ユーザーのセルフ登録時にCAPTCHAを必須にします。",
"install.require_sign_in_view": "ページ閲覧にサインインが必要",
@@ -307,6 +329,13 @@
"install.admin_password": "パスワード",
"install.confirm_password": "パスワード確認",
"install.admin_email": "メールアドレス",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Giteaをインストール",
"install.test_git_failed": "'git'コマンドが確認できません: %v",
"install.sqlite3_not_available": "GiteaのこのバージョンはSQLite3をサポートしていません。 公式のバイナリ版を %s からダウンロードしてください。 ('gobuild'版でないもの)",
@@ -314,7 +343,6 @@
"install.invalid_db_table": "データベーステーブルの \"%s\" が無効です: %v",
"install.invalid_repo_path": "リポジトリのルートパスが無効です: %v",
"install.invalid_app_data_path": "アプリのデータパス (APP_DATA_PATH) が無効です: %v",
"install.run_user_not_match": "実行ユーザー名が、現在のユーザー名ではありません: %s -> %s",
"install.internal_token_failed": "内部トークンの生成に失敗しました: %v",
"install.secret_key_failed": "シークレットキーの生成に失敗しました: %v",
"install.save_config_failed": "設定ファイルの保存に失敗しました: %v",
@@ -387,6 +415,9 @@
"auth.sign_up_now": "登録はこちら。",
"auth.sign_up_successful": "アカウントは無事に作成されました。ようこそ!",
"auth.confirmation_mail_sent_prompt_ex": "新しい確認メールを <b>%s</b> に送信しました。 %s以内にメールボックスを確認し、登録手続きを完了してください。 登録メールアドレスが間違っている場合は、もういちどサインインすると変更することができます。",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.must_change_password": "パスワードの更新",
"auth.allow_password_change": "ユーザーはパスワードの変更が必要 (推奨)",
"auth.reset_password_mail_sent_prompt": "<b>%s</b> に確認メールを送信しました。 %s以内に受信トレイを確認し、アカウント回復手続きを完了してください。",
@@ -2971,6 +3002,7 @@
"admin.users.last_login": "前回のサインイン",
"admin.users.never_login": "未サインイン",
"admin.users.send_register_notify": "ユーザーに登録通知を送る",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.new_success": "ユーザーアカウント \"%s\" を作成しました。",
"admin.users.edit": "編集",
"admin.users.auth_source": "認証ソース",
@@ -3743,5 +3775,15 @@
"git.filemode.normal_file": "ノーマルファイル",
"git.filemode.executable_file": "実行可能ファイル",
"git.filemode.symbolic_link": "シンボリックリンク",
"git.filemode.submodule": "サブモジュール"
"git.filemode.submodule": "サブモジュール",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+50 -2
View File
@@ -259,6 +259,8 @@
"install.general_title": "기본설정",
"install.app_name": "사이트 제목",
"install.app_name_helper": "회사이름을 넣으세요.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "리포지토리 최상위 경로",
"install.repo_path_helper": "Git 원격 리포지토리는 이 디렉터리에 저장 됩니다.",
"install.lfs_path": "Git LFS 루트 경로",
@@ -284,8 +286,32 @@
"install.smtp_from_helper": "Gitea 가 사용할 이메일 주소. 이메일 주소 또는 \"이름\" <email@example.com> 형식으로 입력하세요.",
"install.mailer_user": "SMTP 사용자이름",
"install.mailer_password": "SMTP 비밀번호",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "가입시 이메일 확인 필수",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "이메일 알림 켜기",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "서버 및 기타 서비스 설정",
"install.disable_registration": "사용자 등록 비활성화",
"install.disable_registration_popup": "사용자가 직접 등록할 수 없게 합니다. 운영자만이 추가할 수 있습니다.",
@@ -294,6 +320,8 @@
"install.openid_signin_popup": "OpenID 를 이용한 로그인 가능여부",
"install.openid_signup": "OpenID 가입 가능여부",
"install.openid_signup_popup": "OpenID를 통한 가입 가능여부",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "가입 CAPTCHA 활성화",
"install.enable_captcha_popup": "사용자 등록시 캡차 요구",
"install.require_sign_in_view": "페이지를 보기 위해 로그인 하기",
@@ -304,6 +332,13 @@
"install.admin_password": "비밀번호",
"install.confirm_password": "비밀번호 확인",
"install.admin_email": "이메일 주소",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Gitea 설치하기",
"install.test_git_failed": "'git' 명령 테스트 실패: %v",
"install.sqlite3_not_available": "해당 버전에서는 SQLite3를 지원하지 않습니다. %s에서 공식 버전을 다운로드해주세요. ('gobuild' 버전이 아닙니다.)",
@@ -311,7 +346,6 @@
"install.invalid_db_table": "데이터베이스 테이블 '%s' 이 유효하지 않습니다: %v",
"install.invalid_repo_path": "리포지토리의 경로가 올바르지 않습니다: %v",
"install.invalid_app_data_path": "앱 데이터 경로가 올바르지 않습니다.: %v",
"install.run_user_not_match": "실행 사용자명이 현재 사용자명과 다릅니다.: %s -> %s",
"install.internal_token_failed": "내부 토큰의 생성에 실패했습니다: %v",
"install.secret_key_failed": "비밀 키 생성에 실패했습니다: %v",
"install.save_config_failed": "설정을 저장할 수 없습니다: %v",
@@ -384,6 +418,9 @@
"auth.sign_up_now": "지금 가입하세요.",
"auth.sign_up_successful": "계정이 성공적으로 생성되었습니다. 환영합니다!",
"auth.confirmation_mail_sent_prompt_ex": "새로운 확인 이메일을 <b>%s</b>에 전송하였습니다. %s 이내에 이메일 받은 편지함을 확인 후, 등록절차를 완료하여 주시길 바랍니다. 등록한 이메일 주소가 잘못된 경우, 다시 로그인하면 변경할 수 있습니다.",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.must_change_password": "비밀번호를 변경하세요.",
"auth.allow_password_change": "사용자에게 비밀번호 변경을 요청 (권장됨)",
"auth.reset_password_mail_sent_prompt": "확인 메일이 <b>%s</b>로 전송되었습니다. 받은 편지함으로 도착한 메일을 %s 안에 확인해서 비밀번호 찾기 절차를 완료하십시오.",
@@ -2996,6 +3033,7 @@
"admin.users.last_login": "마지막 로그인",
"admin.users.never_login": "로그인 한 적 없음",
"admin.users.send_register_notify": "사용자 등록 알림 전송",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.new_success": "사용자 계정 \"%s\"이 생성되었습니다.",
"admin.users.edit": "수정하기",
"admin.users.auth_source": "인증 소스",
@@ -3807,5 +3845,15 @@
"actions.general.cross_repo_desc": "선택된 저장소가 이 소유자의 모든 저장소에서 액션 작업을 실행할 때 GITEA_TOKEN을 사용하여 (읽기 전용으로) 액세스할 수 있도록 허용합니다.",
"actions.general.cross_repo_selected": "선택된 리포지토리",
"actions.general.cross_repo_target_repos": "대상 리포지토리",
"actions.general.cross_repo_add": "대상 리포지토리 추가"
"actions.general.cross_repo_add": "대상 리포지토리 추가",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+62 -8
View File
@@ -162,6 +162,7 @@
"startpage.lightweight_desc": "Gitea ir miminālas prasības un to var darbināt uz nedārga Raspberry Pi datora. Ietaupi savai ierīcei resursus!",
"startpage.license": "Atvērtā pirmkoda",
"install.install": "Instalācija",
"install.installing_desc": "Installing now, please wait…",
"install.title": "Sākotnējā konfigurācija",
"install.docker_helper": "Ja Gitea ir uzstādīts Docker konteinerī, izlasiet <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">vadlīninas</a> pirms maināt iestatījumus.",
"install.require_db_desc": "Gitea nepieciešams MySQL, PostgreSQL, MSSQL, SQLite3 vai TiDB (izmantojot MySQL protokolu).",
@@ -173,17 +174,26 @@
"install.db_name": "Datu bāzes nosaukums",
"install.db_schema": "Shēma",
"install.db_schema_helper": "Atstājiet tukšu, lai izmantu datubāzes noklusēto (\"public\").",
"install.ssl_mode": "SSL",
"install.path": "Ceļš",
"install.sqlite_helper": "Faila ceļš SQLite3 datubāzei.<br>Ievadiet absolūto ceļu, ja Gitea tiek startēts kā serviss.",
"install.reinstall_error": "Nevar instalēt datubāzē, kura jau satur Gitea datus",
"install.reinstall_confirm_message": "Veicot Gitea datubāzēs atkārtotu instalēšanu, tas var izraisīt vairākas problēmas. Būtu jāizmanto esošais \"app.ini\", lai palaistu Gitea. Apstipriniet, ja patiešām vēlaties to darīt:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "Apstiprinat, ka esat pārliecināts, ka Gitea izmanto pareizu app.ini faila atrašanās vietu un patiešām vēlaties veikt atkārtotu instalāciju, tāpat apstiprinat, ka tas var radīt augstāk minētās problēmas.",
"install.err_empty_db_path": "Nav norādīts SQLite3 datu bāzes ceļš.",
"install.no_admin_and_disable_registration": "Reģistrāciju nevar atslēgt, kamēr nav izveidots administratora konts.",
"install.err_empty_admin_password": "Administratora kontam ir obligāti jānorāda parole.",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "Vispārīgie iestatījumi",
"install.app_name": "Vietnes nosaukums",
"install.app_name_helper": "Šeit var ievadīt savas kompānijas nosaukumu.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Repozitoriju glabāšanas ceļš",
"install.repo_path_helper": "Git repozitoriji tiks glabāti šajā direktorijā.",
"install.lfs_path": "Git LFS glabāšanas vieta",
@@ -195,6 +205,7 @@
"install.ssh_port": "SSH servera ports",
"install.ssh_port_helper": "Porta numurs, kuru SSH serveris klausīsies. Atstājiet tukšu, lai atspējotu.",
"install.http_port": "Gitea HTTP klausīšanās ports",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "Gitea pamata URL",
"install.app_url_helper": "Pamata adrese HTTP(S) klonēšanas URL un e-pastu paziņojumiem.",
"install.log_root_path": "Žurnalizēšanas ceļš",
@@ -204,18 +215,37 @@
"install.smtp_addr": "SMTP resursdators",
"install.smtp_port": "SMTP ports",
"install.smtp_from": "Nosūtīt e-pastu kā",
"install.smtp_from_invalid": "The \"Send Email As\" address is invalid",
"install.smtp_from_helper": "E-pasta adrese, ko Gitea izmantos. Ievadiet tika e-pasta adrese vai izmantojiet \"Vārds\" <epasts@domens.lv> formātu.",
"install.mailer_user": "SMTP lietotājvārds",
"install.mailer_password": "SMTP parole",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Reģistrējoties pieprasīt apstiprināt e-pastu",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Iespējot e-pasta paziņojumus",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Servera un citu servisu iestatījumi",
"install.offline_mode": "Iespējot bezsaistes režīmu",
"install.offline_mode_popup": "Atspējot ārējos satura piegādes tīklus, lai visi resursi tiktu piegādāti lokāli.",
"install.disable_gravatar": "Atspējot Gravatar",
"install.disable_gravatar_popup": "Atspējot Gravatar un citus avotus, visus avatarus augšupielādēs lietotāji vai izmantos noklusēto attēlu.",
"install.federated_avatar_lookup": "Iespējot apvienotās profila bildes",
"install.federated_avatar_lookup_popup": "Iespējot apvienoto profila bilžu meklētāju, lai izmantotu atvērtā koda apvienoto servisu balstītu uz Libravatar.",
"install.disable_registration": "Atspējot lietotāju reģistrāciju",
"install.disable_registration_popup": "Atspējot iespēju reģistrēties. Tikai administratori varēs izveidot jaunus kontus.",
"install.allow_only_external_registration_popup": "Atļaut reģistrēties tikai ar ārējiem servisiem",
@@ -223,6 +253,8 @@
"install.openid_signin_popup": "Iespējot lietotāju pieteikšanos ar OpenID.",
"install.openid_signup": "Iespējot reģistrāciju, izmantojot OpenID",
"install.openid_signup_popup": "Iespējot lietotāju reģistrāciju pirms tam autorizējoties ar OpenID.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Pieprasīt drošības kodu lietotāju reģistrācijā",
"install.enable_captcha_popup": "Lietotājam reģistrējoties, pieprasīt ievadīt drošības kodu.",
"install.require_sign_in_view": "Pieprasīt pieteikšanos, lai aplūkotu lapas",
@@ -233,6 +265,13 @@
"install.admin_password": "Parole",
"install.confirm_password": "Apstipriniet paroli",
"install.admin_email": "E-pasta adrese",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Instalēt Gitea",
"install.test_git_failed": "Kļūda pārbaudot 'git' komandu: %v",
"install.sqlite3_not_available": "Jūsu pašreizējā versija neatbalsta SQLite3, lūdzu lejupielādējiet oficiālo bināro versiju no %s, NEVIS gobuild versiju.",
@@ -240,7 +279,6 @@
"install.invalid_db_table": "Datubāzes tabula \"%s\" ir kļūdaina: %v",
"install.invalid_repo_path": "Nederīga repozitorija glabāšanas vieta: %v",
"install.invalid_app_data_path": "Lietojumprogrammas datu ceļš ir kļūdains: %v",
"install.run_user_not_match": "Izpildes lietotājs nav pašreizējais lietotājs: %s -> %s",
"install.internal_token_failed": "Neizdevās uzģenerēt iekšējās saziņas pilnvaru: %v",
"install.secret_key_failed": "Neizdevās uzģenerēt drošības atslēgu: %v",
"install.save_config_failed": "Neizdevās saglabāt konfigurāciju: %v",
@@ -256,10 +294,12 @@
"install.no_reply_address_helper": "Domēns lietotāja e-pasta adresei git žurnālos, ja lietotājs izvēlas paturēt savu e-pasta adresi privātu. Piemēram, ja lietotājs ir 'janis' un domēns 'neatbildet.piemers.lv', tad e-pasta adrese būs 'janis@neatbildet.piemers.lv'.",
"install.password_algorithm": "Paroles jaucējsummas algoritms",
"install.invalid_password_algorithm": "Kļūdaina paroles jaucējfunkcija",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "Iespējot jaunu versiju paziņojumus",
"install.enable_update_checker_helper": "Periodiski pārbaudīt jaunu version pieejamību, izgūstot datus no gitea.io.",
"install.env_config_keys": "Vides konfigurācija",
"install.env_config_keys_prompt": "Šie vides mainīgie tiks pielietoti arī konfigurācijas failā:",
"install.config_write_file_prompt": "These configuration options will be written into: %s",
"home.uname_holder": "Lietotājvārds vai e-pasts",
"home.password_holder": "Parole",
"home.switch_dashboard_context": "Mainīt infopaneļa kontekstu",
@@ -299,6 +339,9 @@
"auth.forgot_password": "Aizmirsi paroli?",
"auth.sign_up_successful": "Konts tika veiksmīgi izveidots. Laipni lūdzam!",
"auth.must_change_password": "Mainīt paroli",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.allow_password_change": "Pieprasīt lietotājam mainīt paroli (ieteicams)",
"auth.reset_password_mail_sent_prompt": "Apstiprināšanas e-pasts tika nosūtīts uz <b>%s</b>. Pārbaudiet savu e-pasta kontu tuvāko %s laikā, lai pabeigtu paroles atjaunošanas procesu.",
"auth.active_your_account": "Aktivizēt savu kontu",
@@ -2393,6 +2436,7 @@
"admin.users.created": "Izveidots",
"admin.users.last_login": "Pēdējā pieteikšanās",
"admin.users.send_register_notify": "Nosūtīt lietotājam reģistrācijas paziņojumu",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.new_success": "Lietotāja konts \"%s\" tika izveidots.",
"admin.users.edit": "Labot",
"admin.users.auth_source": "Autentificēšanas avots",
@@ -3042,5 +3086,15 @@
"git.filemode.normal_file": "Parasts fails",
"git.filemode.executable_file": "Izpildāmais fails",
"git.filemode.symbolic_link": "Simboliska saite",
"git.filemode.submodule": "Apakšmodulis"
"git.filemode.submodule": "Apakšmodulis",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+72 -8
View File
@@ -101,6 +101,7 @@
"startpage.lightweight": "Lichtgewicht",
"startpage.lightweight_desc": "Gitea heeft hele lage systeemeisen, je kunt Gitea al draaien op een goedkope Raspberry Pi.",
"install.install": "Installatie",
"install.installing_desc": "Installing now, please wait…",
"install.title": "Initiële configuratie",
"install.docker_helper": "Als je gitea draait in Docker, Lees eerst de <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">documentatie</a> voordat je een instelling aanpast.",
"install.require_db_desc": "Gitea vereist MySQL, PostgreSQL, MSSQL, SQLite3 of TiDB (MySQL protocol).",
@@ -110,48 +111,80 @@
"install.user": "Gebruikersnaam",
"install.password": "Wachtwoord",
"install.db_name": "Database naam",
"install.db_schema": "Schema",
"install.db_schema_helper": "Laat leeg voor de standaard database (\"openbaar\").",
"install.ssl_mode": "SSL",
"install.path": "Pad",
"install.sqlite_helper": "Bestandspad voor de SQLite3-database.<br>Vul een volledig pad in als je GItea als een service uitvoert.",
"install.reinstall_error": "U probeert te installeren in een bestaande Gitea database",
"install.reinstall_confirm_message": "Herinstalleren met een bestaande Gitea-database kan meerdere problemen veroorzaken. In de meeste gevallen kun je het bestaande \"app.ini\" gebruiken om Gitea te laten draaien. Als je weet wat je aan het doen bent, bevestig dan het volgende:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "Je bevestigt dat je er absoluut zeker van bent dat deze Gitea draait met de juiste app. Geen locatie en dat je zeker weet dat je opnieuw moet installeren. Je bevestigt dat je de hierbovenstaande risico's erkent.",
"install.err_empty_db_path": "SQLite3 database pad mag niet leeg zijn.",
"install.no_admin_and_disable_registration": "U kunt zelf-registratie van de gebruiker niet uitschakelen zonder het maken van een administrator-account.",
"install.err_empty_admin_password": "Het administrator-wachtwoord mag niet leeg zijn.",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "Algemene Instellingen",
"install.app_name": "Naam site",
"install.app_name_helper": "U kan de naam van uw bedrijf hier invullen.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Repositories basis map",
"install.repo_path_helper": "Externe git repositories worden opgeslagen in deze map.",
"install.lfs_path": "Git LFS root pad",
"install.lfs_path_helper": "Bestanden bijgehouden door Git LFS zullenworden opgeslagen in deze map. Laat leeg om uit te schakelen.",
"install.run_user": "Uitvoeren als gebruiker",
"install.run_user_helper": "The operating system username that Gitea runs as, it must have write access to the data paths. This value is auto-detected and cannot be changed here. To use a different user, restart Gitea under that account.",
"install.domain": "Server Domein",
"install.domain_helper": "Domein of hostadres voor de server.",
"install.ssh_port": "SSH server-poort",
"install.ssh_port_helper": "Nummer van de poort die uw SSH-server gebruikt. Laat dit veld leeg om de SSH functie uit te schakelen.",
"install.http_port": "Gitea HTTP-poort",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "Gitea base URL",
"install.app_url_helper": "Basisadres voor HTTP(S) kloon URL's en e-mailmeldingen.",
"install.log_root_path": "Log-pad",
"install.log_root_path_helper": "Logboekbestanden worden geschreven naar deze map.",
"install.optional_title": "Optionele instellingen",
"install.email_title": "E-mail instellingen",
"install.smtp_addr": "SMTP Host",
"install.smtp_port": "SMTP Poort",
"install.smtp_from": "E-mails versturen als",
"install.smtp_from_invalid": "The \"Send Email As\" address is invalid",
"install.smtp_from_helper": "E-mailadres dat Gitea gaat gebruiken. Voer een gewoon e-mailadres in of gebruik de \"Naam\" <email@example.com> -indeling.",
"install.mailer_user": "SMTP gebruikersnaam",
"install.mailer_password": "SMTP wachtwoord",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "E-mailbevestiging vereist bij registreren",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Activeer e-mailnotificaties",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Server en Third-Party Service-instellingen",
"install.offline_mode": "Lokale modus inschakelen",
"install.offline_mode_popup": "Schakel third-party content uit en gebruik alleen lokale middelen.",
"install.disable_gravatar": "Gravatar uitschakelen",
"install.disable_gravatar_popup": "Gravatar en derden avatar bronnen uitschakelen. Een standaard avatar zal worden gebruikt, tenzij een gebruiker een lokale avatar uploadt.",
"install.federated_avatar_lookup": "Federated Avatars toestaan",
"install.federated_avatar_lookup_popup": "Enable federated avatars lookup to use federated open source service based on libravatar.",
"install.disable_registration": "Schakel zelf registratie uit",
"install.disable_registration_popup": "Schakel zelfregistratie uit, alleen admins kunnen accounts maken.",
"install.allow_only_external_registration_popup": "Registratie alleen via externe diensten toestaan",
@@ -159,22 +192,32 @@
"install.openid_signin_popup": "Gebruikerslogin via OpenID inschakelen.",
"install.openid_signup": "OpenID zelf-registratie inschakelen",
"install.openid_signup_popup": "OpenID zelfregistratie inschakelen.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Registratie CAPTCHA inschakelen",
"install.enable_captcha_popup": "Vereis captcha validatie voor zelf-registratie van gebruiker.",
"install.require_sign_in_view": "Vereis inloggen om pagina's te kunnen bekijken",
"install.require_sign_in_view_popup": "Limit page access to signed-in users. Visitors will only see the sign-in and registration pages.",
"install.admin_setting_desc": "Het creëren van een administrator-account is optioneel. De eerste geregistreerde gebruiker wordt automatisch de beheerder.",
"install.admin_title": "Instellingen beheerdersaccount",
"install.admin_name": "Admin gebruikersnaam",
"install.admin_password": "Wachtwoord",
"install.confirm_password": "Verifieer wachtwoord",
"install.admin_email": "E-mailadres",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Installeer Gitea",
"install.test_git_failed": "Git test niet gelukt: 'git' commando %v",
"install.sqlite3_not_available": "Deze Gitea-versie biedt geen ondersteuning voor SQLite3. Download de officiële build van %s (niet de versie van de 'gobuild').",
"install.invalid_db_setting": "De database instelling zijn niet correct: %v",
"install.invalid_db_table": "The database table \"%s\" is invalid: %v",
"install.invalid_repo_path": "Het pad van de hoofdmap van de repository is ongeldig: %v",
"install.invalid_app_data_path": "Ongeldig app-gegevenspad: %v",
"install.run_user_not_match": "De 'uitvoeren als' gebruikersnaam is niet de huidige gebruikersnaam: %s -> %s",
"install.internal_token_failed": "Interne token genereren mislukt: %v",
"install.secret_key_failed": "Geheime sleutel genereren mislukt: %v",
"install.save_config_failed": "Kan de configuratie niet opslaan: %v",
@@ -189,6 +232,13 @@
"install.no_reply_address": "Verborgen e-maildomein",
"install.no_reply_address_helper": "Domeinnaam voor gebruikers met een verborgen e-mailadres. Bijvoorbeeld zal de gebruikersnaam 'joe' in Git worden geregistreerd als 'joe@noreply.example.org' als het verborgen email domein is ingesteld op 'noreply.example.org'.",
"install.password_algorithm": "Wachtwoord Hash Algoritme",
"install.invalid_password_algorithm": "Invalid password hash algorithm",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "Enable Update Checker",
"install.enable_update_checker_helper": "Checks for new version releases periodically by connecting to gitea.io.",
"install.env_config_keys": "Environment Configuration",
"install.env_config_keys_prompt": "The following environment variables will also be applied to your configuration file:",
"install.config_write_file_prompt": "These configuration options will be written into: %s",
"home.uname_holder": "Gebruikersnaam of e-mailadres",
"home.password_holder": "Wachtwoord",
"home.switch_dashboard_context": "Wissel voorpaginacontext",
@@ -220,6 +270,9 @@
"auth.forgot_password_title": "Wachtwoord vergeten",
"auth.forgot_password": "Wachtwoord vergeten?",
"auth.must_change_password": "Uw wachtwoord wijzigen",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.allow_password_change": "Verplicht de gebruiker om zijn/haar wachtwoord te wijzigen (aanbevolen)",
"auth.reset_password_mail_sent_prompt": "Een bevestigingsmail is verstuurd naar <b>%s</b>. Controleer uw inbox in de volgende %s om het herstel van uw account te voltooien.",
"auth.active_your_account": "Activeer uw account",
@@ -1780,6 +1833,7 @@
"admin.users.created": "Aangemaakt",
"admin.users.last_login": "Laatste keer ingelogd",
"admin.users.send_register_notify": "Stuur gebruikersregistratie notificatie",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.edit": "Bewerken",
"admin.users.auth_source": "Authenticatiebron",
"admin.users.local": "Lokaal",
@@ -2093,5 +2147,15 @@
"actions.runners.task_list.run": "Uitvoeren",
"actions.runners.task_list.repository": "Opslagplaats",
"actions.runners.status.active": "Actief",
"actions.runners.version": "Versie"
"actions.runners.version": "Versie",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+70 -8
View File
@@ -106,6 +106,7 @@
"startpage.lightweight_desc": "Gitea ma niskie minimalne wymagania i może działać na niedrogim Raspberry Pi. Oszczędzaj energię swojego komputera!",
"startpage.license": "Otwarte źródło",
"install.install": "Instalacja",
"install.installing_desc": "Installing now, please wait…",
"install.title": "Wstępna konfiguracja",
"install.docker_helper": "Jeśli używasz Gitea za pomocą Docker'a, przeczytaj <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">dokumentację</a> przed wprowadzeniem jakichkolwiek zmian.",
"install.require_db_desc": "Gitea wymaga MySQL, PostgreSQL, MSSQL, SQLite3 lub TiDB (protokół MySQL).",
@@ -117,27 +118,38 @@
"install.db_name": "Nazwa bazy danych",
"install.db_schema": "Schemat",
"install.db_schema_helper": "Pozostaw puste dla domyślnego schematu bazy danych (\"public\").",
"install.ssl_mode": "SSL",
"install.path": "Ścieżka",
"install.sqlite_helper": "Ścieżka pliku dla bazy danych SQLite3.<br>Wpisz ścieżkę bezwzględną, jeśli Gitea jest uruchomiona jako usługa.",
"install.reinstall_error": "Próbujesz zainstalować w istniejącej już bazie danych Gitea",
"install.reinstall_confirm_message": "Ponowna instalacja z istniejącą bazą danych Gitea może powodować wiele problemów. W większości przypadków powinieneś użyć swojego istniejącego \"app.ini\" do uruchomienia Gitea. Jeśli wiesz, co robisz, potwierdź następujące działania:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "Potwierdzasz, że jesteś całkowicie pewien, że ta Gitea działa z app.ini w poprawnej lokalizacji i że jesteś pewien, że musisz ponownie zainstalować. Potwierdzasz powyższe ryzyko.",
"install.err_empty_db_path": "Ścieżka do bazy danych SQLite3 nie może być pusta.",
"install.no_admin_and_disable_registration": "Nie możesz wyłączyć możliwości samodzielnej rejestracji kont użytkowników bez stworzenia konta administratora.",
"install.err_empty_admin_password": "Hasło administratora nie może być puste.",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "Ustawienia ogólne",
"install.app_name": "Tytuł witryny",
"install.app_name_helper": "Wprowadź nazwę firmy.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Katalog repozytoriów",
"install.repo_path_helper": "Zdalne repozytoria Git zostaną zapisane w tym katalogu.",
"install.lfs_path": "Ścieżka główna Git LFS",
"install.lfs_path_helper": "W tym katalogu będą przechowywane pliki śledzone za pomocą Git LFS. Pozostaw puste, aby wyłączyć LFS.",
"install.run_user": "Uruchom jako nazwa użytkownika",
"install.run_user_helper": "The operating system username that Gitea runs as, it must have write access to the data paths. This value is auto-detected and cannot be changed here. To use a different user, restart Gitea under that account.",
"install.domain": "Domena serwera",
"install.domain_helper": "Adres domeny lub hosta serwera.",
"install.ssh_port": "Port serwera SSH",
"install.ssh_port_helper": "Numer portu, na którym nasłuchuje Twój serwer SSH. Pozostaw puste, aby wyłączyć.",
"install.http_port": "Port nasłuchiwania HTTP Gitea",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "Podstawowy adres URL Gitea",
"install.app_url_helper": "Podstawowy adres dla klonowania adresów URL HTTP(S) oraz powiadomień e-mail.",
"install.log_root_path": "Ścieżka dla logów",
@@ -147,18 +159,37 @@
"install.smtp_addr": "Serwer SMTP",
"install.smtp_port": "Port SMTP",
"install.smtp_from": "Wyślij e-mail jako",
"install.smtp_from_invalid": "The \"Send Email As\" address is invalid",
"install.smtp_from_helper": "Adres e-mail, z którego Gitea będzie korzystać. Wpisz prosty adres e-mail, lub użyj formatu \"Nazwa\" <email@example.com>.",
"install.mailer_user": "Nazwa użytkownika SMTP",
"install.mailer_password": "Hasło SMTP",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Wymagają potwierdzenia e-mail przy rejestracji",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Włącz powiadomienia e-mail",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Ustawienia serwera i innych usług",
"install.offline_mode": "Włącz tryb lokalny",
"install.offline_mode_popup": "Wyłącz zewnętrzne usługi dostarczania i dostarczaj wszystkie zasoby lokalnie.",
"install.disable_gravatar": "Wyłącz Gravatar",
"install.disable_gravatar_popup": "Wyłącz Gravatar i inne usługi zewnętrzne awatarów. Zostanie zastosowany domyślny awatar, chyba że użytkownik prześle swój własny.",
"install.federated_avatar_lookup": "Włącz zewnętrzne awatary",
"install.federated_avatar_lookup_popup": "Enable federated avatars lookup to use federated open source service based on libravatar.",
"install.disable_registration": "Wyłącz rejestrację dwuskładnikową",
"install.disable_registration_popup": "Wyłącz samodzielną rejestrację użytkowników. Tylko administratorzy będą w stanie tworzyć nowe konta.",
"install.allow_only_external_registration_popup": "Włącz rejestrację wyłącznie za pomocą zewnętrznych usług",
@@ -166,22 +197,32 @@
"install.openid_signin_popup": "Włącz logowanie użytkowników za pomocą OpenID.",
"install.openid_signup": "Włącz samodzielną rejestrację za pomocą OpenID",
"install.openid_signup_popup": "Włącz samodzielną rejestrację opartą o OpenID.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Włącz CAPTCHA przy rejestracji",
"install.enable_captcha_popup": "Wymagaj walidacji CAPTCHA przy samodzielnej rejestracji użytkownika.",
"install.require_sign_in_view": "Wymagaj zalogowania w celu przeglądania stron",
"install.require_sign_in_view_popup": "Limit page access to signed-in users. Visitors will only see the sign-in and registration pages.",
"install.admin_setting_desc": "Tworzenie konta administratora jest opcjonalne. Pierwszy zarejestrowany użytkownik automatycznie zostanie administratorem.",
"install.admin_title": "Ustawienia konta administratora",
"install.admin_name": "Nazwa użytkownika administratora",
"install.admin_password": "Hasło",
"install.confirm_password": "Potwierdź hasło",
"install.admin_email": "Adres e-mail",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Zainstaluj Gitea",
"install.test_git_failed": "Nie udało się przetestować polecenia „git”: %v",
"install.sqlite3_not_available": "Twoje wydanie Gitea nie obsługuje SQLite3. Pobierz oficjalne wydanie z %s (NIE wersję \"gobuild\").",
"install.invalid_db_setting": "Nieprawidłowe ustawienia bazy danych: %v",
"install.invalid_db_table": "The database table \"%s\" is invalid: %v",
"install.invalid_repo_path": "Ścieżka repozytorium nie jest poprawna: %v",
"install.invalid_app_data_path": "Ścieżka danych aplikacji jest nieprawidłowa: %v",
"install.run_user_not_match": "Użytkownik \"uruchom jako\" nie jest obecnym użytkownikiem: %s -> %s",
"install.internal_token_failed": "Nie udało się wygenerować tokenu wewnętrznego: %v",
"install.secret_key_failed": "Nie udało się wygenerować tajnego klucza: %v",
"install.save_config_failed": "Nie udało się zapisać konfiguracji: %v",
@@ -196,6 +237,13 @@
"install.no_reply_address": "Ukryta domena e-mail",
"install.no_reply_address_helper": "Nazwa domeny dla użytkowników z ukrytym adresem e-mail. Przykładowo, użytkownik \"jan\" będzie zalogowany na Git'cie jako \"jan@noreply.example.org\", jeśli domena ukrytego adresu e-mail jest ustawiona na \"noreply.example.org\".",
"install.password_algorithm": "Algorytm hashowania haseł",
"install.invalid_password_algorithm": "Invalid password hash algorithm",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "Enable Update Checker",
"install.enable_update_checker_helper": "Checks for new version releases periodically by connecting to gitea.io.",
"install.env_config_keys": "Environment Configuration",
"install.env_config_keys_prompt": "The following environment variables will also be applied to your configuration file:",
"install.config_write_file_prompt": "These configuration options will be written into: %s",
"home.uname_holder": "Nazwa użytkownika lub adres email",
"home.password_holder": "Hasło",
"home.switch_dashboard_context": "Przełącz kontekst pulpitu",
@@ -229,6 +277,9 @@
"auth.forgot_password_title": "Zapomniałem hasła",
"auth.forgot_password": "Zapomniałeś hasła?",
"auth.must_change_password": "Zaktualizuj swoje hasło",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.allow_password_change": "Użytkownik musi zmienić hasło (zalecane)",
"auth.reset_password_mail_sent_prompt": "E-mail potwierdzający został wysłany na adres <b>%s</b>. Sprawdź swoją skrzynkę odbiorczą w przeciągu %s, aby ukończyć proces odzyskiwania konta.",
"auth.active_your_account": "Aktywuj swoje konto",
@@ -1766,6 +1817,7 @@
"admin.users.created": "Utworzony",
"admin.users.last_login": "Ostatnie logowanie",
"admin.users.send_register_notify": "Wyślij użytkownikowi powiadomienie o rejestracji",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.edit": "Edytuj",
"admin.users.auth_source": "Źródło uwierzytelniania",
"admin.users.local": "Lokalny",
@@ -2110,5 +2162,15 @@
"actions.runners.task_list.repository": "Repozytorium",
"actions.runners.status.active": "Aktywne",
"actions.runners.version": "Wersja",
"git.filemode.symbolic_link": "Dowiązanie symboliczne"
"git.filemode.symbolic_link": "Dowiązanie symboliczne",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+52 -8
View File
@@ -200,6 +200,7 @@
"startpage.license": "Código Aberto",
"startpage.license_desc": "Receba <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%[1]s\">%[2]s</a>! Junte-se a nós <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%[3]s\">contribuindo</a> para tornar este projeto ainda melhor. Não seja tímido, seja um colaborador!",
"install.install": "Instalação",
"install.installing_desc": "Installing now, please wait…",
"install.title": "Configuração Inicial",
"install.docker_helper": "Se você está rodando o Gitea dentro do Docker, por favor leia a <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">documentação</a> cuidadosamente antes de alterar qualquer coisa nesta página.",
"install.require_db_desc": "Gitea requer MySQL, PostgreSQL, MSSQL, SQLite3 ou TiDB (protocolo MySQL).",
@@ -211,6 +212,7 @@
"install.db_name": "Nome do Banco de Dados",
"install.db_schema": "Esquema",
"install.db_schema_helper": "Deixe em branco para banco de dados padrão (\"public\").",
"install.ssl_mode": "SSL",
"install.path": "Caminho",
"install.sqlite_helper": "Caminho do arquivo do banco de dados SQLite3.<br>Informe um caminho absoluto se você executar o Gitea como um serviço.",
"install.reinstall_error": "Você está tentando instalar em um banco de dados existente do Gitea",
@@ -228,6 +230,8 @@
"install.general_title": "Configurações Gerais",
"install.app_name": "Nome do Site",
"install.app_name_helper": "Você pode inserir o nome da empresa aqui.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Caminho Raíz do Repositório",
"install.repo_path_helper": "Todos os repositórios remotos do Git serão salvos neste diretório.",
"install.lfs_path": "Caminho raiz do Git LFS",
@@ -253,15 +257,33 @@
"install.smtp_from_helper": "Endereço de e-mail que o Gitea irá usar. Digite um endereço de e-mail simples ou use o formato \"Nome\" <email@example.com>.",
"install.mailer_user": "Nome de usuário do SMTP",
"install.mailer_password": "Senha do SMTP",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Exigir Confirmação de E-mail para se Cadastrar",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Habilitar Notificações de E-mail",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Configurações de Servidor e Serviços de Terceiros",
"install.offline_mode": "Habilitar Autenticação Local",
"install.offline_mode_popup": "Desabilitar redes de entrega de conteúdo de terceiros e entregar todos os recursos localmente.",
"install.disable_gravatar": "Desabilitar o Gravatar",
"install.disable_gravatar_popup": "Desabilitar o gravatar e avatar de fontes de terceiros. Um avatar padrão será usado a menos que um usuário localmente carrega um avatar.",
"install.federated_avatar_lookup": "Habilitar Avatares Federativos",
"install.federated_avatar_lookup_popup": "Habilitar a busca federativa de avatares a usar o serviço federativo de código aberto baseado no libravatar.",
"install.disable_registration": "Desabilitar Auto-Cadastro",
"install.disable_registration_popup": "Desabilitar auto-cadastro de usuário. Somente os administradores serão capazes de criar novas contas de usuário.",
"install.allow_only_external_registration_popup": "Permitir Cadastro Somente por Meio de Serviços Externos",
@@ -269,6 +291,8 @@
"install.openid_signin_popup": "Habilitar o acesso de usuários via OpenID.",
"install.openid_signup": "Habilitar o auto-cadastro via OpenID",
"install.openid_signup_popup": "Habilitar o auto-cadastro com base no OpenID.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Habilitar CAPTCHA ao registrar",
"install.enable_captcha_popup": "Obrigar validação por CAPTCHA para auto-cadastro de usuários.",
"install.require_sign_in_view": "Exigir Acesso para a Visualização de Páginas",
@@ -279,6 +303,13 @@
"install.admin_password": "Senha",
"install.confirm_password": "Confirmar Senha",
"install.admin_email": "Endereço de E-mail",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Instalar Gitea",
"install.test_git_failed": "Falha ao testar o comando 'git': %v",
"install.sqlite3_not_available": "Esta versão do Gitea não suporta SQLite3. Por favor faça o download da versão binária oficial em %s (não utilize a versão 'gobuild').",
@@ -286,7 +317,6 @@
"install.invalid_db_table": "A tabela \"%s\" do banco de dados é inválida: %v",
"install.invalid_repo_path": "A raiz do repositório está inválida: %v",
"install.invalid_app_data_path": "O caminho dos dados do aplicativo é inválido: %v",
"install.run_user_not_match": "O nome de usuário 'Executar como' não é o nome de usuário atual: %s -> %s",
"install.internal_token_failed": "Falha ao gerar o token interno: %v",
"install.secret_key_failed": "Falha ao gerar a chave secreta: %v",
"install.save_config_failed": "Falha ao salvar a configuração: %v",
@@ -357,6 +387,9 @@
"auth.sign_up_now": "Cadastre-se agora.",
"auth.sign_up_successful": "A conta foi criada com sucesso. Bem-vindo!",
"auth.confirmation_mail_sent_prompt_ex": "Um novo e-mail de confirmação foi enviado para <b>%s</b>. Por favor, verifique sua caixa de entrada dentro dos próximos %s para concluir o processo de registro. Se o seu endereço de e-mail de registro estiver incorreto, você pode fazer login novamente e alterá-lo.",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.must_change_password": "Redefina sua senha",
"auth.allow_password_change": "Exigir que o usuário redefina a senha (recomendado)",
"auth.reset_password_mail_sent_prompt": "Um e-mail de confirmação foi enviado para <b>%s</b>. Por favor, verifique sua caixa de entrada dentro do(s) próximo(s) %s para concluir o processo de recuperação de conta.",
@@ -2614,6 +2647,7 @@
"admin.users.last_login": "Último Acesso",
"admin.users.never_login": "Nunca Acessado",
"admin.users.send_register_notify": "Enviar Notificação de Cadastro de Usuário",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.new_success": "Usuário \"%s\" criado.",
"admin.users.edit": "Editar",
"admin.users.auth_source": "Fonte da Autenticação",
@@ -3286,5 +3320,15 @@
"git.filemode.normal_file": "Arquivo normal",
"git.filemode.executable_file": "Arquivo executável",
"git.filemode.symbolic_link": "Link simbólico",
"git.filemode.submodule": "Submódulo"
"git.filemode.submodule": "Submódulo",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+50 -8
View File
@@ -249,6 +249,8 @@
"install.general_title": "Configurações gerais",
"install.app_name": "Título do sítio",
"install.app_name_helper": "Pode escrever aqui o nome da sua companhia.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Localização dos repositórios",
"install.repo_path_helper": "Os repositórios Git remotos serão guardados nesta pasta.",
"install.lfs_path": "Localização do Git LFS",
@@ -274,15 +276,33 @@
"install.smtp_from_helper": "Endereço de email que o Gitea vai usar. Insira um endereço de email simples ou use o formato \"Nome\" <email@exemplo.com>.",
"install.mailer_user": "Nome de utilizador do SMTP",
"install.mailer_password": "Senha do SMTP",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Exigir confirmação de email para se inscrever",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Habilitar notificações por email",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Configurações do servidor e de terceiros",
"install.offline_mode": "Habilitar o modo local",
"install.offline_mode_popup": "Desabilitar redes de entrega de conteúdos de terceiros e servir localmente todos os recursos.",
"install.disable_gravatar": "Desabilitar o Gravatar",
"install.disable_gravatar_popup": "Desabilitar o Gravatar e fontes de avatares de terceiros. Será usado um avatar padrão, a não ser que o utilizador carregue um avatar localmente.",
"install.federated_avatar_lookup": "Habilitar avatares federados",
"install.federated_avatar_lookup_popup": "Habilitar pesquisa de avatares federada usando o Libravatar.",
"install.disable_registration": "Desabilitar a auto-inscrição",
"install.disable_registration_popup": "Desabilitar a auto-inscrição do utilizador. Somente os administradores poderão criar novas contas de utilizador.",
"install.allow_only_external_registration_popup": "Permitir a inscrição somente por meio de serviços externos",
@@ -290,6 +310,8 @@
"install.openid_signin_popup": "Habilitar o início de sessão do utilizador usando o OpenID.",
"install.openid_signup": "Habilitar a auto-inscrição com OpenID",
"install.openid_signup_popup": "Habilitar a utilização do OpenID para fazer auto-inscrições.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Habilitar CAPTCHA na inscrição",
"install.enable_captcha_popup": "Exigir CAPTCHA na auto-inscrição de utilizadores.",
"install.require_sign_in_view": "Exigir sessão iniciada para visualizar páginas",
@@ -300,6 +322,13 @@
"install.admin_password": "Senha",
"install.confirm_password": "Confirme a senha",
"install.admin_email": "Endereço de email",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Instalar Gitea",
"install.test_git_failed": "Não foi possível testar o comando 'git': %v",
"install.sqlite3_not_available": "Esta versão do Gitea não suporta o SQLite3. Descarregue a versão binária oficial em %s (não utilize a versão 'gobuild').",
@@ -307,7 +336,6 @@
"install.invalid_db_table": "A tabela \"%s\" da base de dados é inválida: %v",
"install.invalid_repo_path": "A localização base dos repositórios é inválida: %v",
"install.invalid_app_data_path": "A localização dos dados da aplicação é inválido: %v",
"install.run_user_not_match": "O nome de utilizador para 'executar como' não é o nome de utilizador corrente: %s → %s",
"install.internal_token_failed": "Falha ao gerar o código interno: %v",
"install.secret_key_failed": "Falha ao gerar a chave secreta: %v",
"install.save_config_failed": "Falhou ao guardar a configuração: %v",
@@ -380,6 +408,9 @@
"auth.sign_up_now": "Inscreva-se agora.",
"auth.sign_up_successful": "A conta foi criada com sucesso. Bem-vindo/a!",
"auth.confirmation_mail_sent_prompt_ex": "Foi enviado um email de confirmação para <b>%s</b>. Verifique a sua caixa de entrada dentro de %s para completar o processo de registo. Se o seu endereço de email de registo estiver errado, pode iniciar a sessão novamente e mudá-lo.",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.must_change_password": "Mude a sua senha",
"auth.allow_password_change": "Exigir que o utilizador mude a senha (recomendado)",
"auth.reset_password_mail_sent_prompt": "Foi enviado um email de confirmação para <b>%s</b>. Verifique a sua caixa de entrada dentro de %s para completar o processo de recuperação.",
@@ -2951,6 +2982,7 @@
"admin.users.last_login": "Último acesso",
"admin.users.never_login": "Nunca acedeu",
"admin.users.send_register_notify": "Enviar notificação de registo de utilizador",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.new_success": "A conta de utilizador \"%s\" foi criada.",
"admin.users.edit": "Editar",
"admin.users.auth_source": "Fonte de autenticação",
@@ -3724,5 +3756,15 @@
"git.filemode.normal_file": "Ficheiro normal",
"git.filemode.executable_file": "Ficheiro executável",
"git.filemode.symbolic_link": "Ligação simbólica",
"git.filemode.submodule": "Submódulo"
"git.filemode.submodule": "Submódulo",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
File diff suppressed because it is too large Load Diff
+62 -8
View File
@@ -157,6 +157,7 @@
"startpage.lightweight_desc": "Gitea имеет низкие системные требования и может работать на недорогом Raspberry Pi. Экономьте энергию вашей машины!",
"startpage.license": "Открытый исходный код",
"install.install": "Установка",
"install.installing_desc": "Installing now, please wait…",
"install.title": "Начальная конфигурация",
"install.docker_helper": "Если вы запускаете Gitea внутри Docker, пожалуйста внимательно прочтите <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">документацию</a> перед тем, как изменить любые настройки.",
"install.require_db_desc": "Gitea требует MySQL, PostgreSQL, MSSQL, SQLite3 или TiDB (через протокол MySQL).",
@@ -168,17 +169,26 @@
"install.db_name": "Имя базы данных",
"install.db_schema": "Схема",
"install.db_schema_helper": "Оставьте пустым для значения по умолчанию (\"public\").",
"install.ssl_mode": "SSL",
"install.path": "Путь",
"install.sqlite_helper": "Путь к файлу базы данных SQLite3.<br>Введите абсолютный путь, если вы запускаете Gitea как службу.",
"install.reinstall_error": "Вы пытаетесь произвести установку в уже существующую базу данных Gitea",
"install.reinstall_confirm_message": "Переустановка в уже существующую базу данных Gitea может вызвать несколько проблем. В большинстве случаев вы должны использовать существующий \"app.ini\" для запуска Gitea. Если вы понимаете, что вы делаете, подтвердите:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "Вы подтверждаете, что полностью уверены, что этот Gitea запущен при коренном расположении app.ini и вы уверены, что вам нужна переустановка. Вы подтверждаете, что соглашаетесь с указанными выше рисками.",
"install.err_empty_db_path": "Путь к базе данных SQLite3 не может быть пустым.",
"install.no_admin_and_disable_registration": "Вы не можете отключить регистрацию до создания учётной записи администратора.",
"install.err_empty_admin_password": "Пароль администратора не может быть пустым.",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "Основные настройки",
"install.app_name": "Название сайта",
"install.app_name_helper": "Здесь вы можете ввести название своей компании.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Путь до корня репозитория",
"install.repo_path_helper": "Все удалённые Git репозитории будут сохранены в эту директорию.",
"install.lfs_path": "Путь к корневому каталогу Git LFS",
@@ -190,6 +200,7 @@
"install.ssh_port": "Порт SSH сервера",
"install.ssh_port_helper": "Номер порта, который использует SSH сервер. Оставьте пустым, чтобы отключить SSH.",
"install.http_port": "Gitea HTTP порт",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "Базовый URL Gitea",
"install.app_url_helper": "Этот параметр влияет на URL для клонирования по HTTP/HTTPS и на некоторые уведомления по электронной почте.",
"install.log_root_path": "Путь к журналу",
@@ -199,18 +210,37 @@
"install.smtp_addr": "Узел SMTP",
"install.smtp_port": "SMTP-порт",
"install.smtp_from": "Отправить эл. почту как",
"install.smtp_from_invalid": "The \"Send Email As\" address is invalid",
"install.smtp_from_helper": "Адрес электронной почты, который будет использоваться Gitea. Введите обычный адрес электронной почты или используйте формат \"Имя\" <email@example.com>.",
"install.mailer_user": "SMTP логин",
"install.mailer_password": "SMTP пароль",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Требовать подтверждение по электронной почте для регистрации",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Разрешить почтовые уведомления",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Сервер и настройки внешних служб",
"install.offline_mode": "Включить локальный режим",
"install.offline_mode_popup": "Отключить сторонние сети доставки контента и отдавать все ресурсы из их локальных копий.",
"install.disable_gravatar": "Отключить Gravatar",
"install.disable_gravatar_popup": "Отключить Gravatar и сторонние источники аватаров. Если пользователь не загрузит аватар локально, то по умолчанию будет использоваться стандартный аватар.",
"install.federated_avatar_lookup": "Включить федеративные аватары",
"install.federated_avatar_lookup_popup": "Включите поиск федеративного аватара для использования службы с открытым исходным кодом на основе libravatar.",
"install.disable_registration": "Отключить самостоятельную регистрацию",
"install.disable_registration_popup": "Отключить самостоятельную регистрацию. Только администраторы смогут создавать новые учётные записи пользователей.",
"install.allow_only_external_registration_popup": "Разрешить регистрацию только через сторонние сервисы",
@@ -218,6 +248,8 @@
"install.openid_signin_popup": "Включить вход через OpenID.",
"install.openid_signup": "Включить регистрацию через OpenID",
"install.openid_signup_popup": "Включить саморегистрацию OpenID.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Включить CAPTCHA при регистрации",
"install.enable_captcha_popup": "Запрашивать капчу при регистрации пользователя.",
"install.require_sign_in_view": "Требовать авторизации для просмотра страниц",
@@ -228,6 +260,13 @@
"install.admin_password": "Пароль",
"install.confirm_password": "Подтвердить пароль",
"install.admin_email": "Адрес эл. почты",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Установить Gitea",
"install.test_git_failed": "Не удалось проверить 'git' команду: %v",
"install.sqlite3_not_available": "Эта версия Gitea не поддерживает SQLite3. Пожалуйста, загрузите официальную бинарную версию из %s (не 'go build' версия).",
@@ -235,7 +274,6 @@
"install.invalid_db_table": "Таблица «%s» базы данных некорректна: %v",
"install.invalid_repo_path": "Недопустимый путь к корню репозитория: %v",
"install.invalid_app_data_path": "Неверный путь к приложению: %v",
"install.run_user_not_match": "Текущий пользователь не является пользователем для запуска: %s -> %s",
"install.internal_token_failed": "Не удалось создать внутренний токен: %v",
"install.secret_key_failed": "Не удалось создать секретный ключ: %v",
"install.save_config_failed": "Не удалось сохранить конфигурацию: %v",
@@ -251,10 +289,12 @@
"install.no_reply_address_helper": "Доменное имя для пользователей со скрытым адресом электронной почты. Например, имя пользователя 'joe' будет зарегистрировано в Git как 'joe@noreply.example.org' если скрытый домен электронной почты установлен как 'noreply.example.org'.",
"install.password_algorithm": "Алгоритм хеширования пароля",
"install.invalid_password_algorithm": "Некорректный алгоритм хеширования пароля",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "Включить проверку обновлений",
"install.enable_update_checker_helper": "Периодически проверяет наличие новых версий, подключаясь к gitea.io.",
"install.env_config_keys": "Настройка окружения",
"install.env_config_keys_prompt": "Следующие переменные окружения также будут применены к вашему конфигурационному файлу:",
"install.config_write_file_prompt": "These configuration options will be written into: %s",
"home.uname_holder": "Имя пользователя / Адрес эл. почты",
"home.password_holder": "Пароль",
"home.switch_dashboard_context": "Переключить контекст панели управления",
@@ -294,6 +334,9 @@
"auth.forgot_password": "Забыли пароль?",
"auth.sign_up_successful": "Учётная запись успешно создана. Добро пожаловать!",
"auth.must_change_password": "Обновить пароль",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.allow_password_change": "Требовать смену пароля пользователем (рекомендуется)",
"auth.reset_password_mail_sent_prompt": "Письмо с подтверждением отправлено на <b>%s</b>. Пожалуйста, проверьте входящую почту в течение %s, чтобы завершить процесс восстановления аккаунта.",
"auth.active_your_account": "Активируйте свой аккаунт",
@@ -2345,6 +2388,7 @@
"admin.users.created": "Создано",
"admin.users.last_login": "Последний вход",
"admin.users.send_register_notify": "Отправить пользователю уведомление о регистрации",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.new_success": "Учётная запись «%s» создана.",
"admin.users.edit": "Редактировать",
"admin.users.auth_source": "Источник аутентификации",
@@ -2982,5 +3026,15 @@
"git.filemode.normal_file": "Обычный файл",
"git.filemode.executable_file": "Исполняемый файл",
"git.filemode.symbolic_link": "Символическая ссылка",
"git.filemode.submodule": "Подмодуль"
"git.filemode.submodule": "Подмодуль",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+77 -8
View File
@@ -94,8 +94,10 @@
"startpage.lightweight_desc": "Gitea අඩු අවම අවශ්යතා ඇති අතර මිල අඩු Raspberry Pi මත ධාවනය කළ හැකිය. ඔබේ යන්ත්ර ශක්තිය සුරකින්න!",
"startpage.license": "විවෘත මූලාශ්‍ර",
"install.install": "ස්ථාපනය",
"install.installing_desc": "Installing now, please wait…",
"install.title": "මූලික වින්යාසය",
"install.docker_helper": "ඔබ Docker තුළ Gitea ධාවනය කරන්නේ නම්, කරුණාකර ඕනෑම සැකසුම් වෙනස් කිරීමට පෙර <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">ලියකියවිලි</a> කියවන්න.",
"install.require_db_desc": "Gitea requires MySQL, PostgreSQL, MSSQL, SQLite3 or TiDB (MySQL protocol).",
"install.db_title": "දත්ත සමුදායේ සැකසුම්",
"install.db_type": "දත්ත සමුදායේ වර්ගය",
"install.host": "සත්කාරක",
@@ -104,24 +106,38 @@
"install.db_name": "දත්ත සමුදායේ නම",
"install.db_schema": "යෝජනා ක්රමය",
"install.db_schema_helper": "දත්ත සමුදා පෙරනිමි සඳහා හිස්ව තබන්න (“පොදු”).",
"install.ssl_mode": "SSL",
"install.path": "මාර්ගය",
"install.sqlite_helper": "SQLite3 දත්ත සමුදාය සඳහා ගොනු මාර්ගය.<br>ඔබ සේවාවක් ලෙස Gitea ධාවනය කරන්නේ නම් නිරපේක්ෂ මාර්ගයක් ඇතුල් කරන්න.",
"install.reinstall_error": "You are trying to install into an existing Gitea database",
"install.reinstall_confirm_message": "Re-installing with an existing Gitea database can cause multiple problems. In most cases, you should use your existing \"app.ini\" to run Gitea. If you know what you are doing, confirm the following:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "You confirm that you are absolutely sure that this Gitea is running with the correct app.ini location and that you are sure that you have to re-install. You confirm that you acknowledge the above risks.",
"install.err_empty_db_path": "SQLite3 දත්ත සමුදා මාර්ගය හිස් විය නොහැක.",
"install.no_admin_and_disable_registration": "පරිපාලක ගිණුමක් නිර්මාණය නොකර පරිශීලක ස්වයං ලියාපදිංචිය අක්රිය කළ නොහැක.",
"install.err_empty_admin_password": "පරිපාලක මුරපදය හිස් විය නොහැක.",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "පොදු සැකසුම්",
"install.app_name": "අඩවියේ සිරැසිය",
"install.app_name_helper": "ඔබට ඔබේ සමාගමේ නම මෙහි ඇතුළත් කළ හැකිය.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "ගබඩාව මූල මාර්ගය",
"install.repo_path_helper": "දුරස්ථ Git ගබඩාව මෙම නාමාවලියට සුරැකෙනු ඇත.",
"install.lfs_path": "Git LFS මූල මාර්ගය",
"install.lfs_path_helper": "Git LFS විසින් ලුහුබැඳ ගොනු මෙම බහලුම තුළ ගබඩා කරනු ඇත. අක්රිය කිරීමට හිස් තබන්න.",
"install.run_user": "පරිශීලක නාමය ලෙස ධාවනය",
"install.run_user_helper": "The operating system username that Gitea runs as, it must have write access to the data paths. This value is auto-detected and cannot be changed here. To use a different user, restart Gitea under that account.",
"install.domain": "සේවාදායකයේ වසම",
"install.domain_helper": "සේවාදායකය සඳහා ඩොමේන් හෝ ධාරක ලිපිනය.",
"install.ssh_port": "SSH සේවාදායකය වරාය",
"install.ssh_port_helper": "වරාය අංකය ඔබගේ SSH සේවාදායකය සවන් දෙයි. අක්රිය කිරීමට හිස් තබන්න.",
"install.http_port": "HTTP සවන් දෙන්න වරාය",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "මූලික URL එක කරන්න",
"install.app_url_helper": "HTTP සඳහා මූලික ලිපිනය (S) URL පරිගණක ක්රිඩාවට සමාන සහ විද්යුත් තැපැල් දැනුම්දීම්.",
"install.log_root_path": "ලොග් මාර්ගය",
@@ -131,18 +147,37 @@
"install.smtp_addr": "SMTP සත්කාරක",
"install.smtp_port": "ප්රශ්නය විසඳිලා වරාය",
"install.smtp_from": "ලෙස වි-තැපෑල යවන්න",
"install.smtp_from_invalid": "The \"Send Email As\" address is invalid",
"install.smtp_from_helper": "විද්යුත් තැපැල් ලිපිනය Gitea භාවිතා කරනු ඇත. සරල විද්යුත් තැපැල් ලිපිනයක් ඇතුළත් කරන්න හෝ “නම” <email@example.com> ආකෘතිය භාවිතා කරන්න.",
"install.mailer_user": "SMTP පරිශීලක නාමය",
"install.mailer_password": "SMTP මුරපදය",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "ලියාපදිංචි වීමට විද්යුත් තැපැල් තහවුරු කිරීම අවශ්ය වේ",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "වි-තැපැල් දැනුම්දීම් සබල කරන්න",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "සේවාදායකය සහ තෙවන පාර්ශවීය සේවා සැකසුම්",
"install.offline_mode": "දේශීය ප්රකාරය සක්රීය කරන්න",
"install.offline_mode_popup": "තෙවන පාර්ශවීය අන්තර්ගත බෙදාහැරීමේ ජාල අක්රීය කර දේශීයව සියලු සම්පත් සේවය කරන්න.",
"install.disable_gravatar": "ග්‍රැවටාර් අබල කරන්න",
"install.disable_gravatar_popup": "Gravatar සහ තෙවන පාර්ශවීය avatar ප්රභවයන් අක්රීය කරන්න. පරිශීලකයෙකු දේශීයව අවතාරයක් උඩුගත නොකරන්නේ නම් පෙරනිමි අවතාරයක් භාවිතා කරනු ඇත.",
"install.federated_avatar_lookup": "ෆෙඩරල් අවතාර් සක්රීය කරන්න",
"install.federated_avatar_lookup_popup": "Libravatar භාවිතා ෆෙඩරල් අවතාර් විමසිම සක්රීය කරන්න.",
"install.disable_registration": "ස්වයං ලියාපදිංචිය අක්රීය කරන්න",
"install.disable_registration_popup": "පරිශීලක ස්වයං ලියාපදිංචිය අක්රීය කරන්න. නව පරිශීලක ගිණුම් නිර්මාණය කිරීමට හැක්කේ පරිපාලකයින්ට පමණි.",
"install.allow_only_external_registration_popup": "විදේශ සේවා මගින් පමණක් ලියාපදිංචි වීමට ඉඩ දෙන්න",
@@ -150,21 +185,34 @@
"install.openid_signin_popup": "OpenID හරහා පරිශීලක සං in ා සක්රීය කරන්න.",
"install.openid_signup": "OpenID ස්වයං ලියාපදිංචිය සක්රීය කරන්න",
"install.openid_signup_popup": "Openid-මත පදනම් පරිශීලක ස්වයං ලියාපදිංචිය සක්රීය කරන්න.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "ලියාපදිංචි CAPTCHA සක්රීය කරන්න",
"install.enable_captcha_popup": "පරිශීලක ස්වයං ලියාපදිංචිය සඳහා CAPTCHA අවශ්ය වේ.",
"install.require_sign_in_view": "පිටු බැලීම සඳහා සිග්න්-දී අවශ්ය",
"install.require_sign_in_view_popup": "Limit page access to signed-in users. Visitors will only see the sign-in and registration pages.",
"install.admin_setting_desc": "පරිපාලක ගිණුමක් නිර්මාණය කිරීම අත්යවශ්ය නොවේ. පළමු ලියාපදිංචි පරිශීලකයා ස්වයංක්රීයව පරිපාලකයෙකු බවට පත්වනු ඇත.",
"install.admin_title": "පරිපාලක ගිණුමේ සැකසුම්",
"install.admin_name": "පරිපාලක පරිශීලක නාමය",
"install.admin_password": "මුරපදය",
"install.confirm_password": "මුරපදය තහවුරු කරන්න",
"install.admin_email": "වි-තැපැල් ලිපිනය",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "ගිටියා ස්ථාපනය කරන්න",
"install.test_git_failed": "'git' විධානය පරීක්ෂා කළ නොහැකි විය: %v",
"install.sqlite3_not_available": "මෙම Gitea අනුවාදය SQLite3 සඳහා සහය නොදක්වයි. කරුණාකර නිල ද්විමය අනුවාදය %s වෙතින් බාගත කරන්න ('gobuild' අනුවාදය නොවේ).",
"install.invalid_db_setting": "දත්ත සමුදා සැකසුම් අවලංගුයි: %v",
"install.invalid_db_table": "The database table \"%s\" is invalid: %v",
"install.invalid_repo_path": "නිධි මූල මාර්ගය අවලංගුයි: %v",
"install.run_user_not_match": "'ලෙස ධාවනය කරන්න' පරිශීලක නාමය වත්මන් පරිශීලක නාමය නොවේ: %s -> %s",
"install.invalid_app_data_path": "The app data path is invalid: %v",
"install.internal_token_failed": "Failed to generate internal token: %v",
"install.secret_key_failed": "Failed to generate secret key: %v",
"install.save_config_failed": "වින්යාසය සුරැකීමට අසමත් විය: %v",
"install.invalid_admin_setting": "පරිපාලක ගිණුම් සැකසුම අවලංගුයි: %v",
"install.invalid_log_root_path": "ලොග් මාර්ගය අවලංගුයි: %v",
@@ -177,6 +225,13 @@
"install.no_reply_address": "සැඟවුණු වි-තැපැල් වසම",
"install.no_reply_address_helper": "සැඟවුණු විද්යුත් තැපැල් ලිපිනයක් සහිත පරිශීලකයින් සඳහා ඩොමේන් නාමය. උදාහරණයක් ලෙස, සැඟවුණු විද්යුත් තැපැල් වසම 'no.example.org' ලෙස සකසා තිබේ නම්, 'ජෝ' යන පරිශීලක නාමය ගිට් 'joe@noreply.example.org' ලෙස ලොගින් වනු ලැබේ.",
"install.password_algorithm": "මුරපදය හැෂ් ඇල්ගොරිතම",
"install.invalid_password_algorithm": "Invalid password hash algorithm",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "Enable Update Checker",
"install.enable_update_checker_helper": "Checks for new version releases periodically by connecting to gitea.io.",
"install.env_config_keys": "Environment Configuration",
"install.env_config_keys_prompt": "The following environment variables will also be applied to your configuration file:",
"install.config_write_file_prompt": "These configuration options will be written into: %s",
"home.uname_holder": "පරිශීලක නාමය හෝ වි-තැපෑල",
"home.password_holder": "මුරපදය",
"home.switch_dashboard_context": "සංදර්භය උපකරණ පුවරුව මාරු",
@@ -209,6 +264,9 @@
"auth.forgot_password_title": "මුරපදය අමතක වුණා",
"auth.forgot_password": "මුරපදය අමතක වුණා ද?",
"auth.must_change_password": "මුරපදය යාවත්කාල කරන්න",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.allow_password_change": "මුරපදය වෙනස් කිරීමට පරිශීලකයාට අවශ්ය වේ (නිර්දේශිත)",
"auth.reset_password_mail_sent_prompt": "තහවුරු කිරීමේ විද්යුත් තැපෑලක් <b>%s</b>වෙත යවා ඇත. ඊළඟ තුළ ඔබගේ එන ලිපි පරීක්ෂා කරන්න %s ගිණුම යථා ක්රියාවලිය සම්පූර්ණ කිරීම සඳහා.",
"auth.active_your_account": "ඔබගේ ගිණුම ක්‍රියාත්මක කරන්න",
@@ -1816,6 +1874,7 @@
"admin.users.created": "සෑදීම",
"admin.users.last_login": "අවසන් සංඥා දී",
"admin.users.send_register_notify": "පරිශීලක ලියාපදිංචි දැනුම්දීම යවන්න",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.edit": "සංස්කරණය",
"admin.users.auth_source": "සත්යාපන මූලාශ්රය",
"admin.users.local": "ස්ථානීය",
@@ -2189,5 +2248,15 @@
"actions.runners.status.active": "ක්රියාකාරී",
"actions.runners.version": "අනුවාදය",
"actions.runs.commit": "කැප",
"git.filemode.symbolic_link": "සංකේතාත්මක සබැඳිය"
"git.filemode.symbolic_link": "සංකේතාත්මක සබැඳිය",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+69 -8
View File
@@ -154,56 +154,90 @@
"startpage.lightweight_desc": "Gitea má minimálne požiadavky a môže bežať na Raspberry Pi. Šetrite energiou vášho stroja!",
"startpage.license": "Otvorený zdrojový kód",
"install.install": "Inštalácia",
"install.installing_desc": "Installing now, please wait…",
"install.title": "Východzia konfigurácia",
"install.docker_helper": "Ak spúšťate Gitea v Docker kontajneri, prečítajte si <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">dokumentáciu</a> pred zmenou akýchkoľvek nastavení.",
"install.require_db_desc": "Gitea vyžaduje MySQL, PostgreSQL, MSSQL, SQLite3 alebo TiDB (MySQL protokol).",
"install.db_title": "Nastavenie databázy",
"install.db_type": "Typ databázy",
"install.host": "Host",
"install.user": "Používateľské meno",
"install.password": "Heslo",
"install.db_name": "Názov databázy",
"install.db_schema": "Schéma",
"install.db_schema_helper": "Nechajte prázdne pre predvolené nastavenie (\"public\").",
"install.ssl_mode": "SSL",
"install.path": "Cesta",
"install.sqlite_helper": "Cesta k súboru databázy SQLite3.<br>Ak spúšťate Gitea ako službu, zadajte absolútnu cestu.",
"install.reinstall_error": "Pokúšate sa inštalovať do existujúcej databázy Gitea",
"install.reinstall_confirm_message": "Opätovná inštalácia s existujúcou databázou Gitea môže spôsobiť viacero problémov. Vo väčšine prípadov by ste na spustenie Gitea mali použiť svoj existujúci súbor „app.ini“. Ak viete, čo robíte, potvrďte nasledujúce:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "Potvrdzujete, že ste si úplne istí, že táto Gitea beží so správnym umiestnením app.ini a že ste si istí, že ju musíte znova nainštalovať. Potvrdzujete, že beriete na vedomie vyššie uvedené riziká.",
"install.err_empty_db_path": "Cesta k databáze SQLite3 nesmie byť prázdna.",
"install.no_admin_and_disable_registration": "Nemôžete zakázať registráciu bez vytvorenia administrátorského účtu.",
"install.err_empty_admin_password": "Heslo administrátora nemôže byť prázdne.",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "Všeobecné nastavenia",
"install.app_name": "Názov webu",
"install.app_name_helper": "Sem môžete zadať meno vašej spoločnosti.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Koreňový adresár repozitárov",
"install.repo_path_helper": "Vzdialené úložiská Git sa uložia do tohto adresára.",
"install.lfs_path": "Koreňový adresár Git LFS",
"install.lfs_path_helper": "Súbory sledované systémom Git LFS budú uložené v tomto adresári. Ak chcete deaktivovať, ponechajte prázdne.",
"install.run_user": "Spustiť ako používateľ",
"install.run_user_helper": "The operating system username that Gitea runs as, it must have write access to the data paths. This value is auto-detected and cannot be changed here. To use a different user, restart Gitea under that account.",
"install.domain": "Doména serveru",
"install.domain_helper": "Adresa domény alebo hostiteľa serveru.",
"install.ssh_port": "Port SSH servera",
"install.ssh_port_helper": "Číslo portu na ktorom načúva SSH server. Keď ponecháte prázdne, SSH server zakážete.",
"install.http_port": "HTTP port pre Gitea",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "Základná URL Gitea",
"install.app_url_helper": "Základná adresa pre klonované HTTP(S) URL adresy a e-mailové upozornenia.",
"install.log_root_path": "Adresár logov",
"install.log_root_path_helper": "Do tohoto adresára budú uložené súbory protokolu.",
"install.optional_title": "Voliteľné nastavenia",
"install.email_title": "Nastavenia e-mailu",
"install.smtp_addr": "SMTP Host",
"install.smtp_port": "SMTP Port",
"install.smtp_from": "Odoslať e-mail ako",
"install.smtp_from_invalid": "The \"Send Email As\" address is invalid",
"install.smtp_from_helper": "E-mailová adresa ktorú použije Gitea. Zadajte bežnú e-mailovú adresu alebo použite formát \"Meno\" <email@example.com>.",
"install.mailer_user": "Používateľské meno SMTP",
"install.mailer_password": "SMTP heslo",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Registrácia vyžaduje potvrdenie e-mailu",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Povoliť e-mailové upozornenia",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Nastavenia servera a ostatných služieb",
"install.offline_mode": "Povoliť miestny režim",
"install.offline_mode_popup": "Zakázať siete doručovania obsahu tretích strán a poskytovať celý obsah lokálne.",
"install.disable_gravatar": "Zakázať Gravatar",
"install.disable_gravatar_popup": "Zakázať Gravatar a cudzie zdroje avatarov. Ak používateľ nenahrá avatara, použije sa predvolený.",
"install.federated_avatar_lookup": "Povoliť avatary z verejných zdrojov",
"install.federated_avatar_lookup_popup": "Povoliť Libavatar na vyhľadávanie avatarov z verejných zdrojov.",
"install.disable_registration": "Zakázať registráciu",
"install.disable_registration_popup": "Zakázať registráciu. Nové používateľské účty budú môcť vytvárať iba správci.",
"install.allow_only_external_registration_popup": "Povoliť registráciu iba skrze externé služby",
@@ -211,6 +245,8 @@
"install.openid_signin_popup": "Povoliť používateľovi prihlásenie pomocou OpenID.",
"install.openid_signup": "Povoliť registráciu pomocou OpenID",
"install.openid_signup_popup": "Povoliť používateľskú registráciu založenú na OpenID.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Povoliť CAPTCHA pri registrácii",
"install.enable_captcha_popup": "Vyžadovať CAPTCHA validáciu pri registrácii používateľa.",
"install.require_sign_in_view": "Vyžadovať prihlásenie na prezeranie stránok",
@@ -221,13 +257,20 @@
"install.admin_password": "Heslo",
"install.confirm_password": "Potvrdiť heslo",
"install.admin_email": "E-mailová adresa",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Nainštalovať Gitea",
"install.test_git_failed": "Nie je možné otestovať príkaz 'git': %v",
"install.sqlite3_not_available": "Táto verzia Gitea nepodporuje SQLite3. Stiahnite si, prosím, oficiálnu verziu z %s (nie verziu \"gobuild\").",
"install.invalid_db_setting": "Nastavenia databázy sú neplatné: %v",
"install.invalid_db_table": "The database table \"%s\" is invalid: %v",
"install.invalid_repo_path": "Koreňová cesta repozitára je neplatná: %v",
"install.invalid_app_data_path": "Cesta k údajom aplikácie je neplatná: %v",
"install.run_user_not_match": "Používateľské meno pre 'spustiť ako' nie je aktuálne používateľské meno: %s -> %s",
"install.internal_token_failed": "Nepodarilo sa vygenerovať interný token: %v",
"install.secret_key_failed": "Nepodarilo sa vygenerovať tajný kľúč: %v",
"install.save_config_failed": "Nepodarilo sa uložiť konfiguráciu: %v",
@@ -243,8 +286,12 @@
"install.no_reply_address_helper": "Doménové meno pre používateľov so skrytou e-mailovou adresou. Napríklad, používateľ s menom 'joe' bude zalogovaný v Git-e ako 'joe@noreply.example.org' ak je skrytá e-mailová doména nastavená na 'noreply.example.org'.",
"install.password_algorithm": "Hašovací algoritmus hesla",
"install.invalid_password_algorithm": "Neplatný hash algoritmus hesla",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "Povoliť kontrolu aktualizácií",
"install.enable_update_checker_helper": "Pravidelne kontroluje nové verzie pripojením k gitea.io.",
"install.env_config_keys": "Environment Configuration",
"install.env_config_keys_prompt": "The following environment variables will also be applied to your configuration file:",
"install.config_write_file_prompt": "These configuration options will be written into: %s",
"home.uname_holder": "Používateľské meno alebo emailová adresa",
"home.password_holder": "Heslo",
"home.switch_dashboard_context": "Prepnúť kontext nástenky",
@@ -282,6 +329,9 @@
"auth.forgot_password_title": "Zabudnuté heslo",
"auth.forgot_password": "Zabudli ste heslo?",
"auth.allow_password_change": "Vyžiadať od používateľa zmenu hesla (doporučuje sa)",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.reset_password_mail_sent_prompt": "Na adresu <b>%s</b> bol odoslaný potvrdzovací e-mail. Skontrolujte si, prosím, vašu doručenú poštu počas najbližších %s pre dokončenie procesu obnovenia účtu.",
"auth.active_your_account": "Aktivovať účet",
"auth.account_activated": "Účet bol aktivovaný",
@@ -1070,6 +1120,7 @@
"admin.users.activated": "Aktivovaný",
"admin.users.edit": "Upraviť",
"admin.users.delete_account": "Odstrániť používateľský účet",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.emails.primary": "Primárny",
"admin.emails.activated": "Aktivovaný",
"admin.emails.filter_sort.email": "E-mailová adresa",
@@ -1160,5 +1211,15 @@
"actions.runners.task_list.repository": "Repozitár",
"actions.runners.status.unspecified": "Neznámy",
"actions.runners.version": "Verzia",
"git.filemode.symbolic_link": "Symbolický odkaz"
"git.filemode.symbolic_link": "Symbolický odkaz",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+82 -8
View File
@@ -80,31 +80,51 @@
"startpage.lightweight": "Lättviktig",
"startpage.lightweight_desc": "Gitea har låga minimum-krav och kan köras på en billig Rasperry Pi. Spara på din maskins kraft!",
"startpage.license": "Öppen källkod",
"install.install": "Installation",
"install.installing_desc": "Installing now, please wait…",
"install.title": "Ursprunglig konfiguration",
"install.docker_helper": "Om du kör Gitea i Docker, vänligen läs igenom <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">dokumentationen</a> innan några inställningar ändras.",
"install.require_db_desc": "Gitea requires MySQL, PostgreSQL, MSSQL, SQLite3 or TiDB (MySQL protocol).",
"install.db_title": "Databasinställningar",
"install.db_type": "Databastyp",
"install.host": "Server",
"install.user": "Användarnamn",
"install.password": "Lösenord",
"install.db_name": "Databasens namn",
"install.db_schema": "Schema",
"install.db_schema_helper": "Lämna tomt för databasens förvalda värde (\"public\").",
"install.ssl_mode": "SSL",
"install.path": "Filväg",
"install.sqlite_helper": "Sökväg för SQLite3-databasen.<br>Ange en absolut sökväg om du kör Gitea som en tjänst.",
"install.reinstall_error": "You are trying to install into an existing Gitea database",
"install.reinstall_confirm_message": "Re-installing with an existing Gitea database can cause multiple problems. In most cases, you should use your existing \"app.ini\" to run Gitea. If you know what you are doing, confirm the following:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "You confirm that you are absolutely sure that this Gitea is running with the correct app.ini location and that you are sure that you have to re-install. You confirm that you acknowledge the above risks.",
"install.err_empty_db_path": "En sökväg till SQLite3-databasen måste anges.",
"install.no_admin_and_disable_registration": "Du kan inte inaktivera självregistrering utan att skapa ett administratörskonto.",
"install.err_empty_admin_password": "Administratörslösenordet kan inte vara tomt.",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "Allmänna inställningar",
"install.app_name": "Sajtens namn",
"install.app_name_helper": "Du kan ange ditt företagsnamn här.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Rotsökväg för utvecklingskatalog",
"install.repo_path_helper": "Fjärrutvecklingskataloger kommer att sparas i denna katalog.",
"install.lfs_path": "LFS Rotsökväg",
"install.lfs_path_helper": "Filer hanterade av Git LFS kommer att sparas i denna mapp. Lämna tom för att avaktivera.",
"install.run_user": "Kör som användarnamn",
"install.run_user_helper": "The operating system username that Gitea runs as, it must have write access to the data paths. This value is auto-detected and cannot be changed here. To use a different user, restart Gitea under that account.",
"install.domain": "Server Domain",
"install.domain_helper": "Domain or host address for the server.",
"install.ssh_port": "SSH-serverport",
"install.ssh_port_helper": "Portnumret som din SSH-server lyssnar på. Lämna tom för att inaktivera.",
"install.http_port": "Gitea HTTP-lyssningsport",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "Gitea URL",
"install.app_url_helper": "Basadressen för HTTP(S)-kloningslänkar och mejlnotifikationer.",
"install.log_root_path": "Loggsökväg",
@@ -114,18 +134,37 @@
"install.smtp_addr": "SMTP-server",
"install.smtp_port": "SMTP-port",
"install.smtp_from": "Skicka Mejl Som",
"install.smtp_from_invalid": "The \"Send Email As\" address is invalid",
"install.smtp_from_helper": "Mejladress som Gitea kommer att använda. Anges i simpelt ('email@example.com') eller fullständigt ('Name <email@example.com>') format.",
"install.mailer_user": "SMTP-Användarnamn",
"install.mailer_password": "SMTP-Lösenord",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Kräv Bekräftelse Via Mejl För Att Registrera",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Aktivera Mejlnotifikationer",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Inställningar för Server- och Tredjepartstjänster",
"install.offline_mode": "Aktivera Lokalt Läge",
"install.offline_mode_popup": "Inaktivera CDN från tredjepart och distribuera samtliga resurser lokalt istället.",
"install.disable_gravatar": "Inaktivera Gravatar",
"install.disable_gravatar_popup": "Inaktivera Gravatar- och avatarskällor från tredjepart. Om användaren inte laddar upp en avatar så kommer en standardavatar att användas.",
"install.federated_avatar_lookup": "Aktivera Federerade Avatarer",
"install.federated_avatar_lookup_popup": "Använd libravatar vid förenad uppslagning av avatarer.",
"install.disable_registration": "Inaktivera Självregistrering",
"install.disable_registration_popup": "Inaktivera självregistrering av användare. Endast administratörer kommer kunna skapa nya konton.",
"install.allow_only_external_registration_popup": "Tillåt registrering endast via externa tjänster",
@@ -133,21 +172,34 @@
"install.openid_signin_popup": "Aktivera användarinloggning via OpenID.",
"install.openid_signup": "Aktivera självregistrering genom OpenID",
"install.openid_signup_popup": "Aktivera OpenID-baserad självregistrering av användare.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Aktivera CAPTCHA registrering",
"install.enable_captcha_popup": "Kräv captcha för användarregistrering.",
"install.require_sign_in_view": "Kräv Inloggning För Att Visa Sidor",
"install.require_sign_in_view_popup": "Limit page access to signed-in users. Visitors will only see the sign-in and registration pages.",
"install.admin_setting_desc": "Skapandet av administratörskonto är frivilligt. Den första användaren som registreras blir automatiskt administratör.",
"install.admin_title": "Inställningar för Administratörskonto",
"install.admin_name": "Användarnamn för Administratör",
"install.admin_password": "Lösenord",
"install.confirm_password": "Bekräfta lösenord",
"install.admin_email": "Mejladress",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Installera Gitea",
"install.test_git_failed": "Misslyckades att testa 'git' kommando: %v",
"install.sqlite3_not_available": "Denna version av Gitea stödjer ej SQLite3. Ladda ner den officiella binären från %s (inte 'gobuild' versionen).",
"install.invalid_db_setting": "Databasinställningarna är ogiltiga: %v",
"install.invalid_db_table": "The database table \"%s\" is invalid: %v",
"install.invalid_repo_path": "Utvecklingskatalogens rotsökväg är ogiltig: %v",
"install.run_user_not_match": "Systemtjänstanvändaren är inte den nuvarande användaren: %s -> %s",
"install.invalid_app_data_path": "The app data path is invalid: %v",
"install.internal_token_failed": "Failed to generate internal token: %v",
"install.secret_key_failed": "Failed to generate secret key: %v",
"install.save_config_failed": "Misslyckades att spara konfigurationen: %v",
"install.invalid_admin_setting": "Inställning för administartörskontot är ogiltig: %v",
"install.invalid_log_root_path": "Sökvägen för loggar är ogiltig: %v",
@@ -159,6 +211,14 @@
"install.default_enable_timetracking_popup": "Aktivera tidsredovisning för nya utvecklingskataloger som standard.",
"install.no_reply_address": "Dold mejldomän",
"install.no_reply_address_helper": "Domännamn för användare med en dold mailadress. Exempelvis kommer användarnamnet 'joe' att loggas i Git som 'joe@noreply.example.org' om dold maildomän är satt till 'noreply.example.org'.",
"install.password_algorithm": "Password Hash Algorithm",
"install.invalid_password_algorithm": "Invalid password hash algorithm",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "Enable Update Checker",
"install.enable_update_checker_helper": "Checks for new version releases periodically by connecting to gitea.io.",
"install.env_config_keys": "Environment Configuration",
"install.env_config_keys_prompt": "The following environment variables will also be applied to your configuration file:",
"install.config_write_file_prompt": "These configuration options will be written into: %s",
"home.uname_holder": "Användarnamn eller Mejladress",
"home.password_holder": "Lösenord",
"home.switch_dashboard_context": "Växla Visad Instrumentpanel",
@@ -190,6 +250,9 @@
"auth.forgot_password_title": "Glömt lösenord",
"auth.forgot_password": "Glömt lösenord?",
"auth.must_change_password": "Ändra ditt lösenord",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.allow_password_change": "Kräv att användaren byter lösenord (rekommenderas)",
"auth.reset_password_mail_sent_prompt": "Ett nytt bekräftelsemail has skickats till <b>%s</b>. Vänligen kontrollera din inkorg inom de kommande %s för att slutföra återställning av ditt konto.",
"auth.active_your_account": "Aktivera ditt konto",
@@ -1445,6 +1508,7 @@
"admin.users.created": "Skapad",
"admin.users.last_login": "Senaste inloggning",
"admin.users.send_register_notify": "Skicka notifiering vid användarregistrering",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.edit": "Redigera",
"admin.users.auth_source": "Autentiseringskälla",
"admin.users.local": "Lokal",
@@ -1733,5 +1797,15 @@
"actions.runners.task_list.run": "Kör",
"actions.runners.task_list.repository": "Utvecklingskatalog",
"actions.runners.status.active": "Aktiv",
"git.filemode.symbolic_link": "Symbolisk länk"
"git.filemode.symbolic_link": "Symbolisk länk",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+50 -8
View File
@@ -256,6 +256,8 @@
"install.general_title": "Genel Ayarlar",
"install.app_name": "Site Başlığı",
"install.app_name_helper": "Şirket adınızı buraya girebilirsiniz.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Depo Kök Yolu",
"install.repo_path_helper": "Tüm uzak Git depoları bu dizine kaydedilecektir.",
"install.lfs_path": "Git LFS Kök Yolu",
@@ -281,15 +283,33 @@
"install.smtp_from_helper": "Gitea'nın kullanacağı e-posta adresi. Yalın bir e-posta adresi girin veya \"İsim\" <eposta@ornek.com> biçimini kullanın.",
"install.mailer_user": "SMTP Kullanıcı Adı",
"install.mailer_password": "SMTP Parolası",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Kayıt için E-posta Doğrulaması Gereksin",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "E-Posta Bildirimlerini Etkinleştir",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Sunucu ve Diğer Servis Ayarları",
"install.offline_mode": "Yerel Kipi Etkinleştir",
"install.offline_mode_popup": "Üçüncü parti içerik teslim ağlarını etkisizleştirin ve bütün kaynakları yerelden sunun.",
"install.disable_gravatar": "Gravatar'ı Devre Dışı Bırak",
"install.disable_gravatar_popup": "Gravatar ve üçüncü parti avatar kaynaklarını iptal edin. Kullanıcı bir avatar yüklemediği zaman varsayılan bir avatar kullanılacaktır.",
"install.federated_avatar_lookup": "Birleştirilmiş Avatarları Etkinleştir",
"install.federated_avatar_lookup_popup": "Libravatar kullanarak federe avatar aramasını etkinleştirin.",
"install.disable_registration": "Kendi Kendine Kaydolmayı Devre Dışı Bırak",
"install.disable_registration_popup": "Kullanıcının kendi kendine kaydolmasını devre dışı bırak. Yalnızca yöneticiler yeni hesaplar oluşturabilecek.",
"install.allow_only_external_registration_popup": "Sadece dış hizmetler aracılığıyla kullanıcı kaydına izin ver",
@@ -297,6 +317,8 @@
"install.openid_signin_popup": "OpenID ile kullanıcı girişini etkinleştir.",
"install.openid_signup": "OpenID ile Kendi Kendine Kaydı Etkinleştir",
"install.openid_signup_popup": "OpenID Tabanlı Kendi Kendi Kullanıcı Kaydını Etkinleştir.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "CAPTCHA kaydını etkinleştir",
"install.enable_captcha_popup": "Kullanıcının kendi kendine kaydolması için captcha doğrulaması gereksin.",
"install.require_sign_in_view": "Sayfaları Görüntülemek için Giriş Yapmak Gereksin",
@@ -307,6 +329,13 @@
"install.admin_password": "Parola",
"install.confirm_password": "Parolayı Doğrula",
"install.admin_email": "E-posta Adresi",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Gitea'u Kur",
"install.test_git_failed": "'git' komut testi başarısız: %v",
"install.sqlite3_not_available": "Bu Gieta sürümü SQLite3 desteklemiyor. Lütfen %s adresinden resmi çalışır sürümü ('gobuild' sürümünü değil) indirin.",
@@ -314,7 +343,6 @@
"install.invalid_db_table": "\"%s\" veritabanı tablosu geçersiz: %v",
"install.invalid_repo_path": "Depo kök dizini geçersiz: %v",
"install.invalid_app_data_path": "Uygulama veri yolu geçersiz: %v",
"install.run_user_not_match": "'Birlikte çalıştır' kullanıcı adı şimdiki kullanıcı adından farklıdır: %s -> %s",
"install.internal_token_failed": "Dahili belirteç oluşturulamadı: %v",
"install.secret_key_failed": "Gizli anahtar oluşturulamadı: %v",
"install.save_config_failed": "%v Yapılandırması kaydedilirken hata oluştu",
@@ -387,6 +415,9 @@
"auth.sign_up_now": "Hemen kaydolun.",
"auth.sign_up_successful": "Hesap başarılı bir şekilde oluşturuldu. Hoşgeldiniz!",
"auth.confirmation_mail_sent_prompt_ex": "Yeni bir doğrulama e-postası <b>%s</b> adresine gönderildi. Lütfen kayıt sürecini tamamlamak için %s içinde gelen kutunuzu denetleyin. Eğer kayıt e-posta adresiniz hatalı ise, tekrar oturum açıp değiştirebilirsiniz.",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.must_change_password": "Parolanızı güncelleyin",
"auth.allow_password_change": "Kullanıcıyı parola değiştirmeye zorla (önerilen)",
"auth.reset_password_mail_sent_prompt": "<b>%s</b> adresine bir onay e-postası gönderildi. Hesap kurtarma işlemini tamamlamak için lütfen gelen kutunuzu sonraki %s içinde kontrol edin.",
@@ -2971,6 +3002,7 @@
"admin.users.last_login": "Son Oturum Açma",
"admin.users.never_login": "Hiç Oturum Açılmadı",
"admin.users.send_register_notify": "Kullanıcı Kayıt Bildirimi Gönder",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.new_success": "\"%s\" kullanıcı hesabı oluşturuldu.",
"admin.users.edit": "Düzenle",
"admin.users.auth_source": "Yetkilendirme Kaynağı",
@@ -3743,5 +3775,15 @@
"git.filemode.normal_file": "Normal dosya",
"git.filemode.executable_file": "Çalıştırılabilir dosya",
"git.filemode.symbolic_link": "Sembolik Bağlantı",
"git.filemode.submodule": "Alt modül"
"git.filemode.submodule": "Alt modül",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+60 -8
View File
@@ -189,6 +189,7 @@
"startpage.lightweight_desc": "Gitea має мінімальні вимоги і може працювати на недорогому Raspberry Pi. Заощаджуйте ресурси вашої машини!",
"startpage.license": "Відкритий вихідний код",
"install.install": "Встановлення",
"install.installing_desc": "Installing now, please wait…",
"install.title": "Початкова конфігурація",
"install.docker_helper": "Якщо ви запускаєте Gitea у Docker, будь ласка, прочитайте <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">документацію</a> перед тим, як змінювати будь-які налаштування.",
"install.require_db_desc": "Gitea потребує MySQL, PostgreSQL, MSSQL, SQLite3 або TiDB (протокол MySQL).",
@@ -200,17 +201,26 @@
"install.db_name": "Назва бази даних",
"install.db_schema": "Схема",
"install.db_schema_helper": "Залиште пустим для типової схеми бази даних (\"публічна\").",
"install.ssl_mode": "SSL",
"install.path": "Шлях",
"install.sqlite_helper": "Шлях до файлу бази даних SQLite3.<br>Введіть абсолютний шлях, якщо ви запускаєте Gіtea як сервіс.",
"install.reinstall_error": "Ви намагаєтеся встановити в наявну базу даних Gitea",
"install.reinstall_confirm_message": "Повторне встановлення в наявну базу даних Gitea може спричинити багато проблем. В більшості випадків, ви повинні використовувати свій наявний \"app.ini\" для запуску Gitea. Якщо ви знаєте, що робите, спробуйте наступне:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "Ви підтверджуєте, що абсолютно впевнені, що Gitea працює з правильним розташуванням файлу app.ini, і що вам потрібно перевстановити програму. Ви підтверджуєте, що усвідомлюєте вищевказані ризики.",
"install.err_empty_db_path": "Шлях до файлу бази даних SQLite3 не може бути порожнім.",
"install.no_admin_and_disable_registration": "Ви не можете вимкнути реєстрацію без створення облікового запису адміністратора.",
"install.err_empty_admin_password": "Пароль адміністратора не може бути порожнім.",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "Загальні налаштування",
"install.app_name": "Назва сайту",
"install.app_name_helper": "Тут ви можете ввести назву своєї компанії.",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "Кореневий шлях сховища",
"install.repo_path_helper": "До цього каталогу буде збережено віддалені сховища Git.",
"install.lfs_path": "Кореневий шлях Git LFS",
@@ -222,6 +232,7 @@
"install.ssh_port": "Порт SSH сервера",
"install.ssh_port_helper": "Номер порту, який використовує SSH сервер. Залиште порожнім, щоб вимкнути SSH.",
"install.http_port": "Gitea HTTP порт",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "Базова URL-адреса Gitea",
"install.app_url_helper": "Базова адреса для URL-адрес клонів HTTP(S) та сповіщень електронною поштою.",
"install.log_root_path": "Шлях до журналу",
@@ -235,15 +246,33 @@
"install.smtp_from_helper": "Адреса електронної пошти, яку буде використовувати Gitea. Введіть звичайну адресу електронної пошти або використовуйте формат «Ім'я» <email@example.com>.",
"install.mailer_user": "Ім'я користувача SMTP",
"install.mailer_password": "Пароль SMTP",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "Вимагати підтвердження електронною поштою для реєстрації",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "Увімкнути сповіщення електронною поштою",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "Налаштування сервера і сторонніх сервісів",
"install.offline_mode": "Увімкнути локальний режим",
"install.offline_mode_popup": "Вимкнути сторонні мережі доставки контенту та обслуговувати всі ресурси локально.",
"install.disable_gravatar": "Вимкнути Gravatar",
"install.disable_gravatar_popup": "Вимкнути Gravatar та сторонні джерела аватарок. Якщо користувач локально не завантажить аватар, буде використовуватися типовий аватар.",
"install.federated_avatar_lookup": "Увімкнути зовнішні аватари",
"install.federated_avatar_lookup_popup": "Увімкнути пошук об'єднаних аватарів за допомогою Libravatar.",
"install.disable_registration": "Вимкнути реєстрацію",
"install.disable_registration_popup": "Вимкнути реєстрацію користувачів, тільки адміністратор може створювати нові облікові записи.",
"install.allow_only_external_registration_popup": "Дозволити реєстрацію тільки через сторонні сервіси",
@@ -251,6 +280,8 @@
"install.openid_signin_popup": "Увімкнути вхід користувачів за допомогою OpenID.",
"install.openid_signup": "Увімкнути самостійну реєстрацію за допомогою OpenID",
"install.openid_signup_popup": "Увімкнути самореєстрацію користувачів на основі OpenID.",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "Увімкнути CAPTCHA для реєстрації",
"install.enable_captcha_popup": "Вимагати CAPTCHA для самореєстрації користувачів.",
"install.require_sign_in_view": "Вимагати авторизації для перегляду сторінок",
@@ -261,6 +292,13 @@
"install.admin_password": "Пароль",
"install.confirm_password": "Підтвердити пароль",
"install.admin_email": "Адреса електронної пошти",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "Встановити Gitea",
"install.test_git_failed": "Не вдалося перевірити команду 'git': %v",
"install.sqlite3_not_available": "Ця версія Gitea не підтримує SQLite3. Будь ласка, завантажте офіційну бінарну версію з %s (не версію gobuild).",
@@ -268,7 +306,6 @@
"install.invalid_db_table": "База даних таблиці \"%s\" є недійсною: %v",
"install.invalid_repo_path": "Кореневий шлях до сховища невірний: %v",
"install.invalid_app_data_path": "Шлях до даних додатка невірний: %v",
"install.run_user_not_match": "Ім'я користувача “Виконати як” не є поточним ім'ям користувача: %s -> %s",
"install.internal_token_failed": "Не вдалося створити внутрішній токен: %v",
"install.secret_key_failed": "Не вдалося створити секретний ключ: %v",
"install.save_config_failed": "Не вдалося зберегти конфігурацію: %v",
@@ -284,6 +321,7 @@
"install.no_reply_address_helper": "Доменне ім'я для користувачів із прихованою електронною адресою. Наприклад, ім'я користувача 'Joe' буде зображатися в Git як 'joe@noreply.example.org', якщо прихований домен електронної пошти встановлено 'noreply.example.org'.",
"install.password_algorithm": "Алгоритм хешування пароля",
"install.invalid_password_algorithm": "Недійсний хеш-алгоритм пароля",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "Увімкнути перевірку оновлень",
"install.enable_update_checker_helper": "Періодично перевіряти наявність нових версій, підключаючись до gitea.io.",
"install.env_config_keys": "Конфігурація середовища",
@@ -340,6 +378,9 @@
"auth.sign_up_now": "Зареєструватися.",
"auth.sign_up_successful": "Обліковий запис створено успішно. Вітаю!",
"auth.confirmation_mail_sent_prompt_ex": "Новий лист з підтвердженням було надіслано на <b>%s</b>. Будь ласка, перевірте свою поштову скриньку протягом наступних %s, щоб завершити процес реєстрації. Якщо ви вказали невірну адресу електронної пошти, ви можете увійти ще раз і змінити її.",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.must_change_password": "Оновити пароль",
"auth.allow_password_change": "Вимагати від користувача змінити пароль (рекомендовано)",
"auth.reset_password_mail_sent_prompt": "На адресу <b>%s</b> було надіслано лист із підтвердженням. Будь ласка, перевірте свою поштову скриньку протягом наступних %s, щоб завершити процес відновлення облікового запису.",
@@ -2533,6 +2574,7 @@
"admin.users.created": "Створено",
"admin.users.last_login": "Останній вхід",
"admin.users.send_register_notify": "Надіслати повідомлення про реєстрацію користувача",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.new_success": "Обліковий запис \"%s\" створено.",
"admin.users.edit": "Редагувати",
"admin.users.auth_source": "Джерело автентифікації",
@@ -3182,5 +3224,15 @@
"git.filemode.normal_file": "Звичайний файл",
"git.filemode.executable_file": "Виконуваний файл",
"git.filemode.symbolic_link": "Символічне посилання",
"git.filemode.submodule": "Підмодуль"
"git.filemode.submodule": "Підмодуль",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+50 -2
View File
@@ -257,6 +257,8 @@
"install.general_title": "一般设置",
"install.app_name": "站点名称",
"install.app_name_helper": "您可以在此输入您公司的名称。",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "仓库根目录",
"install.repo_path_helper": "所有远程 Git 仓库将保存到此目录。",
"install.lfs_path": "LFS根目录",
@@ -282,8 +284,32 @@
"install.smtp_from_helper": "请输入一个用于 Gitea 的邮箱地址,或者使用完整格式:\"名称\" <email@example.com>。",
"install.mailer_user": "SMTP 用户名",
"install.mailer_password": "SMTP 密码",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "需要邮件确认注册",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "启用邮件通知提醒",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "服务器和第三方服务设置",
"install.disable_registration": "禁止用户自助注册",
"install.disable_registration_popup": "禁用用户自助注册。只有管理员才能创建新的用户帐户。",
@@ -292,6 +318,8 @@
"install.openid_signin_popup": "启用通过 OpenID 登录",
"install.openid_signup": "启用 OpenID 自助注册",
"install.openid_signup_popup": "启用基于 OpenID 的用户自助注册。",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "启用注册验证码",
"install.enable_captcha_popup": "要求在用户注册时输入预验证码",
"install.require_sign_in_view": "启用页面访问限制",
@@ -302,6 +330,13 @@
"install.admin_password": "管理员密码",
"install.confirm_password": "确认密码",
"install.admin_email": "邮箱地址",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "立即安装",
"install.test_git_failed": "无法识别 'git' 命令:%v",
"install.sqlite3_not_available": "您所使用的发行版不支持 SQLite3,请从 %s 下载官方构建版,而不是 gobuild 版本。",
@@ -309,7 +344,6 @@
"install.invalid_db_table": "数据库表「%s」无效:%v",
"install.invalid_repo_path": "仓库根目录设置无效:%v",
"install.invalid_app_data_path": "应用数据路径无效: %v",
"install.run_user_not_match": "运行用户名不是当前的用户名:%s -> %s",
"install.internal_token_failed": "生成内部令牌失败:%v",
"install.secret_key_failed": "生成密钥失败:%v",
"install.save_config_failed": "应用配置保存失败:%v",
@@ -382,6 +416,9 @@
"auth.sign_up_now": "立即注册。",
"auth.sign_up_successful": "帐户创建成功。欢迎!",
"auth.confirmation_mail_sent_prompt_ex": "一封新的确认邮件已经发送到 <b>%s</b>。请在 %s 内检查您的收件箱以完成注册流程。 如果您的注册邮箱地址不正确,您可以重新登录并更改它。",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.must_change_password": "更新您的密码",
"auth.allow_password_change": "要求用户更改密码(推荐)",
"auth.reset_password_mail_sent_prompt": "确认邮件已被发送到 <b>%s</b>。请您在 %s 内检查您的收件箱 ,完成密码重置流程。",
@@ -2968,6 +3005,7 @@
"admin.users.last_login": "上次登录",
"admin.users.never_login": "从未登录",
"admin.users.send_register_notify": "发送注册通知",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.new_success": "用户账户「%s」已创建。",
"admin.users.edit": "修改",
"admin.users.auth_source": "认证源",
@@ -3749,5 +3787,15 @@
"git.filemode.normal_file": "普通文件",
"git.filemode.executable_file": "可执行文件",
"git.filemode.symbolic_link": "符号链接",
"git.filemode.submodule": "子模块"
"git.filemode.submodule": "子模块",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+61 -8
View File
@@ -188,6 +188,7 @@
"startpage.license": "開放原始碼",
"startpage.license_desc": "取得 <a target=\"_blank\" rel=\"noopener noreferrer\" href=\"https://code.gitea.io/gitea\">code.gitea.io/gitea</a> !成為一名<a target=\"_blank\" rel=\"noopener noreferrer\" href=\"https://github.com/go-gitea/gitea\">貢獻者</a>和我們一起讓 Gitea 更好,快點加入我們吧!",
"install.install": "安裝頁面",
"install.installing_desc": "Installing now, please wait…",
"install.title": "初始組態",
"install.docker_helper": "如果您在 Docker 中執行 Gitea,請先閱讀<a target=\"_blank\" rel=\"noopener noreferrer\" href=\"%s\">安裝指南</a>再來調整設定。",
"install.require_db_desc": "Gitea 需要 MySQL、PostgreSQL、SQLite3、MSSQL、TiDB (MySQL 協定) 等其中一項。",
@@ -197,18 +198,28 @@
"install.user": "帳號",
"install.password": "密碼",
"install.db_name": "資料庫名稱",
"install.db_schema": "Schema",
"install.db_schema_helper": "留空則使用資料庫預設值(\"public\")。",
"install.ssl_mode": "SSL",
"install.path": "資料庫檔案路徑",
"install.sqlite_helper": "SQLite3 或 TiDB 資料庫的檔案路徑。<br>如果將 Gitea 註冊為服務執行,請輸入絕對路徑。",
"install.reinstall_error": "您正試圖安裝到既有的 Gitea 資料庫中",
"install.reinstall_confirm_message": "使用既有的 Gitea 資料庫來安裝可能造成多種問題。大部分的情形下您應使用既有的「app.ini」來執行 Gitea。如果您知道自己正在做什麼,請確認下列事項:",
"install.reinstall_confirm_check_1": "The data encrypted by the SECRET_KEY in app.ini may be lost: users may not be able to log in with 2FA/OTP and mirrors may not function correctly. By checking this box, you confirm that the current app.ini file contains the correct SECRET_KEY.",
"install.reinstall_confirm_check_2": "The repositories and settings may need to be resynchronized. By checking this box, you confirm that you will resynchronize the hooks for the repositories and authorized_keys file manually. You confirm that you will ensure that repository and mirror settings are correct.",
"install.reinstall_confirm_check_3": "您確認您絕對肯定此 Gitea 在正確的 app.ini 位置上執行,而且您確定您必須重新安裝。您確認您瞭解上述風險。",
"install.err_empty_db_path": "SQLite3 資料庫路徑不可以為空。",
"install.no_admin_and_disable_registration": "您不能夠在未建立管理員使用者的情況下禁止註冊。",
"install.err_empty_admin_password": "管理員密碼不能為空。",
"install.err_empty_admin_email": "The administrator email address cannot be empty.",
"install.err_admin_name_is_reserved": "Administrator username is invalid. Username is reserved.",
"install.err_admin_name_pattern_not_allowed": "Administrator username is invalid. The username matches a reserved pattern.",
"install.err_admin_name_is_invalid": "Administrator username is invalid",
"install.general_title": "一般設定",
"install.app_name": "網站標題",
"install.app_name_helper": "您可以在此輸入您的公司名稱。",
"install.default_language": "Default Language",
"install.default_language_helper": "Used when a user's browser language does not match an available locale.",
"install.repo_path": "儲存庫的根目錄",
"install.repo_path_helper": "所有遠端 Git 儲存庫會儲存到此目錄。",
"install.lfs_path": "Git LFS 根目錄",
@@ -220,6 +231,7 @@
"install.ssh_port": "SSH 伺服器埠",
"install.ssh_port_helper": "SSH 伺服器使用的埠號,留空以停用此設定。",
"install.http_port": "Gitea HTTP 埠",
"install.http_port_helper": "Port number the Gitea web server will listen on.",
"install.app_url": "Gitea 基本 URL",
"install.app_url_helper": "用於 HTTP(S) Clone 和電子郵件通知的基本網址。",
"install.log_root_path": "日誌路徑",
@@ -233,15 +245,33 @@
"install.smtp_from_helper": "Gitea 將會使用的電子信箱,直接輸入電子信箱或使用「\"名稱\" <email@example.com>」的格式。",
"install.mailer_user": "SMTP 帳號",
"install.mailer_password": "SMTP 密碼",
"install.test_mail_to": "Send Testing Email",
"install.test_mail_missing_host": "Please enter the SMTP host before testing email delivery.",
"install.test_mail_missing_recipient": "Please enter a recipient email address before testing email delivery.",
"install.registration_title": "Registration Management",
"install.registration_mode": "Registration Mode",
"install.registration_mode.admin_only": "Administrator-managed accounts only",
"install.registration_mode.admin_only_helper": "Disable self-registration and let administrators create new accounts using the selected administrator-created account mode.",
"install.admin_created_account_mode": "Administrator-Created Account Mode",
"install.admin_created_account_mode.local": "Create local accounts directly",
"install.admin_created_account_mode.local_helper": "Creates active local accounts immediately. Administrators can optionally notify the user by email after creation.",
"install.admin_created_account_mode.invite": "Create invitation-based accounts",
"install.admin_created_account_mode.invite_helper": "Creates inactive accounts with sign-in disabled until the user accepts the emailed invitation link.",
"install.registration_mode.local_only": "Local registration only",
"install.registration_mode.local_only_helper": "Allow new accounts only through Gitea's built-in registration form.",
"install.registration_mode.external_only": "External registration only",
"install.registration_mode.external_only_helper": "Disable the local registration form and accept new accounts only from external identity providers.",
"install.registration_mode.local_and_external": "Local and external registration",
"install.registration_mode.local_and_external_helper": "Allow new accounts through both Gitea's local registration form and external identity providers.",
"install.registration_local_options": "Local Registration Options",
"install.registration_external_options": "External Registration Options",
"install.register_confirm": "要求註冊時確認電子郵件",
"install.register_confirm_helper": "Require users to verify their email address before they can continue.",
"install.register_manual_confirm": "Require Administrator Approval After Email Validation",
"install.register_manual_confirm_helper": "New accounts stay pending until an administrator reviews and approves the request.",
"install.mail_notify": "啟用郵件通知",
"install.mail_notify_helper": "Controls routine notification emails such as watches, mentions, and administrative notices. Activation and invitation emails still use the SMTP configuration above.",
"install.server_service_title": "伺服器和第三方服務設定",
"install.offline_mode": "啟用本地模式",
"install.offline_mode_popup": "停用其他服務並在本地提供所有資源。",
"install.disable_gravatar": "停用 Gravatar",
"install.disable_gravatar_popup": "停用 Gravatar 和其他大頭貼服務。除非使用者在本地上傳大頭貼,否則將使用預設的大頭貼。",
"install.federated_avatar_lookup": "啟用 Federated Avatars",
"install.federated_avatar_lookup_popup": "使用 Libravatar 以啟用 Federated Avatar 查詢服務",
"install.disable_registration": "關閉註冊功能",
"install.disable_registration_popup": "關閉註冊功能,只有管理員可以新增帳戶。",
"install.allow_only_external_registration_popup": "只允許從外部服務註冊",
@@ -249,6 +279,8 @@
"install.openid_signin_popup": "啟用 OpenID 登入",
"install.openid_signup": "啟用 OpenID 註冊",
"install.openid_signup_popup": "啟用基於 OpenID 的註冊",
"install.openid_signin_helper": "Allow users to sign in through OpenID providers.",
"install.openid_signup_helper": "Allow new accounts to be created through OpenID providers.",
"install.enable_captcha": "在註冊時啟用驗證碼",
"install.enable_captcha_popup": "要求在用戶註冊時輸入驗證碼",
"install.require_sign_in_view": "需要登入才能瀏覽頁面",
@@ -259,6 +291,13 @@
"install.admin_password": "管理員密碼",
"install.confirm_password": "確認密碼",
"install.admin_email": "電子信箱",
"install.admin_management_policy": "Administration Management Policy",
"install.admin_management_policy.super_admin_only": "Only super admins manage admins",
"install.admin_management_policy.super_admin_only_helper": "Regular admins can manage only non-admin accounts. Any admin-to-admin change or deletion requires a super administrator.",
"install.admin_management_policy.grantor_only": "Grantor manages promoted admins",
"install.admin_management_policy.grantor_only_helper": "Regular admins can promote users to administrator and can later modify or delete only the administrators they directly promoted.",
"install.admin_management_policy.grantor_inheritance": "Grantor chain with inheritance",
"install.admin_management_policy.grantor_inheritance_helper": "Like grantor-only, but if the direct grantor becomes inactive or has sign-in disabled, management passes up the admin grant chain until an eligible admin is found. If none is found, super admins keep control.",
"install.install_btn_confirm": "安裝 Gitea",
"install.test_git_failed": "無法識別「git」命令:%v",
"install.sqlite3_not_available": "您目前的版本不支援 SQLite3,請從 %s 下載官方的預先編譯版本 (不是 gobuild 版本)。",
@@ -266,7 +305,6 @@
"install.invalid_db_table": "資料庫的資料表「%s」無效: %v",
"install.invalid_repo_path": "儲存庫根目錄設定不正確:%v",
"install.invalid_app_data_path": "無效的應用程式資料路徑:%v",
"install.run_user_not_match": "「以...執行」的使用者名稱不是目前的使用者名稱:%s -> %s",
"install.internal_token_failed": "產生內部 Token 失敗:%v",
"install.secret_key_failed": "產生密鑰失敗:%v",
"install.save_config_failed": "儲存設定失敗:%v",
@@ -282,6 +320,7 @@
"install.no_reply_address_helper": "作為隱藏電子信箱使用者的域名。例如,如果隱藏的電子信箱域名設定為「noreply.example.org」,帳號「joe」將以「joe@noreply.example.org」的身分登錄到 Git 中。",
"install.password_algorithm": "密碼雜湊演算法",
"install.invalid_password_algorithm": "無效的密碼雜湊演算法",
"install.password_algorithm_helper": "Set the password hashing algorithm. Algorithms have differing requirements and strengths. The argon2 algorithm is rather secure but uses a lot of memory and may be inappropriate for small systems.",
"install.enable_update_checker": "啟用更新檢查器",
"install.enable_update_checker_helper": "定期連線到 gitea.io 檢查更新。",
"install.env_config_keys": "環境組態設定",
@@ -331,6 +370,9 @@
"auth.sign_up_now": "還沒有帳戶?馬上註冊。",
"auth.sign_up_successful": "帳戶已成功建立。歡迎您!",
"auth.confirmation_mail_sent_prompt_ex": "新的確認信已寄到<b>%s</b>。請在接下來的 %s 確認您的收件夾來完成註冊手續。如果您的註冊地址有錯誤,您可以再次登入並修改它。",
"auth.confirmation_mail_pending_signup": "A confirmation email has already been sent to <b>%s</b>. Please activate it before creating another account.",
"auth.confirmation_mail_resend_failed": "The confirmation email could not be sent. Please try again later or contact an administrator.",
"auth.confirmation_mail_resend_not_available": "This account can no longer receive confirmation emails.",
"auth.must_change_password": "更新您的密碼",
"auth.allow_password_change": "要求使用者更改密碼 (推薦)",
"auth.reset_password_mail_sent_prompt": "確認信已發送至 <b>%s</b>。請在 %s內檢查您的收件匣並完成帳戶救援作業。",
@@ -2610,6 +2652,7 @@
"admin.users.created": "建立時間",
"admin.users.last_login": "上次登入",
"admin.users.send_register_notify": "寄送使用者註冊通知",
"admin.users.send_register_invite": "Send User Registration Invitation",
"admin.users.new_success": "已建立新帳戶「%s」。",
"admin.users.edit": "編輯",
"admin.users.auth_source": "認證來源",
@@ -3297,5 +3340,15 @@
"git.filemode.normal_file": "一般檔案",
"git.filemode.executable_file": "可執行檔",
"git.filemode.symbolic_link": "符號連結",
"git.filemode.submodule": "子模組"
"git.filemode.submodule": "子模組",
"auth.accept_your_invitation": "Accept Your Invitation",
"auth.invitation_mail_pending_login": "An invitation email has already been sent to <b>%s</b>. Please accept it before signing in.",
"auth.invitation_mail_sent_prompt_ex": "A new invitation email has been sent to <b>%s</b>. Please use the link within the next %s to activate your account.",
"auth.invitation_mail_resend_failed": "The invitation email could not be sent. Please try again later or contact an administrator.",
"auth.invitation_mail_resend_not_available": "This account can no longer receive invitation emails.",
"auth.invitation_resend_prompt": "Did not receive the invitation email?",
"auth.invitation_resend_button": "Resend",
"admin.users.send_register_notify_helper": "The account will be activated and validated immediately.",
"admin.users.send_register_invite_helper": "The user must accept the emailed invitation before the account becomes active.",
"install.language_balloon": "Choose a language"
}
+8 -3
View File
@@ -59,7 +59,7 @@
"pdfobject": "2.3.1",
"perfect-debounce": "2.1.0",
"postcss": "8.5.8",
"rollup-plugin-license": "3.7.0",
"rolldown-license-plugin": "2.2.0",
"sortablejs": "1.15.7",
"swagger-ui-dist": "5.32.1",
"tailwindcss": "3.4.19",
@@ -73,8 +73,7 @@
"vite-string-plugin": "2.0.2",
"vue": "3.5.31",
"vue-bar-graph": "2.2.0",
"vue-chartjs": "5.3.3",
"wrap-ansi": "10.0.0"
"vue-chartjs": "5.3.3"
},
"devDependencies": {
"@eslint-community/eslint-plugin-eslint-comments": "4.7.1",
@@ -153,5 +152,11 @@
"string.prototype.includes": "npm:@nolyfill/string.prototype.includes@^1",
"string.prototype.trimend": "npm:@nolyfill/string.prototype.trimend@^1"
}
},
"scripts": {
"0-codex-gpt-login": "./.codex_gpt_login.sh",
"1-configure-buid": "./.configure.sh",
"2-update-gitea": "./.update-gitea.sh",
"3-smart-build": "./.smart-build.sh"
}
}
Symlink
+1
View File
@@ -0,0 +1 @@
/usr/bin/pnpm
+8 -361
View File
@@ -185,9 +185,9 @@ importers:
postcss:
specifier: 8.5.8
version: 8.5.8
rollup-plugin-license:
specifier: 3.7.0
version: 3.7.0(picomatch@4.0.4)(rollup@4.60.1)
rolldown-license-plugin:
specifier: 2.2.0
version: 2.2.0
sortablejs:
specifier: 1.15.7
version: 1.15.7
@@ -230,9 +230,6 @@ importers:
vue-chartjs:
specifier: 5.3.3
version: 5.3.3(chart.js@4.5.1)(vue@3.5.31(typescript@6.0.2))
wrap-ansi:
specifier: 10.0.0
version: 10.0.0
devDependencies:
'@eslint-community/eslint-plugin-eslint-comments':
specifier: 4.7.1
@@ -1235,144 +1232,6 @@ packages:
'@rolldown/pluginutils@1.0.0-rc.2':
resolution: {integrity: sha512-izyXV/v+cHiRfozX62W9htOAvwMo4/bXKDrQ+vom1L1qRuexPock/7VZDAhnpHCLNejd3NJ6hiab+tO0D44Rgw==}
'@rollup/rollup-android-arm-eabi@4.60.1':
resolution: {integrity: sha512-d6FinEBLdIiK+1uACUttJKfgZREXrF0Qc2SmLII7W2AD8FfiZ9Wjd+rD/iRuf5s5dWrr1GgwXCvPqOuDquOowA==}
cpu: [arm]
os: [android]
'@rollup/rollup-android-arm64@4.60.1':
resolution: {integrity: sha512-YjG/EwIDvvYI1YvYbHvDz/BYHtkY4ygUIXHnTdLhG+hKIQFBiosfWiACWortsKPKU/+dUwQQCKQM3qrDe8c9BA==}
cpu: [arm64]
os: [android]
'@rollup/rollup-darwin-arm64@4.60.1':
resolution: {integrity: sha512-mjCpF7GmkRtSJwon+Rq1N8+pI+8l7w5g9Z3vWj4T7abguC4Czwi3Yu/pFaLvA3TTeMVjnu3ctigusqWUfjZzvw==}
cpu: [arm64]
os: [darwin]
'@rollup/rollup-darwin-x64@4.60.1':
resolution: {integrity: sha512-haZ7hJ1JT4e9hqkoT9R/19XW2QKqjfJVv+i5AGg57S+nLk9lQnJ1F/eZloRO3o9Scy9CM3wQ9l+dkXtcBgN5Ew==}
cpu: [x64]
os: [darwin]
'@rollup/rollup-freebsd-arm64@4.60.1':
resolution: {integrity: sha512-czw90wpQq3ZsAVBlinZjAYTKduOjTywlG7fEeWKUA7oCmpA8xdTkxZZlwNJKWqILlq0wehoZcJYfBvOyhPTQ6w==}
cpu: [arm64]
os: [freebsd]
'@rollup/rollup-freebsd-x64@4.60.1':
resolution: {integrity: sha512-KVB2rqsxTHuBtfOeySEyzEOB7ltlB/ux38iu2rBQzkjbwRVlkhAGIEDiiYnO2kFOkJp+Z7pUXKyrRRFuFUKt+g==}
cpu: [x64]
os: [freebsd]
'@rollup/rollup-linux-arm-gnueabihf@4.60.1':
resolution: {integrity: sha512-L+34Qqil+v5uC0zEubW7uByo78WOCIrBvci69E7sFASRl0X7b/MB6Cqd1lky/CtcSVTydWa2WZwFuWexjS5o6g==}
cpu: [arm]
os: [linux]
libc: [glibc]
'@rollup/rollup-linux-arm-musleabihf@4.60.1':
resolution: {integrity: sha512-n83O8rt4v34hgFzlkb1ycniJh7IR5RCIqt6mz1VRJD6pmhRi0CXdmfnLu9dIUS6buzh60IvACM842Ffb3xd6Gg==}
cpu: [arm]
os: [linux]
libc: [musl]
'@rollup/rollup-linux-arm64-gnu@4.60.1':
resolution: {integrity: sha512-Nql7sTeAzhTAja3QXeAI48+/+GjBJ+QmAH13snn0AJSNL50JsDqotyudHyMbO2RbJkskbMbFJfIJKWA6R1LCJQ==}
cpu: [arm64]
os: [linux]
libc: [glibc]
'@rollup/rollup-linux-arm64-musl@4.60.1':
resolution: {integrity: sha512-+pUymDhd0ys9GcKZPPWlFiZ67sTWV5UU6zOJat02M1+PiuSGDziyRuI/pPue3hoUwm2uGfxdL+trT6Z9rxnlMA==}
cpu: [arm64]
os: [linux]
libc: [musl]
'@rollup/rollup-linux-loong64-gnu@4.60.1':
resolution: {integrity: sha512-VSvgvQeIcsEvY4bKDHEDWcpW4Yw7BtlKG1GUT4FzBUlEKQK0rWHYBqQt6Fm2taXS+1bXvJT6kICu5ZwqKCnvlQ==}
cpu: [loong64]
os: [linux]
libc: [glibc]
'@rollup/rollup-linux-loong64-musl@4.60.1':
resolution: {integrity: sha512-4LqhUomJqwe641gsPp6xLfhqWMbQV04KtPp7/dIp0nzPxAkNY1AbwL5W0MQpcalLYk07vaW9Kp1PBhdpZYYcEw==}
cpu: [loong64]
os: [linux]
libc: [musl]
'@rollup/rollup-linux-ppc64-gnu@4.60.1':
resolution: {integrity: sha512-tLQQ9aPvkBxOc/EUT6j3pyeMD6Hb8QF2BTBnCQWP/uu1lhc9AIrIjKnLYMEroIz/JvtGYgI9dF3AxHZNaEH0rw==}
cpu: [ppc64]
os: [linux]
libc: [glibc]
'@rollup/rollup-linux-ppc64-musl@4.60.1':
resolution: {integrity: sha512-RMxFhJwc9fSXP6PqmAz4cbv3kAyvD1etJFjTx4ONqFP9DkTkXsAMU4v3Vyc5BgzC+anz7nS/9tp4obsKfqkDHg==}
cpu: [ppc64]
os: [linux]
libc: [musl]
'@rollup/rollup-linux-riscv64-gnu@4.60.1':
resolution: {integrity: sha512-QKgFl+Yc1eEk6MmOBfRHYF6lTxiiiV3/z/BRrbSiW2I7AFTXoBFvdMEyglohPj//2mZS4hDOqeB0H1ACh3sBbg==}
cpu: [riscv64]
os: [linux]
libc: [glibc]
'@rollup/rollup-linux-riscv64-musl@4.60.1':
resolution: {integrity: sha512-RAjXjP/8c6ZtzatZcA1RaQr6O1TRhzC+adn8YZDnChliZHviqIjmvFwHcxi4JKPSDAt6Uhf/7vqcBzQJy0PDJg==}
cpu: [riscv64]
os: [linux]
libc: [musl]
'@rollup/rollup-linux-s390x-gnu@4.60.1':
resolution: {integrity: sha512-wcuocpaOlaL1COBYiA89O6yfjlp3RwKDeTIA0hM7OpmhR1Bjo9j31G1uQVpDlTvwxGn2nQs65fBFL5UFd76FcQ==}
cpu: [s390x]
os: [linux]
libc: [glibc]
'@rollup/rollup-linux-x64-gnu@4.60.1':
resolution: {integrity: sha512-77PpsFQUCOiZR9+LQEFg9GClyfkNXj1MP6wRnzYs0EeWbPcHs02AXu4xuUbM1zhwn3wqaizle3AEYg5aeoohhg==}
cpu: [x64]
os: [linux]
libc: [glibc]
'@rollup/rollup-linux-x64-musl@4.60.1':
resolution: {integrity: sha512-5cIATbk5vynAjqqmyBjlciMJl1+R/CwX9oLk/EyiFXDWd95KpHdrOJT//rnUl4cUcskrd0jCCw3wpZnhIHdD9w==}
cpu: [x64]
os: [linux]
libc: [musl]
'@rollup/rollup-openbsd-x64@4.60.1':
resolution: {integrity: sha512-cl0w09WsCi17mcmWqqglez9Gk8isgeWvoUZ3WiJFYSR3zjBQc2J5/ihSjpl+VLjPqjQ/1hJRcqBfLjssREQILw==}
cpu: [x64]
os: [openbsd]
'@rollup/rollup-openharmony-arm64@4.60.1':
resolution: {integrity: sha512-4Cv23ZrONRbNtbZa37mLSueXUCtN7MXccChtKpUnQNgF010rjrjfHx3QxkS2PI7LqGT5xXyYs1a7LbzAwT0iCA==}
cpu: [arm64]
os: [openharmony]
'@rollup/rollup-win32-arm64-msvc@4.60.1':
resolution: {integrity: sha512-i1okWYkA4FJICtr7KpYzFpRTHgy5jdDbZiWfvny21iIKky5YExiDXP+zbXzm3dUcFpkEeYNHgQ5fuG236JPq0g==}
cpu: [arm64]
os: [win32]
'@rollup/rollup-win32-ia32-msvc@4.60.1':
resolution: {integrity: sha512-u09m3CuwLzShA0EYKMNiFgcjjzwqtUMLmuCJLeZWjjOYA3IT2Di09KaxGBTP9xVztWyIWjVdsB2E9goMjZvTQg==}
cpu: [ia32]
os: [win32]
'@rollup/rollup-win32-x64-gnu@4.60.1':
resolution: {integrity: sha512-k+600V9Zl1CM7eZxJgMyTUzmrmhB/0XZnF4pRypKAlAgxmedUA+1v9R+XOFv56W4SlHEzfeMtzujLJD22Uz5zg==}
cpu: [x64]
os: [win32]
'@rollup/rollup-win32-x64-msvc@4.60.1':
resolution: {integrity: sha512-lWMnixq/QzxyhTV6NjQJ4SFo1J6PvOX8vUx5Wb4bBPsEb+8xZ89Bz6kOXpfXj9ak9AHTQVQzlgzBEc1SyM27xQ==}
cpu: [x64]
os: [win32]
'@rtsao/scc@1.1.0':
resolution: {integrity: sha512-zt6OdqaDoOnJ1ZYsCYGt9YmWzDXl4vQdKTyJev62gFhRGKdx7mcT54V9KIjg+d2wi9EXsPvAPKe7i7WjfVWB8g==}
@@ -1892,10 +1751,6 @@ packages:
resolution: {integrity: sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==}
engines: {node: '>=8'}
ansi-styles@6.2.3:
resolution: {integrity: sha512-4Dj6M28JB+oAH8kFkTLUo+a2jwOFkuqb3yucU0CANcRRUbxS0cP0nZYCGjcc3BNXwRIsUVmDGgzawme7zvJHvg==}
engines: {node: '>=12'}
ansi_up@6.0.6:
resolution: {integrity: sha512-yIa1x3Ecf8jWP4UWEunNjqNX6gzE4vg2gGz+xqRGY+TBSucnYp6RRdPV4brmtg6bQ1ljD48mZ5iGSEj7QEpRKA==}
@@ -1916,10 +1771,6 @@ packages:
resolution: {integrity: sha512-COROpnaoap1E2F000S62r6A60uHZnmlvomhfyT2DlTcrY1OrBKn2UhH7qn5wTC9zMvD0AY7csdPSNwKP+7WiQw==}
engines: {node: '>= 0.4'}
array-find-index@1.0.2:
resolution: {integrity: sha512-M1HQyIXcBGtVywBt8WVdim+lrNaK7VHp99Qt5pSNziXznKHViIBbXWtfRTpEFpF/c4FdfxNAsCCwPp5phBYJtw==}
engines: {node: '>=0.10.0'}
asciinema-player@3.15.1:
resolution: {integrity: sha512-agVYeNlPxthLyAb92l9AS7ypW0uhesqOuQzyR58Q4Sj+MvesQztZBgx86lHqNJkB8rQ6EP0LeA9czGytQUBpYw==}
@@ -2113,9 +1964,6 @@ packages:
resolution: {integrity: sha512-ObxuY6vnbWTN6Od72xfwN9DbzC7Y2vv8u1Soi9ahRKL37gb6y1qk6/dgjs+3JWuXJHWvsg3BXIwzd/rkmAwavg==}
engines: {node: '>= 12.0.0'}
commenting@1.1.0:
resolution: {integrity: sha512-YeNK4tavZwtH7jEgK1ZINXzLKm6DZdEMfsaaieOsCAN0S8vsY7UeuO3Q7d/M018EFgE+IeUAuBOKkFccBZsUZA==}
compare-versions@6.1.1:
resolution: {integrity: sha512-4hm4VPpIecmlg59CHXnRDnqGplJFrbLG4aFEl5vl6cK1u76ws3LLvX7ikFnTDl5vo39sjWD6AaDPYodJp/NNHg==}
@@ -3385,9 +3233,6 @@ packages:
mlly@1.8.2:
resolution: {integrity: sha512-d+ObxMQFmbt10sretNDytwt85VrbkhhUA/JBGm1MPaWJ65Cl4wOgLaB1NYvJSZ0Ef03MMEU/0xpPMXUIQ29UfA==}
moment@2.30.1:
resolution: {integrity: sha512-uEmtNhbDOrWPFS+hdjFCBfy9f2YoyzRpwcl+DqpC6taX21FzsTLQVbMV/W7PzNSX6x/bhC1zA3c2UQ5NzH6how==}
moo@0.5.3:
resolution: {integrity: sha512-m2fmM2dDm7GZQsY7KK2cme8agi+AAljILjQnof7p1ZMDe6dQ4bdnSMx0cPppudoeNv5hEFQirN6u+O4fDE0IWA==}
@@ -3478,10 +3323,6 @@ packages:
package-manager-detector@1.6.0:
resolution: {integrity: sha512-61A5ThoTiDG/C8s8UMZwSorAGwMJ0ERVGj2OjoW5pAalsNOg15+iQiPzrLJ4jhZ1HJzmC2PIHT2oEiH3R5fzNA==}
package-name-regex@2.0.6:
resolution: {integrity: sha512-gFL35q7kbE/zBaPA3UKhp2vSzcPYx2ecbYuwv1ucE9Il6IIgBDweBlH8D68UFGZic2MkllKa2KHCfC1IQBQUYA==}
engines: {node: '>=12'}
parent-module@1.0.1:
resolution: {integrity: sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==}
engines: {node: '>=6'}
@@ -3706,22 +3547,14 @@ packages:
robust-predicates@3.0.3:
resolution: {integrity: sha512-NS3levdsRIUOmiJ8FZWCP7LG3QpJyrs/TE0Zpf1yvZu8cAJJ6QMW92H1c7kWpdIHo8RvmLxN/o2JXTKHp74lUA==}
rolldown-license-plugin@2.2.0:
resolution: {integrity: sha512-7a/v9/9o5/pCpPtx4WSX68/xHC8wmmR/cxkofWQ7I7ep5Tvhjb9KkIUdTyuKc52SHiGSz2PxrS0qm/z2PjJyiQ==}
rolldown@1.0.0-rc.12:
resolution: {integrity: sha512-yP4USLIMYrwpPHEFB5JGH1uxhcslv6/hL0OyvTuY+3qlOSJvZ7ntYnoWpehBxufkgN0cvXxppuTu5hHa/zPh+A==}
engines: {node: ^20.19.0 || >=22.12.0}
hasBin: true
rollup-plugin-license@3.7.0:
resolution: {integrity: sha512-RvvOIF+GH3fBR3wffgc/vmjQn6qOn72WjppWVDp/v+CLpT0BbcRBdSkPeeIOL6U5XccdYgSIMjUyXgxlKEEFcw==}
engines: {node: '>=14.0.0'}
peerDependencies:
rollup: ^1.0.0 || ^2.0.0 || ^3.0.0 || ^4.0.0
rollup@4.60.1:
resolution: {integrity: sha512-VmtB2rFU/GroZ4oL8+ZqXgSA38O6GR8KSIvWmEFv63pQ0G6KaBH9s07PO8XTXP4vI+3UJUEypOfjkGfmSBBR0w==}
engines: {node: '>=18.0.0', npm: '>=8.0.0'}
hasBin: true
roughjs@4.6.6:
resolution: {integrity: sha512-ZUz/69+SYpFN/g/lUlo2FXcIjRkSu3nDarreVdGGndHEBJ6cXPdKguS8JGxwj5HA5xIbVKSmLgr5b3AWxtRfvQ==}
@@ -3805,27 +3638,6 @@ packages:
resolution: {integrity: sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==}
engines: {node: '>=0.10.0'}
spdx-compare@1.0.0:
resolution: {integrity: sha512-C1mDZOX0hnu0ep9dfmuoi03+eOdDoz2yvK79RxbcrVEG1NO1Ph35yW102DHWKN4pk80nwCgeMmSY5L25VE4D9A==}
spdx-exceptions@2.5.0:
resolution: {integrity: sha512-PiU42r+xO4UbUS1buo3LPJkjlO7430Xn5SVAhdpzzsPHsjbYVflnnFdATgabnLude+Cqu25p6N+g2lw/PFsa4w==}
spdx-expression-parse@3.0.1:
resolution: {integrity: sha512-cbqHunsQWnJNE6KhVSMsMeH5H/L9EpymbzqTQ3uLwNCLZ1Q481oWaofqH7nO6V07xlXwY6PhQdQ2IedWx/ZK4Q==}
spdx-expression-validate@2.0.0:
resolution: {integrity: sha512-b3wydZLM+Tc6CFvaRDBOF9d76oGIHNCLYFeHbftFXUWjnfZWganmDmvtM5sm1cRwJc/VDBMLyGGrsLFd1vOxbg==}
spdx-license-ids@3.0.23:
resolution: {integrity: sha512-CWLcCCH7VLu13TgOH+r8p1O/Znwhqv/dbb6lqWy67G+pT1kHmeD/+V36AVb/vq8QMIQwVShJ6Ssl5FPh0fuSdw==}
spdx-ranges@2.1.1:
resolution: {integrity: sha512-mcdpQFV7UDAgLpXEE/jOMqvK4LBoO0uTQg0uvXUewmEFhpiZx5yJSZITHB8w1ZahKdhfZqP5GPEOKLyEq5p8XA==}
spdx-satisfies@5.0.1:
resolution: {integrity: sha512-Nwor6W6gzFp8XX4neaKQ7ChV4wmpSh2sSDemMFSzHxpTw460jxFYeOn+jq4ybnSSw/5sc3pjka9MQPouksQNpw==}
spectral-cli-bundle@1.0.7:
resolution: {integrity: sha512-vIUC0nwv9tYxWV1xHdR3CTVDOEEtLKaDCcQpARZgO0Db7VmSpSWJ4xrnVPNSmO59hBtGwW2CVzHf0OimJBaKAA==}
engines: {node: '>=20'}
@@ -4256,10 +4068,6 @@ packages:
resolution: {integrity: sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==}
engines: {node: '>=0.10.0'}
wrap-ansi@10.0.0:
resolution: {integrity: sha512-SGcvg80f0wUy2/fXES19feHMz8E0JoXv2uNgHOu4Dgi2OrCy1lqwFYEJz1BLbDI0exjPMe/ZdzZ/YpGECBG/aQ==}
engines: {node: '>=20'}
write-file-atomic@7.0.1:
resolution: {integrity: sha512-OTIk8iR8/aCRWBqvxrzxR0hgxWpnYBblY1S5hDWBQfk/VFmJwzmJgQFN3WsoUKHISv2eAwe+PpbUzyL1CKTLXg==}
engines: {node: ^20.17.0 || >=22.9.0}
@@ -5205,81 +5013,6 @@ snapshots:
'@rolldown/pluginutils@1.0.0-rc.2': {}
'@rollup/rollup-android-arm-eabi@4.60.1':
optional: true
'@rollup/rollup-android-arm64@4.60.1':
optional: true
'@rollup/rollup-darwin-arm64@4.60.1':
optional: true
'@rollup/rollup-darwin-x64@4.60.1':
optional: true
'@rollup/rollup-freebsd-arm64@4.60.1':
optional: true
'@rollup/rollup-freebsd-x64@4.60.1':
optional: true
'@rollup/rollup-linux-arm-gnueabihf@4.60.1':
optional: true
'@rollup/rollup-linux-arm-musleabihf@4.60.1':
optional: true
'@rollup/rollup-linux-arm64-gnu@4.60.1':
optional: true
'@rollup/rollup-linux-arm64-musl@4.60.1':
optional: true
'@rollup/rollup-linux-loong64-gnu@4.60.1':
optional: true
'@rollup/rollup-linux-loong64-musl@4.60.1':
optional: true
'@rollup/rollup-linux-ppc64-gnu@4.60.1':
optional: true
'@rollup/rollup-linux-ppc64-musl@4.60.1':
optional: true
'@rollup/rollup-linux-riscv64-gnu@4.60.1':
optional: true
'@rollup/rollup-linux-riscv64-musl@4.60.1':
optional: true
'@rollup/rollup-linux-s390x-gnu@4.60.1':
optional: true
'@rollup/rollup-linux-x64-gnu@4.60.1':
optional: true
'@rollup/rollup-linux-x64-musl@4.60.1':
optional: true
'@rollup/rollup-openbsd-x64@4.60.1':
optional: true
'@rollup/rollup-openharmony-arm64@4.60.1':
optional: true
'@rollup/rollup-win32-arm64-msvc@4.60.1':
optional: true
'@rollup/rollup-win32-ia32-msvc@4.60.1':
optional: true
'@rollup/rollup-win32-x64-gnu@4.60.1':
optional: true
'@rollup/rollup-win32-x64-msvc@4.60.1':
optional: true
'@rtsao/scc@1.1.0': {}
'@scarf/scarf@1.4.0': {}
@@ -5925,8 +5658,6 @@ snapshots:
dependencies:
color-convert: 2.0.1
ansi-styles@6.2.3: {}
ansi_up@6.0.6: {}
any-promise@1.3.0: {}
@@ -5942,8 +5673,6 @@ snapshots:
aria-query@5.3.2: {}
array-find-index@1.0.2: {}
asciinema-player@3.15.1:
dependencies:
'@babel/runtime': 7.29.2
@@ -6112,8 +5841,6 @@ snapshots:
comment-parser@1.4.6: {}
commenting@1.1.0: {}
compare-versions@6.1.1: {}
concat-map@0.0.1: {}
@@ -7556,8 +7283,6 @@ snapshots:
pkg-types: 1.3.1
ufo: 1.6.3
moment@2.30.1: {}
moo@0.5.3: {}
ms@2.1.3: {}
@@ -7627,8 +7352,6 @@ snapshots:
package-manager-detector@1.6.0: {}
package-name-regex@2.0.6: {}
parent-module@1.0.1:
dependencies:
callsites: 3.1.0
@@ -7815,6 +7538,8 @@ snapshots:
robust-predicates@3.0.3: {}
rolldown-license-plugin@2.2.0: {}
rolldown@1.0.0-rc.12(@emnapi/core@1.9.1)(@emnapi/runtime@1.9.1):
dependencies:
'@oxc-project/types': 0.122.0
@@ -7839,51 +7564,6 @@ snapshots:
- '@emnapi/core'
- '@emnapi/runtime'
rollup-plugin-license@3.7.0(picomatch@4.0.4)(rollup@4.60.1):
dependencies:
commenting: 1.1.0
fdir: 6.5.0(picomatch@4.0.4)
lodash: 4.17.23
magic-string: 0.30.21
moment: 2.30.1
package-name-regex: 2.0.6
rollup: 4.60.1
spdx-expression-validate: 2.0.0
spdx-satisfies: 5.0.1
transitivePeerDependencies:
- picomatch
rollup@4.60.1:
dependencies:
'@types/estree': 1.0.8
optionalDependencies:
'@rollup/rollup-android-arm-eabi': 4.60.1
'@rollup/rollup-android-arm64': 4.60.1
'@rollup/rollup-darwin-arm64': 4.60.1
'@rollup/rollup-darwin-x64': 4.60.1
'@rollup/rollup-freebsd-arm64': 4.60.1
'@rollup/rollup-freebsd-x64': 4.60.1
'@rollup/rollup-linux-arm-gnueabihf': 4.60.1
'@rollup/rollup-linux-arm-musleabihf': 4.60.1
'@rollup/rollup-linux-arm64-gnu': 4.60.1
'@rollup/rollup-linux-arm64-musl': 4.60.1
'@rollup/rollup-linux-loong64-gnu': 4.60.1
'@rollup/rollup-linux-loong64-musl': 4.60.1
'@rollup/rollup-linux-ppc64-gnu': 4.60.1
'@rollup/rollup-linux-ppc64-musl': 4.60.1
'@rollup/rollup-linux-riscv64-gnu': 4.60.1
'@rollup/rollup-linux-riscv64-musl': 4.60.1
'@rollup/rollup-linux-s390x-gnu': 4.60.1
'@rollup/rollup-linux-x64-gnu': 4.60.1
'@rollup/rollup-linux-x64-musl': 4.60.1
'@rollup/rollup-openbsd-x64': 4.60.1
'@rollup/rollup-openharmony-arm64': 4.60.1
'@rollup/rollup-win32-arm64-msvc': 4.60.1
'@rollup/rollup-win32-ia32-msvc': 4.60.1
'@rollup/rollup-win32-x64-gnu': 4.60.1
'@rollup/rollup-win32-x64-msvc': 4.60.1
fsevents: 2.3.3
roughjs@4.6.6:
dependencies:
hachure-fill: 0.5.2
@@ -7958,33 +7638,6 @@ snapshots:
source-map-js@1.2.1: {}
spdx-compare@1.0.0:
dependencies:
array-find-index: 1.0.2
spdx-expression-parse: 3.0.1
spdx-ranges: 2.1.1
spdx-exceptions@2.5.0: {}
spdx-expression-parse@3.0.1:
dependencies:
spdx-exceptions: 2.5.0
spdx-license-ids: 3.0.23
spdx-expression-validate@2.0.0:
dependencies:
spdx-expression-parse: 3.0.1
spdx-license-ids@3.0.23: {}
spdx-ranges@2.1.1: {}
spdx-satisfies@5.0.1:
dependencies:
spdx-compare: 1.0.0
spdx-expression-parse: 3.0.1
spdx-ranges: 2.1.1
spectral-cli-bundle@1.0.7:
optionalDependencies:
fsevents: 2.3.3
@@ -8453,12 +8106,6 @@ snapshots:
word-wrap@1.2.5: {}
wrap-ansi@10.0.0:
dependencies:
ansi-styles: 6.2.3
string-width: 8.2.0
strip-ansi: 7.2.0
write-file-atomic@7.0.1:
dependencies:
signal-exit: 4.1.0
+10 -2
View File
@@ -27,6 +27,7 @@ import (
container_module "code.gitea.io/gitea/modules/packages/container"
"code.gitea.io/gitea/modules/setting"
"code.gitea.io/gitea/modules/storage"
"code.gitea.io/gitea/modules/structs"
"code.gitea.io/gitea/modules/util"
"code.gitea.io/gitea/routers/api/packages/helper"
auth_service "code.gitea.io/gitea/services/auth"
@@ -125,8 +126,15 @@ func APIUnauthorizedError(ctx *context.Context) {
// container registry requires that the "/v2" must be in the root, so the sub-path in AppURL should be removed
realmURL := httplib.GuessCurrentHostURL(ctx) + "/v2/token"
ctx.Resp.Header().Add("WWW-Authenticate", `Bearer realm="`+realmURL+`",service="container_registry",scope="*"`)
// support apple container like: container registry login <gitea-host> -u
ctx.Resp.Header().Add("WWW-Authenticate", `Basic realm="Gitea Container Registry"`)
ownerName := ctx.PathParam("username")
owner, _ := user_model.GetUserByName(ctx, ownerName)
requireSignIn := owner != nil && owner.Visibility != structs.VisibleTypePublic
requireSignIn = requireSignIn || setting.Service.RequireSignInViewStrict
if requireSignIn {
// support apple container like: container registry login <gitea-host> -u
ctx.Resp.Header().Add("WWW-Authenticate", `Basic realm="Gitea Container Registry"`)
}
apiErrorDefined(ctx, errUnauthorized)
}
+30 -21
View File
@@ -9,6 +9,7 @@ import (
"fmt"
"io"
"net/http"
"net/url"
"strings"
"time"
@@ -220,30 +221,38 @@ func UploadPackageFile(ctx *context.Context) {
func DownloadPackageFile(ctx *context.Context) {
name := ctx.PathParam("name")
version := ctx.PathParam("version")
architecture := ctx.PathParam("architecture")
group := ctx.PathParam("group")
s, u, pf, err := packages_service.OpenFileForDownloadByPackageNameAndVersion(
ctx,
&packages_service.PackageInfo{
Owner: ctx.Package.Owner,
PackageType: packages_model.TypeRpm,
Name: name,
Version: version,
},
&packages_service.PackageFileInfo{
Filename: fmt.Sprintf("%s-%s.%s.rpm", name, version, ctx.PathParam("architecture")),
CompositeKey: ctx.PathParam("group"),
},
ctx.Req.Method,
)
if err != nil {
if errors.Is(err, util.ErrNotExist) {
apiError(ctx, http.StatusNotFound, err)
} else {
apiError(ctx, http.StatusInternalServerError, err)
}
return
openForDownload := func(filename string) (io.ReadSeekCloser, *url.URL, *packages_model.PackageFile, error) {
return packages_service.OpenFileForDownloadByPackageNameAndVersion(
ctx,
&packages_service.PackageInfo{
Owner: ctx.Package.Owner,
PackageType: packages_model.TypeRpm,
Name: name,
Version: version,
},
&packages_service.PackageFileInfo{
Filename: filename,
CompositeKey: group,
},
ctx.Req.Method,
)
}
s, u, pf, err := openForDownload(fmt.Sprintf("%s-%s.%s.rpm", name, version, architecture))
if errors.Is(err, util.ErrNotExist) && architecture != "noarch" {
s, u, pf, err = openForDownload(fmt.Sprintf("%s-%s.%s.rpm", name, version, "noarch"))
}
if errors.Is(err, util.ErrNotExist) {
apiError(ctx, http.StatusNotFound, err)
return
} else if err != nil {
apiError(ctx, http.StatusInternalServerError, err)
return
}
helper.ServePackageFile(ctx, s, u, pf)
}

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