Skip to content

feat(rewards): geo-restriction guard for campaign opt-in and RWA tokens [RWDS-1077]#27676

Merged
VGR-GIT merged 5 commits into
mainfrom
RWDS-1077-campaign-geo
Mar 20, 2026
Merged

feat(rewards): geo-restriction guard for campaign opt-in and RWA tokens [RWDS-1077]#27676
VGR-GIT merged 5 commits into
mainfrom
RWDS-1077-campaign-geo

Conversation

@VGR-GIT

@VGR-GIT VGR-GIT commented Mar 19, 2026

Copy link
Copy Markdown
Contributor

Summary

  • Shared geo-restriction list: Extracts ONDO_RESTRICTED_COUNTRIES from useRwaTokens into app/util/ondoGeoRestrictions.ts — a single source of truth consumed by both the RWA token hook and the campaign opt-in sheet.
  • Geolocation status selector: Adds selectGeolocationStatus to the geolocationController selector module so components can observe the idle / loading / complete lifecycle.
  • Campaign opt-in guard: CampaignOptInSheet now reads geolocation and blocks the opt-in CTA while geo is still resolving (shows "Checking region…"), then shows an info banner and disables the CTA once the user is confirmed to be in a restricted country.
  • Tests: Unit tests for ONDO_RESTRICTED_COUNTRIES, the new selector, and all geo-loading / geo-restriction paths in CampaignOptInSheet.

Changelog

CHANGELOG entry: Added geo-restriction guard to campaign opt-in sheet, disabling opt-in for users in restricted regions

Related issues

Fixes:

UI — geo-restriction banner

Screenshot from 2026-03-19 11-07-20

The campaign opt-in sheet when the user's detected country is in the restricted list. The info banner reads "Not available in your region — This campaign is not available in your region due to local regulations." and the Opt in button is disabled.

Manual testing steps

  • Device in a restricted country (e.g. set geolocation to US) → banner shown, CTA disabled
  • Device in an allowed country (e.g. AU) → no banner, CTA enabled
  • Geolocation still loading → CTA shows "Checking region…" and is disabled; no banner
  • DEV mode → restriction bypassed (banner never shown)
  • Unit tests pass: yarn jest ondoGeoRestrictions geolocationController/index CampaignOptInSheet

Screenshots/Recordings

Before

After

See UI — geo-restriction banner section above.

Pre-merge author checklist

Pre-merge reviewer checklist

  • I've manually tested the PR (e.g. pull and build branch, run the app, test code being changed).
  • I confirm that this PR addresses all acceptance criteria described in the ticket it closes and includes the necessary testing evidence such as recordings and or screenshots.

🤖 Generated with Claude Code


Note

Medium Risk
Adds gating logic that can disable campaign opt-in based on geolocation state/country, which directly affects user eligibility and conversion. Risk is mitigated by DEV bypass and expanded unit test coverage for loading/restricted/allowed scenarios.

Overview
Adds a geo-restriction guard to CampaignOptInSheet: the CTA now shows Checking region… and is disabled while geolocation is idle/loading, and shows a RewardsInfoBanner + disables opt-in when the user is in a restricted region (including ONDO_HOLDING using the shared Ondo restricted list, with __DEV__ bypass).

Extracts ONDO_RESTRICTED_COUNTRIES into app/util/ondoGeoRestrictions.ts (consumed by both useRwaTokens and campaign opt-in), adds selectGeolocationStatus, and updates translations/tests to cover the new selector, shared list, and geo-loading/restriction behaviors.

Written by Cursor Bugbot for commit 3c269bd. This will update automatically on new commits. Configure here.

…okens

- Extract ONDO_RESTRICTED_COUNTRIES into shared util (ondoGeoRestrictions.ts)
  so the list is a single source of truth used by both the RWA token hook
  and the campaign opt-in sheet
- Add selectGeolocationStatus selector to read the GeolocationController
  status slice (idle / loading / complete)
- Block opt-in CTA with "Checking region…" text while geo is still loading
  (idle or loading status) to avoid a flash of the restriction banner
- Show a "Not available in your region" info banner and disable the CTA
  for users in restricted countries on ONDO_HOLDING campaigns
- Add unit tests for ondoGeoRestrictions, geolocationController selectors,
  and geo-loading / geo-restriction paths in CampaignOptInSheet

RWDS-1077

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
@VGR-GIT VGR-GIT requested a review from a team as a code owner March 19, 2026 10:18
@github-actions

Copy link
Copy Markdown
Contributor

CLA Signature Action: All authors have signed the CLA. You may need to manually re-run the blocking PR check if it doesn't pass in a few minutes.

@metamaskbot metamaskbot added the team-rewards Rewards team label Mar 19, 2026
@github-actions github-actions Bot added size-L risk-medium Moderate testing recommended · Possible bug introduction risk labels Mar 19, 2026
@metamaskbot metamaskbot added the INVALID-PR-TEMPLATE PR's body doesn't match template label Mar 19, 2026
…onController selector tests

Replace recursive DeepPartial<RootState> return type with an explicit
shallow object type to prevent TypeScript from hitting its type instantiation
depth limit (TS2589) on the large RootState tree.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
@github-actions github-actions Bot added risk-low Low testing needed · Low bug introduction risk and removed risk-medium Moderate testing recommended · Possible bug introduction risk labels Mar 19, 2026
…check

