public async Task <DataResponse> GetResponseAsync(DirectLinkContext context) { await _onStarting; var response = await GetResponseInnerAsync(context); await _onCompleted(response); return(response); }
private async Task <DataResponse> GetResponseInnerAsync(DirectLinkContext context) { try { var data = await GetDataAsync(context.Path, context); if (_errorPath != null && context.Path.StartsWith(_errorPath)) { var exceptionFeature = context.HttpContext.Features.Get <IExceptionHandlerPathFeature>(); if (exceptionFeature != null) { Exception exceptionThatOccurred = exceptionFeature.Error; data.Message = exceptionThatOccurred.Message; return(new DataResponse(StatusCodes.Status500InternalServerError, data)); } } if (!data.IsAuthorized || !data.IsRouted) { var _path = !data.IsAuthorized ? _notAuthPath : _notFoundPath; var statusCode = !data.IsAuthorized ? StatusCodes.Status403Forbidden : StatusCodes.Status404NotFound; if (_path == null) { return(new DataResponse(statusCode)); } var isAuthorized = data.IsAuthorized; var routed = data.IsRouted; data = await GetDataAsync(_path, context); data.IsAuthorized = isAuthorized; data.IsRouted = routed; return(new DataResponse(statusCode, data)); } return(new DataResponse(StatusCodes.Status200OK, data)); } catch (Exception ex) { if (_errorPath == null) { return(new DataResponse(StatusCodes.Status500InternalServerError, null, ex.Message)); } try { var data = await GetDataAsync(_errorPath, context); data.Message = ex.Message; return(new DataResponse(StatusCodes.Status500InternalServerError, data)); } catch (Exception exception) { return(new DataResponse(StatusCodes.Status500InternalServerError, null, exception.Message)); } } }
public async Task Invoke(HttpContext httpContext, DirectLinkContext context, IRoutingService routingService, IHotNodeService nodeService) { var request = httpContext.Request; context.HttpContext = httpContext; context.Path = request.PathBase.Value + request.Path.Value + request.QueryString; var response = await routingService.GetResponseAsync(context); httpContext.Response.StatusCode = response.StatusCode; httpContext.Response.Headers["Cache-Control"] = "no-store"; if (response.Data != null) { var dataJson = JsonConvert.SerializeObject(response.Data); foreach (var style in response.Data.Styles) { context.Tags.Head.AddLink(style.Value); } foreach (var script in response.Data.Scripts) { context.Tags.Head.AddScript(script.Value); } context.Data.Add("title", context.Title); context.Data.Add("metaTags", context.Tags.GetMetaTags()); context.Data.Add("headTags", context.Tags.Head); context.Data.Add("contentTags", context.Tags.Content); context.Data.Add("bodyTags", context.Tags.Body); context.Data.Add("serverTime", DateTime.Now.Ticks.ToString()); var contextDataJson = JsonConvert.SerializeObject(context.Data); var cookiesJson = JsonConvert.SerializeObject(httpContext.Request.Cookies.ToDictionary(k => k.Key, v => v.Value)); var content = $@"{{""moduleName"":""{_moduleName}"",""args"":[""{_wwwroot}"",{dataJson},{contextDataJson},{cookiesJson}]}}"; var payload = new StringContent(content, Encoding.UTF8, "application/json"); var result = await nodeService.InvokeExportAsync <string>(CancellationToken.None, payload); await httpContext.Response.WriteAsync(result); return; } if (response.Message != null) { await httpContext.Response.WriteAsync(response.Message); } }
private async Task <DirectLinkData> GetDataAsync(string path, DirectLinkContext context) { var name = _componentsService.GetComponentName(_entryType); var fullname = name; var data = new DirectLinkData(name, _provider, _authorizationService, _componentsService); var authorized = await AuthorizationHelper.AuthorizeAsync(_entryType, context.User, _authorizationService); if (!authorized) { data.IsAuthorized = false; data.Title = context.Title; return(data); } var link = (IInternalDirectLink <ViewModel>)_provider.GetService(_entryType); var args = Array.Empty <object>(); var viewModel = data.CreateViewModel(link, args, name); data.AddAssets(name); await data.AddStateAsync(name, fullname, viewModel, context.User); var idx = path.IndexOf('#'); if (idx >= 0) { path = path.Substring(0, idx); } var routedPath = ""; context.PathBase = ""; foreach (var pathBase in _pathBases) { if (path.StartsWith(pathBase)) { context.PathBase = pathBase; routedPath = pathBase; path = path.Substring(pathBase.Length, path.Length - pathBase.Length); } } var routes = Routes.Get(_entryType); if (routes == null) { data.IsRouted = true; data.Title = context.Title; return(data); } var restPath = path; while (true) { args = null; Route nextRoute = null; foreach (var route in routes) { if (route.Regex == null) { if (restPath.StartsWith(route.Template) || (restPath == "" || restPath == "/") && route.Default) { nextRoute = route; args = nextRoute.Args; if (route.Default) { routedPath += restPath; restPath = ""; } else { routedPath += route.Template; restPath = restPath.Substring(route.Template.Length); } break; } } else { var m = route.Regex.Match(restPath); if (!m.Success) { continue; } if (m.Groups.Count - 1 != route.Parameters.Count) { break; } var values = m.Groups.Skip(1).Select(p => p.Value).ToArray(); if (RouteTypesHelper.TryGetArgs(route.Parameters, values, ref args)) { if (route.Args != null) { args = args.Concat(route.Args).ToArray(); } nextRoute = route; routedPath += m.Groups[0]; restPath = restPath.Substring(m.Value.Length); break; } } } if (nextRoute == null) { break; } var routerViewModel = (RouterViewModel)viewModel; routerViewModel.OnRouted(nextRoute); name = nextRoute.Type != null ? _componentsService.GetComponentName(nextRoute.Type) : nextRoute.Name; fullname += $".{name}"; routerViewModel.Component = new RouteComponent(name, fullname); data.AddAssets(name); if (nextRoute.Type != null) { authorized = await AuthorizationHelper.AuthorizeAsync(nextRoute.Type, context.User, _authorizationService); if (!authorized) { data.IsAuthorized = false; break; } link = (IInternalDirectLink <ViewModel>)_provider.GetService(nextRoute.Type); args = args ?? Array.Empty <object>(); viewModel = data.CreateViewModel(link, args, name); var succeeded = await data.AddStateAsync(name, fullname, viewModel, context.User); if (!succeeded) { data.IsAuthorized = false; break; } routes = Routes.Get(nextRoute.Type); if (routes == null) { if (restPath == "/") { routedPath += "/"; } break; } } else { if (nextRoute.State != null) { data.States.Add(fullname, nextRoute.State); } else { if (args == null) { data.States.Add(fullname, new Dictionary <string, object> { { "args", null } }); } else { var values = new Dictionary <string, object>(); for (int i = 0; i < nextRoute.Parameters.Count; ++i) { values.Add(nextRoute.Parameters[i].Name, args[i]); } data.States.Add(fullname, new Dictionary <string, object> { { "args", values } }); } } if (restPath == "/") { routedPath += "/"; } break; } } data.IsRouted = routedPath == context.PathBase + path; data.Title = context.Title; return(data); }