Jewelry AI · home screen
The home screen reports an outage in one section and not in the others
Three parts of one screen are drawn from three different sources: a list held inside the app, configuration that only the server can supply, and a cache on your device. An outage reaches each of them differently, which is why the screen looks half normal and half broken.
Three sources on one screen
The home screen is not assembled from a single answer. Its category grid comes from a list held inside the app, its tools row comes from server configuration and nothing else, and its recent strip is read first from a store on the device (verified in the application source in August 2026).
An outage therefore reaches the three sections unequally. The tools row cannot draw anything without configuration, so it reports the failure. The category grid does not need the server in order to draw four cards, so it draws them. A strip with earlier work behind it fills from the cache and looks ordinary.
One statement about the connection is made in one place: a banner across the top of the screen (components/ui/offline-banner.tsx:17-22). Everything below it keeps its own behaviour.
A screen that is half normal and half broken is that difference becoming visible. It is one outage reaching three suppliers, not several separate faults.
Each part of the screen, its supplier, and what an outage does to it
Read this table downwards before drawing any conclusion from a single section.
| Part of the screen | Where its content comes from | With the server unreachable |
|---|---|---|
| Connection banner | The app's own view of the connection | Appears across the top of the screen |
| Category grid | Server configuration, with a list held in the app as the fallback | Draws four cards; it has no loading state and no error state |
| Tools row | Server configuration only | Reports that the tools could not be loaded, with a retry button |
| Recent strip, account with earlier work | An account-scoped store on the device, read before the server answers | Fills from the cache; some pictures may not resolve |
| Recent strip, account with no work at all | Neither source has anything to give | Shows an error box with a retry button |
The tools row is the only part that reports the outage
It is also the part written to be pessimistic: with no answer from the server, a tool is reported as closed rather than open.
- Loading and unreachable are two different pictures.
- Four skeleton cards mean configuration is still loading. A load-failure message with a retry button means it could not be fetched. Real availability appears only in the third state, after configuration arrives (apps/jewelry-mobile/src/features/home/tools-section.tsx).
- Absent configuration counts as closed.
- Availability is resolved only from server configuration, and a null configuration produces an unavailable tool rather than an optimistic open one (apps/jewelry-mobile/src/features/generation/tools.ts).
- Loading is no longer disguised as coming soon.
- A correction recorded in tools-section.tsx (commit 81f8fff) separated the loading state from the unreachable one. Before it, all four tools appeared as coming soon while configuration was still on its way. That is past behaviour, not what you are looking at now.
- Which tools are open cannot be read from the application at all.
- It depends entirely on the server's configuration at the moment you ask, so neither the code nor this page can state it. The row is a display of an answer, not a source of one.
Why the category grid still looks complete
The grid asks for the categories the server has opened, and when that answer is empty or absent it uses the list held in the app instead (apps/jewelry-mobile/src/features/generation/config.ts). The visible result is four cards, in every condition.
The sequence is the app's as well: ring, bracelet, necklace, earring, in that fixed order, whatever order the server sent (config.ts:43, with the behaviour pinned by home-registry.test.ts:24).
A card being present is therefore not a promise that the category can produce an image. What decides that is tool availability inside the Create flow, and while the server is unreachable that answer does not exist on the device.
The grid has no loading state and no error state of its own (apps/jewelry-mobile/src/features/home/category-grid.tsx). It has no way to report an outage, so its calm appearance is not a second opinion contradicting the tools row.
The one branch where the strip does report the outage
The empty area of the strip has two branches. With the server unreachable and no jobs held at all, it shows an error box and a retry button (apps/jewelry-mobile/src/features/home/recent-generations.tsx). With the server reachable and no jobs, it shows a different, ordinary empty state that belongs to the page about the strip itself.
The error box is therefore a statement about two things at once: the server could not be reached, and there was nothing cached to draw instead. An account with earlier work does not reach that branch.
The home screen has no pull-to-refresh: its scrolling container is not given a refresh control (components/ui/screen-container.tsx:59-66). The retry buttons inside the sections that failed are the manual way to ask again, and there is no gesture that does the same thing.
Conclusions this screen invites but does not support
Each of these follows naturally from what is on the screen, and each one is wrong for the reason beside it.
Reading four category cards as four working categories.
The grid falls back to the app's own list; what can actually be generated is decided by tool configuration, not by the presence of a card.
Reading a tools load failure as a withdrawn feature or a restricted account.
It is the error state of a section whose only supplier is server configuration, and it is retried with the button beside it.
Reading a populated strip as proof that your work is stored on the phone.
It is an offline cache of an account-scoped store; the record itself is held on the server.
Reading a placeholder on an older card as a deleted image.
Cached picture addresses have a limited life, so an entry can still be listed while its address no longer resolves.
Reading the calm category grid as evidence that the connection is fine.
The grid has neither a loading state nor an error state, so it looks the same either way and carries no information about the server.
What this screen cannot tell you
These are outside what the home screen knows, and no reading of it will produce them.
- Which tools are open for generation. That is the server's configuration at the moment you ask, and it is not readable from the application.
- Whether a category you can see is able to produce an image.
- Why the server could not be reached, or when it will answer.
- What your work history contains beyond whatever happens to be cached on this device.
- How the strip is composed, captioned or timed; those rules belong to the page about the strip itself.
- Anything about being signed out or returned to the welcome screen, which is account lifecycle rather than home-screen behaviour.
Questions
The tools section says it could not load, but the categories look fine. Is the app broken?
No. The two sections have different suppliers. The tools row is resolved only from server configuration (apps/jewelry-mobile/src/features/generation/tools.ts), so with no answer it shows its load-failure state. The category grid falls back to a list held inside the app and has no error state of its own (apps/jewelry-mobile/src/features/home/category-grid.tsx), so it draws four cards regardless. The banner at the top is the screen's single statement about the connection.
Do the four category cards mean all four categories will generate?
No. The grid shows the categories the server has opened, and when that answer is empty or missing it uses the app's own list instead (apps/jewelry-mobile/src/features/generation/config.ts), always in the fixed order ring, bracelet, necklace, earring (config.ts:43). Whether a category can produce an image is decided by tool availability in the Create flow, which is a separate answer.
My earlier generations still appear with no connection. Are they stored on my phone?
What you are seeing is an account-scoped cache that is read before any server answer (apps/jewelry-mobile/src/features/generation/store.tsx). The code treats it as the offline case: the record of your work is held on the server and the local copy exists for this situation (apps/jewelry-mobile/src/features/generation/storage-keys.ts:16-17). Because the cached picture addresses have a limited life, older cards can fall back to a placeholder.
There is no pull-to-refresh. How do I make the home screen try again?
Use the retry button in the section that failed. The home screen's scrolling container is not given a refresh control (components/ui/screen-container.tsx:59-66), so pulling down does nothing. A tool's open or coming-soon state is only meaningful once configuration has actually arrived; until then the app reports a tool as closed rather than assuming it is open.