Skip to content

Community feature#121

Merged
apps4av merged 4 commits into
masterfrom
community-feature
May 26, 2026
Merged

Community feature#121
apps4av merged 4 commits into
masterfrom
community-feature

Conversation

@apps4av
Copy link
Copy Markdown
Owner

@apps4av apps4av commented May 26, 2026

No description provided.

apps4av and others added 4 commits May 25, 2026 17:22
A pilot-only social network on Firestore, gated behind the same
RevenueCat Pro entitlement as Flight Intelligence and Backup/Sync.

Features:
- Create, discover, join, and leave groups (public or private)
- Private groups: discoverable by name, owner approves each request
- Per-group feed with posts (1000 chars + optional ICAO tag)
- Members tab with owner-only approve/reject/remove controls
- Editable pilot profile (name, home airport, ratings, aircraft, bio)
- iOS/Android only, in-app notifications only (red badge on Members tab)

Backend:
- firestore.rules with self-only profile writes, owner-only deletes,
  public/private feed gating, and counter-only updates for members
- firestore.indexes.json + .firebaserc preconfigured for the project
- All Firestore access funneled through CommunityRepository

UI:
- Entry point: Pro Services bottom sheet -> Community
- Routed at /community via the existing showPaywall(...) helper
- Friendly setup banner shown if Firestore rules haven't been deployed

Docs:
- USER_MANUAL.md: new section 11.4, updated Pro row in platform table,
  six new entries in the Section 14 path index, UC-24 and UC-25 added

Co-authored-by: Cursor <cursoragent@cursor.com>
Fixes the security audit findings on the v1 Community rules. All
changes are rules-only except a small members-screen tweak so that
non-members of private groups see a friendly message instead of a raw
permission-denied error.

Critical / high:
- Counter updates now require an exact +/-1 delta and forbid negative
  values, instead of allowing any signed-in user to set memberCount
  and postCount to arbitrary numbers (audit #1). Long-term fix is a
  Cloud Function trigger; documented in the rules file.
- All user-writable documents (profile, group, member, post,
  userGroups index) are now whitelisted on field keys and validated
  on types, lengths, and enum values, closing latent privilege
  escalation paths and DoS via oversized documents (audit #2, #4, #8,
  #12, #13).
- Removed the unconstrained isGroupOwner(gid) branch on member create.
  Owner approvals now flow through update of an existing pending doc,
  with status pinned to pending -> active and role/joinedAt frozen
  (audit #3).

Medium:
- Member rosters are no longer enumerable by strangers. Reads of
  groups/{gid}/members require self, owner, public visibility, or
  active membership (audit #6).
- Posts are now bounded to 1000 characters at the rule level (audit
  #7) and to a fixed field whitelist (audit #8).

Hardening:
- isActiveMember consolidated to a single get() lookup pattern via
  helper functions (audit #10 partial).
- All timestamps validated as `is timestamp`; full server-timestamp
  enforcement deferred to a future Cloud Function (audit #13).

Knowingly not fixed in v1 (documented inline):
- Group metadata visibility: the group doc remains readable by any
  signed-in pilot so the Discover tab can surface private groups by
  name. Sensitive future fields must live in a separate restricted
  subcollection (audit #5).
- Counter drift under adversarial use: ruled-bounded to +/-1 per call;
  long-term fix requires Cloud Functions (audit #11).
- Owners can technically self-delete their membership through this
  rule; rules cannot distinguish "owner leaves" from "owner deletes
  group". The client repository blocks owner-leave at call time
  (audit #9).

Co-authored-by: Cursor <cursoragent@cursor.com>
Fixes "Looking up a deactivated widget's ancestor is unsafe" crash
when a Join/Leave/Delete future completes after the user has navigated
away from the screen.

- JoinLeaveButton._say bails when the button is unmounted before
  invoking the parent's onMessage closure. This was the source of the
  reported stack: _say -> onMessage -> Toast.showToast -> Theme.of
  against a deactivated element.
- _MembershipBanner.onMessage additionally guards with context.mounted
  since it is a StatelessWidget whose element can be deactivated by a
  parent rebuild while the child button is still mounted.
- Four other catch blocks (group create, post compose, profile edit,
  group delete) wrap their Toast.showToast call in a mounted check so
  failed-write toasts cannot fire after navigation.

Co-authored-by: Cursor <cursoragent@cursor.com>
- New _DisclaimerStrip widget shown above the tabs on the main
  Community screen: a compact, always-visible reminder that tap-opens
  the full disclaimer.
- Info icon in the AppBar opens the same disclaimer dialog so it's
  reachable from anywhere on the screen.
- Four points covered in the dialog:
    * Apps4Av is not responsible for data loss
    * Don't share sensitive information
    * Apps4Av does not moderate community activity
    * Apps4Av will not share data with third parties
- USER_MANUAL section 11.4 lists the same four points.

Co-authored-by: Cursor <cursoragent@cursor.com>
@apps4av apps4av merged commit edddfa7 into master May 26, 2026
3 of 5 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant