public void RemoveIsSerializedCorrectly() { JsonPatchDocument document = new JsonPatchDocument(); document.AppendRemove("/a/b/c"); Assert.AreEqual(document.ToString(), "[{\"op\":\"remove\",\"path\":\"/a/b/c\"}]"); }
public async Task UpdateTwinAsync(DigitalTwinsClient client) { // ------------------ UPDATE TWIN (Longer example than in the runnable sample)--------------------- // <UpdateTwin> var updateTwinData = new JsonPatchDocument(); updateTwinData.AppendAdd("/Temperature", 25.0); updateTwinData.AppendAdd("/myComponent/Property", "Hello"); // Un-set a property updateTwinData.AppendRemove("/Humidity"); await client.UpdateDigitalTwinAsync("myTwin", updateTwinData).ConfigureAwait(false); // </UpdateTwin> }
public void MultipleOperationsSerializedInOrder() { JsonPatchDocument document = new JsonPatchDocument(); document.AppendTest("/a/b/c", "\"foo\""); document.AppendAdd("/a/b/c", "42"); document.AppendReplace("/a/b/c", "[ \"foo\", \"bar\" ]"); document.AppendRemove("/a/b/c"); document.AppendMove("/a/b/c", "/a/b/d"); document.AppendCopy("/a/b/c", "/a/b/d"); Assert.AreEqual(document.ToString(), "[" + "{\"op\":\"test\",\"path\":\"/a/b/c\",\"value\":\"foo\"}," + "{\"op\":\"add\",\"path\":\"/a/b/c\",\"value\":42}," + "{\"op\":\"replace\",\"path\":\"/a/b/c\",\"value\":[\"foo\",\"bar\"]}," + "{\"op\":\"remove\",\"path\":\"/a/b/c\"}," + "{\"op\":\"move\",\"from\":\"/a/b/c\",\"path\":\"/a/b/d\"}," + "{\"op\":\"copy\",\"from\":\"/a/b/c\",\"path\":\"/a/b/d\"}" + "]"); }
public async Task DigitalTwins_Lifecycle() { DigitalTwinsClient client = GetClient(); string roomTwinId = await GetUniqueTwinIdAsync(client, TestAssetDefaults.RoomTwinIdPrefix).ConfigureAwait(false); string floorModelId = await GetUniqueModelIdAsync(client, TestAssetDefaults.FloorModelIdPrefix).ConfigureAwait(false); string roomModelId = await GetUniqueModelIdAsync(client, TestAssetDefaults.RoomModelIdPrefix).ConfigureAwait(false); try { // arrange // create room model string roomModel = TestAssetsHelper.GetRoomModelPayload(roomModelId, floorModelId); await client.CreateModelsAsync(new List <string> { roomModel }).ConfigureAwait(false); // act // create room twin BasicDigitalTwin roomTwin = TestAssetsHelper.GetRoomTwinPayload(roomModelId); await client.CreateOrReplaceDigitalTwinAsync <BasicDigitalTwin>(roomTwinId, roomTwin).ConfigureAwait(false); // get twin await client.GetDigitalTwinAsync <BasicDigitalTwin>(roomTwinId).ConfigureAwait(false); // update twin JsonPatchDocument updateTwinPatchDocument = new JsonPatchDocument(); updateTwinPatchDocument.AppendAdd("/Humidity", 30); updateTwinPatchDocument.AppendReplace("/Temperature", 70); updateTwinPatchDocument.AppendRemove("/EmployeeId"); var requestOptions = new UpdateDigitalTwinOptions { IfMatch = "*" }; await client.UpdateDigitalTwinAsync(roomTwinId, updateTwinPatchDocument, requestOptions).ConfigureAwait(false); // delete a twin await client.DeleteDigitalTwinAsync(roomTwinId).ConfigureAwait(false); // assert Func <Task> act = async() => { await client.GetDigitalTwinAsync <BasicDigitalTwin>(roomTwinId).ConfigureAwait(false); }; act.Should().Throw <RequestFailedException>() .And.Status.Should().Be((int)HttpStatusCode.NotFound); } finally { // cleanup try { if (!string.IsNullOrWhiteSpace(roomModelId)) { await client.DeleteModelAsync(roomModelId).ConfigureAwait(false); } } catch (Exception ex) { Assert.Fail($"Test clean up failed: {ex.Message}"); } } }
public async Task DigitalTwins_DeleteTwinSucceedsIfMatchProvidesCorrectEtag() { DigitalTwinsClient client = GetClient(); string roomTwinId = await GetUniqueTwinIdAsync(client, TestAssetDefaults.RoomTwinIdPrefix).ConfigureAwait(false); string floorModelId = await GetUniqueModelIdAsync(client, TestAssetDefaults.FloorModelIdPrefix).ConfigureAwait(false); string roomModelId = await GetUniqueModelIdAsync(client, TestAssetDefaults.RoomModelIdPrefix).ConfigureAwait(false); try { // arrange // create room model string roomModel = TestAssetsHelper.GetRoomModelPayload(roomModelId, floorModelId); await client.CreateModelsAsync(new List <string> { roomModel }).ConfigureAwait(false); // act // create room twin BasicDigitalTwin roomTwin = TestAssetsHelper.GetRoomTwinPayload(roomModelId); await client.CreateOrReplaceDigitalTwinAsync <BasicDigitalTwin>(roomTwinId, roomTwin).ConfigureAwait(false); // update twin JsonPatchDocument updateTwinPatchDocument = new JsonPatchDocument(); updateTwinPatchDocument.AppendAdd("/Humidity", 30); updateTwinPatchDocument.AppendReplace("/Temperature", 70); updateTwinPatchDocument.AppendRemove("/EmployeeId"); await client.UpdateDigitalTwinAsync(roomTwinId, updateTwinPatchDocument, ETag.All).ConfigureAwait(false); // get twin ETag?correctETag = (await client.GetDigitalTwinAsync <BasicDigitalTwin>(roomTwinId).ConfigureAwait(false)).Value.ETag; Assert.IsNotNull(correctETag); try { // since the ETag is not out of date, this call should not throw a 412 await client.DeleteDigitalTwinAsync(roomTwinId, correctETag).ConfigureAwait(false); } catch (RequestFailedException ex) when(ex.Status == (int)HttpStatusCode.PreconditionFailed) { throw new AssertionException("UpdateRelationship should not have thrown PreconditionFailed because the ETag was up to date", ex); } } finally { // cleanup try { if (!string.IsNullOrWhiteSpace(roomModelId)) { await client.DeleteModelAsync(roomModelId).ConfigureAwait(false); } } catch (Exception ex) { Assert.Fail($"Test clean up failed: {ex.Message}"); } } }
public async Task DigitalTwins_DeleteTwinFailsIfMatchProvidesOutdatedEtag() { DigitalTwinsClient client = GetClient(); string roomTwinId = await GetUniqueTwinIdAsync(client, TestAssetDefaults.RoomTwinIdPrefix).ConfigureAwait(false); string floorModelId = await GetUniqueModelIdAsync(client, TestAssetDefaults.FloorModelIdPrefix).ConfigureAwait(false); string roomModelId = await GetUniqueModelIdAsync(client, TestAssetDefaults.RoomModelIdPrefix).ConfigureAwait(false); try { // arrange // create room model string roomModel = TestAssetsHelper.GetRoomModelPayload(roomModelId, floorModelId); await client.CreateModelsAsync(new List <string> { roomModel }).ConfigureAwait(false); // act // create room twin BasicDigitalTwin roomTwin = TestAssetsHelper.GetRoomTwinPayload(roomModelId); await client.CreateOrReplaceDigitalTwinAsync <BasicDigitalTwin>(roomTwinId, roomTwin).ConfigureAwait(false); // get twin ETag?etagBeforeUpdate = (await client.GetDigitalTwinAsync <BasicDigitalTwin>(roomTwinId).ConfigureAwait(false)).Value.ETag; // update twin JsonPatchDocument updateTwinPatchDocument = new JsonPatchDocument(); updateTwinPatchDocument.AppendAdd("/Humidity", 30); updateTwinPatchDocument.AppendReplace("/Temperature", 70); updateTwinPatchDocument.AppendRemove("/EmployeeId"); await client.UpdateDigitalTwinAsync(roomTwinId, updateTwinPatchDocument, ETag.All).ConfigureAwait(false); // assert Func <Task> act = async() => { // since the ETag is out of date, this call should throw a 412 await client.DeleteDigitalTwinAsync(roomTwinId, etagBeforeUpdate).ConfigureAwait(false); }; act.Should().Throw <RequestFailedException>() .And.Status.Should().Be((int)HttpStatusCode.PreconditionFailed); } finally { // cleanup try { if (!string.IsNullOrWhiteSpace(roomModelId)) { await client.DeleteModelAsync(roomModelId).ConfigureAwait(false); } } catch (Exception ex) { Assert.Fail($"Test clean up failed: {ex.Message}"); } } }
public async Task DigitalTwins_PatchTwinFailsIfInvalidETagProvided() { DigitalTwinsClient client = GetClient(); string roomTwinId = await GetUniqueTwinIdAsync(client, TestAssetDefaults.RoomTwinIdPrefix).ConfigureAwait(false); string floorModelId = await GetUniqueModelIdAsync(client, TestAssetDefaults.FloorModelIdPrefix).ConfigureAwait(false); string roomModelId = await GetUniqueModelIdAsync(client, TestAssetDefaults.RoomModelIdPrefix).ConfigureAwait(false); try { // arrange // create room model string roomModel = TestAssetsHelper.GetRoomModelPayload(roomModelId, floorModelId); await client.CreateModelsAsync(new List <string> { roomModel }).ConfigureAwait(false); // act // create room twin BasicDigitalTwin roomTwin = TestAssetsHelper.GetRoomTwinPayload(roomModelId); await client.CreateOrReplaceDigitalTwinAsync <BasicDigitalTwin>(roomTwinId, roomTwin).ConfigureAwait(false); // get twin ETag?etagBeforeUpdate = (await client.GetDigitalTwinAsync <BasicDigitalTwin>(roomTwinId).ConfigureAwait(false)).Value.ETag; Assert.IsNotNull(etagBeforeUpdate); // update twin once to make the previous etag fall out of date JsonPatchDocument updateTwinPatchDocument = new JsonPatchDocument(); updateTwinPatchDocument.AppendAdd("/Humidity", 30); updateTwinPatchDocument.AppendReplace("/Temperature", 70); updateTwinPatchDocument.AppendRemove("/EmployeeId"); await client.UpdateDigitalTwinAsync(roomTwinId, updateTwinPatchDocument, ETag.All).ConfigureAwait(false); // update twin again, but with an out of date etag, which should cause a 412 from service JsonPatchDocument secondUpdateTwinPatchDocument = new JsonPatchDocument(); secondUpdateTwinPatchDocument.AppendReplace("/Humidity", 80); Func <Task> act = async() => { await client.UpdateDigitalTwinAsync(roomTwinId, secondUpdateTwinPatchDocument, etagBeforeUpdate).ConfigureAwait(false); }; act.Should().Throw <RequestFailedException>() .And.Status.Should().Be((int)HttpStatusCode.PreconditionFailed); } finally { // cleanup try { if (!string.IsNullOrWhiteSpace(roomModelId)) { await client.DeleteModelAsync(roomModelId).ConfigureAwait(false); } } catch (Exception ex) { Assert.Fail($"Test clean up failed: {ex.Message}"); } } }
public async Task DigitalTwins_PatchTwinSucceedsIfCorrectETagProvided() { DigitalTwinsClient client = GetClient(); string roomTwinId = await GetUniqueTwinIdAsync(client, TestAssetDefaults.RoomTwinIdPrefix).ConfigureAwait(false); string floorModelId = await GetUniqueModelIdAsync(client, TestAssetDefaults.FloorModelIdPrefix).ConfigureAwait(false); string roomModelId = await GetUniqueModelIdAsync(client, TestAssetDefaults.RoomModelIdPrefix).ConfigureAwait(false); try { // arrange // create room model string roomModel = TestAssetsHelper.GetRoomModelPayload(roomModelId, floorModelId); await CreateAndListModelsAsync(client, new List <string> { roomModel }).ConfigureAwait(false); // act // create room twin BasicDigitalTwin roomTwin = TestAssetsHelper.GetRoomTwinPayload(roomModelId); await client.CreateOrReplaceDigitalTwinAsync <BasicDigitalTwin>(roomTwinId, roomTwin).ConfigureAwait(false); // update twin once JsonPatchDocument updateTwinPatchDocument = new JsonPatchDocument(); updateTwinPatchDocument.AppendAdd("/Humidity", 30); updateTwinPatchDocument.AppendReplace("/Temperature", 70); updateTwinPatchDocument.AppendRemove("/EmployeeId"); await client.UpdateDigitalTwinAsync(roomTwinId, updateTwinPatchDocument, ETag.All).ConfigureAwait(false); // get twin ETag?etagBeforeUpdate = (await client.GetDigitalTwinAsync <BasicDigitalTwin>(roomTwinId).ConfigureAwait(false)).Value.ETag; Assert.IsNotNull(etagBeforeUpdate); // update twin again, but with the correct etag JsonPatchDocument secondUpdateTwinPatchDocument = new JsonPatchDocument(); secondUpdateTwinPatchDocument.AppendReplace("/Humidity", 80); try { await client.UpdateDigitalTwinAsync(roomTwinId, secondUpdateTwinPatchDocument, etagBeforeUpdate).ConfigureAwait(false); } catch (RequestFailedException ex) when(ex.Status == (int)HttpStatusCode.PreconditionFailed) { throw new AssertionException("UpdateDigitalTwin should not have thrown PreconditionFailed because the ETag was up to date", ex); } } catch (Exception ex) { Assert.Fail($"Failure in executing a step in the test case: {ex.Message}."); } finally { // cleanup try { if (!string.IsNullOrWhiteSpace(roomModelId)) { await client.DeleteModelAsync(roomModelId).ConfigureAwait(false); } } catch (Exception ex) { Assert.Fail($"Test clean up failed: {ex.Message}"); } } }