Skip to content

LEGLINK-807: Implement Measure Mappings Functionality - #1807

Merged
johnbritton merged 10 commits into
devfrom
users/jbritton/LEGLINK-807
Aug 11, 2026
Merged

LEGLINK-807: Implement Measure Mappings Functionality#1807
johnbritton merged 10 commits into
devfrom
users/jbritton/LEGLINK-807

Conversation

@johnbritton

@johnbritton johnbritton commented Aug 10, 2026

Copy link
Copy Markdown
Contributor

🛠️ Description of Changes

Add a Measure Mappings API.

🧪 Testing Performed

Tested with Postman.

🧑‍🔬 Unit Testing

  • I have written or updated unit tests to cover my changes
  • Coverage: 12.9%

📓 Documentation Updated

Please update any relevant sections in the project documentation that were impacted by the changes in the PR.

Summary by CodeRabbit

  • New Features
    • Added measure mapping fields for Measure, DQM, and Frequency.
    • Added filtered, sortable, and paginated search.
    • Added validation for referenced DQMs and required request values.
    • Added bulk deletion of all measure mappings.
  • Bug Fixes
    • Duplicate measure/DQM combinations now return clear validation errors.
    • Updates preserve existing values when validation fails.
    • Measure mapping updates now correctly persist all submitted fields.

@coderabbitai

coderabbitai Bot commented Aug 10, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

Important

Review skipped

Auto incremental reviews are disabled on this repository.

Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro Plus

Run ID: e4980fc0-b63a-4b12-94c8-b8a5831be9d6

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Use the checkbox below for a quick retry:

  • 🔍 Trigger review
📝 Walkthrough

Walkthrough

Measure mappings now store measure, DQM, and frequency values. Search supports sanitized filters and paging. Create and update validate DQMs and duplicate mappings. A delete-all endpoint and tenant migration were added.

Changes

Measure mapping lifecycle

Layer / File(s) Summary
Mapping data and database contract
DotNet/DMRP/Data/Entities/MeasureMapping.cs, DotNet/DMRP/Data/Repository/Mappings/MeasureMappingConfigMap.cs, DotNet/Shared/Application/Models/Integration/DMRP/DMRPApiModels.cs, DotNet/Tenant/Migrations/*
Measure mappings now include validated Measure, DQM, and Frequency fields. The tenant schema adds these columns and a unique (Measure, DQM) index.
Filtered paging search
DotNet/DMRP/Models/SearchMeasureMappingDto.cs, DotNet/DMRP/Business/Queries/MeasureMappingQueries.cs, DotNet/DMRP/Controllers/MeasureMappingsController.cs, DotNet/ServiceTests/UnitTests/DMRP/MeasureMappingQueriesTests.cs, DotNet/ServiceTests/IntegrationTests/DMRP/MeasureMappingsControllerTests.cs
Search uses sanitized DTO values, optional measure, DQM, and frequency filters, and populated response models.
Validated writes and bulk deletion
DotNet/DMRP/Business/Managers/MeasureMappingManager.cs, DotNet/DMRP/Controllers/MeasureMappingsController.cs, DotNet/ServiceTests/IntegrationTests/DMRP/MeasureMappingsControllerTests.cs, DotNet/DMRP/DMRP.csproj, DotNet/*/packages.lock.json, Tests/BackendE2ETests/packages.lock.json
Create and update classify database uniqueness errors, validate DQMs through MeasureEval, preserve updated fields, and return structured validation errors. Bulk deletion removes all mappings and reports failures. LinkSdk and related dependency resolutions were added.

Estimated code review effort: 3 (Moderate) | ~25 minutes

Sequence Diagram(s)

sequenceDiagram
  participant Client
  participant MeasureMappingsController
  participant MeasureEval
  participant MeasureMappingManager
  participant TenantDatabase
  Client->>MeasureMappingsController: Submit mapping
  MeasureMappingsController->>MeasureEval: Validate DQM
  MeasureEval-->>MeasureMappingsController: Return validation status
  MeasureMappingsController->>MeasureMappingManager: Save mapping
  MeasureMappingManager->>TenantDatabase: Persist mapping
  TenantDatabase-->>MeasureMappingManager: Return save result
  MeasureMappingManager-->>MeasureMappingsController: Return mapping or duplicate error
  MeasureMappingsController-->>Client: Return API response
Loading

Possibly related PRs

