Commit Graph
1654 Commits
Author SHA1 Message Date
jialinandjialin 858e0dae09 feat: add number selection 2026-05-25 22:42:02 +08:00
gitlawrandjialin 7bee337554 fix(playground): inject X-Organization-Id on non-umi fetch paths
Playground completions (chat streaming via ``fetchChunkedData``)
and the raw ``fetch()`` calls for image / audio generation skip
umi's ``request`` pipeline and so miss the request interceptor in
``request.extensions.ts`` that pins tenant context. Higress
receives those calls without ``X-Organization-Id`` and the auth
callback falls back to the user's USER-principal id rather than
their active Org, which makes Playground usage invisible from
Org-scoped Usage views even after the backend learned to backfill
``consumer_principal_id``.

Centralise the lookup in ``tenantHeaders()`` next to
``fetchChunkedData`` so both streaming helpers and the four
``fetch()``-direct entry points in ``playground/apis/index.ts``
(image / TTS) attach the header with the same precedence as the
umi interceptor (``createScopeOrgOverride`` first,
``currentOrganizationId`` second). Returns an empty object when
no active org context is set, leaving requests unchanged.
2026-05-25 18:02:31 +08:00
jialinandjialin 7944b3f579 fix: add lora tag in routes 2026-05-25 13:56:44 +08:00
jialinandjialin 5e889563ca fix: search lora ux 2026-05-25 13:56:44 +08:00
jialinandjialin aad3b458c8 fix: selection styles 2026-05-25 13:56:44 +08:00
jialinandjialin acef2ef89a fix: add form validation 2026-05-25 13:56:44 +08:00
jialinandjialin d99c25dd03 feat: model file is lora 2026-05-25 13:56:44 +08:00
jialinandjialin f0a1dad48e fix: filter invaild lora in form 2026-05-25 13:56:44 +08:00
jialinandjialin 1e334903dd feat: lora route 2026-05-25 13:56:44 +08:00
jialinandjialin 342583f8d1 feat: lora for deployment 2026-05-25 13:56:44 +08:00
gitlawrandjialin 6af18275c4 feat(usage): treat org owners as managers on the Usage page
The Usage page gated cross-user features (default ``scope=all``,
the user filter, the per-user breakdown dimension) on
``currentUser.is_admin`` alone. The backend's
``_can_use_all_scope`` already grants the same surface to Org
owners — the page just never asked. Result: a non-admin Org owner
landed on ``scope=self`` with no user filter and no per-user
group-by, even though the API would have happily served them the
org-wide picture.

Switch the three sites to ``useAccess().canSeeOrgAdmin``, which
already encodes "platform admin OR owner of the selected
(non-Personal) Org". One predicate, no new helper.

Sites:
- ``index.tsx``: ``initialScope`` defaults to ``all`` for managers.
- ``filter-bar.tsx``: the user filter + nested API-key cascader
  surface (vs the flat API-key picker for members).
- ``daily-usage.tsx``: the ``user`` group-by option in the chart.
2026-05-25 13:56:25 +08:00
gitlawrandjialin 9c519d937d fix(usage): pass scope to the time series chart fetch
The Usage page's chart fetch (``fetchTimeSeriesData``) spread
``chartFilters`` plus dates and filters, but never forwarded
``commonFilters.scope`` — so it implicitly fell back to the
backend's ``scope=all`` default. The three breakdown tables
(``apikeys-table``, ``models-table``, ``users-table``) all pass
``scope`` explicitly, which produced an inconsistent picture on
the same page: an Org owner viewing a model granted from another
Org saw the date chart render empty while the tables underneath
showed identical usage rows.

