Rewards System Documentation
A comprehensive walkthrough for the implementation of Scratch Cards, Bonus Coins, and In-App Purchases within the Bites Apps ecosystem.
Project Scope
This documentation covers the synchronization between the moviebites-api backend and the
bites-fe-rn-v1 React Native frontend.
Core Features
Daily Check-in
7-day streak logic with dynamic bonus coin rewards based on server-side configurations.
Scratch Cards
Interactive SVG masking for a premium mobile feel, with randomized backend reward calculation.
Coin Purchases
Full integration with Adapty SDK and REST API for secure purchase verification.
Backend Architecture
Details on Drizzle schemas, API routes, and reward processing logic in moviebites-api.
Database Schema (Drizzle ORM)
Core Tables (src/db/schema/rewards.ts)
user_balances: Trackscoins(paid) andbonus(earned).reward_transactions: Audit log for every change. Includestype,source,amount.reward_settings: Key-value store fordaily_check_in,streak_7_bonus, etc.
Deep-Dive: Feature Nesting & Flow
1. Scratch Card Lifecycle
API receives POST /scratch/:instanceId from frontend.
Verifies card ownership, ensures isScratched is false, and checks expiresAt.
Calculates reward based on template (Fixed vs Random minAmount to maxAmount).
Updates card status, increments balance, and logs transaction in one D1 batch.
2. Daily Check-in Streak
Compares today with lastCheckInDate. If split by 1 day,
newStreak = (old % 7) + 1.
Awards streak_7_bonus if newStreak == 7, otherwise daily_check_in.
3. Purchase Verification
Calls Adapty REST API to fetch the user's transaction truth.
Checks if transactionId exists in purchase_logs to prevent double-spending.
4. Episode Unlocking (Spend Flow)
Verifies series/episode existence and user's current bonus or coins balance.
Deducts cost, records unlocked_content, and logs transaction in a single atomic operation.
5. AdMob SSV Flow
AdMob server pings GET /ad-ssv-callback with signed reward metadata.
Backend validates `transaction_id` unique check before granting bonus points.
Async Processing
Uses Cloudflare Queues via reward-processor.ts for reliable reward granting
from external webhooks (Adapty, Tapjoy) with retry logic and idempotency checks.
Frontend Implementation
Implementation details for bites-fe-rn-v1 using React Native and Reanimated.
Interactive Scratch Card (ScratchCard.tsx)
Uses SharedValue for SVG path string and point counts to ensure 60fps.
Gesture.Pan() onUpdate appends coordinates to the mask path.
Once pointsCount > 100, calls runOnJS(onScratchComplete)().
Technical Touchpoints
Coin Purchase Flow
- Initiation:
rewardsService.trackPurchaseInitiatelogs intent. - Payment:
adapty.makePurchase(product)triggers OS sheet. - Verification: Success sends profileId to
POST /verify-purchase. - Refresh: Frontend calls
loadData()to update UI balances locally.
Ad Reward Flow
- Initiation:
RewardsScreencallsrewardsService.trackAdInitiate. - Display:
adMobHelper.showRewardedAdis triggered. - Refresh: Frontend waits 2s (for SSV) then calls
loadData().
Episode Unlock Flow
- Check: Page loads and checks
RewardsService.isUnlocked. - Unlock: If locked, clicking "Unlock" triggers
RewardsService.unlockEpisode.
Social Reward Flow
- Redirect: User clicks social icon -> opens platform URL.
- Claim: User returns and clicks "Claim" ->
POST /social/claim. - Validation: Backend verifies platform and grants reward once per user.
Service Mapping (rewardsService.ts)
| Method | Endpoint |
|---|---|
getBalance |
GET /balance/:userId |
scratchCard |
POST /scratch/:id |
verifyPurchase |
POST /verify-purchase |
Replication Guide
Step-by-step instructions for porting the Rewards system to your new project.
Database Setup
1. Migrations: Create the user_balances, reward_transactions,
user_scratch_cards, and reward_settings tables.
2. Initial Config: Seed reward_settings with default values (check_in=10,
streak=50, ad_reward=10).
Backend Implementation
1. Service Layer: Implement a RewardProcessor to handle balance updates.
Use transactions.
2. Routes: Create the /rewards endpoints. Ensure idempotency via
transactionId checks.
Frontend Integration
1. API Service: Port rewardsService.ts and update the baseURL.
2. UI Implementation: For Web/HTML5, adapt ScratchCard to use HTML5
Canvas or CSS masking.
External Services Setup
Configure AdMob SSV, OneSignal App IDs, and Adapty Secret Keys in your environment variables.
Admin Tools
Implement admin routes to create Scratch Card Templates and assign cards to users based on targeting (all, platform, or specific user).