Skip to content

Commit 274d1b2

Browse files
authored
Merge branch 'main' into migrate-og-takumi-v2
2 parents 672fe1b + 3bf7280 commit 274d1b2

106 files changed

Lines changed: 3925 additions & 1424 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

docs/source-code-audit-2026-06-23.md

Lines changed: 14 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -17,9 +17,11 @@ These are quick, high-leverage patches because later fixes can reuse them instea
1717
- [done 2026-06-24: `pnpm run test:unit`, `pnpm test`] Make `pnpm test` honest about TypeScript tests, or split script names so validation expectations are clear.
1818
- [done 2026-06-24: `pnpm run test:tsc`, `pnpm run test:lint`] Default non-submit buttons/select triggers to `type="button"`, fix the shared pagination label/id contract, and clean up tooltip child prop merging.
1919
- [done 2026-06-24: `pnpm run test:unit`, `pnpm run test:tsc`, `pnpm run test:lint`] Add tiny helpers for response filenames, package slug encoding, and row-local ids.
20-
- Add tiny helpers for external URL normalization, internal route classification, and guarded storage.
21-
- Fix custom `useMutation` stale callbacks, clipboard/copied-state timers, docs sidebar timers, popup blocked-state handling, and simple page-visibility/reduced-motion helpers.
22-
- Normalize easy static data contracts: maintainer bare-domain URLs, Scarf id validation, public-library selector, partner analytics seed buckets, blog image URLs, host cache purge response policy.
20+
- [done 2026-06-24: `pnpm test`, 60-route local smoke] Add tiny helpers for external URL normalization, internal route classification, and guarded storage.
21+
- [done 2026-06-24: `pnpm test`, 60-route local smoke] Share low-risk clipboard/copy-state timers and auth popup centering.
22+
- Fix custom `useMutation` stale callbacks, docs sidebar timers, remaining popup blocked-state handling, and remaining page-visibility/reduced-motion call sites.
23+
- [done 2026-06-24: `pnpm test`, 60-route local smoke] Normalize maintainer bare-domain URLs, add Scarf/social URL contract tests, and centralize the public-library selector.
24+
- Normalize partner analytics seed buckets, blog image URLs, and host cache purge response policy.
2325

2426
### 2. One-off cleanup that lowers noise
2527

@@ -33,10 +35,10 @@ Do these early when they're obvious and isolated, but don't let them block highe
3335

3436
These are small enough to do before deeper refactors and they reduce risk while larger helpers are being designed.
3537

36-
- Analytics proxy header allowlist, GitHub webhook fail-closed secret, Cloudflare-first IP extraction, route response filename sanitizing, Discord raw-body size/signature-shape guard, MCP transport content-type/length guard and masked errors.
37-
- Public pagination and route-search caps, admin pagination/range caps, docs feedback content caps, showcase field/array caps, Shopify page-size/quantity/discount caps, UploadThing client preflight caps, image transform clamps, community-resource frontmatter schema.
38-
- URL/link hardening: Intent metadata URLs, Intent tarball source paths, markdown/source/search link classification, legacy redirect segment matching, local docs path containment.
39-
- OAuth/login quick fixes: return-to key mismatch, login modal stale callbacks, provider route param picklists, session revocation conflict retry, and session base64 fallback removal once covered.
38+
- [done 2026-06-24: `pnpm test:tsc`, `pnpm test:lint`, `pnpm test`] Analytics proxy header allowlist, GitHub webhook fail-closed secret, Cloudflare-first IP extraction, route response filename sanitizing, Discord raw-body size/signature-shape guard, MCP transport content-type/length guard and masked errors.
39+
- [done 2026-06-24: `pnpm test:tsc`, `pnpm test:lint`, `pnpm test`] Public pagination and route-search caps, admin pagination/range caps, docs feedback content caps, showcase field/array caps, Shopify page-size/quantity/discount caps, UploadThing client preflight caps, image transform clamps, community-resource frontmatter schema.
40+
- [done 2026-06-24: `pnpm test:tsc`, `pnpm test:lint`, `pnpm test`] URL/link hardening: Intent metadata URLs, Intent tarball source paths, markdown/source/search link classification, legacy redirect segment matching, local docs path containment.
41+
- [done 2026-06-24: `pnpm test:tsc`, `pnpm test:lint`, `pnpm test`] OAuth/login quick fixes: return-to key mismatch, login modal stale callbacks, provider route param picklists, session revocation conflict retry, and session base64 fallback removal once covered.
4042

4143
### 4. Small controllers that prevent repeat bugs
4244

@@ -89,9 +91,12 @@ Treat these as tracked initiatives, not normal cleanup PRs.
8991

9092
## Batch Log
9193

94+
- 2026-06-24: Landed the grouped security pass across public request boundaries, OAuth/login/session flows, builder/GitHub deploy APIs, outbound fetches, stats/Intent/docs/shop/showcase caps, UploadThing/image preflight, markdown/search link classification, docs redirects/path containment, and community-resource frontmatter validation.
95+
- 2026-06-24: Second pass simplified the security patch by sharing bounded body readers, npm package-name/page/date/chart schemas, and URL normalization; removed the local application-starter request guard while preserving same-origin/content-type/body-size enforcement.
9296
- 2026-06-24: Added shared response filename/content-disposition helpers, package route slug encoding helpers, and row-local id helpers; wired them into builder/docs downloads, Intent registry links, and moderation note inputs.
9397
- 2026-06-24: Hardened shared UI primitives: defaulted shop buttons and shared select triggers to non-submit buttons, gave pagination a unique page-size label/id pair plus non-submit controls, and made Tooltip merge trigger handlers/refs without `any`.
9498
- 2026-06-24: Added `test:unit` and wired it into `pnpm test` so existing TypeScript assertion tests run in the default validation path.
99+
- 2026-06-24: Added guarded browser storage/effect helpers, migrated low-risk clipboard/timer/popup/storage/reduced-motion call sites, centralized public-library selection, normalized maintainer URLs, and added static data contract tests.
95100
- 2026-06-23: Audit created and ordered.
96101

