BikeControl (SwiftControl)
使用 Zwift Click、Zwift Play、Shimano Di2 或任何藍牙控制器,搭配 MyWhoosh、Rouvy、Zwift 等。iOS、Android、Windows、macOS 均可免費試用。
AI 翻译
尚未检测到更新。GitHub 发布版本后会显示在这里。
个人 GitHub 账号下公开仓库的所有者可以登录并验证所有权,自行管理介绍,无需管理员批准。
登录并生成验证文件,在 30 分钟内将其提交到此仓库的默认分支。其他分支或分叉仓库中的文件无效。然后在下方检查文件,即可无需管理员批准直接管理项目。请保留文件以维持管理权限。
如需登录,将前往登录页面。登录后请回到此处,再次点击所选的验证按钮。
在项目文件夹中运行 /nomorevibe verify,即可验证所有权并自行管理介绍。
一分钟完成验证正在加载完整 README。 以下为已保存的摘录。
Youth sports league scheduling SaaS — www.thefieldslate.com.
League commissioners create seasons, divisions, and teams; generate conflict-free game and practice schedules; manage venues, officials, interleague play, snack shacks, and pay tracking; and share schedules with coaches and families.查看完整 README ↗Youth sports league scheduling SaaS — www.thefieldslate.com.
League commissioners create seasons, divisions, and teams; generate conflict-free game and practice schedules; manage venues, officials, interleague play, snack shacks, and pay tracking; and share schedules with coaches and families.
main auto-deploys to productionThis is a production-only environment — there is no staging.
npm run dev # local preview (.env.local required)
npx tsc --noEmit # required before every commit
npx eslint <paths> # required before every commit
git push origin main # deploys to production via Vercel
Database migrations live in supabase/migrations/ (numbered 00NN_name.sql) and are applied to the live project via the Supabase MCP/dashboard — the files in the repo are the record, not the applicator. Verify schema changes against the live catalog before writing code that depends on them.
leagues = seasons. archived_at IS NULL means active. Archived seasons free their plan-cap slots.org_id = the owner's profile id. Resolve with getCurrentOrgId() (src/lib/orgs/context.ts). Multi-admin orgs share via org_members; membership checks go through the SECURITY DEFINER is_org_member() — never inline its logic.profiles.plan (free | pro | elite) is the canonical tier source. UI gating via isProPlus/isElite + FeatureLockedCard/UpgradeModal; cap enforcement lives in the create RPCs (create_division_atomic, create_team, create_league…), with matching UI counters in src/lib/plan/counts.ts — the two layers must agree.umpires + official_* tables): season-scoped roster with contact info, weekly availability windows, blackout dates, certifications, a coached-team link (umpires.team_id), and normalized season roles (official_roles). Role writes are dual-format during migration: free text in game_umpires.role/umpire_role_rates.role plus role_id → official_roles; divisions.umpire_roles jsonb stays populated until a future cleanup migration.src/lib/umpires/auto-assign.ts) is best-effort and two-tier: fully-qualified first (availability, weekly cap, no blackout, no coach conflict, no overlap), then a soft tier that relaxes availability and weekly caps. Blackouts, coach conflicts, double-booking, and time overlap are always hard blocks. Division priority orders assignment. All of its date math is client-side local-timezone (src/lib/umpires/eligibility.ts) — do not call from server code without adding a timezone parameter.src/types/database.ts is hand-curated — never regenerate it wholesale. Add new tables/columns surgically and keep the Functions map empty; RPC call sites rely on the as never convention.head: true counts combined with !inner joins return wrong numbers — fetch ids first, then count with .in(). Plain single-table filtered counts are safe.app/icon.svg, apple-icon.png, opengraph-image.png — do not add metadata.icons.#0b1c39, paper #f4f5f0, green #22c55e, dark green #16a34a.Loader2 busy states, router.refresh() after client writes, modal overlay structure, 44px tap targets on mobile surfaces).