New `mobile` Django app mounted at /app/ -- the installed PWA for Member mode (M1-M7, see design_handoff_rosterchief_platform/README.md). Coach mode (C1-C6) is a later phase and has no routes yet. Foundation pieces: - assets/mobile.css: Tailwind v4 theme reusing management.css's design tokens (same per-club --tenant-* theming pattern), plus the ice/coach accent and mobile's 14px card radius. - PushSubscription model + pywebpush-based sender (mobile/services/push.py), wired to notifications.Notification via a post_save signal so the existing notification system gains a push channel without knowing about PWAs itself. - Per-club manifest.webmanifest + service worker (served at /app/sw.js) + a server-rendered fallback home-screen icon (club initials on secondary_color) for clubs without an uploaded logo -- confirmed with the user as the fallback, never a generic RosterChief mark. - App shell (base.html): navy header, person switcher (every child a signed-in parent manages, plus "Me"), bottom tab bar, safe-area insets. Vendored htmx + Alpine for the screens built on top of it. - Placeholder views/routes for all seven M1-M7 screens so the shell is fully wired end-to-end before each screen is built out individually. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01ECGMEwrc2k4D8VQuwjstj9
22 lines
978 B
Python
22 lines
978 B
Python
from django.urls import path
|
|
|
|
from . import views
|
|
|
|
app_name = "mobile"
|
|
|
|
urlpatterns = [
|
|
# PWA plumbing.
|
|
path("manifest.webmanifest", views.ManifestView.as_view(), name="manifest"),
|
|
path("sw.js", views.ServiceWorkerView.as_view(), name="service_worker"),
|
|
path("icon/<int:size>.png", views.AppIconView.as_view(), name="icon"),
|
|
path("push/subscribe/", views.PushSubscribeView.as_view(), name="push_subscribe"),
|
|
# Member mode (M1-M7).
|
|
path("", views.HomeView.as_view(), name="home"),
|
|
path("calendar/", views.CalendarView.as_view(), name="calendar"),
|
|
path("events/<uuid:pk>/", views.EventDetailView.as_view(), name="event_detail"),
|
|
path("news/<slug:slug>/", views.NewsDetailView.as_view(), name="news_detail"),
|
|
path("me/", views.MeView.as_view(), name="me"),
|
|
path("me/<uuid:member_id>/edit/", views.EditProfileView.as_view(), name="edit_profile"),
|
|
path("notifications/", views.NotificationsView.as_view(), name="notifications"),
|
|
]
|