Commit Graph
122 Commits
Author SHA1 Message Date
xvkong233 40240ed02b fix(nat): strip only dashboard-issued Authorization credentials at NAT ingress
Since 2640b86 (v2.2.11, 2026-07-20) the NAT ingress deleted the entire
Authorization header, breaking self-hosted apps behind the tunnel that
authenticate with their own Bearer tokens (e.g. the Qinglong panel login
loop).

Strip only credentials issued by this dashboard and forward foreign ones:

- controller.IsDashboardCredential classifies an Authorization value as
  dashboard-issued via a signature-only JWT parser derived from the auth
  middleware (same key, HS256 pinned, claims validation deliberately
  skipped so an expired panel token is still recognized and kept out of
  the tunnel) or an api_tokens lookup for PAT-shaped values. Unknown PATs,
  foreign signatures, other schemes and missing values pass through. When
  classification cannot complete (parser not ready, DB nil or error) the
  verdict fails closed (strip) and the log carries a fixed reason only,
  never credential content.
- Both NAT capability variants (default, and agent-compat legacy /
  invalid-capability / post-consume paths) replace the unconditional
  Del("Authorization") with stripDashboardCredential. The rpc package
  receives the classifier through SetNATDashboardCredentialGate, the same
  injection pattern as SetMCPKillSwitchObserver; an unwired gate keeps the
  historical strip-everything behavior.

Tests: controller classification semantics (panel JWT, expired panel JWT
and panel PAT stripped; foreign-signed JWT, unknown nzp_ token, random
strings, non-Bearer schemes and missing header pass through; parser
unavailable, DB nil and DB error fail closed with credential-free logs)
plus rpc unit and flow coverage for both variants (dashboard credentials
never reach the forwarded bytes; foreign and missing Authorization are
forwarded untouched).

Compatibility: no API, database or frontend changes; NAT backends that do
not use Authorization behave exactly as before.
2026-10-01 11:17:45 +00:00
naibaandnaiba/CloudCode 2640b86d3a feat(agentcompat): expose dashboard capability routes
Co-authored-by: naiba/CloudCode <hi+cloudcode@nai.ba>
2026-07-20 04:30:50 +00:00
naiba 083bc985c5 feat(auth): split inventory scope out of server scope
Carve a new nezha:inventory:{read,delete,*} resource family out of
nezha:server:*. Listing and deleting servers/server-groups (GET /server,
/server-group, /ws/server, batch-delete/server[-group], MCP server.list)
now require nezha:inventory:*, while nezha:server:* covers per-server
runtime operations (get, exec, fs, config, metrics, batch-move,
force-update).

Also declare MCP tool OutputSchema for exec/fs/meta/server/transfer and
wrap server.list output in {servers,count} so strict MCP clients accept
the structured result. Correct the /file all-of scope entry and the stale
server:read documentation.
2026-05-31 15:14:41 +00:00
naibaandcloudcode e8dabf5bc6 feat(auth): add PAT auth, scoped REST/MCP access, CSRF, and tenant isolation
Introduce Personal Access Tokens (nzp_*) as a stateless auth path alongside
JWT, gated per-endpoint by a scope middleware (nezha:{resource}:{verb}) with
fail-closed empty-scope defaults and a server-id whitelist. Self-management
endpoints (profile, api-tokens, oauth2 bind, refresh-token) explicitly reject
PATs to block privilege-escalation chains. A revoke registry tears down active
long-lived connections (terminal, fm, ws, transfer, mcp) the moment a PAT is
deleted, with a tombstone closing the revoke->register race.

Add an MCP endpoint that proxies tool calls (exec, fs read/write/delete,
transfer) to agents over gRPC, guarded by origin/DNS-rebinding checks, a
per-token rate limiter, audit logging, and a kill switch. Serialize all
sends through the IOStream wrapper to honour grpc-go's concurrency contract.

Add CSRF double-submit protection on unsafe cookie-authenticated methods,
exempting authenticated PAT requests by context identity (not a forgeable
Authorization header). Apply visibility/whitelist filtering consistently
across list, get-by-id, and mutate paths to enforce tenant isolation.

