public async Task WhenUpdatingAResource_GivenAUserWithNoWritePermissions_TheServerShouldReturnForbidden() { await Client.RunAsUser(TestUsers.WriteOnlyUser, TestApplications.NativeClient); Observation createdResource = await Client.CreateAsync(Samples.GetDefaultObservation()); await Client.RunAsUser(TestUsers.ReadOnlyUser, TestApplications.NativeClient); FhirException fhirException = await Assert.ThrowsAsync <FhirException>(async() => await Client.UpdateAsync(createdResource)); Assert.Equal(ForbiddenMessage, fhirException.Message); Assert.Equal(HttpStatusCode.Forbidden, fhirException.StatusCode); }
public async Task GivenADeletedIdAndVersionId_WhenGettingAResource_TheServerShouldReturnAGoneStatus() { Observation createdResource = await _client.CreateAsync(Samples.GetDefaultObservation().ToPoco <Observation>()); using FhirResponse deleteResponse = await _client.DeleteAsync(createdResource); var deletedVersion = WeakETag.FromWeakETag(deleteResponse.Headers.ETag.ToString()).VersionId; using FhirException ex = await Assert.ThrowsAsync <FhirException>( () => _client.VReadAsync <Observation>(ResourceType.Observation, createdResource.Id, deletedVersion)); Assert.Equal(System.Net.HttpStatusCode.Gone, ex.StatusCode); }
public async Task GivenAResource_WhenHardDeleting_ThenServerShouldDeleteAllRelatedResourcesSuccessfully() { List <string> versionIds = new List <string>(); using FhirResponse <Observation> response1 = await _client.CreateAsync(Samples.GetDefaultObservation ().ToPoco <Observation>()); Observation observation = response1.Resource; string resourceId = observation.Id; versionIds.Add(observation.Meta.VersionId); // Update the observation. observation.Status = ObservationStatus.EnteredInError; using FhirResponse <Observation> response2 = await _client.UpdateAsync(observation); versionIds.Add(response2.Resource.Meta.VersionId); // Delete the observation await _client.DeleteAsync(observation); // Update the observation to resurrect the resource. observation.Status = ObservationStatus.Final; observation.Subject = new ResourceReference("Patient/123"); using FhirResponse <Observation> response3 = await _client.UpdateAsync(observation); versionIds.Add(response3.Resource.Meta.VersionId); // Hard-delete the resource. await _client.HardDeleteAsync(observation); // Getting the resource should result in NotFound. await ExecuteAndValidateNotFoundStatus(() => _client.ReadAsync <Observation>(ResourceType.Observation, resourceId)); // Each version read should also result in NotFound. foreach (string versionId in versionIds) { await ExecuteAndValidateNotFoundStatus(() => _client.VReadAsync <Observation>(ResourceType.Observation, resourceId, versionId)); } // History API should return NotFound. await ExecuteAndValidateNotFoundStatus(() => _client.SearchAsync($"Observation/{resourceId}/_history")); async Task ExecuteAndValidateNotFoundStatus(Func <Task> action) { using FhirException exception = await Assert.ThrowsAsync <FhirException>(action); Assert.Equal(HttpStatusCode.NotFound, exception.StatusCode); } }
public async Task GivenPatientWithReplacedByLink_WhenRunningPatientEverythingWithPreferHeaderSetToStrictHandling_ThenMovedPermanentlyIsReturned() { string searchUrl = $"Patient/{Fixture.PatientWithReplacedByLink.Id}/$everything"; using FhirException ex = await Assert.ThrowsAsync <FhirException>(() => Client.SearchAsync(searchUrl, Tuple.Create(KnownHeaders.Prefer, "handling=strict"))); // Confirm header location contains url for the correct request string id = Fixture.PatientReferencedByReplacedByLink.Id; string uri = $"/{KnownResourceTypes.Patient}/{id}/$everything"; Assert.Contains(uri, ex.Content.Headers.GetValues(HeaderNames.ContentLocation).First()); Assert.Equal(HttpStatusCode.MovedPermanently, ex.StatusCode); Assert.Contains(string.Format(Core.Resources.EverythingOperationResourceIrrelevant, Fixture.PatientWithReplacedByLink.Id, Fixture.PatientReferencedByReplacedByLink.Id), ex.Message); }
public async Task GivenAUserWithNoConvertDataPermissions_WhenConvertData_TheServerShouldReturnForbidden() { if (!_convertDataEnabled) { return; } TestFhirClient tempClient = _client.CreateClientForUser(TestUsers.ReadOnlyUser, TestApplications.NativeClient); var parameters = Samples.GetDefaultConvertDataParameter().ToPoco <Parameters>(); FhirException fhirException = await Assert.ThrowsAsync <FhirException>(async() => await tempClient.ConvertDataAsync(parameters)); Assert.Equal(ForbiddenMessage, fhirException.Message); Assert.Equal(HttpStatusCode.Forbidden, fhirException.StatusCode); }
public async Task GivenListOfResources_WhenSearchedWithInvalidTotalType_ThenExceptionShouldBeThrown(string key, string val) { Patient[] patients = await Client.CreateResourcesAsync <Patient>(3); using FhirException ex = await Assert.ThrowsAsync <FhirException>(() => Client.SearchAsync($"Patient?{key}={val}")); var expectedStatusCode = HttpStatusCode.BadRequest; Assert.Equal(expectedStatusCode, ex.StatusCode); var supportedTotalTypes = new string($"'{TotalType.Accurate}', '{TotalType.None}'").ToLower(CultureInfo.CurrentCulture); var expectedErrorMessage = $"{expectedStatusCode}: " + string.Format(Core.Resources.InvalidTotalParameter, val, supportedTotalTypes); Assert.Equal(expectedErrorMessage, ex.Message); }
public async Task GivenAnIncorrectETagHeader_WhenUpdatingAResource_TheServerShouldReturnAnError() { Observation createdResource = await _client.CreateAsync(Samples.GetDefaultObservation().ToPoco <Observation>()); // Specify a version that is one off from the version of the existing resource var incorrectVersionId = int.Parse(createdResource.Meta.VersionId) + 1; var weakETag = $"W/\"{incorrectVersionId.ToString()}\""; using FhirException ex = await Assert.ThrowsAsync <FhirException>(() => _client.UpdateAsync(createdResource, weakETag)); #if Stu3 Assert.Equal(HttpStatusCode.Conflict, ex.StatusCode); #else Assert.Equal(HttpStatusCode.PreconditionFailed, ex.StatusCode); #endif }
public async Task GivenImportOperationEnabled_WhenImportInvalidResourceUrl_ThenBadRequestShouldBeReturned() { _metricHandler?.ResetCount(); var request = new ImportRequest() { InputFormat = "application/fhir+ndjson", InputSource = new Uri("https://other-server.example.org"), StorageDetail = new ImportRequestStorageDetail() { Type = "azure-blob" }, Input = new List <InputResource>() { new InputResource() { Url = new Uri("https://fhirtest-invalid.com"), Type = "Patient", }, }, }; Uri checkLocation = await ImportTestHelper.CreateImportTaskAsync(_client, request); FhirException fhirException = await Assert.ThrowsAsync <FhirException>( async() => { HttpResponseMessage response; while ((response = await _client.CheckImportAsync(checkLocation, CancellationToken.None)).StatusCode == System.Net.HttpStatusCode.Accepted) { await Task.Delay(TimeSpan.FromSeconds(5)); } }); Assert.Equal(HttpStatusCode.BadRequest, fhirException.StatusCode); // Only check metric for local tests if (_fixture.IsUsingInProcTestServer) { var notificationList = _metricHandler.NotificationMapping[typeof(ImportTaskMetricsNotification)]; Assert.Single(notificationList); var notification = notificationList.First() as ImportTaskMetricsNotification; Assert.Equal(TaskResult.Fail.ToString(), notification.Status); Assert.Null(notification.DataSize); Assert.Null(notification.SucceedCount); Assert.Null(notification.FailedCount); } }
private async Task GivenExecuteAndValidateNotFoundStatus(Func <Task> action) { FhirException exception = null; do { if (exception?.StatusCode == (HttpStatusCode)429) { // Wait for a little bit before retrying if we are geting throttled. await Task.Delay(500); } exception = await Assert.ThrowsAsync <FhirException>(action); }while (exception.StatusCode == (HttpStatusCode)429); Assert.Equal(HttpStatusCode.NotFound, exception.StatusCode); exception.Dispose(); }
public async Task GivenListOfResources_WhenSearchedWithTotalTypeEstimate_ThenExceptionShouldBeThrown() { const int numberOfResources = 5; var tag = new Coding(string.Empty, Guid.NewGuid().ToString()); Patient patient = Samples.GetDefaultPatient().ToPoco <Patient>(); for (int i = 0; i < numberOfResources; i++) { patient.Meta = new Meta(); patient.Meta.Tag.Add(tag); await Client.CreateAsync(patient); } FhirException ex = await Assert.ThrowsAsync <FhirException>(() => Client.SearchAsync($"Patient?_total=estimate")); Assert.Equal(HttpStatusCode.Forbidden, ex.StatusCode); }
public async Task GivenImportOperationEnabled_WhenImportOperationTriggeredBeforePreviousTaskCompleted_ThenConflictShouldBeReturned() { string patientNdJsonResource = Samples.GetNdJson("Import-Patient"); patientNdJsonResource = Regex.Replace(patientNdJsonResource, "##PatientID##", m => Guid.NewGuid().ToString("N")); (Uri location, string etag) = await ImportTestHelper.UploadFileAsync(patientNdJsonResource, _fixture.CloudStorageAccount); var request = new ImportRequest() { InputFormat = "application/fhir+ndjson", InputSource = new Uri("https://other-server.example.org"), StorageDetail = new ImportRequestStorageDetail() { Type = "azure-blob" }, Input = new List <InputResource>() { new InputResource() { Url = location, Etag = etag, Type = "Patient", }, }, }; request.Mode = ImportConstants.InitialLoadMode; request.Force = true; Uri checkLocation = await ImportTestHelper.CreateImportTaskAsync(_client, request); FhirException fhirException = await Assert.ThrowsAsync <FhirException>(async() => await _client.ImportAsync(request.ToParameters(), CancellationToken.None)); Assert.Equal(HttpStatusCode.Conflict, fhirException.StatusCode); HttpResponseMessage response; while ((response = await _client.CheckImportAsync(checkLocation, CancellationToken.None)).StatusCode == System.Net.HttpStatusCode.Accepted) { await Task.Delay(TimeSpan.FromSeconds(5)); } }
private Task R4FhirExceptionProcessing(HttpContext context, FhirException FhirException, FhirFormatType AcceptFormatType) { R4Model.OperationOutcome?R4OperationOutcomeResult; if (FhirException is FhirFatalException FatalExec) { R4OperationOutcomeResult = IOperationOutComeSupportFactory.GetR4().GetFatal(FatalExec.MessageList); } else if (FhirException is FhirErrorException ErrorExec) { R4OperationOutcomeResult = IOperationOutComeSupportFactory.GetR4().GetError(ErrorExec.MessageList); } else if (FhirException is FhirWarnException WarnExec) { R4OperationOutcomeResult = IOperationOutComeSupportFactory.GetR4().GetWarning(WarnExec.MessageList); } else if (FhirException is FhirInfoException InfoExec) { R4OperationOutcomeResult = IOperationOutComeSupportFactory.GetR4().GetInformation(InfoExec.MessageList); } else { R4OperationOutcomeResult = IOperationOutComeSupportFactory.GetR4().GetFatal(new string[] { $"Unexpected FhirException type encountered of : {FhirException.GetType().FullName}" }); } context.Response.StatusCode = (int)FhirException.HttpStatusCode; context.Response.ContentType = Bug.Api.ContentFormatters.FhirMediaType.GetMediaTypeHeaderValue(R4OperationOutcomeResult.GetType(), AcceptFormatType).Value; if (AcceptFormatType == FhirFormatType.xml) { return(context.Response.WriteAsync(IR4SerializationToXml.SerializeToXml(R4OperationOutcomeResult))); } else if (AcceptFormatType == FhirFormatType.json) { return(context.Response.WriteAsync(IR4SerializationToJson.SerializeToJson(R4OperationOutcomeResult))); } else { string msg = $"Unexpected FhirFormatType type encountered of : {AcceptFormatType.GetType().FullName}"; _logger.LogError(msg); throw new ApplicationException(msg); } }
public async Task GivenAUserWithHardDeletePermissions_WhenHardDeletingAResource_TheServerShouldReturnSuccess() { TestFhirClient tempClient = _client.CreateClientForUser(TestUsers.ReadWriteUser, TestApplications.NativeClient); Observation createdResource = await tempClient.CreateAsync(Samples.GetDefaultObservation().ToPoco <Observation>()); tempClient = _client.CreateClientForUser(TestUsers.AdminUser, TestApplications.NativeClient); // Hard-delete the resource. await tempClient.HardDeleteAsync(createdResource); tempClient = _client.CreateClientForUser(TestUsers.ReadOnlyUser, TestApplications.NativeClient); // Getting the resource should result in NotFound. await ExecuteAndValidateNotFoundStatus(() => tempClient.ReadAsync <Observation>(ResourceType.Observation, createdResource.Id)); async Task <FhirException> ExecuteAndValidateNotFoundStatus(Func <Task> action) { using FhirException exception = await Assert.ThrowsAsync <FhirException>(action); Assert.Equal(HttpStatusCode.NotFound, exception.StatusCode); return(exception); } }
public async Task GivenAResourceThatWasRenamed_WhenSearched_ThenExceptionShouldBeThrown() { FhirException exception = await Assert.ThrowsAsync <FhirException>(() => _client.SearchAsync("Sequence")); Assert.Equal(HttpStatusCode.NotFound, exception.StatusCode); }
public async Task GivenAnUnsupportedResourceType_WhenPostingToHttp_TheServerShouldRespondWithANotFoundResponse() { using FhirException ex = await Assert.ThrowsAsync <FhirException>(() => _client.CreateAsync("NotObservation", Samples.GetDefaultObservation().ToPoco <Observation>())); Assert.Equal(HttpStatusCode.NotFound, ex.StatusCode); }
public async Task GivenBundleTypeIsMissing_WhenSubmittingABundle_ThenMethodNotAllowedExceptionIsReturned() { using FhirException ex = await Assert.ThrowsAsync <FhirException>(() => _client.PostBundleAsync(Samples.GetJsonSample("Bundle-TypeMissing").ToPoco <Bundle>())); ValidateOperationOutcome(ex.StatusCode.ToString(), ex.OperationOutcome, "MethodNotAllowed", "Bundle type is not present. Possible values are: transaction or batch", IssueType.Forbidden); }
public async Task GivenANonBundleResource_WhenSubmittingABatch_ThenBadRequestIsReturned() { using FhirException ex = await Assert.ThrowsAsync <FhirException>(() => _client.PostBundleAsync(Samples.GetDefaultObservation().ToPoco <Observation>())); Assert.Equal(HttpStatusCode.BadRequest, ex.StatusCode); }
public async Task GivenInvalidPrettyParameter_WhenGettingMetadata_TheServerShouldReturnBadRequest(string value) { using FhirException ex = await Assert.ThrowsAsync <FhirException>(async () => await _client.ReadAsync <CapabilityStatement>($"metadata?_pretty={value}")); Assert.Equal(HttpStatusCode.BadRequest, ex.StatusCode); }
public async Task GivenInvalidFormatParameter_WhenGettingMetadata_TheServerShouldReturnNotAcceptable() { using FhirException ex = await Assert.ThrowsAsync <FhirException>(async () => await _client.ReadAsync <CapabilityStatement>("metadata?_format=blah")); Assert.Equal(HttpStatusCode.NotAcceptable, ex.StatusCode); }
public async Task GivenAProperBundle_WhenSubmittingATransactionForCosmosDbDataStore_ThenNotSupportedIsReturned() { using FhirException ex = await Assert.ThrowsAsync <FhirException>(() => _client.PostBundleAsync(Samples.GetDefaultTransaction().ToPoco <Bundle>())); Assert.Equal(HttpStatusCode.MethodNotAllowed, ex.StatusCode); }
public async Task GivenAServerThatDoesNotSupportIt_WhenSubmittingAPatch_ThenMethodNotAllowedIsReturned() { using FhirException ex = await Assert.ThrowsAsync <FhirException>(() => _client.PatchAsync("Patient/1234", "patch content")); Assert.Equal(HttpStatusCode.MethodNotAllowed, ex.StatusCode); }
public async Task WhenSubmittingABatch_GivenAProperBundle_ThenNotSupportedIsReturned() { FhirException ex = await Assert.ThrowsAsync <FhirException>(() => Client.PostBundleAsync(Samples.GetDefaultBatch().ToPoco <Bundle>())); Assert.Equal(HttpStatusCode.MethodNotAllowed, ex.StatusCode); }