etherpad-lite/admin
John McLear 02e00ad615
fix(admin): restore SearchField + sorting modules used by AuthorPage (#7746)
* fix(admin): restore SearchField + sorting modules used by AuthorPage

PR #7736 ("replace hardcoded German strings with i18n keys") deleted
admin/src/components/SearchField.tsx and admin/src/utils/sorting.ts as
"orphan modules (no longer imported anywhere after #7716)". At that
point, the GDPR admin AuthorPage (PR #7667) had not yet landed on
develop. When #7667 merged afterwards, the new admin/src/pages/AuthorPage.tsx
brought back imports of SearchField and determineSorting — but the
files were already gone, leaving develop with broken admin imports.

This breaks `pnpm --filter admin run build-copy` on every CI job that
builds the admin UI:

  src/pages/AuthorPage.tsx(6,27): error TS2307: Cannot find module
    '../components/SearchField.tsx' or its corresponding type
    declarations.
  src/pages/AuthorPage.tsx(9,32): error TS2307: Cannot find module
    '../utils/sorting.ts' or its corresponding type declarations.
  src/pages/AuthorPage.tsx(207,29): error TS7006: Parameter 'v'
    implicitly has an 'any' type.

Backend tests, Frontend admin tests, Docker (build-test,
build-test-local-plugin, build-test-db-drivers), rate limit, and
Upgrade from latest release all fail at the admin build step on
develop.

Restore both files verbatim from before the deletion (commit ff7c4d531^).
With them back in place AuthorPage.tsx's existing imports resolve, the
implicit-any on the SearchField onChange callback goes away (typed via
SearchFieldProps), and `pnpm --filter admin run build-copy` succeeds.

This is the minimal, surgical fix; whether SearchField / determineSorting
should ultimately be inlined into AuthorPage is a separate cleanup.

Test plan:
  - cd admin && pnpm exec tsc --noEmit        → no errors
  - cd admin && pnpm exec tsc && pnpm exec vite build → built in 545ms

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>

* test(admin-i18n-lint): invert orphan-modules assertion now that AuthorPage imports them

PR #7736 added a lint assertion that admin/src/components/SearchField.tsx
and admin/src/utils/sorting.ts must NOT exist, on the assumption they
were dead code after #7716. They aren't — the GDPR AuthorPage (#7667)
imports both. The previous commit restored the files; this commit flips
the assertion so the test:

  - verifies both files exist
  - verifies admin/src/pages/AuthorPage.tsx still imports them

If a future cleanup wants to delete these modules, the test now forces
the author to also delete or refactor the AuthorPage consumption first,
preventing a repeat of the merge-order accident that produced this bug.

Test plan:
  - cd src && pnpm exec vitest run tests/backend-new/specs/admin-i18n-source-lint.test.ts
    → 14 passed (14)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>

---------

Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-15 08:40:15 +01:00
..
public feat(gdpr): admin UI for author erasure (follow-up to #7550) (#7667) 2026-05-14 08:11:48 +01:00
scripts feat(admin): document admin endpoints in OpenAPI (#7693) (#7705) 2026-05-10 15:55:33 +08:00
src fix(admin): restore SearchField + sorting modules used by AuthorPage (#7746) 2026-05-15 08:40:15 +01:00
.eslintrc.cjs Feat/admin react (#6211) 2024-03-09 23:07:09 +01:00
.gitignore Feat/admin react (#6211) 2024-03-09 23:07:09 +01:00
index.html Feat/admin react (#6211) 2024-03-09 23:07:09 +01:00
package.json build(deps): bump @tanstack/react-query from 5.100.9 to 5.100.10 (#7732) 2026-05-13 20:39:31 +02:00
README.md feat(admin): document admin endpoints in OpenAPI (#7693) (#7705) 2026-05-10 15:55:33 +08:00
tsconfig.json feat(admin): document admin endpoints in OpenAPI (#7693) (#7705) 2026-05-10 15:55:33 +08:00
tsconfig.node.json Feat/admin react (#6211) 2024-03-09 23:07:09 +01:00
vite.config.ts fix(admin): restore i18n on /admin (issue #7586) (#7602) 2026-04-26 03:07:45 +01:00

Admin UI

Vite + React 19 single-page app served at /admin. Talks to the backend over socket.io for the existing settings / plugins / pads pages, and (when endpoints are added to the OpenAPI spec) over a typed REST client.

Scripts

Script What it does
pnpm dev gen:api + Vite dev server (expects backend on :9001).
pnpm gen:api Regenerates src/api/{schema.d.ts,version.ts} from the OpenAPI spec.
pnpm build gen:api + tsc + vite build.
pnpm build-copy Same, but writes into ../src/templates/admin.
pnpm test gen:api + smoke tests for the API client wiring.
pnpm lint ESLint.

Typed API client

The admin uses openapi-typescript to generate types from src/node/hooks/express/openapi.ts, openapi-fetch for typed requests, and openapi-react-query for TanStack Query bindings.

Generated files

admin/src/api/schema.d.ts and admin/src/api/version.ts are generated by gen:api and gitignored — never commit them. They are produced by:

pnpm --filter admin gen:api

admin/scripts/gen-api.mjs loads src/node/hooks/express/openapi.ts, calls generateDefinitionForVersion for the latest API version, pipes the JSON through openapi-typescript to produce schema.d.ts, and emits a runtime constant LATEST_API_VERSION (read from info.version in the spec) to version.ts so client.ts can build the right /api/<version>/ baseUrl.

gen:api runs as the first step of dev, build, build-copy, and test, so a fresh checkout produces the generated files automatically when any of those scripts is invoked. After modifying any of the following, the next pnpm <dev|build|test> will refresh the generated files; you can also run gen:api directly:

  • src/node/hooks/express/openapi.ts
  • src/node/handler/APIHandler.ts (changes to latestApiVersion)
  • the resource definitions referenced by openapi.ts

Using the client

import { $api } from './api/client';

const SettingsPanel = () => {
  const { data } = $api.useQuery('get', '/admin/settings'); // example
  return <pre>{JSON.stringify(data, null, 2)}</pre>;
};

The admin endpoints are not yet present in the OpenAPI spec — this client is in place to support upcoming work (see issue #7638 follow-up). For now, it is exercised only by the smoke test.