Mirrors the __DEV__ bypass already present in useRwaTokens. In dev builds
geo-restriction is always disabled so developers can test the opt-in flow
without needing to use a VPN or mock geolocation.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
@github-actions github-actions Bot added risk-medium Moderate testing recommended · Possible bug introduction risk and removed risk-low Low testing needed · Low bug introduction risk labels Mar 19, 2026
@VGR-GIT VGR-GIT enabled auto-merge March 19, 2026 11:59
@github-actions github-actions Bot added risk-low Low testing needed · Low bug introduction risk and removed risk-medium Moderate testing recommended · Possible bug introduction risk labels Mar 19, 2026

@cursor cursor Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Cursor Bugbot has reviewed your changes and found 1 potential issue.

Fix All in Cursor

Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, have a team admin enable autofix in the Cursor dashboard.

@github-actions github-actions Bot added risk-low Low testing needed · Low bug introduction risk and removed risk-low Low testing needed · Low bug introduction risk labels Mar 20, 2026
@github-actions

Copy link
Copy Markdown
Contributor

🔍 Smart E2E Test Selection

  • Selected E2E tags: SmokeWalletPlatform
  • Selected Performance tags: None (no tests recommended)
  • Risk Level: low
  • AI Confidence: 78%
click to see 🤖 AI reasoning details

E2E Test Selection:
The changes in this PR are focused on:

  1. New geolocation selector (selectGeolocationStatus): A simple new Redux selector reading GeolocationController.status. Low risk, no breaking changes.

  2. Shared geo-restriction utility (ondoGeoRestrictions.ts): Extracts the ONDO_RESTRICTED_COUNTRIES set from useRwaTokens.ts into a shared module. Pure refactoring - same data, same logic, just shared. The useRwaTokens hook (used in Trending's RWA tokens section) now imports from this shared utility.

  3. CampaignOptInSheet geo-restriction feature: New geo-restriction logic added to the campaign opt-in sheet. Shows an info banner and disables the opt-in button for users in restricted countries. This is a new feature gate, not a breaking change to existing flows.

  4. Localization strings: New strings for geo-restriction banner - additive only.

E2E Test Impact:

  • No existing E2E tests cover Rewards/Campaigns or RWA tokens directly (confirmed by searching tests/smoke/).
  • The useRwaTokens hook is used in the Trending view's RWA tokens section, which is covered by SmokeWalletPlatform (Trending tests).
  • The refactoring of ONDO_RESTRICTED_COUNTRIES could theoretically affect RWA token filtering in Trending if the import breaks, so SmokeWalletPlatform is appropriate to validate the Trending functionality still works.
  • The CampaignOptInSheet changes don't have direct E2E test coverage, but the Trending integration is the closest touchpoint.
  • No other tags are directly impacted - this doesn't touch confirmations, accounts, networks, swaps, or other major flows.

Performance Test Selection:
No performance-sensitive changes. The modifications are: (1) a new simple Redux selector, (2) a code organization refactor (extracting a constant Set to a shared file), (3) new geo-restriction UI logic in a bottom sheet component (not a list or performance-critical path), and (4) new localization strings. None of these changes affect rendering performance, data loading, account/network lists, or app startup.

View GitHub Actions results

@github-actions

Copy link
Copy Markdown
Contributor

E2E Fixture Validation — Schema is up to date
15 value mismatches detected (expected — fixture represents an existing user).
View details

@EugeniyBykov EugeniyBykov self-requested a review March 20, 2026 07:57
@sonarqubecloud

Copy link
Copy Markdown

@codecov-commenter

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 77.77778% with 4 lines in your changes missing coverage. Please review.
✅ Project coverage is 82.35%. Comparing base (eb832ce) to head (3c269bd).
⚠️ Report is 13 commits behind head on main.

Files with missing lines Patch % Lines
...ewards/components/Campaigns/CampaignOptInSheet.tsx 73.33% 3 Missing and 1 partial ⚠️
Additional details and impacted files
@@           Coverage Diff            @@
##             main   #27676    +/-   ##
========================================
  Coverage   82.34%   82.35%            
========================================
  Files        4787     4795     +8     
  Lines      123646   123774   +128     
  Branches    27511    27549    +38     
========================================
+ Hits       101822   101932   +110     
- Misses      14779    14785     +6     
- Partials     7045     7057    +12     

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

@VGR-GIT VGR-GIT added this pull request to the merge queue Mar 20, 2026
Merged via the queue into main with commit 4d25a94 Mar 20, 2026
195 of 199 checks passed
@VGR-GIT VGR-GIT deleted the RWDS-1077-campaign-geo branch March 20, 2026 11:17
@github-actions github-actions Bot locked and limited conversation to collaborators Mar 20, 2026
@metamaskbot metamaskbot added the release-7.72.0 Issue or pull request that will be included in release 7.72.0 label Mar 20, 2026
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.

Labels

INVALID-PR-TEMPLATE PR's body doesn't match template release-7.72.0 Issue or pull request that will be included in release 7.72.0 risk-low Low testing needed · Low bug introduction risk size-L team-rewards Rewards team

Projects

None yet

Development

Successfully merging this pull request may close these issues.

7 participants