public Task When_road_nodes_were_imported() { var data = _fixture .CreateMany <ImportedRoadNode>(new Random().Next(1, 100)) .Select(@event => { var point = GeometryTranslator.Translate(@event.Geometry); var pointShapeContent = new PointShapeContent( Be.Vlaanderen.Basisregisters.Shaperon.Geometries.GeometryTranslator.FromGeometryPoint( new NetTopologySuite.Geometries.Point(point.X, point.Y) ) ); var expectedRecord = new RoadNodeRecord { Id = @event.Id, DbaseRecord = new RoadNodeDbaseRecord { WK_OIDN = { Value = @event.Id }, WK_UIDN = { Value = @event.Id + "_" + @event.Version }, TYPE = { Value = RoadNodeType.Parse(@event.Type).Translation.Identifier }, LBLTYPE = { Value = RoadNodeType.Parse(@event.Type).Translation.Name }, BEGINTIJD = { Value = @event.Origin.Since }, BEGINORG = { Value = @event.Origin.OrganizationId }, LBLBGNORG = { Value = @event.Origin.Organization } }.ToBytes(_services.MemoryStreamManager, Encoding.UTF8), ShapeRecordContent = pointShapeContent.ToBytes(_services.MemoryStreamManager, Encoding.UTF8), ShapeRecordContentLength = pointShapeContent.ContentLength.ToInt32(), BoundingBox = RoadNodeBoundingBox.From(pointShapeContent.Shape) }; return(new { ImportedRoadNode = @event, ExpectedRecord = expectedRecord }); }).ToList(); return(new RoadNodeRecordProjection(new RecyclableMemoryStreamManager(), Encoding.UTF8) .Scenario() .Given(data.Select(d => d.ImportedRoadNode)) .Expect(data.Select(d => d.ExpectedRecord))); }
public RoadNodeRecordProjection(RecyclableMemoryStreamManager manager, Encoding encoding) { if (manager == null) { throw new ArgumentNullException(nameof(manager)); } if (encoding == null) { throw new ArgumentNullException(nameof(encoding)); } When <Envelope <ImportedRoadNode> >(async(context, envelope, token) => { var typeTranslation = RoadNodeType.Parse(envelope.Message.Type).Translation; var dbaseRecord = new RoadNodeDbaseRecord { WK_OIDN = { Value = envelope.Message.Id }, WK_UIDN = { Value = envelope.Message.Id + "_" + envelope.Message.Version }, TYPE = { Value = typeTranslation.Identifier }, LBLTYPE = { Value = typeTranslation.Name }, BEGINTIJD = { Value = envelope.Message.Origin.Since }, BEGINORG = { Value = envelope.Message.Origin.OrganizationId }, LBLBGNORG = { Value = envelope.Message.Origin.Organization } }; var point = GeometryTranslator.FromGeometryPoint(BackOffice.Core.GeometryTranslator.Translate(envelope.Message.Geometry)); var pointShapeContent = new PointShapeContent(point); await context.RoadNodes.AddAsync(new RoadNodeRecord { Id = envelope.Message.Id, ShapeRecordContent = pointShapeContent.ToBytes(manager, encoding), ShapeRecordContentLength = pointShapeContent.ContentLength.ToInt32(), DbaseRecord = dbaseRecord.ToBytes(manager, encoding), BoundingBox = RoadNodeBoundingBox.From(pointShapeContent.Shape) }, token); }); When <Envelope <RoadNetworkChangesBasedOnArchiveAccepted> >(async(context, envelope, token) => { foreach (var message in envelope.Message.Changes.Flatten()) { switch (message) { case RoadNodeAdded node: var typeTranslation = RoadNodeType.Parse(node.Type).Translation; var dbaseRecord = new RoadNodeDbaseRecord { WK_OIDN = { Value = node.Id }, WK_UIDN = { Value = node.Id + "_0" }, // 1? TYPE = { Value = typeTranslation.Identifier }, LBLTYPE = { Value = typeTranslation.Name }, BEGINTIJD = { Value = LocalDateTimeTranslator.TranslateFromWhen(envelope.Message.When) }, BEGINORG = { Value = envelope.Message.OrganizationId }, LBLBGNORG = { Value = envelope.Message.Organization } }; var point = GeometryTranslator.FromGeometryPoint(BackOffice.Core.GeometryTranslator.Translate(node.Geometry)); var pointShapeContent = new PointShapeContent(point); await context.RoadNodes.AddAsync(new RoadNodeRecord { Id = node.Id, ShapeRecordContent = pointShapeContent.ToBytes(manager, encoding), ShapeRecordContentLength = pointShapeContent.ContentLength.ToInt32(), DbaseRecord = dbaseRecord.ToBytes(manager, encoding), BoundingBox = RoadNodeBoundingBox.From(pointShapeContent.Shape) }, token); break; } } }); }
public AddressExtractProjection(IOptions <ExtractConfig> extractConfig, Encoding encoding, WKBReader wkbReader) { _encoding = encoding ?? throw new ArgumentNullException(nameof(encoding)); When <Envelope <AddressWasRegistered> >(async(context, message, ct) => { await context.AddressExtract.AddAsync(new AddressExtractItem { AddressId = message.Message.AddressId, StreetNameId = message.Message.StreetNameId, Complete = false, DbaseRecord = new AddressDbaseRecord { huisnr = { Value = message.Message.HouseNumber }, versieid = { Value = message.Message.Provenance.Timestamp.ToBelgianDateTimeOffset().FromDateTimeOffset() } }.ToBytes(_encoding), }, cancellationToken: ct); }); When <Envelope <AddressBecameComplete> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); item.Complete = true; UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressStreetNameWasChanged> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); item.StreetNameId = message.Message.StreetNameId; UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressStreetNameWasCorrected> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); item.StreetNameId = message.Message.StreetNameId; UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressBecameCurrent> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); UpdateDbaseRecordField(item, record => record.status.Value = StatusCurrent); UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressBecameIncomplete> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); if (item != null) // in rare cases were we might get this event after an AddressWasRemoved event, we can just ignore it { item.Complete = false; UpdateVersie(item, message.Message.Provenance.Timestamp); } }); When <Envelope <AddressBecameNotOfficiallyAssigned> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); UpdateDbaseRecordField(item, record => record.offtoegknd.Value = false); UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressHouseNumberWasChanged> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); UpdateDbaseRecordField(item, record => record.huisnr.Value = message.Message.HouseNumber); UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressHouseNumberWasCorrected> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); UpdateDbaseRecordField(item, record => record.huisnr.Value = message.Message.HouseNumber); UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressOfficialAssignmentWasRemoved> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); if (item != null) // in rare cases were we might get this event after an AddressWasRemoved event, we can just ignore it { UpdateDbaseRecordField(item, record => record.offtoegknd.Value = null); UpdateVersie(item, message.Message.Provenance.Timestamp); } }); When <Envelope <AddressPersistentLocalIdWasAssigned> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); if (item != null) // in rare cases were we might get this event after an AddressWasRemoved event, we can just ignore it { UpdateDbaseRecordField(item, record => { record.id.Value = $"{extractConfig.Value.DataVlaanderenNamespace}/{message.Message.PersistentLocalId}"; record.adresid.Value = message.Message.PersistentLocalId; }); } }); When <Envelope <AddressPositionWasCorrected> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); if (item != null) // in rare cases were we might get this event after an AddressWasRemoved event, we can just ignore it { UpdateDbaseRecordField(item, record => { record.posgeommet.Value = Map(message.Message.GeometryMethod); record.posspec.Value = Map(message.Message.GeometrySpecification); }); var coordinate = wkbReader.Read(message.Message.ExtendedWkbGeometry.ToByteArray()).Coordinate; var pointShapeContent = new PointShapeContent(new Point(coordinate.X, coordinate.Y)); item.ShapeRecordContent = pointShapeContent.ToBytes(); item.ShapeRecordContentLength = pointShapeContent.ContentLength.ToInt32(); item.MinimumX = pointShapeContent.Shape.X; item.MaximumX = pointShapeContent.Shape.X; item.MinimumY = pointShapeContent.Shape.Y; item.MaximumY = pointShapeContent.Shape.Y; UpdateVersie(item, message.Message.Provenance.Timestamp); } }); When <Envelope <AddressPositionWasRemoved> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); if (item != null) // in rare cases were we might get this event after an AddressWasRemoved event, we can just ignore it { UpdateDbaseRecordField(item, record => { record.posgeommet.Value = null; record.posspec.Value = null; }); item.ShapeRecordContent = null; item.ShapeRecordContentLength = 0; item.MaximumX = 0; item.MinimumX = 0; item.MaximumY = 0; item.MinimumY = 0; UpdateVersie(item, message.Message.Provenance.Timestamp); } }); When <Envelope <AddressPostalCodeWasChanged> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); UpdateDbaseRecordField(item, record => record.postcode.Value = message.Message.PostalCode); UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressPostalCodeWasCorrected> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); if (item != null) { UpdateDbaseRecordField(item, record => record.postcode.Value = message.Message.PostalCode); UpdateVersie(item, message.Message.Provenance.Timestamp); } }); When <Envelope <AddressPostalCodeWasRemoved> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); if (item != null) { UpdateDbaseRecordField(item, record => record.postcode.Value = null); UpdateVersie(item, message.Message.Provenance.Timestamp); } }); When <Envelope <AddressStatusWasCorrectedToRemoved> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); UpdateDbaseRecordField(item, record => record.status.Value = null); UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressStatusWasRemoved> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); if (item != null) // in rare cases were we might get this event after an AddressWasRemoved event, we can just ignore it { UpdateDbaseRecordField(item, record => record.status.Value = null); UpdateVersie(item, message.Message.Provenance.Timestamp); } }); When <Envelope <AddressWasCorrectedToCurrent> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); UpdateDbaseRecordField(item, record => record.status.Value = StatusCurrent); UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressWasCorrectedToNotOfficiallyAssigned> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); UpdateDbaseRecordField(item, record => record.offtoegknd.Value = false); UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressWasCorrectedToOfficiallyAssigned> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); UpdateDbaseRecordField(item, record => record.offtoegknd.Value = true); UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressWasCorrectedToProposed> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); UpdateDbaseRecordField(item, record => record.status.Value = StatusProposed); UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressWasCorrectedToRetired> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); UpdateDbaseRecordField(item, record => record.status.Value = StatusRetired); UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressWasOfficiallyAssigned> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); UpdateDbaseRecordField(item, record => record.offtoegknd.Value = true); UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressWasPositioned> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); if (item != null) // in rare cases were we might get this event after an AddressWasRemoved event, we can just ignore it { UpdateDbaseRecordField(item, record => { record.posgeommet.Value = Map(message.Message.GeometryMethod); record.posspec.Value = Map(message.Message.GeometrySpecification); }); var coordinate = wkbReader.Read(message.Message.ExtendedWkbGeometry.ToByteArray()).Coordinate; var pointShapeContent = new PointShapeContent(new Point(coordinate.X, coordinate.Y)); item.ShapeRecordContent = pointShapeContent.ToBytes(); item.ShapeRecordContentLength = pointShapeContent.ContentLength.ToInt32(); item.MinimumX = pointShapeContent.Shape.X; item.MaximumX = pointShapeContent.Shape.X; item.MinimumY = pointShapeContent.Shape.Y; item.MaximumY = pointShapeContent.Shape.Y; UpdateVersie(item, message.Message.Provenance.Timestamp); } }); When <Envelope <AddressWasProposed> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); UpdateDbaseRecordField(item, record => record.status.Value = StatusProposed); UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressWasRemoved> >(async(context, message, ct) => { var address = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); context.AddressExtract.Remove(address); }); When <Envelope <AddressWasRetired> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); UpdateDbaseRecordField(item, record => record.status.Value = StatusRetired); UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressBoxNumberWasChanged> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); UpdateDbaseRecordField(item, record => record.busnr.Value = message.Message.BoxNumber); UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressBoxNumberWasCorrected> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); UpdateDbaseRecordField(item, record => record.busnr.Value = message.Message.BoxNumber); UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressBoxNumberWasRemoved> >(async(context, message, ct) => { var item = await context.AddressExtract.FindAsync(message.Message.AddressId, cancellationToken: ct); UpdateDbaseRecordField(item, record => record.busnr.Value = null); UpdateVersie(item, message.Message.Provenance.Timestamp); }); When <Envelope <AddressHouseNumberWasImportedFromCrab> >(async(context, message, ct) => DoNothing()); When <Envelope <AddressHouseNumberStatusWasImportedFromCrab> >(async(context, message, ct) => DoNothing()); When <Envelope <AddressHouseNumberPositionWasImportedFromCrab> >(async(context, message, ct) => DoNothing()); When <Envelope <AddressHouseNumberMailCantonWasImportedFromCrab> >(async(context, message, ct) => DoNothing()); When <Envelope <AddressSubaddressWasImportedFromCrab> >(async(context, message, ct) => DoNothing()); When <Envelope <AddressSubaddressPositionWasImportedFromCrab> >(async(context, message, ct) => DoNothing()); When <Envelope <AddressSubaddressStatusWasImportedFromCrab> >(async(context, message, ct) => DoNothing()); }