Compare commits
2
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
b30fa664d8 | ||
|
|
0dd26a711a |
@@ -34,6 +34,12 @@ notification points at. The projection is a cache of the register; ZGW is no lon
|
|||||||
as a kenmerk — so the record is read back through the ACL (`POST /register-records/read`).
|
as a kenmerk — so the record is read back through the ACL (`POST /register-records/read`).
|
||||||
§8.1 applies to Objecten exactly as ADR-0028 established: the ACL is the only code that talks
|
§8.1 applies to Objecten exactly as ADR-0028 established: the ACL is the only code that talks
|
||||||
to it.
|
to it.
|
||||||
|
- The accepted acties are `create`, `update` and `partial_update`. The last one is not
|
||||||
|
defensive breadth: the ACL upserts with PATCH, and DRF routes a PATCH through the notifying
|
||||||
|
`update()` while naming the action `partial_update` — which is what Objecten publishes. So
|
||||||
|
every approval arrives as `partial_update`, and accepting only `create`/`update` drops the
|
||||||
|
one state change this slice exists to project. `destroy` is deliberately not accepted:
|
||||||
|
removing a registration from the public register is its own decision.
|
||||||
- The record already carries `id`, `status` and `reference`, so the row is the record. The
|
- The record already carries `id`, `status` and `reference`, so the row is the record. The
|
||||||
zaak-shaped surface goes: `IsZaakCreated`, `IsZaakStatusSet`, `ZaakUrl`, `ZaakId`, and
|
zaak-shaped surface goes: `IsZaakCreated`, `IsZaakStatusSet`, `ZaakUrl`, `ZaakId`, and
|
||||||
`ToEntry`'s `Resource == "status"` inference are replaced by `IsRegisterRecordWritten` +
|
`ToEntry`'s `Resource == "status"` inference are replaced by `IsRegisterRecordWritten` +
|
||||||
|
|||||||
@@ -18,10 +18,20 @@ public sealed record Notification(
|
|||||||
string Actie,
|
string Actie,
|
||||||
Uri ResourceUrl)
|
Uri ResourceUrl)
|
||||||
{
|
{
|
||||||
/// <summary>A register record written to Objecten — <c>create</c> on submit, <c>update</c> on
|
/// <summary>
|
||||||
/// approval, since the ACL upserts the same object for a registration (§8.6).</summary>
|
/// A register record written to Objecten — <c>create</c> on submit and <c>partial_update</c> on
|
||||||
|
/// approval, since the ACL upserts the same object for a registration (§8.6).
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// <c>partial_update</c> is what a PATCH actually reports: DRF routes it through the notifying
|
||||||
|
/// <c>update()</c> but names the action <c>partial_update</c>, and that is what Objecten puts in
|
||||||
|
/// the notification. <c>update</c> is accepted too, so a PUT-shaped write would project the same
|
||||||
|
/// way. <c>destroy</c> is deliberately not: removing a registration from the public register is
|
||||||
|
/// its own decision, not a side effect of this one.
|
||||||
|
/// </remarks>
|
||||||
public bool IsRegisterRecordWritten =>
|
public bool IsRegisterRecordWritten =>
|
||||||
Kanaal == "objecten" && Resource == "object" && Actie is "create" or "update";
|
Kanaal == "objecten" && Resource == "object"
|
||||||
|
&& Actie is "create" or "update" or "partial_update";
|
||||||
|
|
||||||
/// <summary>The object holding the register record. For a <c>resource: object</c> notification
|
/// <summary>The object holding the register record. For a <c>resource: object</c> notification
|
||||||
/// Objecten sends the object as both <c>hoofdObject</c> and <c>resourceUrl</c> — the object is
|
/// Objecten sends the object as both <c>hoofdObject</c> and <c>resourceUrl</c> — the object is
|
||||||
|
|||||||
@@ -38,13 +38,17 @@ public sealed class NotificationProjectorTests
|
|||||||
Assert.Equal("REG-2026-0001", entry.Reference);
|
Assert.Equal("REG-2026-0001", entry.Reference);
|
||||||
}
|
}
|
||||||
|
|
||||||
[Fact]
|
// The ACL PATCHes the same object on approval. DRF routes a PATCH through `update()` but reports
|
||||||
public async Task approval_updates_the_same_row_from_ingediend_to_ingeschreven()
|
// the action as `partial_update`, which is what Objecten puts in the notification — so accepting
|
||||||
|
// only `create`/`update` silently drops every approval.
|
||||||
|
[Theory]
|
||||||
|
[InlineData("partial_update")]
|
||||||
|
[InlineData("update")]
|
||||||
|
public async Task approval_updates_the_same_row_from_ingediend_to_ingeschreven(string actie)
|
||||||
{
|
{
|
||||||
var projector = Projector();
|
var projector = Projector();
|
||||||
await projector.HandleAsync(RecordWritten());
|
await projector.HandleAsync(RecordWritten());
|
||||||
// The ACL PATCHes the same object on approval, so Objecten publishes an `update`.
|
await projector.HandleAsync(RecordWritten(actie, status: RegistrationStatus.Ingeschreven));
|
||||||
await projector.HandleAsync(RecordWritten("update", status: RegistrationStatus.Ingeschreven));
|
|
||||||
|
|
||||||
var entry = Assert.Single(await _store.AllAsync());
|
var entry = Assert.Single(await _store.AllAsync());
|
||||||
Assert.Equal(ZaakId, entry.Id);
|
Assert.Equal(ZaakId, entry.Id);
|
||||||
@@ -112,7 +116,7 @@ public sealed class NotificationProjectorTests
|
|||||||
{
|
{
|
||||||
var projector = Projector();
|
var projector = Projector();
|
||||||
await projector.HandleAsync(RecordWritten());
|
await projector.HandleAsync(RecordWritten());
|
||||||
await projector.HandleAsync(RecordWritten("update", status: RegistrationStatus.Ingeschreven));
|
await projector.HandleAsync(RecordWritten("partial_update", status: RegistrationStatus.Ingeschreven));
|
||||||
var callsAfterProjection = _acl.CallCount;
|
var callsAfterProjection = _acl.CallCount;
|
||||||
|
|
||||||
await projector.RebuildAsync();
|
await projector.RebuildAsync();
|
||||||
|
|||||||
Reference in New Issue
Block a user