97102
## Highest Priority Findings
@@ -2183,7 +2188,7 @@ This is a strong candidate for a reusable TanStack docs-site cache helper or at
21832188

21842189
### Good pattern: slim data modules with explicit heavy-data escape hatches
21852190

2186-
`src/libraries/libraries.ts:1-2` keeps base library data lightweight, while `src/libraries/index.tsx:34-44` explicitly avoids re-exporting extended per-library landing-page projects that contain React nodes and heavier assets. This is the right shape for global navigation/docs data: a slim default import path plus opt-in heavy modules for routes that actually render the full experience.
2191+
`src/libraries/libraries.ts:1-2` keeps base library data lightweight, while `src/libraries/index.tsx:34-44` explicitly avoids re-exporting extended per-library landing-page projects that contain React nodes and heavier assets. `publicLibraries` and `isPublicLibrary` now give navigation/search/API callers one shared public catalog boundary. This is the right shape for global navigation/docs data: a slim default import path plus opt-in heavy modules for routes that actually render the full experience.
21872192

21882193
### Good pattern: lazy activation for expensive navbar features
21892194

@@ -2206,6 +2211,7 @@ This is a strong candidate for a reusable TanStack docs-site cache helper or at
22062211
- Builder definition schema shared between client UI, validate, compile, download, deploy, and MCP.
22072212
- A deploy-dialog controller shared by builder-generated projects and docs example deployment.
22082213
- React/browser effect helpers for timed flags, popup polling, clipboard writes, guarded storage, outside-click behavior, and drag-resize listeners.
2214+
- Static data contract tests for public catalogs, maintainer/social URLs, package metadata IDs, and other small hand-authored data tables.
22092215
- An OAuth PKCE helper with atomic code consumption patterns for Drizzle/Postgres.
22102216
- A first-party OAuth callback helper that validates provider params, clears transient cookies on every exit, and normalizes provider token/profile responses.
22112217
- A React Query query-options linter/helper that asserts query keys include every query-function input.

src/auth/cli-tickets.server.ts

Lines changed: 23 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99
*/
1010

1111
const TICKET_TTL_MS = 5 * 60 * 1000
12+
const MAX_TICKETS = 1_000
1213

1314
interface CliTicket {
1415
userId: string | null
@@ -38,18 +39,34 @@ const tickets: Map<string, CliTicket> = (globalScope[TICKETS_KEY] ??= new Map<
3839
if (!globalScope[TICKETS_INTERVAL_KEY]) {
3940
globalScope[TICKETS_INTERVAL_KEY] = setInterval(
4041
() => {
41-
const now = Date.now()
42-
for (const [id, ticket] of tickets) {
43-
if (ticket.expiresAt < now) {
44-
tickets.delete(id)
45-
}
46-
}
42+
cleanupExpiredTickets()
4743
},
4844
60 * 1000, // every minute
4945
)
5046
}
5147

48+
function cleanupExpiredTickets() {
49+
const now = Date.now()
50+
for (const [id, ticket] of tickets) {
51+
if (ticket.expiresAt < now) {
52+
tickets.delete(id)
53+
}
54+
}
55+
}
56+
57+
function trimTicketStore() {
58+
cleanupExpiredTickets()
59+
60+
while (tickets.size >= MAX_TICKETS) {
61+
const oldestId = tickets.keys().next().value
62+
if (!oldestId) break
63+
tickets.delete(oldestId)
64+
}
65+
}
66+
5267
export function createCliTicket(): string {
68+
trimTicketStore()
69+
5370
const id = crypto.randomUUID()
5471
tickets.set(id, {
5572
userId: null,

src/auth/client.ts

Lines changed: 9 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
*/
77

88
import type { OAuthProvider } from './types'
9+
import { openCenteredPopupWindow } from '~/utils/browser-effects'
910

1011
// ============================================================================
1112
// Auth Client
@@ -36,15 +37,13 @@ export const authClient = {
3637
* Initiate OAuth sign-in in a popup window (for modal-based login)
3738
*/
3839
socialPopup: ({ provider }: { provider: OAuthProvider }) => {
39-
const width = 500
40-
const height = 600
41-
const left = window.screenX + (window.outerWidth - width) / 2
42-
const top = window.screenY + (window.outerHeight - height) / 2
43-
window.open(
44-
`/auth/${provider}/start?popup=true`,
45-
'tanstack-oauth',
46-
`width=${width},height=${height},left=${left},top=${top},popup=yes`,
47-
)
40+
return openCenteredPopupWindow({
41+
url: `/auth/${provider}/start?popup=true`,
42+
target: 'tanstack-oauth',
43+
width: 500,
44+
height: 600,
45+
features: ['popup=yes'],
46+
})
4847
},
4948
},
5049

@@ -74,7 +73,7 @@ export function navigateToSignIn(
7473
window.location.href = url
7574
} else {
7675
const url = returnTo
77-
? `/login?returnTo=${encodeURIComponent(returnTo)}`
76+
? `/login?redirect=${encodeURIComponent(returnTo)}`
7877
: '/login'
7978
window.location.href = url
8079
}

0 commit comments

Comments
 (0)