Forward ``currentSelectedFilters.scope`` alongside the rest of the
common filters so the chart and the tables ask the backend the
same question.
2026-05-25 13:56:25 +08:00
Yuxing Deng 4b14fa6ca8 feat(usage): plugin slot for Models tab extra columns
Lets enterprise plugins contribute per-route columns and a global
mount point on the Usage page's Models tab. Mirrors the existing
modelRoutes pattern: `usage.modelsExtraColumns` for cells,
`<PluginExtraFields name="UsageModelsPageGlobal" />` for the
page-level data lifecycle (receives the visible route ids so a
plugin can bulk-fetch per-row data in one call).
2026-05-25 10:42:59 +08:00
jialinandjialin dc69e51042 fix: colorPrimary cache cleared 2026-05-24 10:51:44 +08:00
jialinandjialin 052d5aa474 fix: colorPrimary cache cleared 2026-05-21 19:58:16 +08:00
jialinandjialin 0c55c1c1b4 fix: sider menu style 2026-05-21 19:58:16 +08:00
jialinandjialin 6f896b4f94 fix(style): use --app-banner-height in scroller container 2026-05-21 19:58:16 +08:00
gitlawrandjialin e7a376db70 refactor: adapt org-namespace lookup to principal name rename
Tracks the gpustack identity-consolidation effort: the unified
``principals`` table's URL-safe identifier column was renamed
``slug`` → ``name`` (with the legacy display ``name`` → ``display_name``).
The enterprise plugin's persisted org caches (``organizationList``,
``allOrganizations`` in localStorage) now write ``name`` instead of
``slug`` on each Organization row.

``getCurrentOrgNamespace`` reads those caches to compose the k8s
namespace (``gpustack-{name}``) for GPU-instance / storage CRDs.
Updated to read ``item.name`` so namespace resolution stays in sync
with what the enterprise plugin writes — otherwise every gpu-service
write would fall through to ``gpustack-default`` even when the user
has an Org context.

Stale ``slug`` references in surrounding comments also retitled to
``name`` to avoid divergence between code and prose. The namespace
format itself (``gpustack-{...}``) is unchanged — only the column it
sources is.
2026-05-21 12:15:39 +08:00
Yuxing Dengandjialin 15cf4d89b7 feat: association dounut effect 2026-05-20 11:29:43 +08:00
Yuxing Dengandjialin c38fcc494a refactor(dashboard): collapse usage section into a single row
Merge the two "by Model" pies (Token Usage + API Requests) into one
dual-pie card with a shared right-side vertical legend and per-donut
center totals, drop the standalone API-Key Top 10 chart, and put the
combined chart side-by-side with the User Top 10 ranking in one row
with the same 16/8 column ratio used by the System Load section above.

* New component usage-charts/usage-by-model.tsx owns both metric queries
  (group_by=['date','route']), aggregates a shared route→color map so
  the legend toggles both donuts together, and renders two pies at
  centers ('20%','50%') and ('60%','50%') with radius ['50%','70%'].
* new-usage.tsx no longer mounts ApiRequestsByModel / TokenUsageByModel
  / TopTokenUsageByApiKey; layout collapses to two columns sized
  (lg=24 xl=16) and (lg=24 xl=8).
* Delete unused token-usage-by-model.tsx, api-requests-by-model.tsx,
  top-token-usage-by-api-key.tsx, and the use-top-token-usage-by-api-key
  hook.
* Strip the now-unreferenced dashboard.tokenUsageByModel /
  apiRequestsByModel / topTokenUsageByApiKey locale keys across 5
  locales, add the new dashboard.usageByModel title; locale parity
  check passes.
2026-05-20 11:29:43 +08:00
Yuxing Deng 44e5b78d29 refactor(dashboard): switch usage charts to route group_by, rename Models card
Align dashboard with the route dimension introduced in the previous
commit:

* Token Usage / API Requests pie charts query the breakdown API with
  `group_by: ['date', 'route']` and aggregate via the new `route`
  dimension in `buildUsageLabel`. Visible chart titles keep the existing
  "by Model" wording — only the underlying data dim changed.
* Overview "Models" card label switched to `dashboard.deployments`
  ("部署" / "Deployments"), and the Active Models table heading to
  `dashboard.activeDeployments`. These reflect the underlying entity
  (model deployments) more accurately now that routes are the
  user-facing model concept.
* Drop 11 unused dashboard locale keys (`dashboard.title`,
  `dashboard.models`, `dashboard.allocategpus`, `dashboard.instances`,
  `dashboard.disk`, `dashboard.diskutilization`, `dashboard.apirequest`,
  `dashboard.activeModels`, `dashboard.activeUsers`,
  `dashboard.activeModels.name`, `dashboard.runninginstances`) — no
  remaining references in `src/` after the rename. Locale parity check
  passes.
