Repository navigation
Conversation
Codex Review SummaryThis comment shows the latest Codex review activity on this pull request.
ℹ️ About Codex in GitHubYour team has set up Codex to review pull requests in this repo. Reviews are triggered when you
Codex reacts with 👀 while any review is running, comments if it has suggestions, and reacts with 👍 once all reviews finish with no findings. |
There was a problem hiding this comment.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: 85935d38a3
ℹ️ About Codex in GitHub
Codex has been enabled to automatically review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
When you sign up for Codex through ChatGPT, Codex can also answer questions or update the PR, like "@codex address that feedback".
| const { gender, ...rest } = filter | ||
| if (!gender) return rest | ||
| const genders = [] | ||
| for (let g = gender.min; g <= gender.max; g += 1) genders.push(g) |
There was a problem hiding this comment.
When personal-shiny IDs force the v3 path while the user has legacy filtering enabled, gender.min/max can come directly from an unconstrained G... expression in dnfifyIvFilter; for example, G0-1000000000 makes this synchronous loop allocate a billion entries and can block or exhaust the Node process before the request reaches Golbat. Clamp or reject bounds outside Golbat's supported gender enum rather than expanding an arbitrary range.
Useful? React with 👍 / 👎.
| // Golbat applies shiny_for before its result limit, so zoomed out views | ||
| // aren't truncated by non shiny Pokémon | ||
| const scanFilters = useV3 | ||
| ? filters.map((filter) => |
There was a problem hiding this comment.
Add a shiny-only clause when no DNF filters exist
When Only Show Personal Shinies is enabled but the current IV/PvP/species settings produce no Golbat DNF clauses (for example, all Pokémon with unconstrained global IV settings and hundo disabled), filters is empty, so this map adds no shiny_for clause. Golbat then applies the result limit to all Pokémon, and the later JavaScript filter can miss every shiny in a dense or zoomed-out viewport; add a shiny-only clause when the DNF list is empty so filtering still occurs before the limit.
Useful? React with 👍 / 👎.
| color="secondary" | ||
| style={{ width: 50, minHeight: 38 }} | ||
| style={{ | ||
| width: staticSetting.type === 'text' ? 160 : 50, |
There was a problem hiding this comment.
Remove the unapproved input-width change
This conditional expands the user-option control from 50px to 160px, but the review request contains no explicit permission to adjust spacing; the root AGENTS.md forbids introducing spacing-related style changes without that permission. Retain the existing width or obtain explicit permission before including this layout change.
AGENTS.md reference: AGENTS.md:L7-L7
Useful? React with 👍 / 👎.
| // v3 wraps the list with scan stats | ||
| results = /** @type {any} */ (results)?.pokemon | ||
| } | ||
| if (onlyPersonalShiny) { |
There was a problem hiding this comment.
Apply personal-shiny filtering to manual-ID fallbacks
When a deep link or manual ID is absent from the v3 scan—or was removed here because it is not shiny—the later /api/pokemon/id/... fallback appends an unannotated object after this filter. PkmnBackend.valid does not test shiny_for, so that Pokémon can still be returned while Only Show Personal Shinies is active, and a true shiny loaded only by ID cannot be highlighted; annotate or filter the fallback result before appending it.
Useful? React with 👍 / 👎.
| const onlyPersonalShiny = | ||
| annotateFor.length > 0 && !!args.filters.onlyPersonalShiny |
There was a problem hiding this comment.
Honor the shiny-only toggle with empty player IDs
On a Golbat-backed map, if the user enables Only Show Personal Shinies before entering IDs, clears the field, or supplies only invalid IDs, parsePlayerIds returns an empty array and this expression silently turns the requested filter off. The server then performs a regular v2 scan and returns all otherwise-selected Pokémon while the UI still says the shiny-only filter is enabled; preserve the toggle intent and return no matches or disable/validate the toggle until valid IDs exist.
Useful? React with 👍 / 👎.
|
IMO Whichever route for shiny PR is selected (assuming this sticks around) should merge after #1258 and get the capability using this |
Shundos are personal shinies with 100% IV. The onlyShundo toggle narrows Golbat v3 scan clauses to 100% IV alongside shiny_for, and shundo markers glow purple to stand apart from other personal shinies. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Personal shiny ids, only personal shinies and only shundos options were sent to the client disabled when the user lacked the personalShiny perm. Omit them from the client menus entirely instead. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
A Shiny IV Range slider under IV Range filters personal shinies separately. Shiny filters replace every global and per-Pokemon IV range with the shiny range and are sent as extra shiny_for clauses in the same Golbat v3 scan, so the regular IV Range no longer affects shinies. Leagues, zero/hundo, size and stat filters still apply to shinies. The slider is hidden without the personalShiny perm and defaults to 0-100. Regenerated env config also picks up the existing personal shiny client options. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…Map#1258) * feat(golbat): discover instance capabilities from /api/status Add a GolbatCapabilities service that reads GET /api/status from every configured Golbat endpoint and keeps { features, limits, filters } per instance, keyed by the endpoint base url. Discovery runs from DbManager.getDbContext (startup and config reload), refreshes every five minutes, and rechecks an instance immediately, debounced to once per 30 s, when a scanner call answers 400/422 — the first sign of a downgrade. A 404 or non-JSON body means an older Golbat with no capabilities; any other failure keeps the last good result. Pokestop.getAvailable now decides showcase focus support from supportsFilter(mem, 'showcase_focus') when the status route advertises filters, and only falls back to the deprecated per-response showcase_focus_filter flag for a build that does not. The hard error on an unsupported build is unchanged; only the source of truth moves. The header builder shared by the evaluator and the service is extracted into scannerHeaders.js. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016611GTrQ2W8WcznKrLQnMv * fix(pokestop): re-read Golbat status without the recheck debounce The unsupported showcase-focus verdict in Pokestop.getAvailable called the debounced recheck(), which shares its 30 s floor with the periodic status fetch. A Golbat upgrade landing inside that window left the availability pass throwing until the next one. Use refresh() there: it is still single-flight, and the path is already throttled by the availability refresh window. The debounce stays on the hot-path recheck triggered by 4xx scanner responses. The replaced test now drives the real registry with a fake transport so it exercises the debounce instead of a mocked method. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016611GTrQ2W8WcznKrLQnMv * fix(golbat): harden capability discovery per review - Keep every distinct credential set configured for a shared endpoint url and fall through to the next on 401/403, remembering the set that works. - Read the status body outside the JSON parse guard so a stalled or reset body keeps the last good capabilities instead of recording a legacy result. - Force at most one status refresh per availability payload when showcase focus is unsupported, so failing session inits no longer re-read the status on every page load. - Resolve rechecks against the registered endpoint url instead of splitting at the first /api/, so endpoints configured with a path still recheck. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Fable 5.1 <noreply@anthropic.com>
# [1.54.0](WatWowMap/ReactMap@v1.53.2...v1.54.0) (2026-10-20) ### Features * **golbat:** discover instance capabilities from /api/status ([WatWowMap#1258](WatWowMap#1258)) ([c83f93f](WatWowMap@c83f93f))
Personal shinies at 70-99% IV get a ground ripple with twinkling stars, and shundos get a crowned effect: breathing aura, spinning spectrum halo, iridescent sheen across the sprite and twinkling stars. Shinies under 70% keep the static gold glow. Effects are CSS layers in the fancy Pokemon marker, animating only transform, opacity and background-position. Stars stay clear of the weather boost icon, markers are offset so they don't pulse in unison, and motion stops under prefers-reduced-motion. A new shinySparkles user setting (default on, personalShiny perm) turns them off. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Pokemon ids sent to clients are now the encounter id encrypted as a single AES-128 block, with zeroed padding authenticating the token on the way back in. The key is generated into server/.cache and created atomically so PM2 cluster workers share it; purging it only invalidates tokens issued before the next restart. pokemonSingle still accepts raw encounter ids so Poracle links keep working, and returns the token for the client to use. Controlled by api.hideEncounterIds, on by default. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
Summary
Adds personal shiny support using Golbat's v3 pokemon scan (
annotate_for/shiny_for).shiny_forto every Golbat filter clause, so filtering happens before Golbat's result limit and works at any zoompersonalShinypermission (authentication.perms.personalShiny) gates the feature per role;map.misc.enablePersonalShinytoggles it map-wide/api/status(cached 5 min per endpoint) and falls back to the v2 scan whenannotate_forisn't advertised