Suggested reviewers: smailliwcs

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 75.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
Title check ✅ Passed The title clearly identifies the implementation of Measure Mappings functionality and matches the main changes.
Description check ✅ Passed The description covers the changes, testing, unit tests, coverage, and documentation sections required by the template.
✨ Finishing Touches 💡 1
📝 Generate docstrings 💡
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch users/jbritton/LEGLINK-807

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.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@coderabbitai coderabbitai 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.

Actionable comments posted: 6

🧹 Nitpick comments (3)
DotNet/DMRP/Business/Managers/MeasureMappingManager.cs (2)

18-19: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Add XUnit coverage for DeleteAllAsync branches.

IMeasureMappingManager has one concrete implementation, and it already provides DeleteAllAsync. Add small focused tests for the success path, OperationCanceledException propagation, and the generic/DbUpdateException error paths.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@DotNet/DMRP/Business/Managers/MeasureMappingManager.cs` around lines 18 - 19,
Add focused xUnit coverage for DeleteAllAsync in the concrete
IMeasureMappingManager implementation, covering successful completion,
propagation of OperationCanceledException, generic exception handling, and
DbUpdateException handling. Reuse the existing test setup and assertions for
manager error behavior, keeping each branch test small and isolated.

53-72: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Add focused XUnit coverage for the new branches.

MeasureMappingManagerTests.cs does not cover the SQLite 2067 and SQL Server 2601/2627 unique-failure branches introduced by IsUniqueIndexViolation(), nor the non-unique commit failure branches for CreateAsync and UpdateAsync. Add focused repository-mock tests for CreateAsync, UpdateAsync, and DeleteAllAsync (records, empty set, cancellation, and repository save failure). Do not use a network database.

Applies to: 53-72, 97-102, 139-162

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@DotNet/DMRP/Business/Managers/MeasureMappingManager.cs` around lines 53 - 72,
Expand MeasureMappingManagerTests with focused XUnit repository-mock coverage
for CreateAsync, UpdateAsync, and DeleteAllAsync, including records, empty
results, cancellation, and save failures. Add CreateAsync tests that trigger
IsUniqueIndexViolation for SQLite error 2067 and SQL Server errors 2601/2627,
plus non-unique commit failures for both CreateAsync and UpdateAsync; assert the
expected exception and activity behavior without using a network database.

Source: Path instructions

DotNet/DMRP/Models/SearchMeasureMappingDto.cs (1)

21-29: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Add focused XUnit tests for each normalization branch.

Add tests for PageSize below 1, above 100, and within range. Add tests for PageNumber below 1 and within range. Also verify the new string-filter sanitization.

As per path instructions, "If/Else or Switch/Case blocks are introduced or modified — ensure each branch has a corresponding unit test."

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@DotNet/DMRP/Models/SearchMeasureMappingDto.cs` around lines 21 - 29, Add
focused xUnit tests for the normalization logic in SearchMeasureMappingDto,
covering PageSize below 1, above 100, and within the valid range, plus
PageNumber below 1 and within range. Add assertions for the string-filter
sanitization introduced alongside this logic, with each conditional branch
exercised independently.

Source: Path instructions

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@DotNet/DMRP/Controllers/MeasureMappingsController.cs`:
- Around line 247-250: Update DqmExistsAsync in
DotNet/DMRP/Controllers/MeasureMappingsController.cs (lines 247-250) to
distinguish a 404 from other MeasureEval failures, propagating non-404 errors so
they are not reported as missing DQMs. Update the endpoints at lines 101-104 and
153-156 to return RFC Problem Details with a standard 502 or 503 for those
upstream failures. Extend
DotNet/ServiceTests/IntegrationTests/DMRP/MeasureMappingsControllerTests.cs
lines 33-41 with mocked 5xx responses and assertions for the gateway status and
problem-details response.
- Around line 216-217: Apply the existing ValidateAntiForgeryOrBearerToken
validation attribute to the DeleteAllMeasureMappings action, matching the
protection already used by the create and update endpoints while leaving its
deletion behavior unchanged.
- Around line 48-49: Update MeasureMappingsController.GetMeasureMappings to bind
SearchMeasureMappingDto from the query string by adding the appropriate
query-binding annotation, while preserving the existing GET route and
cancellation token behavior.

In `@DotNet/DMRP/Models/SearchMeasureMappingDto.cs`:
- Around line 17-20: Update SearchMeasureMappingDto.Sanitize() to sanitize the
Measure and DQM string query parameters as well as SortBy, using
HtmlInputSanitizer.Sanitize() or SanitizeAndRemove() as appropriate before the
values reach MeasureMappingQueries.

