R1 cleanup: collAnon and dead code gone, no IndexedDB, honest PWA files
Build / Build (push) Successful in 51s
Build / Build (push) Successful in 51s
Starts the completion program (SocialPub docs/ROADMAP.md, "Owner decisions on finishing everything", 2026-10-17). - The localizer's namespace is decePubClient.Services; collAnon is gone from the repo. - Dead code: PagesBase, VConstants, SettingsOptions, ViewLanguage, unused APIs routes, InstanceService.Self, RequestStats.LastOf/AverageMs, PostAnon/DeleteTotallyAnon, unused AppStatusService methods and their main.js helpers (the app badge stays for Web Push), ExtensionMethods/SUtility leftovers (Markdig and BlazorZXingJs packages go), unused PublicCacheData/PageSettings/AppConfiguration fields, commented-out code. - The client log in IndexedDB, which nothing ever read, goes with the whole IndexedDB layer (DnetIndexedDb, IStorage): logs go to the browser console; main.js deletes the old "data" database once. - The solution names the real ClientModels project. Unused vendor assets (fontawesome, solid, open-iconic, rxjs) go. - robots.txt disallows everything; manifest.json and index.html say decePub; the service worker's cache name follows each publish's assets version, so old caches are purged. - MessageType is Visibility (member names kept: they are resx keys); ExpandMessage.razor is Thread.razor (same route). - i18n: dead keys removed, Italian "camera" is "punto di vista", DInputBase/DCalendar validation messages come from ErrorMessages, DataTransfer's spinner has its label. - CLAUDE.md follows: client storage, JS interop, PWA, the D fields' messages. Verified: dotnet build decePubClient.csproj and decePubClient.sln -c Release (0 errors, no new warnings); a Pasture publish served by the pasture's decepub peer. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01WpVCoDeM1qUTRp4fXQdfof
This commit is contained in:
1 parent
e4414f1ac9
commit
fd2f2e7c65
79 files changed
+155
-6673
No files matched your search
@@ -14,8 +14,6 @@ columns: navigation, the feed with a tab per kind of feed, and a 3D globe that f
|
||||
in tooltips wherever there is data. Development builds point at a local PrivaPub on `http://127.0.0.1:6970`
|
||||
(`wwwroot/appsettings.Development.json`, never published).
|
||||
|
||||
`Docs/Insomnia_APIs.json` is an old API collection for a localhost backend. Don't treat it as PrivaPub's API.
|
||||
|
||||
## Sibling repo dependency
|
||||
|
||||
The project references `../SocialPub/PrivaPub.ClientModels/PrivaPub.ClientModels.csproj`, so SocialPub must be
|
||||
@@ -83,7 +81,7 @@ without network access. NuGet restore still uses nuget.org.
|
||||
clean-clone publish would ship `app.css` without its `.gz`/`.br` copies and outside `service-worker-assets.js`.
|
||||
The deploy workflow checks for `css/app.css.gz`.
|
||||
- `bash tools/tailwind.sh watch` rebuilds the CSS live next to `dotnet watch`.
|
||||
- Tailwind scans every file `.gitignore` doesn't exclude (minus `tools/`, `wwwroot/vendor/`, `Docs/`), and only
|
||||
- Tailwind scans every file `.gitignore` doesn't exclude (minus `tools/` and `wwwroot/vendor/`), and only
|
||||
generates the classes it finds written out **whole**. Never build a class name by concatenation or interpolation (`"btn-" + size`, `$"btn-{size}"`). Write
|
||||
every variant as a literal, e.g. in a switch arm.
|
||||
|
||||
@@ -214,7 +212,7 @@ supplies:
|
||||
- `AfterRenderAsyncJobs`, run once after the next render;
|
||||
- `WhenOnline` / `StartOnlinePolling`.
|
||||
|
||||
`PagesBase` is an empty subclass of it that nothing uses. Never redeclare the base's members in a component.
|
||||
Never redeclare the base's members in a component.
|
||||
|
||||
**UI feedback.**
|
||||
- `Services/ToastService.cs` is the snackbar: the SUtility extensions `AddResponseError(WebResult)` (silent on
|
||||
@@ -234,7 +232,7 @@ supplies:
|
||||
`SUtility.DefaultSerializer` (camelCase, enums by name like PrivaPub, `ClientJsonContext`) for `clientapi/`. A payload
|
||||
can be an object (JSON), name/value pairs (a form) or a `Func<HttpContent>` (multipart), built once per attempt.
|
||||
- Auth levels: `Get` / `Post` / `Put` / `Patch` / `Delete` need credentials and end the session when PrivaPub refuses
|
||||
them; `GetAnon` / `PostAnon` add them when there are some; `*TotallyAnon` send none (the login must not carry a JWT:
|
||||
them; `GetAnon` adds them when there are some; `*TotallyAnon` send none (the login must not carry a JWT:
|
||||
PrivaPub redirects it).
|
||||
- `retryOnError` backoff: 1, 2, 4, 8, 16, 29 s, then 60 s, for at most 10 minutes.
|
||||
- Each request has its own timeout (`Measure`): 100 s, or 10 minutes for a multipart body (an upload); the
|
||||
@@ -252,7 +250,7 @@ supplies:
|
||||
- **One sign-in** (`Services/AuthService.cs`, `Pages/Login.razor`): the root signs in on `/clientapi/user/login`, then
|
||||
each persona the client uses gets its own Mastodon token in exchange for the JWT (PrivaPub's `PersonaExchange`,
|
||||
RFC 8693 on `/oauth/token`, first-party client id `AppConfiguration:ClientId`). `AuthData` keeps the JWT and the
|
||||
persona tokens; logout revokes every persona token, then forgets the session and IndexedDB.
|
||||
persona tokens; logout revokes every persona token, then forgets the session.
|
||||
- **The ways in** (sign-up is closed on PrivaPub; owner decision 2026-10-16):
|
||||
- **Setup** (`Pages/Setup.razor` at `/setup`): while PrivaPub has no administrator (`/clientapi/user/setup`), the first
|
||||
login is made there, first come, first served, with its first persona. It becomes the administrator, and setup
|
||||
@@ -334,7 +332,7 @@ supplies:
|
||||
(`/api/v2/search`, never resolving), once typing pauses.
|
||||
An edited post's card says so, and its versions open from there (`/statuses/:id/history`, newest first; PrivaPub
|
||||
keeps a remote post's earlier versions from its edits and from Pleroma's `formerRepresentations`).
|
||||
- **Threads** (`Pages/ExpandMessage.razor` at `/expand/{id}`): opening a remote thread makes PrivaPub read its replies
|
||||
- **Threads** (`Pages/Thread.razor` at `/expand/{id}`): opening a remote thread makes PrivaPub read its replies
|
||||
from their servers (its FEP-7888 `context`, else `replies`), so the page reads the thread again after 4 and 15 seconds
|
||||
and adds what was found, in the thread's order.
|
||||
- **Interaction policies** (GoToSocial's, and FEP-5624's `canReply` on a PeerTube video whose comments are moderated): a
|
||||
@@ -444,17 +442,14 @@ supplies:
|
||||
- Lookup order: this repo's `Resources/AllStrings.resx` (+ `.it.resx`), then `FieldsNameResource`, then
|
||||
`ErrorsResource`.
|
||||
- A missing key renders as the key itself, formatted with its arguments, so a typo fails silently.
|
||||
- The class lives in namespace `collAnon.Client.Services`, a leftover from another project.
|
||||
- `Resources/ErrorMessages.resx` is read by `[Required]` / `[StringLength]` through `ErrorMessageResourceType`. A new key
|
||||
needs its `public static string` property in `ErrorMessages.Designer.cs` too, or validation throws at runtime.
|
||||
- `Resources/ErrorMessages.resx` is read by `[Required]` / `[StringLength]` through `ErrorMessageResourceType`, and by the
|
||||
D fields' parse errors (`DInputBase`, `DCalendar`) through the static `ErrorMessages.InvalidValue` / `InvalidDate`. A new
|
||||
key needs its `public static string` property in `ErrorMessages.Designer.cs` too, or validation throws at runtime.
|
||||
|
||||
**Client storage** comes in two layers:
|
||||
- **localStorage** (Blazored.LocalStorage, camelCase JSON) holds `AuthData`, `PublicCacheData`, `FeedFilter` and the
|
||||
server cache `ServerInfos`, keyed by `nameof(Type)`.
|
||||
- **IndexedDB** (DnetIndexedDb, database `data`) is reached through `IStorage`. Its schema is declared in
|
||||
`GenericExtensions.AddIndexedDb()`, and you must bump `WithVersion` when you change it.
|
||||
- The schema is at version 3: the `ClientLogs` store that `IStorage.AddLog` writes (version 2 added it; version 3 left
|
||||
the mock feed's `Message` store out).
|
||||
**Client storage** is localStorage (Blazored.LocalStorage, camelCase JSON): `AuthData`, `PublicCacheData`, `FeedFilter`
|
||||
and the server cache `ServerInfos`, keyed by `nameof(Type)`. There is no IndexedDB: `ILoggingService` writes to the
|
||||
browser console only, and `main.js` deletes the database (`data`) where the client once kept its log, wherever a browser
|
||||
still holds it.
|
||||
|
||||
**Auth.** `TokenAuthStateProvider` holds `AuthData` (localStorage, cached in memory) and builds the auth state from
|
||||
it: the root's name, its policies as claims, and the current persona. Pages that need a session carry
|
||||
@@ -464,10 +459,12 @@ it: the root's name, its policies as claims, and the current persona. Pages that
|
||||
- `wwwroot/main.js` defines `window.*` helpers. `Services/AppStatusService.cs` calls them, mostly through the
|
||||
synchronous `IJSInProcessRuntime`.
|
||||
- Each helper reports its errors back through `window.logFromJs`.
|
||||
- The other scripts (IndexedDB, HeadElement, rxjs) are loaded by `<script>` tags in `wwwroot/index.html`; the feed's
|
||||
- The other scripts (`js/theme.js`, HeadElement's, `vendor/cally.js`, `js/blurhash.js`) are loaded by `<script>` tags in
|
||||
`wwwroot/index.html`; the feed's
|
||||
modules (`js/feed.js`, `js/globe.js`) are imported on demand through `IJSObjectReference`.
|
||||
|
||||
**PWA.** Published builds use `wwwroot/service-worker.published.js`, and `service-worker.js` is the dev version.
|
||||
**PWA.** Published builds use `wwwroot/service-worker.published.js`, and `service-worker.js` is the dev version. The
|
||||
published worker names its cache after the assets manifest's version, so each publish drops the previous cache.
|
||||
|
||||
## Development rules
|
||||
|
||||
|
||||
Reference in new issue
Block a user