public async ValueTask InvokeAsync(IDirectiveContext context)
        {
            // context.Result = context.ArgumentValue< Language >( nameof( LanguageDirective.Name ) );
            context.ContextData[nameof(LanguageDirective.Name)] = context.ArgumentValue <Language>(nameof(LanguageDirective.Name));

            await _next(context);
        }
        private static async Task AuthorizeAsync(
            IDirectiveContext context,
            DirectiveDelegate next)
        {
            AuthorizeDirective directive = context.Directive
                                           .ToObject <AuthorizeDirective>();

            ClaimsPrincipal principal = context
                                        .CustomProperty <ClaimsPrincipal>(nameof(ClaimsPrincipal));

            var allowed = IsInRoles(principal, directive.Roles);

#if !ASPNETCLASSIC
            if (allowed && NeedsPolicyValidation(directive))
            {
                allowed = await AuthorizeWithPolicyAsync(
                    context, directive, principal)
                          .ConfigureAwait(false);
            }
#endif
            if (allowed)
            {
                await next(context);
            }
            else if (context.Result == null)
            {
                context.Result = QueryError.CreateFieldError(
                    "The current user is not authorized to " +
                    "access this resource.",
                    context.Path,
                    context.FieldSelection);
            }
        }
        private QueryRequest CreateQuery(
            IDirectiveContext directiveContext)
        {
            var rewriter       = new ExtractRemoteQueryRewriter();
            var fieldSelection = (FieldNode)rewriter.Rewrite(
                directiveContext.FieldSelection,
                directiveContext.FieldSelection.GetSchemaName());

            OperationType operation =
                GetOperationType(directiveContext);

            Stack <SelectionPathComponent> selectionPath =
                GetSelectionPath(directiveContext);

            IReadOnlyDictionary <string, object> variables =
                CreateVariables(directiveContext, selectionPath);

            DocumentNode query = CreateDelegationQuery(
                operation, selectionPath, fieldSelection);

            return(new QueryRequest(SerializeQuery(query))
            {
                VariableValues = variables
            });
        }
Exemple #4
0
        private static async Task <AuthState> CheckPermissionsAsync(
            IDirectiveContext context,
            AuthorizeDirective directive)
        {
            if (!TryGetAuthenticatedPrincipal(context, out ClaimsPrincipal? principal))
            {
                return(AuthState.NotAuthenticated);
            }

            if (IsInAnyRole(principal !, directive.Roles))
            {
                if (NeedsPolicyValidation(directive))
                {
                    return(await AuthorizeWithPolicyAsync(
                               context, directive, principal !)
                           .ConfigureAwait(false));
                }
                else
                {
                    return(AuthState.Allowed);
                }
            }

            return(AuthState.NotAllowed);
        }
Exemple #5
0
        public async Task InvokeAsync(IDirectiveContext context)
        {
            AuthorizeDirective directive = context.Directive
                                           .ToObject <AuthorizeDirective>();

            if (directive.Apply == ApplyPolicy.AfterResolver)
            {
                await _next(context).ConfigureAwait(false);

                AuthState state = await CheckPermissionsAsync(
                    context, directive)
                                  .ConfigureAwait(false);

                if (state != AuthState.Allowed && !IsErrorResult(context))
                {
                    SetError(context, directive, state);
                }
            }
            else
            {
                AuthState state = await CheckPermissionsAsync(
                    context, directive)
                                  .ConfigureAwait(false);

                if (state == AuthState.Allowed)
                {
                    await _next(context).ConfigureAwait(false);
                }
                else
                {
                    SetError(context, directive, state);
                }
            }
        }