Migrate legacy mcp:* scopes: rewrite read/exec to nezha:* equivalents and
drop dangerous write/delete/wildcard grants.

Co-authored-by: cloudcode <cloudcode@users.noreply.github.com>
2026-05-30 15:56:44 +00:00
naibaandcloudcode a4f4cb1f34 fix(fm): switch create FM session to POST to defeat CSRF
GET /api/v1/file?id=<server> created an FM stream on the agent stream
and committed real state change (TaskTypeFM dispatched). With JWT
cookie SameSite=Lax a victim's browser would still send the cookie on
a top-level cross-site GET, so an attacker could trick a logged-in
user into opening an FM session on any of their own servers, consuming
resources and triggering the agent's FM machinery without consent.

Mirror the GHSA-8qhj-4f8c-j8qg fix: move the route to POST. SameSite=
Lax cookies are not sent on cross-site POST. Frontend (admin-frontend)
adjusted in a follow-up commit.

Co-authored-by: cloudcode <cloudcode@users.noreply.github.com>
2026-05-26 04:07:49 +00:00
naibaandcloudcode 9c0fa84c95 fix(cron): switch manual trigger to POST to defeat CSRF
GHSA-8qhj-4f8c-j8qg: GET /api/v1/cron/:id/manual changed shared state
on the agent stream, and the JWT cookie is SameSite=Lax so a victim's
browser would send the cookie on a top-level cross-site GET. An
attacker could trick a logged-in user into firing any of their own
cron commands.

Switch the route to POST: SameSite=Lax cookies are not sent on cross-
site POST, closing the CSRF window without introducing a new token.

Tests:
- TestCronManualTriggerRejectsCrossSiteGET locks in that GET no longer
  resolves.
- TestCronManualTriggerAcceptsSameSitePOST locks in the legitimate POST
  still works.

Frontend (admin-frontend) updated in a follow-up commit.

