using Microsoft.AspNetCore.Mvc; using Newtonsoft.Json.Linq; using Newtonsoft.Json.Schema; using System.Reflection; using System.Text; using DevLab.JmesPath; using afd_2._0.webapi.example.JMESPathCustomFunctions; namespace afd_2._0.webapi.example.Controllers { [ApiController] [Route("[controller]")] public class ExampleCarInsuranceController : ControllerBase { private readonly JmesPath _jmesPath = new JmesPath(); /// /// JMESPath expression to check if ageAtReferenceDate of policyHolder >= 18, /// at reference date, which is an attribute of the commonFunctional. /// const string cJMESPathExpression = "(policy[].party[?entityType == 'policyHolder' && birthDate.ageAtReferenceDate(@, $.commonFunctional[0].referenceDate) >= `18`][] != `[]`)"; /// /// Constructor /// public ExampleCarInsuranceController() { // Register JamesPath and its custom function. _jmesPath = new JmesPath(); _jmesPath.FunctionRepository.Register(); } /// /// Operation to add a new insurance /// /// [HttpPost("new")] public IActionResult NewInsurance() { try { // Read example request and afd-schema from embedded resources. var request = JObject.Parse(ReadEmbeddedResource("submitPolicy_new_request.json")); var schema = JSchema.Parse(ReadEmbeddedResource("submitPolicy_new_request_schema.json")); // 1. Check request against AFD-schema if (!request.IsValid(schema)) { return BadRequest(new { message = "The request is invalid against AFD-schema." }); } // 2. Check request against JMESPath Expression(s) using JmesPath custom function ageAtReferenceDate if (!bool.Parse(_jmesPath.Transform(request.ToString(), cJMESPathExpression))) { return BadRequest(new { message = $"The request is invalid against JMESPath expression."}); } return Ok(); } catch (Exception ex) { return BadRequest(new { message = $"request failed: {ex.Message}" }); } } /// /// /// /// private bool ValidateAgainstJmesPath(JObject request) { var requestJsonString = request.ToString(); const string PolicyHolderIsOlderThan18AtReferenceDateRule = "(policy[].party[?entityType == 'policyHolder' && birthDate.ageAtReferenceDate(@, $.commonFunctional[0].referenceDate) >= `18`][] != `[]`)"; bool result = bool.Parse( _jmesPath.Transform(requestJsonString, PolicyHolderIsOlderThan18AtReferenceDateRule )); return result; } /// /// Read file 'fileName' from embedded resource /// /// The example request private static string ReadEmbeddedResource(string fileName) { var resourceName = Assembly.GetExecutingAssembly().GetManifestResourceNames().Single(str => str.EndsWith(fileName)); using var stream = Assembly.GetExecutingAssembly().GetManifestResourceStream(resourceName) ?? throw new Exception($"Could not read resourd: {resourceName}"); using var streamReader = new StreamReader(stream, Encoding.UTF8); return streamReader.ReadToEnd(); } } }