Skip to content

[GPT-161] docs(specs): add sort/filter design for events and interviews#483

Merged
Hackin7 merged 32 commits into
AdvisorySG:mainfrom
Hackin7:filter-addition
Jun 8, 2026
Merged

[GPT-161] docs(specs): add sort/filter design for events and interviews#483
Hackin7 merged 32 commits into
AdvisorySG:mainfrom
Hackin7:filter-addition

Conversation

@Hackin7

@Hackin7 Hackin7 commented May 6, 2026

Copy link
Copy Markdown
Contributor

Captures the brainstorming output for two features (overview index) and
the full design spec for Feature 1 — multi-tag client-side filtering on
the /events/ and /interviews/ collections, with URL sync and
load-more pagination.

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

image

Hackin7 and others added 16 commits May 6, 2026 01:44
Captures the brainstorming output for two features (overview index) and
the full design spec for Feature 1 — multi-tag client-side filtering on
the /events/ and /interviews/ collections, with URL sync and
load-more pagination.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Twelve-task TDD-light plan derived from
2026-05-06-sort-filter-design.md, covering Alpine component, partial,
template wiring, routes update, accessibility, SEO canonical,
graceful-degradation and final scenario sweep.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Extends the prior tag-filter feature with: Typesense-backed search,
4-option sort dropdown, and approach-A template pagination (20 blocks,
2000 ceiling) to fix the limit='all' cap at 100 posts.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
9 tasks ordered: full-corpus load (1) → sort (2-4) → search (5-8) →
end-to-end verification (9). Each implementation task ends with build,
gscan lint, manual browser check, and commit.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Re-add the comment explaining tabindex="-1" enables loadMore() focus
(lost during the sub-partial extraction) and document that limit=100
is Ghost's per-page cap, not an arbitrary choice.

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

Hackin7 commented May 6, 2026

Copy link
Copy Markdown
Contributor Author
image

Hackin7 and others added 5 commits May 6, 2026 11:07
…mption

Hoist the four-mode allowlist to a module constant so the URL parser,
the dropdown UI (Task 4), and the sort comparator share one source of
truth. Document the implicit single-parent assumption in _reorderDom
so a future partial split won't silently re-parent cards.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Match the established mb-6 cadence used by the chip row directly below.
Keeps vertical rhythm consistent now that toolbar precedes chips.

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

Hackin7 commented May 6, 2026

Copy link
Copy Markdown
Contributor Author
image

Hackin7 and others added 7 commits May 6, 2026 11:38
The slug list now appears in two formats per page (Ghost filter syntax
+ plain comma-separated). Comment explains the constraint so future
edits don't drift one without the other.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Two correctness fixes surfaced in code review before Task 8 wires the UI:

1. _runSearch now captures the AbortController locally so finally{} only
   clears isSearching when THIS call is still the latest. Otherwise rapid
   typing makes the spinner flicker off when the aborted call's finally
   fires while the superseding call is still in flight.

2. clearFilters now aborts any in-flight search, clears the debounce
   timer, and forces a URL write. Without this, a stale Typesense
   response could land after the clear and re-populate searchSlugs,
   and ?sort= or ?q= could linger in the URL when their watchers
   weren't dirty.

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

Tailwind 3.0 JIT in this project doesn't reliably emit arbitrary
values like min-w-[200px], so the toolbar would have collapsed below
the intended threshold on narrow viewports. Inline style guarantees
the constraint regardless of the JIT scan.

Also: $event.target.focus() in the Esc handler is a no-op (the input
already has focus when Esc fires) — drop. And use the U+2026 ellipsis
in the placeholder to match the Searching… indicator.

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

Hackin7 commented May 6, 2026

Copy link
Copy Markdown
Contributor Author
image

Hackin7 and others added 2 commits May 6, 2026 12:36
Four cleanups from the whole-branch review:

1. setSearchQuery short-circuits to immediate _runSearch when input is
   empty/sub-threshold. Previously Esc-to-clear left the URL ?q= and
   result count stale for the full 250ms debounce window.

2. init() normalizes sub-threshold ?q= values to '' so a hand-crafted
   /events/?q=x doesn't sit in the input with no active search behind it.

3. New hasActiveFilters() getter consolidates the
   "tags || search || sort != newest" expression that had been
   duplicated in three x-show bindings.

4. Refresh stale "Not consumed in Task 3" comment on the tagSlugs
   constructor parameter — now describes its actual role (Typesense
   filter_by scoping).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Three Typesense settings (host, api_key, collection) move from JS-file
constants to package.json config.custom defaults, admin-overridable in
Ghost → Design → Customize. default.hbs injects the resolved values
into window.__TYPESENSE_CONFIG__ before the bundle loads, and the
wrapper reads from there at search time (with the same defaults as
fallback for partial-page-render contexts).

Operationally: deploying to a different Ghost instance no longer
requires editing the theme — admins point the search at their own
Typesense backend via the Customize panel. The API key remains
search-only by design (read-only, public-scoped).

Adds a "Typesense Search" section to README documenting the three
settings and the security model of the embedded key.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@wei2912 wei2912 linked an issue May 19, 2026 that may be closed by this pull request
@wei2912
wei2912 self-requested a review May 19, 2026 14:34
@wei2912 wei2912 changed the title docs(specs): add sort/filter design for events and interviews [GPT-161] docs(specs): add sort/filter design for events and interviews May 19, 2026
@Hackin7

Hackin7 commented Jun 8, 2026

Copy link
Copy Markdown
Contributor Author
image image image

@Hackin7
Hackin7 merged commit ed3a39e into AdvisorySG:main Jun 8, 2026
3 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Development

Successfully merging this pull request may close these issues.

Stories: More sorting features

1 participant