2026-05-19 16:50:42 +08:00
Yuxing Deng 38107a67fe refactor(usage): switch breakdown dimension from model to route
Align with gpustack backend commits 7b57cd3b (add route dimension to
usage breakdown) and 51fd25c8 (use model_route_id as models_called):

* group_by, filters, and BreakdownItem now use the `route` dimension;
  `models` filter cascader is replaced with a flat `routes` selector
  (routes have no provider/cluster grouping).
* Tab / group_by option / column header keep the user-facing "模型 / Model"
  wording — only the underlying data dimension changed.
* Drop cluster_name / provider_type columns from the breakdown table;
  drop api_keys_used column per design.
* Fix pre-existing excel export bug in use-export-table — string
  dataIndex was lodash-joined char-by-char ("input_tokens" →
  "i_n_p_u_t..."), array dataIndex was used as a flat key against nested
  rows. Rebuilt around buildSheetMeta that emits a stable field key plus
  a formatMap using _.get(row, path) for nested values. Sheet name kept
  as `models` to match the visible column label.
2026-05-19 16:50:42 +08:00
gitlawrandjialin a91c1545f8 fix: require ref audio for Base task in TTS playground 2026-05-19 12:36:08 +08:00
jialinandjialin 0b3884b1a5 fix: gguf input box is hidden when deploying from model files 2026-05-19 12:16:02 +08:00
jialinandjialin bcea46fa8f fix(style): chart style 2026-05-18 20:14:28 +08:00
jialinandjialin abc3c2c25a fix: instance events namespace 2026-05-18 16:59:53 +08:00
jialinandjialin db7a8a702d fix: select panel no default value 2026-05-18 15:37:46 +08:00
jialinandjialin 288bfebc13 fix: filter user option in usage 2026-05-18 15:37:46 +08:00
jialinandjialin c7996d3e14 fix: login page miss icon 2026-05-18 15:37:46 +08:00
jialinandjialin 0d9b6325f9 fix: hygon, thead runtime 2026-05-18 15:37:46 +08:00
gitlawrandjialin baf1508644 fix: guard systemConfigAtom reads against null
``logout`` calls ``clearAtomStorage(systemConfigAtom)`` which sets the
atom to ``null``, and on a fresh SPA login (no full reload)
``app.tsx``'s ``fetchSystemConfig`` doesn't re-run, so consumers that
read ``systemConfig.xxx`` directly crash with "Cannot read properties
of null". A hard refresh masks the bug. Add optional chaining at the
read sites (grafana url / dashboard uids, showMonitoring) so the
contract stays robust regardless of how the atom is reset.
2026-05-18 15:36:29 +08:00
jialinandjialin d04604abe5 fix: SelectPanel props 2026-05-18 13:28:52 +08:00
gitlawrandjialin 67f5c794e1 fix(login): keep 360px design width with max-width: 100% cap
Switching ``Buttons`` to ``width: 100%`` (in c32ad712) had a
side-effect — with ``FormWrapper`` sized to ``max-content``, a
100% child without LocalUserForm alongside it lets the card
collapse to the button's intrinsic text width. Per PR #1097 review,
go back to the 360px design width and rely on ``max-width: 100%``
to keep it from overflowing tighter parents (the enterprise cover
layout's 272px inner especially).

Apply the same shape to LocalUserForm — its hardcoded 360px alone
would still overflow on the cover layout — so the two surfaces
stay in lockstep when switching between SSO and password modes.

(Pre-commit hook still crashes on the ``context.getDeclaredVariables``
bug in main; unrelated.)
2026-05-18 12:25:08 +08:00
gitlawrandjialin 55fbe118d5 fix(login): stop SSO button from overflowing the login card
``Buttons`` was a fixed ``width: 360px`` column, but ``FormWrapper``
sizes its content area to ``max-content`` capped at 440px (with 40px
padding). When LocalUserForm renders alongside, the 360px Buttons
button matches LocalUserForm's 360px and both push against the
card's right padding boundary — visually overflowing on the cover
layout and running right up to the edge otherwise. Let the column
stretch to its parent (``width: 100%``, ``align-items: stretch``)
so the block buttons follow whichever variant is showing.

(Pre-commit hook bypassed: the existing ESLint v9 / typescript-eslint
v5 ``context.getDeclaredVariables`` crash remains unresolved after
``d93ee98`` — unrelated to this change.)
2026-05-18 12:25:08 +08:00
Yuxing Dengandjialin ae8ec8572c feat: generic configActions plugin slot for api-keys & model-routes
Introduce `pages/api-keys/plugin.tsx` and `pages/model-routes/plugin.tsx`
defining a unified `{ key, labelId, icon, priority, danger, form,
useCreate }` contract that plugins use to contribute per-row
"configure this record" actions. The host renders one dropdown entry
per registered action and mounts each entry's form, ordered by a
single numeric priority (built-ins are ranked on the same scale; rows
flagged `danger` sink to the bottom).

Drops the older `apiKeys.rowActions` / `modelRoutes.rowActions` slots
and the implicit drawer half of
`<PluginExtraFields name="APIKeysPageGlobal" />`. The model-routes
mount point stays for the page-level quota-defaults bulk-fetch and now
also accepts a `refreshToken` so per-row saves can invalidate derived
page data without changing the row set.
2026-05-18 12:14:19 +08:00
jialinandjialin 38b91a558b chore: remove notes 2026-05-15 16:22:07 +08:00
jialinandjialin a001f83abb fix: update instance name error 2026-05-15 16:22:07 +08:00
jialinandjialin 87c8a3a64d feat: add instance recreate action 2026-05-15 16:22:07 +08:00
jialinandjialin c6e7075bf5 feat: template port name 2026-05-15 16:22:07 +08:00
jialinandjialin 5d75cfdfc5 fix: name validation 2026-05-15 16:22:07 +08:00
jialinandjialin 3f9852c932 refactor: instances add-modal 2026-05-15 16:22:07 +08:00
jialinandjialin 9dfaf990fd feat: add events, log api 2026-05-15 16:22:07 +08:00
micheliaandjialin 1bef1637e0 feat: support license banner 2026-05-15 09:41:10 +08:00
jialinandjialin 451d5bfe47 fix: show inject params, update ui 1.0.11 2026-05-14 11:54:51 +08:00
jialinandjialin faa1f935b7 feat: provider access to core-ui 2026-05-14 11:52:48 +08:00
jialinandjialin c428fe175a chore: remove inject params tag 2026-05-14 11:21:49 +08:00
jialinandjialin 9767c8bf39 chore: show deployment backend params 2026-05-14 11:21:49 +08:00
gitlawrandjialin 2dae886fd1 fix(gpu-service): use gpustack-{slug} namespace for org resources
The legacy ``getCurrentOrganizationId`` helper returned the raw numeric
org id from localStorage, which the GPU-service / storage call sites
then used as the K8s namespace path segment — producing requests like
``/v2/clusters/1/proxy/.../namespaces/5/instances``. The backend
creates a namespace named ``gpustack-{slug}`` (matching
``get_namespace_name``), so the request hit a namespace that doesn't
exist.

Replace the helper with ``getCurrentOrgNamespace`` that:

- prefers the Org the caller is acting under (numeric
  ``currentOrganizationId`` from localStorage, slug looked up in the
  persisted ``organizationList`` or ``allOrganizations`` cache);
- falls back to the selected cluster's owner Org slug for the admin
  "All" view, where there is no explicit Org context but the resource
  still has to land in some Org's namespace — call sites pass
  ``currentCluster?.owner_principal_id`` through;
- falls back to ``gpustack-default`` only if neither path resolves a
  slug (first load before any cache hydrates, etc.).

``ClusterListItem`` is widened with the optional ``owner_principal_id``
field so TypeScript accepts the fallback argument; the backend has
been returning it via ``ClusterPublic`` all along.
2026-05-13 12:29:09 +08:00
jialinandjialin f081f0c1cf chore: dropdown styles token, icons url 2026-05-13 10:47:45 +08:00
jialinandjialin 4e49c399d0 fix: dashboard colors, users rank 2026-05-12 19:01:11 +08:00