In `@DotNet/Shared/Application/Models/Integration/DMRP/DMRPApiModels.cs`:
- Around line 15-19: Add the StringLength validation attribute with a
255-character limit to both the Measure and DQM properties in the DMRP API
model, preserving their existing Required attributes so oversized requests are
rejected at the API boundary.

In `@DotNet/Tenant/Migrations/20260806183143_AddMeasureMappingFields.cs`:
- Around line 13-40: Update the migration’s Up method to stage the new
MeasureMappings fields: preflight existing rows and fail with a clear error when
legacy mappings cannot be mapped safely, then backfill valid unique Measure and
DQM values plus Frequency = "Adhoc" before enforcing non-null constraints and
creating IX_MeasureMappings_Measure_DQM; do not apply empty defaults that create
duplicate index keys.

---

Nitpick comments:
In `@DotNet/DMRP/Business/Managers/MeasureMappingManager.cs`:
- Around line 18-19: Add focused xUnit coverage for DeleteAllAsync in the
concrete IMeasureMappingManager implementation, covering successful completion,
propagation of OperationCanceledException, generic exception handling, and
DbUpdateException handling. Reuse the existing test setup and assertions for
manager error behavior, keeping each branch test small and isolated.
- Around line 53-72: Expand MeasureMappingManagerTests with focused XUnit
repository-mock coverage for CreateAsync, UpdateAsync, and DeleteAllAsync,
including records, empty results, cancellation, and save failures. Add
CreateAsync tests that trigger IsUniqueIndexViolation for SQLite error 2067 and
SQL Server errors 2601/2627, plus non-unique commit failures for both
CreateAsync and UpdateAsync; assert the expected exception and activity behavior
without using a network database.

In `@DotNet/DMRP/Models/SearchMeasureMappingDto.cs`:
- Around line 21-29: Add focused xUnit tests for the normalization logic in
SearchMeasureMappingDto, covering PageSize below 1, above 100, and within the
valid range, plus PageNumber below 1 and within range. Add assertions for the
string-filter sanitization introduced alongside this logic, with each
conditional branch exercised independently.
🪄 Autofix

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro Plus

Run ID: cf6a6faa-043b-4555-bd34-a1d50e20076f

📥 Commits

Reviewing files that changed from the base of the PR and between a787711 and 168ac22.

📒 Files selected for processing (17)
  • DotNet/DMRP/Business/Managers/MeasureMappingManager.cs
  • DotNet/DMRP/Business/Queries/MeasureMappingQueries.cs
  • DotNet/DMRP/Controllers/MeasureMappingsController.cs
  • DotNet/DMRP/DMRP.csproj
  • DotNet/DMRP/Data/Entities/MeasureMapping.cs
  • DotNet/DMRP/Data/Repository/Mappings/MeasureMappingConfigMap.cs
  • DotNet/DMRP/Models/SearchMeasureMappingDto.cs
  • DotNet/DMRP/packages.lock.json
  • DotNet/ServiceTests/IntegrationTests/DMRP/MeasureMappingsControllerTests.cs
  • DotNet/ServiceTests/UnitTests/DMRP/MeasureMappingQueriesTests.cs
  • DotNet/ServiceTests/packages.lock.json
  • DotNet/Shared/Application/Models/Integration/DMRP/DMRPApiModels.cs
  • DotNet/Tenant/Migrations/20260806183143_AddMeasureMappingFields.Designer.cs
  • DotNet/Tenant/Migrations/20260806183143_AddMeasureMappingFields.cs
  • DotNet/Tenant/Migrations/TenantDbContextModelSnapshot.cs
  • DotNet/Tenant/packages.lock.json
  • Tests/BackendE2ETests/packages.lock.json

Comment thread DotNet/DMRP/Controllers/MeasureMappingsController.cs Outdated
Comment thread DotNet/DMRP/Controllers/MeasureMappingsController.cs
Comment thread DotNet/DMRP/Controllers/MeasureMappingsController.cs Outdated
Comment thread DotNet/DMRP/Models/SearchMeasureMappingDto.cs
Comment thread DotNet/Shared/Application/Models/Integration/DMRP/DMRPApiModels.cs
Comment thread DotNet/Tenant/Migrations/20260806183143_AddMeasureMappingFields.cs

@arianamihailescu arianamihailescu 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.

Looks good

@johnbritton
johnbritton merged commit e6276f9 into dev Aug 11, 2026
18 checks passed
@johnbritton
johnbritton deleted the users/jbritton/LEGLINK-807 branch August 11, 2026 18:58
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants