Skip to content

Commit 22d33e6

Browse files
renemadsenclaude
andcommitted
fix: address Copilot review - singleton fetch + backend delete guard
- Fetch all pay rule set names (pageSize: 10000) before opening create modal to ensure singleton filtering works beyond page 1 - Add server-side delete guard with LockedPresetNames HashSet in PayRuleSetService.Delete - returns failure for locked presets Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
1 parent a8b443d commit 22d33e6

2 files changed

Lines changed: 48 additions & 11 deletions

File tree

eFormAPI/Plugins/TimePlanning.Pn/TimePlanning.Pn/Services/PayRuleSetService/PayRuleSetService.cs

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,29 @@ namespace TimePlanning.Pn.Services.PayRuleSetService;
2222

2323
public class PayRuleSetService : IPayRuleSetService
2424
{
25+
private static readonly HashSet<string> LockedPresetNames = new HashSet<string>
26+
{
27+
"GLS-A / 3F - Jordbrug Standard",
28+
"GLS-A / 3F - Jordbrug Dyrehold",
29+
"GLS-A / 3F - Jordbrug Elev u18",
30+
"GLS-A / 3F - Jordbrug Elev o18",
31+
"GLS-A / 3F - Jordbrug Elev u18 Dyrehold",
32+
"GLS-A / 3F - Gartneri Standard",
33+
"GLS-A / 3F - Gartneri Elev u18",
34+
"GLS-A / 3F - Gartneri Elev o18",
35+
"GLS-A / 3F - Skovbrug Standard",
36+
"GLS-A / 3F - Skovbrug Elev u18",
37+
"GLS-A / 3F - Skovbrug Elev o18",
38+
"KA / Krifa - Landbrug Svine/Kvaeg Standard",
39+
"KA / Krifa - Landbrug Svine/Kvaeg Elev",
40+
"KA / Krifa - Landbrug Plantebrug Standard",
41+
"KA / Krifa - Landbrug Plantebrug Elev",
42+
"KA / Krifa - Landbrug Maskinstation Standard",
43+
"KA / Krifa - Landbrug Maskinstation Elev",
44+
"KA / Krifa - Gron Standard",
45+
"KA / Krifa - Gron Elev"
46+
};
47+
2548
private readonly TimePlanningPnDbContext _dbContext;
2649
private readonly ILogger<PayRuleSetService> _logger;
2750

@@ -549,6 +572,11 @@ public async Task<OperationResult> Delete(int id)
549572
return new OperationResult(false, "Pay rule set not found");
550573
}
551574

575+
if (LockedPresetNames.Contains(payRuleSet.Name))
576+
{
577+
return new OperationResult(false, "Cannot delete - this overenskomst is a locked preset and cannot be removed");
578+
}
579+
552580
await payRuleSet.Delete(_dbContext);
553581

554582
return new OperationResult(true, "Pay rule set deleted successfully");

eform-client/src/app/plugins/modules/time-planning-pn/modules/pay-rule-sets/components/pay-rule-sets-container/pay-rule-sets-container.component.ts

Lines changed: 20 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -52,18 +52,27 @@ export class PayRuleSetsContainerComponent implements OnInit, OnDestroy {
5252
}
5353

5454
onCreateClicked(): void {
55-
const dialogRef = this.dialog.open(PayRuleSetsCreateModalComponent, {
56-
minWidth: 1280,
57-
maxWidth: 1440,
58-
data: { existingNames: this.payRuleSets.map(p => p.name) },
59-
});
55+
// Fetch all pay rule set names (not just the current page) for singleton filtering
56+
this.payRuleSetsService
57+
.getPayRuleSets({ offset: 0, pageSize: 10000 })
58+
.subscribe((allData) => {
59+
const allNames = allData && allData.success
60+
? allData.model.payRuleSets.map(p => p.name)
61+
: this.payRuleSets.map(p => p.name);
6062

61-
dialogRef.afterClosed().subscribe((result) => {
62-
if (result) {
63-
// Refresh the table after successful create
64-
this.getPayRuleSets();
65-
}
66-
});
63+
const dialogRef = this.dialog.open(PayRuleSetsCreateModalComponent, {
64+
minWidth: 1280,
65+
maxWidth: 1440,
66+
data: { existingNames: allNames },
67+
});
68+
69+
dialogRef.afterClosed().subscribe((result) => {
70+
if (result) {
71+
// Refresh the table after successful create
72+
this.getPayRuleSets();
73+
}
74+
});
75+
});
6776
}
6877

6978
onEditClicked(payRuleSet: PayRuleSetSimpleModel): void {

0 commit comments

Comments
 (0)