Conversation
WalkthroughAdds TROv2 boost support across domain, presentation, mocks, assets, and localization: new BoostCode.trov2, two color tokens and assets, localization keys/cases, mock JSON entries, UI handling/routing for trov2, dynamic details construction, and a minor header UI adjustment. Changes
Sequence Diagram(s)sequenceDiagram
autonumber
actor User
participant View as Rewards View
participant VM as RewardDetailsViewModel
participant Domain as BoostCode
participant Loc as Localization
participant Colors as ColorEnum/Assets
participant RB as RewardBoostsView
User->>View: Open rewards UI
View->>Domain: Map boost code string -> BoostCode (e.g., "trov2")
Domain-->>View: .trov2
View->>Loc: Resolve titles (rollouts / rolloutsRewards)
View->>Colors: Resolve colors (troRewardsPrimary / troRewardsFill)
User->>View: Tap boost
View->>VM: handleBoostTap(.trov2)
VM-->>RB: Navigate to RewardBoostsView
RB->>RB: getDetailsItems(details) -> build dynamic items
RB-->>User: Render boost details (Progress shown only if percentage exists)
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~25 minutes Possibly related PRs
Suggested reviewers
Poem
Pre-merge checks and finishing touches❌ Failed checks (1 warning)
✅ Passed checks (2 passed)
✨ Finishing touches
🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Actionable comments posted: 1
🧹 Nitpick comments (3)
wxm-ios/Resources/Localizable/Localizable.xcstrings (3)
8517-8527: New analytics label “Rollouts” — confirm pluralization matches existing categoriesLooks good. Is plural “Rollouts” intentional (vs “Rollout”) to align with “Base”, “Beta”, “Compensation”? If not a proper name, consider singular for consistency.
Optional copy tweak:
- "value" : "Rollouts" + "value" : "Rollout"
8528-8538: “Rollouts Rewards” naming — align with category labelIf you switch the category to singular, mirror it here to “Rollout Rewards.” Otherwise, current plural is fine if “Rollouts” is the chosen product term.
Optional copy tweak:
- "value" : "Rollouts Rewards" + "value" : "Rollout Rewards"
8638-8648: Casing polish: prefer “See Details” for CTA consistencyMany CTAs use Title Case; consider capitalizing “Details.”
- "value" : "See details" + "value" : "See Details"
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (16)
PresentationLayer/Constants/ColorEnum.swift(1 hunks)PresentationLayer/Extensions/DomainExtensions/BoostCode+.swift(5 hunks)PresentationLayer/UIComponents/Screens/DailyRewards/Components/BoostsView.swift(2 hunks)PresentationLayer/UIComponents/Screens/DailyRewards/RewardDetailsViewModel.swift(1 hunks)PresentationLayer/UIComponents/Screens/RewardBoosts/RewardBoostsView.swift(3 hunks)PresentationLayer/UIComponents/Screens/StationRewardDetailsView.swift(1 hunks)wxm-ios/DataLayer/DataLayer/Networking/Mock/Jsons/get_device_rewards_analytics_7d.json(5 hunks)wxm-ios/DataLayer/DataLayer/Networking/Mock/Jsons/get_reward_boosts.json(1 hunks)wxm-ios/DataLayer/DataLayer/Networking/Mock/Jsons/get_reward_details.json(1 hunks)wxm-ios/DomainLayer/DomainLayer/Entities/Codables/Me/Network/NetworkDeviceRewardDetailsResponse.swift(2 hunks)wxm-ios/Resources/Colors.xcassets/Boosts/Contents.json(1 hunks)wxm-ios/Resources/Colors.xcassets/Boosts/troRewardsFill.colorset/Contents.json(1 hunks)wxm-ios/Resources/Colors.xcassets/Boosts/troRewardsPrimary.colorset/Contents.json(1 hunks)wxm-ios/Resources/Localizable/Localizable+RewardDetails.swift(2 hunks)wxm-ios/Resources/Localizable/Localizable.xcstrings(2 hunks)wxm-ios/Resources/Localizable/LocalizableString+RewardAnalytics.swift(2 hunks)
🧰 Additional context used
🧬 Code graph analysis (3)
PresentationLayer/UIComponents/Screens/StationRewardDetailsView.swift (1)
WeatherXMTests/PresentationLayer/Extensions/DomainExtensions/NetworkDeviceRewardsResponseTests.swift (1)
boostStartDateString(66-91)
PresentationLayer/UIComponents/Screens/RewardBoosts/RewardBoostsView.swift (2)
WeatherXMTests/PresentationLayer/Extensions/NumericTests.swift (1)
localizedFormatted(42-47)WeatherXMTests/PresentationLayer/Extensions/DomainExtensions/NetworkDeviceRewardsResponseTests.swift (1)
boostStartDateString(66-91)
PresentationLayer/UIComponents/Screens/DailyRewards/Components/BoostsView.swift (1)
PresentationLayer/Constants/FontsEnum.swift (1)
fontAwesome(22-24)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
- GitHub Check: WeatherXM | Unit tests | wxm-ios - iOS
🔇 Additional comments (27)
wxm-ios/Resources/Colors.xcassets/Boosts/troRewardsFill.colorset/Contents.json (1)
1-20: LGTM! Color asset properly defined.The color asset follows the standard Xcode format with valid sRGB components. The color (rgb(170, 47, 98)) provides a distinct purple/magenta shade for TRO boost UI theming.
wxm-ios/DomainLayer/DomainLayer/Entities/Codables/Me/Network/NetworkDeviceRewardDetailsResponse.swift (3)
117-117: LGTM! New enum case properly declared.The
.trov2case addition is consistent with the existingBoostCodeenum structure.
124-125: LGTM! String parsing correctly implemented.The parsing logic properly maps the
"trov2"string to the.trov2enum case, maintaining consistency with the existing pattern.
137-138: LGTM! Raw value mapping is symmetric.The
rawValueimplementation correctly returns"trov2"for the.trov2case, ensuring proper serialization/deserialization.wxm-ios/Resources/Localizable/Localizable+RewardDetails.swift (2)
71-71: LGTM! Localization case properly added.The
boostSeeDetailscase follows the established pattern for reward detail localization entries.
233-234: LGTM! Localization key mapping is correct.The key mapping returns
"reward_details_boost_see_details", maintaining consistency with the existing naming convention.wxm-ios/Resources/Colors.xcassets/Boosts/troRewardsPrimary.colorset/Contents.json (1)
1-20: LGTM! Color asset properly defined.The color asset follows the standard Xcode format with valid sRGB components. The color (rgb(222, 62, 128)) provides a vibrant pink/magenta shade that complements the fill color for TRO boost UI elements.
PresentationLayer/UIComponents/Screens/DailyRewards/RewardDetailsViewModel.swift (1)
227-227: LGTM! Routing logic correctly extended.The
.trov2case is appropriately added to the switch statement, routing TROv2 boosts through the same handling path as beta rewards and corrections. This reuses the existingRewardsBoostViewModeland navigation logic effectively.wxm-ios/Resources/Colors.xcassets/Boosts/Contents.json (1)
1-6: LGTM!Standard Xcode asset catalog metadata for the Boosts color group.
PresentationLayer/Constants/ColorEnum.swift (1)
70-71: LGTM!The new TRO color tokens follow the established naming convention and are properly placed alongside other reward-related colors.
PresentationLayer/UIComponents/Screens/DailyRewards/Components/BoostsView.swift (2)
25-32: LGTM!The "See Details" link with chevron provides clear navigation affordance. Using
foregroundStyleis appropriate for iOS 15+.
43-49: LGTM!Moving the amount display to a separate row maintains the information while accommodating the new "See Details" link above.
PresentationLayer/UIComponents/Screens/RewardBoosts/RewardBoostsView.swift (3)
10-10: LGTM!Import needed for the
BoostDetailsView.Itemtype used in the new helper method.
78-78: LGTM!Replacing hardcoded items with dynamic construction allows the view to adapt to different boost types.
130-152: LGTM!The helper method properly handles optional detail fields, conditionally building the items array. The boost period is always included as it's a required field. This refactor enables support for TROv2 and future boost types with varying field availability.
wxm-ios/DataLayer/DataLayer/Networking/Mock/Jsons/get_reward_boosts.json (1)
1-16: LGTM!The restructured schema for TROv2 boost details is consistent with the UI changes in
RewardBoostsView.swift, which now conditionally renders detail items based on field availability. The simplified details block (station_hours and date range) aligns with the optional field handling implemented in thegetDetailsItemsmethod.PresentationLayer/Extensions/DomainExtensions/BoostCode+.swift (5)
16-17: LGTM!TROv2 display name mapped to the rollouts localization key.
29-30: LGTM!TROv2 primary color mapped to the new
troRewardsPrimarytoken.
42-43: LGTM!TROv2 fill color mapped to the new
troRewardsFilltoken.
55-56: LGTM!TROv2 chart color mapped to
troRewardsPrimary, consistent with the beta rewards pattern.
68-69: LGTM!TROv2 legend title mapped to the rolloutsRewards localization key. All computed properties now comprehensively support the TROv2 boost type.
wxm-ios/DataLayer/DataLayer/Networking/Mock/Jsons/get_reward_details.json (1)
35-43: No change needed for missing max_reward in TROv2 mock. Themax_rewardfield is optional (Double?) and only used for Beta boosts’lostRewardString; for TROv2 (default case) it decodes toniland the UI handles it gracefully.Likely an incorrect or invalid review comment.
PresentationLayer/UIComponents/Screens/StationRewardDetailsView.swift (3)
25-32: LGTM! Good defensive programming.Making the ProgressView conditional prevents rendering a progress bar when completion data is unavailable, which improves UX and avoids misleading users.
35-35: LGTM! Clean refactor.Moving the items construction to a computed property improves readability and maintainability.
40-58: Verify boost period display for nil dates
In StationRewardDetailsView (l.54) and RewardBoostsView (l.149),"\(details.boostStartDateString) - \(details.boostStopDateString)"renders as" - "when both dates are nil. Consider hiding the boost period row or showing a placeholder instead of empty strings.wxm-ios/Resources/Localizable/LocalizableString+RewardAnalytics.swift (2)
23-24: LGTM! Consistent naming pattern.The new enum cases follow the established pattern used by other boost types (e.g.,
beta/betaRewards,compensation/compensationRewards), which maintains consistency across the codebase.
79-82: Localization keys verifiedKeys
reward_analytics_rolloutsandreward_analytics_rollouts_rewardsare present inLocalizable.xcstrings, and.rollouts/.rolloutsRewardsare referenced in the code.
| { | ||
| "code": "trov2", | ||
| "type": "TROv2", | ||
| "boost_period_start": "2025-09-10T00:00:00.000Z", | ||
| "boost_period_end": "2025-09-11T00:00:00.000Z" | ||
| } |
There was a problem hiding this comment.
🧩 Analysis chain
Verify intentionally missing fields in TROv2 details.
The TROv2 details entry omits current_rewards, total_rewards, and completed_percentage fields that are present in other boost detail entries (e.g., lines 136-143). If these fields are intentionally omitted for TROv2 boosts, ensure the UI handles their absence gracefully. Otherwise, add them for consistency.
Run the following script to check how the app handles optional detail fields:
🏁 Script executed:
#!/bin/bash
# Description: Verify handling of optional detail fields in TROv2
# Search for code that accesses these optional fields
rg -nP --type=swift -C3 '\b(currentRewards|totalRewards|completedPercentage)\b' -g '!*Test*'Length of output: 29078
Include missing reward fields in TROv2 analytics mock
Add current_rewards, total_rewards, and completed_percentage to the TROv2 details entry so it aligns with the NetworkDeviceRewardsResponse.Details model and renders correctly in the UI.
🤖 Prompt for AI Agents
In
wxm-ios/DataLayer/DataLayer/Networking/Mock/Jsons/get_device_rewards_analytics_7d.json
around lines 162 to 167, the TROv2 details object is missing the required fields
current_rewards, total_rewards, and completed_percentage; update that JSON entry
to include these three fields with appropriate numeric values (e.g.,
current_rewards and total_rewards as numbers and completed_percentage as a
number between 0 and 100) so the mock conforms to
NetworkDeviceRewardsResponse.Details and the UI renders correctly.
Code Coverage Summary
|
348ed29 to
2b345f3
Compare
Code Coverage Summary
|
2b345f3 to
cde11ec
Compare
There was a problem hiding this comment.
Actionable comments posted: 1
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (16)
PresentationLayer/Constants/ColorEnum.swift(1 hunks)PresentationLayer/Extensions/DomainExtensions/BoostCode+.swift(5 hunks)PresentationLayer/UIComponents/Screens/DailyRewards/Components/BoostsView.swift(2 hunks)PresentationLayer/UIComponents/Screens/DailyRewards/RewardDetailsViewModel.swift(1 hunks)PresentationLayer/UIComponents/Screens/RewardBoosts/RewardBoostsView.swift(3 hunks)PresentationLayer/UIComponents/Screens/StationRewardDetailsView.swift(1 hunks)wxm-ios/DataLayer/DataLayer/Networking/Mock/Jsons/get_device_rewards_analytics_7d.json(5 hunks)wxm-ios/DataLayer/DataLayer/Networking/Mock/Jsons/get_reward_boosts.json(1 hunks)wxm-ios/DataLayer/DataLayer/Networking/Mock/Jsons/get_reward_details.json(1 hunks)wxm-ios/DomainLayer/DomainLayer/Entities/Codables/Me/Network/NetworkDeviceRewardDetailsResponse.swift(2 hunks)wxm-ios/Resources/Colors.xcassets/Boosts/Contents.json(1 hunks)wxm-ios/Resources/Colors.xcassets/Boosts/troRewardsFill.colorset/Contents.json(1 hunks)wxm-ios/Resources/Colors.xcassets/Boosts/troRewardsPrimary.colorset/Contents.json(1 hunks)wxm-ios/Resources/Localizable/Localizable+RewardDetails.swift(2 hunks)wxm-ios/Resources/Localizable/Localizable.xcstrings(2 hunks)wxm-ios/Resources/Localizable/LocalizableString+RewardAnalytics.swift(2 hunks)
✅ Files skipped from review due to trivial changes (3)
- wxm-ios/Resources/Colors.xcassets/Boosts/troRewardsPrimary.colorset/Contents.json
- wxm-ios/Resources/Colors.xcassets/Boosts/troRewardsFill.colorset/Contents.json
- wxm-ios/Resources/Colors.xcassets/Boosts/Contents.json
🚧 Files skipped from review as they are similar to previous changes (8)
- wxm-ios/DataLayer/DataLayer/Networking/Mock/Jsons/get_reward_details.json
- wxm-ios/Resources/Localizable/Localizable.xcstrings
- PresentationLayer/UIComponents/Screens/StationRewardDetailsView.swift
- wxm-ios/DomainLayer/DomainLayer/Entities/Codables/Me/Network/NetworkDeviceRewardDetailsResponse.swift
- PresentationLayer/UIComponents/Screens/DailyRewards/RewardDetailsViewModel.swift
- PresentationLayer/UIComponents/Screens/RewardBoosts/RewardBoostsView.swift
- wxm-ios/Resources/Localizable/Localizable+RewardDetails.swift
- wxm-ios/DataLayer/DataLayer/Networking/Mock/Jsons/get_device_rewards_analytics_7d.json
🧰 Additional context used
🧬 Code graph analysis (1)
PresentationLayer/UIComponents/Screens/DailyRewards/Components/BoostsView.swift (1)
PresentationLayer/Constants/FontsEnum.swift (1)
fontAwesome(22-24)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
- GitHub Check: WeatherXM | Unit tests | wxm-ios - iOS
🔇 Additional comments (6)
wxm-ios/Resources/Localizable/LocalizableString+RewardAnalytics.swift (1)
23-24: LGTM! Localization keys properly added for TROv2 rollouts.The new enum cases and their key mappings follow the established pattern for boost-related localization entries. The implementation is consistent with existing beta and compensation reward cases.
Also applies to: 79-82
PresentationLayer/Constants/ColorEnum.swift (1)
70-71: LGTM! Color tokens properly added for TROv2 visual styling.The new color enum cases follow the established naming convention and are positioned logically alongside other boost-related color tokens.
PresentationLayer/UIComponents/Screens/DailyRewards/Components/BoostsView.swift (3)
25-32: LGTM! "See details" indicator properly added.The UI enhancement with localized text and chevron icon improves the user experience by clearly indicating that the boost item is tappable for more details.
42-49: LGTM! Rewards display properly restructured.The HStack restructuring provides better spacing and layout for the rewards information.
1-66: AI summary mentions changes not visible in the provided code.The AI summary states: "Replaced the previous inline construction of BoostDetailsView items with a new helper function getDetailsItems(details:)" and mentions DomainLayer import and BoostDetailsView initialization changes. However, these changes are not visible in the provided annotated code, which only shows UI modifications to the header and rewards display sections.
PresentationLayer/Extensions/DomainExtensions/BoostCode+.swift (1)
16-17: LGTM! Comprehensive TROv2 boost code support added.All computed properties are properly updated to handle the new
.trov2case with appropriate mappings to color tokens and localization keys. The implementation is consistent with existing boost code patterns and ensures exhaustive switch coverage.Also applies to: 29-30, 42-43, 55-56, 68-69
| "title": "TROv2 Rewards", | ||
| "description": "A reward boost used to distribute additional rewards to TROv2 devices", | ||
| "total_rewardable_hours": 39563725, | ||
| "about": "Stations deployed in Targeted Rollouts (TROv2) will earn extra rewards for 2 years. \n Here’s how it works: \nevery day, your station earns its normal Base Reward\n on top of that, you’ll get a Rewards Boost equal to your Base Reward so your daily rewards = Base Reward + Rewards Boost (equal to base) \n \nThese boosted rewards are added to the total pool and shared as usual:\n25% goes to deployers \n75% goes to the supporters pool", |
There was a problem hiding this comment.
Keep mock duration consistent with the described 2‑year boost
Metadata line 8 states the TROv2 boost runs for 2 years, but the dates define only ~11.5 months (2025‑10‑04 → 2026‑09‑19). This mismatch can mislead mock consumers and skew any duration‑based logic/tests. Please align the stop date with a full two‑year window.
"boost_start_date": "2025-10-04T00:00:00.000Z",
- "boost_stop_date": "2026-09-19T00:00:00.000Z"
+ "boost_stop_date": "2027-10-03T00:00:00.000Z"Also applies to: 13-14
🤖 Prompt for AI Agents
In wxm-ios/DataLayer/DataLayer/Networking/Mock/Jsons/get_reward_boosts.json
around line 8 (and also lines 13-14), the mock text claims a 2‑year boost but
the date range only covers ~11.5 months; update the stop date(s) so the period
is a full two years from the stated start date (e.g., if start is 2025-10-04,
change stop to 2027-10-04) and make the same adjustment for the other date
entries on lines 13-14 so the mock duration matches the described 2-year boost.
Code Coverage Summary
|
cde11ec to
d8b0ffb
Compare
Code Coverage Summary
|
Why?
Handle TRO boost code
How?
Testing
Test the mock scheme and ensure everything is handled properly
Additional context
fixes fe-2019
Summary by CodeRabbit
New Features
Style