示例#1
0
 public async Task <HalResourceInspectedContext> InspectAsync(HalResourceInspectingContext context)
 {
     this.inspectingContext = context
                              ?? throw new ArgumentNullException(nameof(context));
     this.currentIndex = 0;
     return(await Next());
 }
        public HalResourceInspectedContext(HalResourceInspectingContext context)
        {
            if (context == null)
            {
                throw new ArgumentNullException(nameof(context));
            }

            this.Resource       = context.Resource;
            this.ActionContext  = context.ActionContext;
            this.IsRootResource = context.IsRootResource;
        }
        public void OnInspectingResource(HalResourceInspectingContext context)
        {
            if (context == null)
            {
                throw new ArgumentNullException(nameof(context));
            }

            if (context.Resource == null)
            {
                logger.LogDebug("Resource is null. Nothing to inspect.");
                return;
            }

            if (context.ActionContext == null)
            {
                throw new ArgumentException("ActionContext cannot be null.", nameof(context));
            }

            if (!(context.ActionContext.ActionDescriptor is ControllerActionDescriptor descriptor))
            {
                throw new HalException("Could not establish ControllerActionDescriptor reference.");
            }

            var links = linkService.GetLinks <HalLinkAttribute>(descriptor, context.ActionContext, context.OriginalObject);

            if (context.Resource.Links == null && links.Count > 0)
            {
                context.Resource.Links = new List <ILink>();
            }

            foreach (var link in links)
            {
                var hlink = new Link(link.Rel, link.Uri);
                context.Resource.Links.Add(hlink);
                if (link.IsSingular)
                {
                    if (context.Resource.SingularRelations == null)
                    {
                        context.Resource.SingularRelations = new HashSet <string>();
                    }

                    if (!context.Resource.SingularRelations.Contains(link.Rel))
                    {
                        context.Resource.SingularRelations.Add(link.Rel);
                    }
                }
            }
        }
示例#4
0
        public async Task <HalResourceInspectedContext> OnResourceInspectionAsync(
            HalResourceInspectingContext context,
            HalResourceInspectionDelegate next)
        {
            var inspectedContext = await next();

            if (inspectedContext.Resource?.Links == null)
            {
                return(inspectedContext);
            }

            var httpContext    = context.ActionContext.HttpContext;
            var requestFeature = httpContext.Features.Get <IHttpRequestFeature>();
            var links          = inspectedContext.Resource.Links.ToList();

            foreach (var link in links)
            {
                // TODO: Account for external links.
                var halRequestFeature = new HalHttpRequestFeature(requestFeature)
                {
                    Method = "GET",
                    Path   = link.HRef
                };

                var linkContext = new LinkValidationHttpContext(httpContext, halRequestFeature);

                // Invoke the mvc pipeline. The LinkValidationFilter will short circuit
                // the request after the authorization filters have executed.
                await context.MvcPipeline.Pipeline(linkContext);

                var response = linkContext.Response as HalHttpResponse;
                if (response.Resource == LinkValidatedResult.LinkValidatedObject)
                {
                    logger.LogDebug("Client has permissions to access link '{0}'.", link);
                }
                else
                {
                    logger.LogDebug("Client does not have permission to access link '{0}'. Removing link from resource.", link);
                    inspectedContext.Resource.Links.Remove(link);
                }
            }

            return(inspectedContext);
        }
示例#5
0
 public void OnInspectingResource(HalResourceInspectingContext context)
 {
 }
示例#6
0
        public async Task <HalResourceInspectedContext> OnResourceInspectionAsync(
            HalResourceInspectingContext context,
            HalResourceInspectionDelegate next)
        {
            if (context == null)
            {
                throw new ArgumentNullException(nameof(context));
            }

            if (next == null)
            {
                throw new ArgumentNullException(nameof(next));
            }

            if (!context.IsRootResource)
            {
                throw new NotSupportedException("This inspector does not support embedded resources.");
            }

            if (context.Resource == null)
            {
                return(await next());
            }

            if (context.ActionContext == null)
            {
                throw new ArgumentException("ActionContext cannot be null.", nameof(context));
            }

            if (!(context.ActionContext.ActionDescriptor is ControllerActionDescriptor descriptor))
            {
                throw new HalException("Could not establish ControllerActionDescriptor reference.");
            }

            if (context.ActionContext.HttpContext == null || context.ActionContext.HttpContext.Features == null)
            {
                throw new ArgumentException("HttpContext features cannot be null.", nameof(context));
            }

            if (context.MvcPipeline == null)
            {
                throw new ArgumentException("Context does not contain the mvc pipeline.", nameof(context));
            }

            var requestFeature = context.ActionContext.HttpContext.Features.Get <IHttpRequestFeature>();
            var links          = linkService.GetLinks <HalEmbedAttribute>(descriptor, context.ActionContext, context.OriginalObject);

            foreach (var link in links)
            {
                var halRequestFeature = new HalHttpRequestFeature(requestFeature)
                {
                    Method = "GET",
                    Path   = link.Uri
                };

                var halContext = new HalHttpContext(context.ActionContext.HttpContext, halRequestFeature);

                logger.LogDebug("About to invoke MVC pipeline with a GET request on path '{0}'.", link.Uri);
                await context.MvcPipeline.Pipeline(halContext);

                var response = halContext.Response as HalHttpResponse;
                if (response.StatusCode >= 200 && response.StatusCode <= 299)
                {
                    logger.LogDebug("MVC pipeline returned success status code {0}. Invoking HAL resource factory.", response.StatusCode);
                    IResource embedded = await context.EmbeddedResourcePipeline(response.ActionContext, response.Resource);

                    embedded.Rel = link.Rel;

                    if (embedded is IResourceCollection collection)
                    {
                        if (collection.Collection != null)
                        {
                            logger.LogDebug("Embedding collection of {0} resources to rel '{0}'", collection.Collection.Count, link.Rel);
                            foreach (var item in collection.Collection)
                            {
                                item.Rel = link.Rel;
                                context.Resource.Embedded.Add(item);
                            }
                        }
                    }
                    else
                    {
                        logger.LogDebug("Embedding resource to rel '{0}'", link.Rel);
                        context.Resource.Embedded.Add(embedded);
                    }
                }
                else
                {
                    logger.LogWarning("MVC pipeline returned non-success status code {0}. Ignoring result.", response.StatusCode);
                }
            }

            var result = await next();

            logger.LogTrace("After invoke next.");

            return(result);
        }