public async Task <HttpResponseMessage> Cqs() { var dotNetType = Request.Headers.Contains("X-Cqs-Object-Type") ? Request.Headers.GetValues("X-Cqs-Object-Type").FirstOrDefault() : null; var cqsName = Request.Headers.Contains("X-Cqs-Name") ? Request.Headers.GetValues("X-Cqs-Name").FirstOrDefault() : null; var json = await Request.Content.ReadAsStringAsync(); object cqsObject, cqsReplyObject = null; if (!string.IsNullOrEmpty(dotNetType)) { cqsObject = _cqsObjectMapper.Deserialize(dotNetType, json); if (cqsObject == null) { _logger.Error($"Could not deserialize[{dotNetType}]: {json}"); var response = Request.CreateResponse(HttpStatusCode.OK); response.StatusCode = HttpStatusCode.BadRequest; response.ReasonPhrase = "Unknown type: " + dotNetType; return(response); } } else if (!string.IsNullOrEmpty(cqsName)) { cqsObject = _cqsObjectMapper.Deserialize(cqsName, json); if (cqsObject == null) { _logger.Error($"Could not deserialize[{cqsName}]: {json}"); var response = Request.CreateResponse(HttpStatusCode.OK); response.StatusCode = HttpStatusCode.BadRequest; response.ReasonPhrase = "Unknown type: " + cqsName; return(response); } } else { var response = Request.CreateResponse(HttpStatusCode.OK); response.StatusCode = HttpStatusCode.BadRequest; response.ReasonPhrase = "Expected a class name in the header 'X-Cqs-Name' or a .NET type name in the header 'X-Cqs-Object-Type'."; return(response); } if (User.Identity.AuthenticationType != "ApiKey") { var prop = cqsObject.GetType().GetProperty("CreatedById"); if ((prop != null) && prop.CanWrite) { prop.SetValue(cqsObject, User.GetAccountId()); } prop = cqsObject.GetType().GetProperty("AccountId"); if ((prop != null) && prop.CanWrite) { prop.SetValue(cqsObject, User.GetAccountId()); } prop = cqsObject.GetType().GetProperty("UserId"); if ((prop != null) && prop.CanWrite) { prop.SetValue(cqsObject, User.GetAccountId()); } } RestrictOnApplicationId(cqsObject); Exception ex = null; try { _logger.Debug("Invoking " + cqsObject.GetType().Name + " " + json); if (IsQuery(cqsObject)) { cqsReplyObject = await InvokeQuery(cqsObject); } else { await InvokeMessage(cqsObject); } if (cqsReplyObject != null) { RestrictOnApplicationId(cqsReplyObject); } await HandleSecurityPrincipalUpdates(); } catch (AggregateException e1) { _logger.Error("Failed to process '" + json + "'.", e1); ex = e1.InnerException; } catch (Exception e1) { _logger.Error("Failed to process2 '" + json + "'.", e1); ex = e1; } if (ex is HttpException) { _logger.Error("HTTP error for " + json, ex); var response = Request.CreateResponse(HttpStatusCode.OK); response.StatusCode = (HttpStatusCode)((HttpException)ex).GetHttpCode(); response.ReasonPhrase = FirstLine(ex.Message); return(response); } if (ex is InvalidCredentialException) { _logger.Error("Auth error for " + json, ex); var authEx = (InvalidCredentialException)ex; var response = Request.CreateResponse(HttpStatusCode.Forbidden); response.StatusCode = HttpStatusCode.Unauthorized; response.ReasonPhrase = FirstLine(ex.Message); return(response); } if (ex != null) { _logger.Error("Failed to process result for " + json, ex); var response = Request.CreateResponse(HttpStatusCode.OK); response.StatusCode = HttpStatusCode.InternalServerError; response.ReasonPhrase = FirstLine(ex.Message); return(response); } var reply = Request.CreateResponse(HttpStatusCode.OK); // for instance commands do not have a return value. if (cqsReplyObject != null) { reply.Headers.Add("X-Cqs-Object-Type", cqsReplyObject.GetType().GetSimpleAssemblyQualifiedName()); reply.Headers.Add("X-Cqs-Name", cqsReplyObject.GetType().Name); if (cqsReplyObject is Exception) { reply.StatusCode = (HttpStatusCode)500; } json = _serializer.Serialize(cqsReplyObject, out var cnt); _logger.Debug("Reply to " + cqsObject.GetType().Name + ": " + json); reply.Content = new StringContent(json, Encoding.UTF8, "application/json"); } else { _logger.Debug("Reply to " + cqsObject.GetType().Name + ": [empty response]"); reply.StatusCode = HttpStatusCode.NoContent; } return(reply); }
public async Task <IActionResult> Cqs() { var headerValue = Request.Headers["X-Cqs-Object-Type"]; var dotNetType = headerValue.Count > 0 ? headerValue[0] : null; headerValue = Request.Headers["X-Cqs-Name"]; var cqsName = headerValue.Count > 0 ? headerValue[0] : null; string json; using (var reader = new StreamReader(Request.Body, Encoding.UTF8, true, 8192, true)) { json = reader.ReadToEnd(); } object cqsObject, cqsReplyObject = null; if (!string.IsNullOrEmpty(dotNetType)) { cqsObject = _cqsObjectMapper.Deserialize(dotNetType, json); if (cqsObject == null) { _logger.Error($"Could not deserialize[{dotNetType}]: {json}"); return(BadRequest(new ErrorMessage($"Unknown type: {dotNetType}"))); } } else if (!string.IsNullOrEmpty(cqsName)) { cqsObject = _cqsObjectMapper.Deserialize(cqsName, json); if (cqsObject == null) { _logger.Error($"Could not deserialize[{cqsName}]: {json}"); return(BadRequest(new ErrorMessage($"Unknown type: {cqsName}"))); } } else { _logger.Error($"Could not deserialize[{cqsName}]: {json}"); return(BadRequest(new ErrorMessage( "Expected a class name in the header 'X-Cqs-Name' or a .NET type name in the header 'X-Cqs-Object-Type'."))); } if (User.Identity.AuthenticationType != "ApiKey") { var prop = cqsObject.GetType().GetProperty("CreatedById"); if (prop != null && prop.CanWrite) { prop.SetValue(cqsObject, User.GetAccountId()); } prop = cqsObject.GetType().GetProperty("AccountId"); if (prop != null && prop.CanWrite) { prop.SetValue(cqsObject, User.GetAccountId()); } prop = cqsObject.GetType().GetProperty("UserId"); if (prop != null && prop.CanWrite) { prop.SetValue(cqsObject, User.GetAccountId()); } } RestrictOnApplicationId(cqsObject); Exception ex = null; try { _logger.Debug("Invoking " + cqsObject.GetType().Name + " " + json); if (IsQuery(cqsObject)) { cqsReplyObject = await InvokeQuery(cqsObject); } else { await InvokeMessage(cqsObject); } _logger.Debug(".. pass1 " + cqsObject.GetType().Name); if (cqsReplyObject != null) { RestrictOnApplicationId(cqsReplyObject); } //await HandleSecurityPrincipalUpdates(); _logger.Debug(".. completed " + cqsObject.GetType().Name); } catch (AggregateException e1) { _logger.Error("Failed to process '" + json + "'.", e1); ex = e1.InnerException; } catch (Exception e1) { _logger.Error("Failed to process2 '" + json + "'.", e1); ex = e1; } if (ex is EntityNotFoundException || ex is Griffin.Data.EntityNotFoundException) { _logger.Error("Entity not found " + json, ex); return(NotFound()); } if (ex is InvalidCredentialException) { _logger.Error("Auth error for " + json, ex); var authEx = (InvalidCredentialException)ex; return(BadRequest(new ErrorMessage(FirstLine(ex.Message)))); } if (ex != null) { _logger.Error("Failed to process result for " + json, ex); return(BadRequest(new ErrorMessage(FirstLine(ex.Message)))); } var result = new ContentResult { ContentType = "application/json" }; // for instance commands do not have a return value. if (cqsReplyObject != null) { Response.Headers.Add("X-Cqs-Object-Type", cqsReplyObject.GetType().GetSimpleAssemblyQualifiedName()); Response.Headers.Add("X-Cqs-Name", cqsReplyObject.GetType().Name); if (cqsReplyObject is Exception) { result.StatusCode = 500; } json = _serializer.Serialize(cqsReplyObject, out var cnt); _logger.Debug("Reply to " + cqsObject.GetType().Name + ": " + json); result.Content = json; } else { _logger.Debug("Reply to " + cqsObject.GetType().Name + ": [empty response]"); result.StatusCode = (int)HttpStatusCode.NoContent; } return(result); }