Exemple #6
0
        private static async Task <AuthState> AuthorizeWithPolicyAsync(
            IDirectiveContext context,
            AuthorizeDirective directive,
            ClaimsPrincipal principal)
        {
            IServiceProvider      services         = context.Service <IServiceProvider>();
            IAuthorizationService?authorizeService =
                services.GetService <IAuthorizationService>();
            IAuthorizationPolicyProvider?policyProvider =
                services.GetService <IAuthorizationPolicyProvider>();

            if (authorizeService == null || policyProvider == null)
            {
                // authorization service is not configured so the user is
                // authorized with the previous checks.
                return(string.IsNullOrWhiteSpace(directive.Policy)
                    ? AuthState.Allowed
                    : AuthState.NotAllowed);
            }

            AuthorizationPolicy?policy = null;

            if ((directive.Roles is null || directive.Roles.Count == 0) &&
                string.IsNullOrWhiteSpace(directive.Policy))
            {
                policy = await policyProvider.GetDefaultPolicyAsync()
                         .ConfigureAwait(false);

                if (policy == null)
                {
                    return(AuthState.NoDefaultPolicy);
                }
            }
Exemple #7
0
        private static async Task <bool> AuthorizeWithPolicyAsync(
            IDirectiveContext context,
            AuthorizeDirective directive,
            ClaimsPrincipal principal)
        {
            IServiceProvider      services         = context.Service <IServiceProvider>();
            IAuthorizationService authorizeService =
                services.GetService <IAuthorizationService>();
            IAuthorizationPolicyProvider policyProvider =
                services.GetService <IAuthorizationPolicyProvider>();

            if (authorizeService == null || policyProvider == null)
            {
                return(string.IsNullOrWhiteSpace(directive.Policy));
            }

            AuthorizationPolicy policy = null;

            if (directive.Roles.Count == 0 &&
                string.IsNullOrWhiteSpace(directive.Policy))
            {
                policy = await policyProvider.GetDefaultPolicyAsync()
                         .ConfigureAwait(false);

                if (policy == null)
                {
                    context.Result = QueryError.CreateFieldError(
                        "The default authorization policy does not exist.",
                        context.FieldSelection);
                }
            }

            else if (!string.IsNullOrWhiteSpace(directive.Policy))
            {
                policy = await policyProvider.GetPolicyAsync(directive.Policy)
                         .ConfigureAwait(false);

                if (policy == null)
                {
                    context.Result = QueryError.CreateFieldError(
                        $"The `{directive.Policy}` authorization policy " +
                        "does not exist.",
                        context.FieldSelection);
                }
            }

            if (context.Result == null && policy != null)
            {
                AuthorizationResult result =
                    await authorizeService.AuthorizeAsync(principal, policy)
                    .ConfigureAwait(false);

                return(result.Succeeded);
            }

            return(false);
        }
Exemple #8
0
 public static void ExportValueAsVariable(
     this IDirectiveContext context)
 {
     if (context.ContextData.TryGetValue(ExportedVariables, out var o) &&
         o is ConcurrentBag <ExportedVariable> exp)
     {
         exp.Add(new ExportedVariable(
                     context.Directive.ToObject <ExportDirective>().As
                     ?? context.Selection.Field.Name.Value,
                     context.Selection.Type,
                     context.Result));
     }
 }
        private Stack <SelectionPathComponent> GetSelectionPath(
            IDirectiveContext directiveContext)
        {
            var directive = directiveContext.Directive
                            .ToObject <DelegateDirective>();

            if (string.IsNullOrEmpty(directive.Path))
            {
                return(new Stack <SelectionPathComponent>());
            }

            return(SelectionPathParser.Parse(new Source(directive.Path)));
        }
Exemple #10
0
        private OperationType GetOperationType(
            IDirectiveContext directiveContext)
        {
            var directive = directiveContext.Directive
                            .ToObject <DelegateDirective>();

            if (!Enum.TryParse(directive.Operation, out OperationType type))
            {
                type = OperationType.Query;
            }

            return(type);
        }
Exemple #11
0
        private static bool TryGetAuthenticatedPrincipal(
            IDirectiveContext context,
            [NotNullWhen(true)] out ClaimsPrincipal?principal)
#endif
        {
            if (context.ContextData.TryGetValue(nameof(ClaimsPrincipal), out var o) &&
                o is ClaimsPrincipal p &&
                p.Identities.Any(t => t.IsAuthenticated))
            {
                principal = p;
                return(true);
            }

            principal = null;
            return(false);
        }
Exemple #12
0
        public async Task InvokeAsync(IDirectiveContext context)
        {
            AuthorizeDirective directive = context.Directive
                                           .ToObject <AuthorizeDirective>();

            ClaimsPrincipal principal     = null;
            var             allowed       = false;
            var             authenticated = false;

            if (context.ContextData.TryGetValue(
                    nameof(ClaimsPrincipal), out var o) &&
                o is ClaimsPrincipal p)
            {
                principal     = p;
                authenticated = allowed =
                    p.Identities.Any(t => t.IsAuthenticated);
            }

            allowed = allowed && IsInAnyRole(principal, directive.Roles);

#if !ASPNETCLASSIC
            if (allowed && NeedsPolicyValidation(directive))
            {
                allowed = await AuthorizeWithPolicyAsync(
                    context, directive, principal)
                          .ConfigureAwait(false);
            }
#endif
            if (allowed)
            {
                await _next(context).ConfigureAwait(false);
            }
            else if (context.Result == null)
            {
                context.Result = ErrorBuilder.New()
                                 .SetMessage(
                    AuthResources.AuthorizeMiddleware_NotAuthorized)
                                 .SetCode(authenticated
                        ? ErrorCodes.Authentication.NotAuthorized
                        : ErrorCodes.Authentication.NotAuthenticated)
                                 .SetPath(context.Path)
                                 .AddLocation(context.FieldSelection)
                                 .Build();
            }
        }
Exemple #13
0
        public void Validate(IDirectiveContext context)
        {
            foreach (InputField argument in context.Field.Arguments)
            {
                foreach (IDirective directive in argument.Directives)
                {
                    object argumentValue =
                        context.Argument <object>(argument.Name);

                    var argumentValidator =
                        directive.ToObject <ArgumentValidationDirective>();

                    argumentValidator.Validator(
                        context, context.FieldSelection,
                        argument.Name, argumentValue);
                }
            }
        }
Exemple #14
0
        private static async Task AuthorizeAsync(
            IDirectiveContext context,
            FieldDelegate next)
        {
            AuthorizeDirective directive = context.Directive
                                           .ToObject <AuthorizeDirective>();

            ClaimsPrincipal principal = null;
            var             allowed   = false;

            if (context.ContextData.TryGetValue(
                    nameof(ClaimsPrincipal), out var o) &&
                o is ClaimsPrincipal p)
            {
                principal = p;
                allowed   = p.Identity.IsAuthenticated;
            }

            allowed = allowed && IsInRoles(principal, directive.Roles);

#if !ASPNETCLASSIC
            if (allowed && NeedsPolicyValidation(directive))
            {
                allowed = await AuthorizeWithPolicyAsync(
                    context, directive, principal)
                          .ConfigureAwait(false);
            }
#endif
            if (allowed)
            {
                await next(context).ConfigureAwait(false);
            }
            else if (context.Result == null)
            {
                context.Result = ErrorBuilder.New()
                                 .SetMessage(
                    "The current user is not authorized to " +
                    "access this resource.")
                                 .SetPath(context.Path)
                                 .AddLocation(context.FieldSelection)
                                 .Build();
            }
        }
Exemple #15
0
        public Task <IExecutionResult> RedirectQueryAsync(
            IDirectiveContext directiveContext)
        {
            if (directiveContext == null)
            {
                throw new ArgumentNullException(nameof(directiveContext));
            }

            string schemaName   = directiveContext.FieldSelection.GetSchemaName();
            var    stitchingCtx = directiveContext.Service <IStitchingContext>();

            IQueryExecuter queryExecuter =
                stitchingCtx.GetQueryExecuter(schemaName);

            QueryRequest queryRequest = CreateQuery(directiveContext);

            return(queryExecuter.ExecuteAsync(
                       queryRequest,
                       directiveContext.RequestAborted));
        }
Exemple #16
0
        private void SetError(
            IDirectiveContext context,
            AuthorizeDirective directive,
            AuthState state)
        {
            switch (state)
            {
            case AuthState.NoDefaultPolicy:
                context.Result = context.Result = ErrorBuilder.New()
                                                  .SetMessage(AuthResources.AuthorizeMiddleware_NoDefaultPolicy)
                                                  .SetCode(ErrorCodes.Authentication.NoDefaultPolicy)
                                                  .SetPath(context.Path)
                                                  .AddLocation(context.Selection.SyntaxNode)
                                                  .Build();
                break;

            case AuthState.PolicyNotFound:
                context.Result = ErrorBuilder.New()
                                 .SetMessage(string.Format(
                                                 CultureInfo.InvariantCulture,
                                                 AuthResources.AuthorizeMiddleware_PolicyNotFound,
                                                 directive.Policy))
                                 .SetCode(ErrorCodes.Authentication.PolicyNotFound)
                                 .SetPath(context.Path)
                                 .AddLocation(context.Selection.SyntaxNode)
                                 .Build();
                break;

            default:
                context.Result = ErrorBuilder.New()
                                 .SetMessage(AuthResources.AuthorizeMiddleware_NotAuthorized)
                                 .SetCode(state == AuthState.NotAllowed
                            ? ErrorCodes.Authentication.NotAuthorized
                            : ErrorCodes.Authentication.NotAuthenticated)
                                 .SetPath(context.Path)
                                 .AddLocation(context.Selection.SyntaxNode)
                                 .Build();
                break;
            }
        }
Exemple #17
0
        // TODO : rework and finalize
        private static IReadOnlyDictionary <string, object> CreateVariables(
            IDirectiveContext directiveContext,
            IEnumerable <SelectionPathComponent> components)
        {
            var root = new Dictionary <string, object>();

            foreach (var component in components)
            {
                foreach (ArgumentNode argument in component.Arguments)
                {
                    if (argument.Value is ScopedVariableNode sv)
                    {
                        switch (sv.Scope.Value)
                        {
                        case "arguments":
                            root[sv.ToVariableName()] =
                                directiveContext.Argument <object>(
                                    sv.Name.Value);
                            break;

                        case "variables":
                            break;

                        case "properties":
                            root[sv.ToVariableName()] = directiveContext
                                                        .Parent <IDictionary <string, object> >()
                                                        [sv.Name.Value];
                            break;

                        default:
                            throw new NotSupportedException();
                        }
                    }
                }
            }

            return(root);
        }
Exemple #18
0
        private static async Task AuthorizeAsync(
            IDirectiveContext context,
            DirectiveDelegate next)
        {
#if !ASPNETCLASSIC
            IAuthorizationService authorizeService = context
                                                     .Service <IAuthorizationService>();
#endif
            ClaimsPrincipal principal = context
                                        .CustomProperty <ClaimsPrincipal>(nameof(ClaimsPrincipal));
            AuthorizeDirective directive = context.Directive
                                           .ToObject <AuthorizeDirective>();
            bool allowed = IsInRoles(principal, directive.Roles);

#if !ASPNETCLASSIC
            if (allowed && !string.IsNullOrEmpty(directive.Policy))
            {
                AuthorizationResult result = await authorizeService
                                             .AuthorizeAsync(principal, directive.Policy);

                allowed = result.Succeeded;
            }
#endif

            if (allowed)
            {
                await next(context);
            }
            else
            {
                context.Result = QueryError.CreateFieldError(
                    "The current user is not authorized to " +
                    "access this resource.",
                    context.Path,
                    context.FieldSelection);
            }
        }
 public Task InvokeAsync(IDirectiveContext context) =>
 Task.CompletedTask;
Exemple #20
0
 private static bool TryGetAuthenticatedPrincipal(
     IDirectiveContext context,
     out ClaimsPrincipal?principal)
Exemple #21
0
        private static async Task <bool> AuthorizeWithPolicyAsync(
            IDirectiveContext context,
            AuthorizeDirective directive,
            ClaimsPrincipal principal)
        {
            IServiceProvider      services         = context.Service <IServiceProvider>();
            IAuthorizationService authorizeService =
                services.GetService <IAuthorizationService>();
            IAuthorizationPolicyProvider policyProvider =
                services.GetService <IAuthorizationPolicyProvider>();

            if (authorizeService == null || policyProvider == null)
            {
                return(string.IsNullOrWhiteSpace(directive.Policy));
            }

            AuthorizationPolicy policy = null;

            if (directive.Roles.Count == 0 &&
                string.IsNullOrWhiteSpace(directive.Policy))
            {
                policy = await policyProvider.GetDefaultPolicyAsync()
                         .ConfigureAwait(false);

                if (policy == null)
                {
                    context.Result = context.Result = ErrorBuilder.New()
                                                      .SetMessage(
                        AuthResources.AuthorizeMiddleware_NoDefaultPolicy)
                                                      .SetCode(AuthErrorCodes.NoDefaultPolicy)
                                                      .SetPath(context.Path)
                                                      .AddLocation(context.FieldSelection)
                                                      .Build();
                }
            }

            else if (!string.IsNullOrWhiteSpace(directive.Policy))
            {
                policy = await policyProvider.GetPolicyAsync(directive.Policy)
                         .ConfigureAwait(false);

                if (policy == null)
                {
                    context.Result = ErrorBuilder.New()
                                     .SetMessage(string.Format(
                                                     CultureInfo.InvariantCulture,
                                                     AuthResources.AuthorizeMiddleware_PolicyNotFound,
                                                     directive.Policy))
                                     .SetCode(AuthErrorCodes.PolicyNotFound)
                                     .SetPath(context.Path)
                                     .AddLocation(context.FieldSelection)
                                     .Build();
                }
            }

            if (context.Result == null && policy != null)
            {
                AuthorizationResult result =
                    await authorizeService.AuthorizeAsync(
                        principal, context, policy)
                    .ConfigureAwait(false);

                return(result.Succeeded);
            }

            return(false);
        }
Exemple #22
0
 private bool IsErrorResult(IDirectiveContext context) =>
 context.Result is IError || context.Result is IEnumerable <IError>;