Co-authored-by: cloudcode <cloudcode@users.noreply.github.com>
2026-05-26 03:59:50 +00:00
naiba 6b88cdb012 feat: server transfer rotation 2026-05-25 10:17:34 +00:00
naibaandnaiba/CloudCode 2573ba7522 fix(controller): restrict waf and online-user listings to admins
Co-authored-by: naiba/CloudCode <hi+cloudcode@nai.ba>
2026-05-17 10:24:19 +08:00
3d0c9b963c feat(v2.0.0): tsdb (#1162)
* feat: tsdb

* fix(ci): remove --parseGoList=false from swag init to fix dependency resolution

* fix(ci): fix swag init directory and temporary remove s390x support due to cgo issues

* fix(ci): fix swag init output directory to cmd/dashboard/docs

* fix(ci): set GOTOOLCHAIN=auto for gosec

* feat: add system storage maintenance for SQLite and TSDB

* shit

* feat: add s390x support and improve service monitoring

* ci: upgrade goreleaser-cross image to v1.25

* ci: add libzstd-dev:s390x for cross-compilation

* ci: build libzstd for s390x from source

* ci: add libzstd_linux_s390x.go for gozstd linking

* ci: use vendor mode for s390x gozstd build

* ci: clone zstd source for s390x build

* refactor(tsdb): rename MaxDiskUsageGB to MinFreeDiskSpaceGB and optimize queries

- Rename config to accurately reflect VictoriaMetrics behavior: minimum free disk space threshold
- Add QueryServiceHistoryByServerID for batch query optimization
- Fix hasStatus to avoid false status counting when only delay data exists
- Fix service aggregation boundary: use successCount*2 >= count
- Fix serviceID parsing with strconv.ParseUint error handling
- Add TagFiltersCacheSize for better query performance

* feat(api): add server metrics endpoint and simplify service history response

- Add /server/:id/metrics API for querying TSDB server metrics
- Simplify getServiceHistory by removing redundant data conversion
- Change AvgDelay type from float32 to float64
- Remove generated swagger docs (to be regenerated)
- Update TSDB query, writer and tests

* chore: 临时禁用不支持前端

* ci: cache zstd build for s390x to speed up CI

* fix(tsdb): fix race conditions, data correctness and optimize performance

- Fix TOCTOU race between IsClosed() and write/query by holding RLock
- Fix delay=0 excluded from stats by using hasDelay flag instead of value > 0
- Fix fmt.Sscanf -> strconv.ParseUint for server_id parsing with error logging
- Fix buffer unbounded growth by flushing inside lock when over maxSize
- Split makeMetricRow into makeServerMetricRow/makeServiceMetricRow
- Extract InitGlobalSettings() from Open() for VictoriaMetrics globals
- Remove redundant instance/GetInstance/SetInstance singleton
- Add error logging for silently skipped block decode errors
- Optimize WriteBatch* to build all rows in single write call
- Optimize downsample to use linear scan instead of map for sorted data
- Optimize query slice reuse across block iterations

* 服务添加DisplayIndex (#1166)

* 服务添加DisplayIndex

* 根据ai建议修改

---------

Co-authored-by: huYang <306061454@qq.com>

* fix(tsdb): restore SQLite fallback and monthly status reload on restart

- Restore ServiceHistory model and SQLite write fallback when TSDB is disabled
- Reload monthlyStatus (30-day) and serviceStatusToday from TSDB/SQLite on startup
- Add SQLite fallback query for /service/:id/history and /server/:id/service
- Remove breaking GET /service/:id endpoint, keep /service/:id/history only
- Add QueryServiceDailyStats to TSDB for per-day aggregation
- Add tests for monthly status and today stats loading from both TSDB and SQLite
- Migrate ServiceHistory table only when TSDB is disabled

* ci: exclude false-positive gosec rules G117, G703, G704

* feat(api): expose tsdb_enabled in setting response

* ci: restore G115 exclusion accidentally dropped in previous commit

* fix: update version numbers for OfficialAdmin and Official templates

* chore: upgrade frontend

* chore: upgrade frontend

---------

Co-authored-by: 胡说丷刂 <34758853+laosan-xx@users.noreply.github.com>
Co-authored-by: huYang <306061454@qq.com>
2026-02-15 13:13:33 +08:00
UUBulb 010ae7ef51 fix: member-created services shouldn't be applied to admin resources (#1113) 2025-08-28 22:37:44 +08:00
naiba 233bbc23b6 feat: 批量转移服务器给其他用户 2025-06-16 23:46:36 +08:00
UUBulb 043d6c4097 feat: update to go1.24 & support listening https (#1002)
* feat: support listening https

* refactor

* modernize

* support snake case in config

* more precise control of config fields

* update goreleaser config

* remove kubeyaml

* fix: expose agent_secret

* chore
2025-02-28 22:02:54 +08:00
UUBulb eeb96caf4d feat: batch set server config (#983)
* feat: batch set server config

* run in parallel

* fix route

* fix

* return some information

* fix order
2025-02-04 11:25:49 +08:00
UUBulb b75a49c3c6 feat: edit server config online (#980)
* feat: edit server config online

* clean

* refactor

* generate template

* fix deadlocks

* fix
2025-01-31 13:33:53 +08:00
UUBulb ec6b9b9b43 feat: option to force authorization for vistor routes (#971) 2025-01-29 19:27:57 +08:00
naiba 2c9d514527 feat: implement client-side status code handling 2025-01-05 23:53:04 +08:00
naiba cd311b4ae6 feat: v1.5.2 2025-01-01 01:02:02 +08:00
UUBulb 178d847836 fix windows ci (#934)
* fix windows ci

* perm

* use custom writer

* remove patches

* fuck codeql
2025-01-01 00:58:57 +08:00
naiba 8836d11c22 Merge branch 'master' of github.com:nezhahq/nezha 2024-12-31 23:58:49 +08:00
naiba fcb0ced018 improve: 404 status code 2024-12-31 23:58:44 +08:00
UUBulb 3d591fae78 fix: struct tag (#932)
* fix: struct tag

* fix: struct tag

* fix: strings conversion

* do not write anything after redirection

* fix table

* fix select
2024-12-31 23:09:58 +08:00
UUBulb 2d03c61f38 fix: oauth2 redirect url not consistent (#930)
* fix: oauth2 redirect url not consistent

* only use one redirect uri

* feat: allow to disable password authentication

* generate translation template

* update error

* redirect

* query
2024-12-31 22:29:29 +08:00
naiba ea60a513b8 fix: home page 404 2024-12-30 21:25:22 +08:00
quanljh 3cce0b03ca fix: return 404 when page not found (#927) 2024-12-30 20:43:37 +08:00
naiba 8b9afbf39c feat: 绑定 oauth2 2024-12-28 23:50:59 +08:00
UUBulb fa30df0320 feat: support id query for "list" apis (#908)
* feat: support id query for "list" apis

* gosec
2024-12-24 23:23:01 +08:00
仓鼠 2dd53c7f38 fix: batch-block online-user request method (#903) 2024-12-22 23:18:08 +08:00
naiba 6dea3e19d2 feat: list & block online users 2024-12-22 01:08:07 +08:00
UUBulb dc0132c9aa feat: user roles (#852)
* [WIP] feat: user roles

* update

* update

* admin handler

* update

* feat: user-specific connection secret

* simplify some logics

* cleanup

* update waf

* update user api error handling

* update waf api

* fix codeql

* update waf table

* fix several problems

* add pagination for waf api

* update permission checks

* switch to runtime check

* 1

* cover?

* some changes
2024-12-22 00:05:41 +08:00
naiba d0b5549cdb feat: enhance template configuration and update README for translation status 2024-12-10 22:27:06 +08:00
naiba 55a867d077 feat: v1.1 2024-12-07 01:18:34 +08:00
naiba dd964f3b26 feat: multi user template 2024-12-06 23:19:28 +08:00
UUBulb 4ddad9ea00 fix service api (#556)
* fix service api

* update ServiceResponseItem

* fix: ddns lock
2024-12-05 21:00:02 +08:00
naiba 21b40fbcb7 fix: windows path issue 2024-11-30 00:02:45 +08:00
naiba 844947f89b fix: home page 500 2024-11-29 22:49:17 +08:00
naiba 9ba3a4fb2b feat: embed dist 2024-11-29 21:31:39 +08:00
naiba 04f33eb4f9 Revert "Fix code scanning alert no. 23: Uncontrolled data used in path expression (#486)"
This reverts commit c2b3d19a51.
2024-11-28 20:38:02 +08:00
naibaandCopilot Autofix powered by AI 8f44c76e4f Fix code scanning alert no. 23: Uncontrolled data used in path expression (#486)
Co-authored-by: Copilot Autofix powered by AI <62310815+github-advanced-security[bot]@users.noreply.github.com>
2024-11-28 20:26:51 +08:00
naiba a7e4fe0909 rename repo 2024-11-28 19:38:54 +08:00
UUBulb 4fed62db46 send country code in ws, update profile api (#22)
* send country code in ws

* make ddns_profiles optional field

* update profile api
2024-11-26 21:30:56 +08:00
UUBulb e465134c11 update profile api (#16)
* update profile api

* rename

* fix realip assertion

* add waf api
2024-11-23 16:22:22 +08:00
naiba 909cd92e9a feat: waf 🤡 2024-11-22 23:57:25 +08:00
naiba f5776c7464 feat: grpc / web get real ip 2024-11-22 00:19:36 +08:00
UUBulb 1c3fd9af1c add force update server api (#13) 2024-11-20 21:36:21 +08:00
naiba 551e826a35 fix: update refresh token endpoint to use hyphen 2024-11-08 23:57:15 +08:00
naiba 323f4d25c2 feat: profile api 2024-11-03 23:28:10 +08:00
uubulb d56224a118 feat: add i18n support 2024-11-01 05:07:04 +08:00
UUBulbandnaiba 029457831d add "network page" api (#460)
* add network api

* a minor change

* only show service name if unauthorized

* update

* 除了 load/初始化 避免在 singleton 进行查询等操作

---------

Co-authored-by: naiba <hi@nai.ba>
2024-10-27 14:43:37 +08:00
UUBulb 70b914d535 add setting api (#461) 2024-10-27 13:10:07 +08:00
UUBulb 8bfe70d519 add cron, nat api & refactor alert rule (#459)
* add cron api & refactor alert rule

* add nat api

* fix swagger

* remove unnecessary steps
2024-10-26 23:57:47 +08:00