Skip to content

[PM 30100][Server] Subscription Discount Database Infrastructure#6936

Merged
cyprain-okeke merged 16 commits intomainfrom
billing/pm-30100/server-subscription-discount-database-infrastructure
Feb 6, 2026
Merged

[PM 30100][Server] Subscription Discount Database Infrastructure#6936
cyprain-okeke merged 16 commits intomainfrom
billing/pm-30100/server-subscription-discount-database-infrastructure

Conversation

@cyprain-okeke
Copy link
Contributor

🎟️ Tracking

https://bitwarden.atlassian.net/browse/PM-30100

📔 Objective

Improve type safety for StripeProductIds in the SubscriptionDiscount entity by changing it from a raw JSON string (string?) to a strongly-typed collection (ICollection?).

This change was suggested during code review to:

  • Provide compile-time type safety instead of runtime JSON parsing
  • Make the API more discoverable (IntelliSense shows it's a collection)
  • Prevent malformed JSON bugs
  • Simplify business logic (no manual JSON serialization/deserialization needed)

🔧 Changes Made

Core Entity

  • Changed StripeProductIds from string? to ICollection? in SubscriptionDiscount.cs
    Data Access Layer
  • EF Core: Added HasConversion() in SubscriptionDiscountEntityTypeConfiguration to automatically serialize/deserialize collections to/from JSON
  • Dapper: Created JsonCollectionTypeHandler and registered it in BaseRepository for JSON conversion

Tests

  • Updated integration test parameter types and test data to use actual collections (e.g., new List { "prod_123" } instead of "["prod_123"]")
  • Added comprehensive unit tests in SubscriptionDiscountTests.cs to verify JSON serialization/deserialization, null handling, and empty collections

📸 Screenshots

⏰ Reminders before review

  • Contributor guidelines followed
  • All formatters and local linters executed and passed
  • Written new unit and / or integration tests where applicable
  • Protected functional changes with optionality (feature flags)
  • Used internationalization (i18n) for all UI strings
  • CI builds passed
  • Communicated to DevOps any deployment requirements
  • Updated any necessary documentation (Confluence, contributing docs) or informed the documentation team

🦮 Reviewer guidelines

  • 👍 (:+1:) or similar for great changes
  • 📝 (:memo:) or ℹ️ (:information_source:) for notes or general info
  • ❓ (:question:) for questions
  • 🤔 (:thinking:) or 💭 (:thought_balloon:) for more open inquiry that's not quite a confirmed issue and could potentially benefit from discussion
  • 🎨 (:art:) for suggestions / improvements
  • ❌ (:x:) or ⚠️ (:warning:) for more significant problems or concerns needing attention
  • 🌱 (:seedling:) or ♻️ (:recycle:) for future improvements or indications of technical debt
  • ⛏ (:pick:) for minor or nitpick changes

@cyprain-okeke cyprain-okeke requested review from a team as code owners February 2, 2026 16:10
@cyprain-okeke cyprain-okeke requested a review from kdenney February 2, 2026 16:10
@github-actions
Copy link
Contributor

github-actions bot commented Feb 2, 2026

Logo
Checkmarx One – Scan Summary & Detailsdc07cb42-ba50-4dea-b15b-b2441f7dec4c

New Issues (2)

Checkmarx found the following issues in this Pull Request

# Severity Issue Source File / Package Checkmarx Insight
1 MEDIUM CSRF /src/Api/Vault/Controllers/CiphersController.cs: 1527
detailsMethod at line 1527 of /src/Api/Vault/Controllers/CiphersController.cs gets a parameter from a user request from id. This parameter value flows ...
Attack Vector
2 MEDIUM CSRF /src/Api/Vault/Controllers/CiphersController.cs: 1403
detailsMethod at line 1403 of /src/Api/Vault/Controllers/CiphersController.cs gets a parameter from a user request from id. This parameter value flows ...
Attack Vector
Fixed Issues (4)

Great job! The following issues were fixed in this Pull Request

Severity Issue Source File / Package
MEDIUM CSRF /src/Api/KeyManagement/Controllers/AccountsKeyManagementController.cs: 145
MEDIUM CSRF /src/Api/Vault/Controllers/CiphersController.cs: 847
MEDIUM CSRF /src/Api/Vault/Controllers/CiphersController.cs: 847
MEDIUM CSRF /src/Api/Vault/Controllers/CiphersController.cs: 293

@codecov
Copy link

codecov bot commented Feb 2, 2026

Codecov Report

❌ Patch coverage is 94.01709% with 7 lines in your changes missing coverage. Please review.
✅ Project coverage is 60.27%. Comparing base (0159052) to head (fd4672a).
⚠️ Report is 2 commits behind head on main.

Files with missing lines Patch % Lines
...e.Dapper/Repositories/JsonCollectionTypeHandler.cs 46.15% 4 Missing and 3 partials ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##             main    #6936      +/-   ##
==========================================
+ Coverage   60.21%   60.27%   +0.05%     
==========================================
  Files        1976     1982       +6     
  Lines       87536    87653     +117     
  Branches     7810     7816       +6     
==========================================
+ Hits        52714    52830     +116     
+ Misses      32907    32904       -3     
- Partials     1915     1919       +4     

☔ 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.

cyprain-okeke and others added 7 commits February 3, 2026 09:15
The previous migrations were missing .Designer.cs files. This commit:
- Removes the incomplete migration files
- Regenerates all three provider migrations (MySQL, Postgres, SQLite) with proper Designer files
- Updates DatabaseContextModelSnapshot.cs for each provider

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
kdenney
kdenney previously approved these changes Feb 3, 2026
Copy link
Contributor

@kdenney kdenney left a comment

Choose a reason for hiding this comment

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

Looks good!

Copy link
Contributor

@mkincaid-bw mkincaid-bw left a comment

Choose a reason for hiding this comment

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

Minor changes requested.

@@ -0,0 +1,19 @@
CREATE VIEW [dbo].[SubscriptionDiscountView]
AS
SELECT
Copy link
Contributor

Choose a reason for hiding this comment

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

The preferred format for simple single table views is to select * from the table (unless some for of transformation is needed on one or more of the columns).
https://contributing.bitwarden.com/contributing/code-style/sql#views

CREATE OR ALTER VIEW [dbo].[SubscriptionDiscountView]
AS
SELECT
[Id],
Copy link
Contributor

Choose a reason for hiding this comment

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

The preferred format for simple single table views is to select * from the table (unless some for of transformation is needed on one or more of the columns).
https://contributing.bitwarden.com/contributing/code-style/sql#views

GO
CREATE NONCLUSTERED INDEX [IX_SubscriptionDiscount_DateRange]
ON [dbo].[SubscriptionDiscount]([StartDate] ASC, [EndDate] ASC)
INCLUDE([StripeProductIds], [AudienceType]);
Copy link
Contributor

Choose a reason for hiding this comment

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

❓ In the SubscriptionDiscount_ReadActive proc, you are selecting * from the table for the specified date range. SQL Server will still need to reference the underlying table for the rest of the columns, so these extra INCLUDE columns are just taking up extra space. Do you need these INCLUDE columns for another query outside of this proc?

.HasMaxLength(100)
.HasColumnType("varchar(100)");

b.Property<decimal?>("PercentOff")
Copy link
Contributor

Choose a reason for hiding this comment

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

This does not align with the SQL server column with a DECIMAL(5,2) data type.

Suggested change
b.Property<decimal?>("PercentOff")
b.Property<decimal?>("PercentOff")
.HasPrecision(5, 2)

kdenney
kdenney previously approved these changes Feb 5, 2026
@cyprain-okeke cyprain-okeke force-pushed the billing/pm-30100/server-subscription-discount-database-infrastructure branch from fba257f to 2055931 Compare February 6, 2026 15:53
@sonarqubecloud
Copy link

sonarqubecloud bot commented Feb 6, 2026

Copy link
Contributor

@mkincaid-bw mkincaid-bw left a comment

Choose a reason for hiding this comment

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

LGTM

@cyprain-okeke cyprain-okeke requested a review from kdenney February 6, 2026 16:26
@cyprain-okeke cyprain-okeke merged commit 67ba9bc into main Feb 6, 2026
52 of 53 checks passed
@cyprain-okeke cyprain-okeke deleted the billing/pm-30100/server-subscription-discount-database-infrastructure branch February 6, 2026 17:24
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.

3 participants