/// <summary> /// Delete entity /// </summary> /// <param name="target">Target entity reference</param> /// <returns></returns> /// <exception cref="ArgumentNullException"></exception> /// <exception cref="ArgumentException"></exception> /// <exception cref="WebApiException"></exception> public virtual async Task DeleteAsync(EntityReference target) { _logger.LogDebug($"Start {nameof(DeleteAsync)}"); if (target == null) { throw new ArgumentNullException(nameof(target)); } if (string.IsNullOrEmpty(target.LogicalName)) { throw new ArgumentException("Entity Logical name cannot be empty."); } var navLink = target.ToNavigationLink(WebApiMetadata); using var httpRequest = new HttpRequestMessage(HttpMethod.Delete, navLink); if (!string.IsNullOrEmpty(target.RowVersion)) { httpRequest.Headers.IfMatch.Add(new EntityTagHeaderValue(target.RowVersion)); } using var httpResponse = await SendAsync(httpRequest, HttpCompletionOption.ResponseHeadersRead, cancellationToken : default) .ConfigureAwait(false); httpRequest.Dispose(); ODataResponseReader.EnsureSuccessStatusCode(httpResponse, _logger); }
/// <summary> /// Clear Lookup field of entity /// </summary> /// <param name="target">Target entity reference</param> /// <param name="propertyName">Lookup property name</param> /// <returns></returns> /// <exception cref="ArgumentNullException"></exception> /// <exception cref="ArgumentException"></exception> public async Task DisassociateAsync(EntityReference target, string propertyName) { _logger.LogDebug($"Start {nameof(DisassociateAsync)}"); if (target == null) { throw new ArgumentNullException(nameof(target)); } if (string.IsNullOrEmpty(target.LogicalName)) { throw new ArgumentException("Entity Logical name cannot be empty."); } var navLink = target.ToNavigationLink(WebApiMetadata); using var httpRequest = new HttpRequestMessage(HttpMethod.Delete, $"{navLink}/{propertyName}/$ref"); using var httpResponse = await SendAsync(httpRequest, HttpCompletionOption.ResponseHeadersRead, cancellationToken : default) .ConfigureAwait(false); httpRequest.Dispose(); ODataResponseReader.EnsureSuccessStatusCode(httpResponse, _logger); }
/// <summary> /// Update entity /// </summary> /// <param name="entity">Entity</param> /// <returns></returns> /// <exception cref="ArgumentNullException"></exception> /// <exception cref="ArgumentException"></exception> /// <exception cref="WebApiException"></exception> public virtual async Task UpdateAsync(Entity entity) { if (entity is null) { throw new ArgumentNullException(nameof(entity)); } if (string.IsNullOrEmpty(entity.LogicalName)) { throw new ArgumentException("Entity Logical name cannot be empty."); } var navLink = entity.ToNavigationLink(WebApiMetadata); var json = JsonConvert.SerializeObject(entity, SerializerSettings); using var httpRequest = new HttpRequestMessage(HttpMethod.Patch, navLink) { Content = new StringContent(json, System.Text.Encoding.UTF8, "application/json") }; if (!string.IsNullOrEmpty(entity.RowVersion)) { httpRequest.Headers.IfMatch.Add(new EntityTagHeaderValue(entity.RowVersion)); } using var httpResponse = await SendAsync(httpRequest, HttpCompletionOption.ResponseHeadersRead, default) .ConfigureAwait(false); httpRequest.Dispose(); ODataResponseReader.EnsureSuccessStatusCode(httpResponse, _logger); }
/// <inheritdoc /> public virtual async Task UpdateAsync(Entity entity, bool allowUpsert = false) { if (entity is null) { throw new ArgumentNullException(nameof(entity)); } if (string.IsNullOrEmpty(entity.LogicalName)) { throw new ArgumentException("Entity Logical name cannot be empty."); } var watch = Stopwatch.StartNew(); _logger.LogDebug("Starting {WebApiOperationName} {TargetEntity}", "UPDATE", entity.LogicalName); var navLink = entity.ToNavigationLink(WebApiMetadata); var json = JsonConvert.SerializeObject(entity, SerializerSettings); using var httpRequest = new HttpRequestMessage(HttpMethod.Patch, navLink) { Content = new StringContent(json, System.Text.Encoding.UTF8, "application/json") }; if (!string.IsNullOrEmpty(entity.RowVersion)) { var tagValue = entity.RowVersion.Replace("W/", ""); if (!tagValue.StartsWith("\"")) { tagValue = $"\"{tagValue}"; } if (!tagValue.EndsWith("\"")) { tagValue = $"{tagValue}\""; } httpRequest.Headers.IfMatch.Add(new EntityTagHeaderValue(tagValue, isWeak: true)); } else if (!allowUpsert) // DISABLE UPSERT. { httpRequest.Headers.Add("If-Match", "*"); } using var httpResponse = await SendAsync(httpRequest, HttpCompletionOption.ResponseHeadersRead, default) .ConfigureAwait(false); httpRequest.Dispose(); ODataResponseReader.EnsureSuccessStatusCode(httpResponse, _logger); watch.Stop(); _logger.LogInformation("Complete {WebApiOperationName} {TargetEntity} in {Elapsed:0.0}ms", "UPDATE", entity.LogicalName, watch.Elapsed.TotalMilliseconds); }
public virtual async Task <Guid> CreateAsync(Entity entity) { if (entity is null) { throw new ArgumentNullException(nameof(entity)); } var collectionName = WebApiMetadata.GetEntitySetName(entity.LogicalName); var json = JsonConvert.SerializeObject(entity, SerializerSettings); using var httpRequest = new HttpRequestMessage(HttpMethod.Post, $"{collectionName}") { Content = new StringContent(json, System.Text.Encoding.UTF8, "application/json") }; using var httpResponse = await SendAsync(httpRequest, HttpCompletionOption.ResponseHeadersRead, default) .ConfigureAwait(false); httpRequest.Dispose(); Guid entityId = default; if (httpResponse.StatusCode == System.Net.HttpStatusCode.NoContent) { if (httpResponse.Headers.TryGetValues("OData-EntityId", out var headersRaw)) { var headers = headersRaw as string[] ?? headersRaw.ToArray(); var rawValue = headers.First().Split("(").Last().Split(")").First(); if (!Guid.TryParse(rawValue, out entityId)) { throw new WebApiException( $"Error parsing response header 'OData-EntityId'. Value: {headers.First()}"); } } else { throw new WebApiException("Response header 'OData-EntityId' not present."); } } else { ODataResponseReader.EnsureSuccessStatusCode(httpResponse, _logger); } return(entityId); }
/// <summary> /// Delete entity /// </summary> /// <param name="target">Target entity reference</param> /// <returns></returns> /// <exception cref="ArgumentNullException"></exception> /// <exception cref="ArgumentException"></exception> /// <exception cref="WebApiException"></exception> public virtual async Task DeleteAsync(EntityReference target) { if (target == null) { throw new ArgumentNullException(nameof(target)); } if (string.IsNullOrEmpty(target.LogicalName)) { throw new ArgumentException("Entity Logical name cannot be empty."); } var watch = Stopwatch.StartNew(); _logger.LogDebug("Starting {WebApiOperationName} {TargetEntity}", "DELETE", target.LogicalName); var requestId = Guid.NewGuid(); var navLink = target.ToNavigationLink(WebApiMetadata); using var httpRequest = new HttpRequestMessage(HttpMethod.Delete, navLink); if (!string.IsNullOrEmpty(target.RowVersion)) { var tagValue = target.RowVersion.Replace("W/", ""); httpRequest.Headers.IfMatch.Add(new EntityTagHeaderValue(tagValue, isWeak: true)); } using var httpResponse = await SendAsync(httpRequest, HttpCompletionOption.ResponseHeadersRead, CancellationToken.None) .ConfigureAwait(false); httpRequest.Dispose(); ODataResponseReader.EnsureSuccessStatusCode(httpResponse, _logger); ValidateResponseContent(httpResponse); watch.Stop(); _logger.LogInformation("Complete {WebApiOperationName} {TargetEntity} in {Elapsed:0.0}ms", "DELETE", target.LogicalName, watch.Elapsed.TotalMilliseconds); }
public virtual async Task <TResponse> ExecuteFunctionAsync <TResponse>(string query, CancellationToken cancellationToken = default) { TResponse result = default; using var httpRequest = new HttpRequestMessage(HttpMethod.Get, query); using var httpResponse = await SendAsync(httpRequest, HttpCompletionOption.ResponseHeadersRead, cancellationToken) .ConfigureAwait(false); httpRequest.Dispose(); ODataResponseReader.EnsureSuccessStatusCode(httpResponse, _logger); var contentStream = await httpResponse.Content.ReadAsStreamAsync().ConfigureAwait(false); using var streamReader = new StreamReader(contentStream); using var jsonReader = new JsonTextReader(streamReader); try { result = _serializer.Deserialize <TResponse>(jsonReader); } catch (NotSupportedException ex) // When content type is not valid { _logger.LogError(ex, "The content type is not supported."); } catch (JsonException ex) // Invalid JSON { _logger.LogError(ex, "Invalid JSON."); } finally { streamReader.Close(); jsonReader.Close(); } return(result); }
public virtual async Task <Guid> CreateAsync(Entity entity) { if (entity is null) { throw new ArgumentNullException(nameof(entity)); } if (string.IsNullOrEmpty(entity.LogicalName)) { throw new ArgumentException("Entity Logical name cannot be empty."); } var watch = Stopwatch.StartNew(); _logger.LogDebug("Starting {WebApiOperationName} {TargetEntity}", "CREATE", entity.LogicalName); var collectionName = WebApiMetadata.GetEntitySetName(entity.LogicalName); var json = JsonConvert.SerializeObject(entity, SerializerSettings); using var httpRequest = new HttpRequestMessage(HttpMethod.Post, $"{collectionName}") { Content = new StringContent(json, System.Text.Encoding.UTF8, "application/json") }; using var httpResponse = await SendAsync(httpRequest, HttpCompletionOption.ResponseHeadersRead, default) .ConfigureAwait(false); httpRequest.Dispose(); Guid entityId = default; if (httpResponse.StatusCode == System.Net.HttpStatusCode.NoContent) { if (httpResponse.Headers.TryGetValues("OData-EntityId", out var headersRaw)) { var headers = headersRaw as string[] ?? headersRaw.ToArray(); var rawValue = headers.First().Split("(").Last().Split(")").First(); if (!Guid.TryParse(rawValue, out entityId)) { throw new WebApiException( $"Error parsing response header 'OData-EntityId'. Value: {headers.First()}"); } } else { _logger.LogError("Response header 'OData-EntityId' not present."); throw new WebApiException("Response header 'OData-EntityId' not present."); } } else { ODataResponseReader.EnsureSuccessStatusCode(httpResponse, _logger); } watch.Stop(); _logger.LogInformation("Complete {WebApiOperationName} {TargetEntity} in {Elapsed:0.0}ms - {EntityId}", "CREATE", entity.LogicalName, watch.Elapsed.TotalMilliseconds, entityId); return(entityId); }