/// <summary>Handles an HTTP request as an asynchronous operation.</summary> /// <param name="context">The <see cref="HttpContext" /> instance for the current request.</param> /// <param name="next">The delegate representing the remaining middleware in the request pipeline.</param> /// <returns>A task that represents the asynchronous operation.</returns> /// <exception cref="ArgumentNullException"><paramref name="context" /> is <see langword="null" />.</exception> public async Task InvokeAsync(HttpContext context, RequestDelegate next) { if (context == null) { throw new ArgumentNullException(nameof(context)); } if (!string.Equals(context.Request.Method, HttpMethods.Post, StringComparison.OrdinalIgnoreCase)) { context.Response.StatusCode = StatusCodes.Status405MethodNotAllowed; return; } if (context.Request.Headers.ContainsKey(HeaderNames.ContentEncoding)) { context.Response.StatusCode = StatusCodes.Status415UnsupportedMediaType; return; } var requestStreamEncoding = default(Encoding); var responseStreamEncoding = default(Encoding); if (!context.Request.Headers.TryGetValue(HeaderNames.ContentType, out var contentTypeHeaderValueString)) { context.Response.StatusCode = StatusCodes.Status415UnsupportedMediaType; return; } if (!MediaTypeHeaderValue.TryParse((string)contentTypeHeaderValueString, out var contentTypeHeaderValue)) { context.Response.StatusCode = StatusCodes.Status415UnsupportedMediaType; return; } if (!contentTypeHeaderValue.MediaType.Equals(MediaTypes.ApplicationJson, StringComparison.OrdinalIgnoreCase)) { context.Response.StatusCode = StatusCodes.Status415UnsupportedMediaType; return; } if (contentTypeHeaderValue.Charset.HasValue && !SupportedEncodings.TryGetValue(contentTypeHeaderValue.Charset.Value, out requestStreamEncoding)) { context.Response.StatusCode = StatusCodes.Status415UnsupportedMediaType; return; } if (!context.Request.Headers.TryGetValue(HeaderNames.Accept, out var acceptTypeHeaderValueString)) { context.Response.StatusCode = StatusCodes.Status406NotAcceptable; return; } if (!MediaTypeHeaderValue.TryParse((string)acceptTypeHeaderValueString, out var acceptTypeHeaderValue)) { context.Response.StatusCode = StatusCodes.Status406NotAcceptable; return; } if (!acceptTypeHeaderValue.MediaType.Equals(MediaTypes.ApplicationJson, StringComparison.OrdinalIgnoreCase)) { context.Response.StatusCode = StatusCodes.Status406NotAcceptable; return; } if (acceptTypeHeaderValue.Charset.HasValue && !SupportedEncodings.TryGetValue(acceptTypeHeaderValue.Charset.Value, out responseStreamEncoding)) { context.Response.StatusCode = StatusCodes.Status406NotAcceptable; return; } requestStreamEncoding ??= SupportedEncodings[Encoding.UTF8.WebName]; responseStreamEncoding ??= SupportedEncodings[Encoding.UTF8.WebName]; var jsonRpcRequestData = default(JsonRpcData <JsonRpcRequest>); try { using (var streamReader = new StreamReader(context.Request.Body, requestStreamEncoding, false, StreamBufferSize, true)) { jsonRpcRequestData = await _serializer.DeserializeRequestDataAsync(streamReader, context.RequestAborted); } } catch (JsonException e) { _logger.LogDataIsInvalid(e); var jsonRpcResponse = StandardJsonRpcResponses[JsonRpcErrorCode.InvalidFormat]; if (_environment.EnvironmentName == Environments.Development) { jsonRpcResponse = new JsonRpcResponse(default, new JsonRpcError(jsonRpcResponse.Error.Code, jsonRpcResponse.Error.Message, e.ToString()));