Files
doris/ui/package.json
c800f2aa61 [feature](ui) Add the new Web UI foundation (#66690)
### What problem does this PR solve?

Issue Number: N/A (draft for early design review)

Related PR: N/A

Problem Summary:

The earlier revisions of this draft added the React application under
`ui-next/` next to the legacy AngularJS `ui/`, so the new UI was never
produced
by a normal build. Reviewers and users had to pass `CUSTOM_UI_DIST` by
hand,
and the packaged default was still the legacy application.

This revision finishes that transition instead of maintaining two
applications:
the React application takes over the `ui/` directory, the AngularJS
application is removed, and `./build.sh --fe` produces the new UI with
no flag
and no change to `build.sh`.

### What changed in the latest revision

- `ui/` now holds the React application; the AngularJS sources are
deleted and
  the `ui-next/` directory name is gone. `build_ui()` already builds
  `${DORIS_HOME}/ui` and packs `${DORIS_HOME}/ui/dist` into the FE
resources, so no build script change is required. `CUSTOM_UI_DIST` still
  works for callers that package a prebuilt directory.
- `@testing-library/dom` is now an explicit dev dependency. React
Testing
  Library only lists it as a peer dependency and re-exports `screen`,
`fireEvent`, `waitFor` and `within` from it, while `build_ui()` installs
with
`--legacy-peer-deps`, which does not install peer dependencies. Without
the
explicit entry the production build fails to type-check every test file.
- `enable_web_ui` now defaults to `true`. It gated the UI routes and the
SPA
forward while the new UI was optional; leaving it `false` would ship a
build
  whose packaged UI answers 404 on every page.
- Also in this revision: the Playground toolbar and
object-tree refinements, and restoring the resolved identity in the
cookie
authentication path so `checkAdminAuth` no longer sees a null user. The
  branch is rebased on master.

### Implemented scope

- English-only login and logout. A Doris user must have global `ADMIN`
  privilege to use UI Next.
- Home version information and complete frontend/backend node status
tables.
- SQL Playground with formatting, a database/table/column object tree,
and
FE-managed JDBC sessions that preserve SQL session state across
statements.
Restored browser session IDs are verified with the owning FE before the
UI
  reports the connection as ready.
- System proc navigation backed by the existing `/rest/v1/system` API.
- Active Sessions backed by the existing `/rest/v1/session` API.
- Log configuration, content, and verbose logger management backed by
the
  existing `/rest/v1/log` API.
- Query Profile list and raw Text details backed by the existing
current-FE
`/rest/v1/query_profile*` APIs. Only `Task Type: QUERY` entries are
shown.
- Visual Profile for structurally compatible `MergedProfile` text.
Parsing is
performed in a bounded browser Worker, ELK produces the compound
Fragment
layout, and React Flow renders the read-only DAG. Missing
`MergedProfile`
data is reported as unavailable; incompatible data reports the parse
reason
  instead of relying on a hard Doris-version gate.
- FE and BE Configuration tables backed by the existing manager
configuration
  APIs. Mutable rows expose an ADMIN-only editor; immutable rows remain
  read-only, including against direct mutation requests.

### FE backend scope

The FE addition remains limited to behavior that cannot live safely in
the
browser:

- Login and logout reuse `/rest/v1/login` and `/rest/v1/logout`. A thin
`/rest/v1/ui/me` endpoint bootstraps the authenticated ADMIN user and
CSRF
  token.
- Home, System, Sessions, Log, Query Profiles, and Configuration reuse
existing
  Doris HTTP controllers rather than adding parallel read controllers.
- Web SQL retains FE-local session ownership, one persistent JDBC
connection
per active session, execution/cancellation, bounded results, idle
cleanup,
  and logout cleanup. It is exposed as the UI-independent
  `/rest/v1/sql-sessions` API under `org.apache.doris.httpv2.websql`.
- Web SQL accepts HTTP Basic authentication or the existing Doris login
cookie;
both require global `ADMIN`. Cookie mutations additionally require CSRF.
- The existing Configuration manager endpoints now accept the
authenticated UI
cookie, preserve ADMIN authorization, use cluster-internal
authentication for
FE/BE fan-out, encode configuration values safely, and reject immutable
FE
  changes server-side.
- `enable_web_ui=true` is an immutable FE-local master switch for UI
routes,
assets, login/bootstrap, and stateful SQL endpoints. Setting it to
`false`
returns 404 for those resources without stopping port 8030 or shared FE
HTTP
  APIs.
- `enable_web_sql_session`, `web_sql_session_idle_timeout_seconds`,
`web_sql_max_sessions`, and `web_sql_max_result_bytes` are mutable.
Running
Web SQL operations read their current values without an FE restart.
Numeric
session limits reject non-positive values; the result-byte limit accepts
  1 through 100 MiB.
- `StatementSubmitter` and the legacy Login controller remain unchanged
from
this PR's master baseline. The legacy Log mutation adds only a cookie
CSRF
  check; its existing log behavior and response remain unchanged.

The Visual Profile parser and graph are adapted from
`apache/doris-website`
PR #4043 at commit `133f948c235995a917b2e1f6d4e9d764b6d62726` under the
Apache License 2.0. The website uploader, AI analysis, hCaptcha,
polling,
storage, recovery, and Docusaurus wrapper are not included.

### FE endpoints used by the UI

Enumerated from `ui/src/api/**`, split by whether the endpoint is added
here or
reused from existing Doris controllers.

Added by this PR:

| Endpoint | Method | Purpose |
| --- | --- | --- |
| `/rest/v1/ui/me` | GET | Bootstrap after login: current ADMIN user and
CSRF token (`UiSessionController`) |
| `/rest/v1/sql-sessions` | POST | Create a Web SQL session
(`WebSqlSessionController`) |
| `/rest/v1/sql-sessions/{id}` | GET, DELETE | Inspect and close a
session |
| `/rest/v1/sql-sessions/{id}/statements` | POST | Execute exactly one
statement |
| `/rest/v1/sql-sessions/{id}/cancel` | POST | Cancel the running
statement |
| `/rest/v1/sql-sessions/{id}/reset` | POST | Reset the connection state
|
| `/rest/v1/hardware_info/fe/version` | GET | Version-only route on the
existing `HardwareInfoController`, so Home does not trigger OSHI
hardware collection |

Reused, no new controller:

| Endpoint | Method | Page | Controller |
| --- | --- | --- | --- |
| `/rest/v1/login` | POST | Login | `WebConfigurer` |
| `/rest/v1/logout` | POST | Sign out | `WebConfigurer` |
| `/rest/v1/system?path=/frontends` | GET | Cluster Overview, Frontends
| `SystemController` |
| `/rest/v1/system?path=/backends` | GET | Cluster Overview, Backends |
`SystemController` |
| `/rest/v1/system?path=...` | GET | Proc System navigation |
`SystemController` |
| `/rest/v1/session` | GET | Sessions | `SessionController` |
| `/rest/v1/log` | GET | Log configuration and contents |
`LogController` |
| `/rest/v1/log` | POST | Add or delete a verbose logger, sent as the
legacy `add_verbose` / `del_verbose` form parameters | `LogController` |
| `/rest/v1/query_profile` | GET | Query Profile list |
`QueryProfileAction` |
| `/rest/v1/query_profile/text/{queryId}` | GET | Raw profile text,
shared by the Text and Visual tabs | `QueryProfileAction` |
| `/rest/v2/manager/node/configuration_info?type={fe\|be}` | POST |
Configuration read | `NodeAction` |
| `/rest/v2/manager/node/set_config/{fe\|be}` | POST | Configuration
update, ADMIN only | `NodeAction` |

`/rest/v1/ui/**` and `/rest/v1/sql-sessions**` go through `uiRequest`,
which
requires the login cookie and sends the CSRF header on mutations.
Everything
else goes through `legacyRequest` and retains each legacy controller's
existing
authorization behavior. The PR-added `/rest/v1/ui/**` and Web SQL
endpoints
require global `ADMIN`; reused legacy endpoints are not all globally
ADMIN-only. Web SQL additionally accepts HTTP Basic.

### Behavior and impact

- The FE web port now serves the React application. The AngularJS
application
  is no longer part of the repository, so a legacy build is no longer a
  rollback option; reverting this change is.
- Node.js 22.12 or newer and npm are required to build FE. The
repository's
  x86, gcc10 and ARM compilation images are updated to provide Node.js
  22.12.0. Neither Node.js nor npm is required at runtime.
- Web SQL sessions remain behind `enable_web_sql_session`.

### Validation

- `./build.sh --fe` with no flags builds the React application and packs
it:
the resulting `doris-fe.jar` `static/` payload matches `ui/dist` file
for
  file.
- `npm run lint`, `npm run typecheck`, `npm run test` and `npm run
build` in
  `ui/`.
- The branch is rebased on master and merges cleanly.

### Release note

The Doris FE Web UI is replaced with a new React application. Repository
compilation images now provide Node.js 22.12.0; the ARM image uses
AlmaLinux 8
because the official Node.js 22 ARM64 binary requires a newer glibc than
CentOS 7 provides.

### Check List (For Author)

- Test
    - [ ] Regression test
    - [x] Unit Test
- [x] Manual test (development and packaging steps are documented in
`ui/README.md`)
    - [ ] No need to test or manual test. Explain why:
- Behavior changed:
    - [ ] No.
- [x] Yes. The FE web port serves the new UI, and the AngularJS UI is
removed.
- Does this need documentation?
- [x] No. Development and packaging instructions are included in
`ui/README.md`.
    - [ ] Yes.

### Follow-up

- Add CI coverage for the UI directory. No workflow currently runs its
lint,
  typecheck, test or build, so frontend regressions cannot fail a build.
- Split the production bundle further; Vite currently reports large ELK
and
  application chunks.

---------

Co-authored-by: Ragnaroos <Ragnaroos@users.noreply.github.com>
Co-authored-by: Claude Opus 5 (1M context) <noreply@anthropic.com>
Co-authored-by: morningman <yunyou@selectdb.com>
2026-08-30 19:19:25 +08:00

53 lines
1.4 KiB
JSON

{
"name": "@apache-doris/ui",
"private": true,
"version": "0.1.0",
"type": "module",
"engines": {
"node": ">=22.12.0"
},
"scripts": {
"dev": "vite --host 0.0.0.0",
"build": "tsc -b && vite build",
"preview": "vite preview",
"lint": "eslint . --max-warnings 0",
"typecheck": "tsc -b --pretty false",
"test": "vitest run",
"test:watch": "vitest",
"test:e2e": "playwright test"
},
"dependencies": {
"@codemirror/lang-sql": "6.10.0",
"@codemirror/view": "6.43.8",
"@tanstack/react-query": "5.101.4",
"@uiw/react-codemirror": "4.25.11",
"@xyflow/react": "12.11.2",
"antd": "6.6.0",
"elkjs": "0.12.0",
"react": "19.2.8",
"react-dom": "19.2.8",
"react-router-dom": "7.18.2",
"sql-formatter": "15.8.2"
},
"devDependencies": {
"@eslint/js": "9.39.2",
"@playwright/test": "1.62.1",
"@testing-library/dom": "10.4.1",
"@testing-library/jest-dom": "7.0.1",
"@testing-library/react": "16.3.2",
"@types/node": "24.10.13",
"@types/react": "19.2.14",
"@types/react-dom": "19.2.3",
"@vitejs/plugin-react": "6.0.5",
"eslint": "9.39.2",
"eslint-plugin-react-hooks": "7.0.1",
"eslint-plugin-react-refresh": "0.4.26",
"globals": "17.3.0",
"jsdom": "30.0.1",
"typescript": "5.9.3",
"typescript-eslint": "8.67.0",
"vite": "8.2.1",
"vitest": "4.1.10"
}
}