asp.net 코어 MVC 3.1 소스 코드 분석 (d)

AuthorizationApplicationModelProvider

이것은 잠재적으로 인증 및 권한 부여 필터를 추가한다

먼저 발견 특성은 컨트롤러와 액션에서 필터리스트에 추가 AuthorizeFilter, 컨트롤러와 액션에 IAuthorizeData 달성하고 IAuthorizeData AuthorizeFilter에 기초하여 필터를 만들

특히 별도의 권한 논리 뒤에 말하기

내부  클래스 AuthorizationApplicationModelProvider : IApplicationModelProvider 
    { 
        개인  읽기 전용 MvcOptions의 _mvcOptions;
        개인  읽기 전용 IAuthorizationPolicyProvider _policyProvider; 

        공개 AuthorizationApplicationModelProvider ( 
            IAuthorizationPolicyProvider policyProvider, 
            iOptions에 <MvcOptions> mvcOptions) 
        { 
            _policyProvider = policyProvider; 
            _mvcOptions = mvcOptions.Value; 
        } 

        공공  INT의 주문 => - 1000 +(10) ; 

        공공  무효 OnProvidersExecuted (ApplicationModelProviderContext 컨텍스트) 
        { 
            //이 의도적으로 비 웁니다. 
        } 

        공공  공극 OnProvidersExecuting (ApplicationModelProviderContext 컨텍스트) 
        { 
            경우 (상황 == NULL의 ) 
            { 
                던져  새로운 경우 ArgumentNullException을 (nameof (컨텍스트)); 
            } 

            경우 (_mvcOptions.EnableEndpointRouting는) 
            { 
                // 엔드 포인트 라우팅을 사용하는 경우, AuthorizationMiddleware이 작업을 수행 인증 필터는 그렇지 않으면 수행 할 것이다.
                //따라서 우리는 필터로 변환 권한 속성에 필요하지 않습니다. 
                반환 ; 
            } 

            의 foreach ( VAR의 controllerModel context.Result.Controllers) 
            { 
                VAR controllerModelAuthData = controllerModel.Attributes.OfType <IAuthorizeData> () .ToArray ();
                경우 (controllerModelAuthData.Length> 0 ) 
                { 
                    controllerModel.Filters.Add (GetFilter (_policyProvider, controllerModelAuthData)); 
                } 
                foreach는 ( var에 속성 controllerModel.Attributes.OfType <IAllowAnonymous> ()) 
                { 
                    controllerModel.Filters.Add ( 새로운 AllowAnonymousFilter ()); 
                } 

                의 foreach ( VAR의 actionModel controllerModel.Actions) 
                { 
                    VAR actionModelAuthData = actionModel.Attributes.OfType <IAuthorizeData> () .ToArray ();
                    경우 (actionModelAuthData.Length> 0 ) 
                    { 
                        actionModel.Filters.Add (GetFilter (_policyProvider, actionModelAuthData)); 
                    } 

                    foreach는( VAR의 특성  actionModel.Attributes.OfType <IAllowAnonymous> ()) 
                    { 
                        actionModel.Filters.Add ( 새로운 AllowAnonymousFilter ()); 
                    } 
                } 
            } 
        } 

        공공  정적 AuthorizeFilter GetFilter (IAuthorizationPolicyProvider policyProvider,는 IEnumerable <IAuthorizeData> authData) 
        { 
            // 주어진 입력에 대한 동일한 정책을 그래서 한 번만 할 것입니다 기본 정책 공급자입니다.
            // 이 항상 동 기적으로 실행됩니다. 
            만약(policyProvider.GetType () == 대해서 typeof (DefaultAuthorizationPolicyProvider)) 
            { 
                VAR의 정책 = AuthorizationPolicy.CombineAsync (policyProvider, authData) .GetAwaiter () getResult를 ().;
                반환  새로운 AuthorizeFilter (정책을); 
            } 
            다른 
            { 
                반환  AuthorizeFilter (policyProvider, authData을); 
            } 
        } 
    }

 

ApiBehaviorApplicationModelProvider

내부  클래스 ApiBehaviorApplicationModelProvider : IApplicationModelProvider 
    { 
        공개 ApiBehaviorApplicationModelProvider ( 
            iOptions에 <ApiBehaviorOptions> apiBehaviorOptions, 
            IModelMetadataProvider modelMetadataProvider, 
            IClientErrorFactory clientErrorFactory, 
            ILoggerFactory loggerFactory) 
        { 
            var에 옵션 = apiBehaviorOptions.Value; 

            ActionModelConventions = 새로운 목록 <IActionModelConvention> () 
            { 
                새로운 ApiVisibilityConvention () 
            }; 

            만약(!의 options.SuppressMapClientErrors) 
            { 
                ActionModelConventions.Add ( ClientErrorResultFilterConvention ()); 
            } 

            경우 (! options.SuppressModelStateInvalidFilter) 
            { 
                ActionModelConventions.Add ( InvalidModelStateFilterConvention ()); 
            } 

            경우 (!의 options.SuppressConsumesConstraintForFormFileParameters) 
            { 
                ActionModelConventions.Add ( ConsumesConstraintForFormFileParameterConvention ()); 
            } 

            VARdefaultErrorType = options.SuppressMapClientErrors? 대해서 typeof ( 공극 ) 대해서 typeof (ProblemDetails);
            VAR defaultErrorTypeAttribute는 = 새로운 ProducesErrorResponseTypeAttribute (defaultErrorType를); 
            ActionModelConventions.Add ( ApiConventionApplicationModelConvention (defaultErrorTypeAttribute)); 

            만약 (!의 options.SuppressInferBindingSourcesForParameters) 
            { 
                ActionModelConventions.Add ( InferParameterBindingInfoConvention (modelMetadataProvider)); 
            } 
        } 

        ///  <말> 
        ///주문이 실행 설정 후 <CREF = "DefaultApplicationModelProvider"을 참조하십시오 /> 및 다른 사용자가 허용
         ///  <CREF = "IApplicationModelProvider"을 참조하십시오 /> 실행 라우팅하는 구성.
        ///  </ 비고> 
        공공  INT의 주문 => - 1000 + 100 ; 

        공개 목록 <IActionModelConvention> ActionModelConventions { 얻을 ; } 

        공공  공극 OnProvidersExecuted (ApplicationModelProviderContext 컨텍스트) 
        { 
        } 

        공공  공극 OnProvidersExecuting (ApplicationModelProviderContext 컨텍스트) 
        {
            foreach는 ( var에 컨트롤러 context.Result.Controllers는) 
            { 
                경우 (! IsApiController (컨트롤러)) 
                { 
                    계속 ; 
                } 

                foreach는 ( var에 행동 controller.Actions) 
                { 
                    // ApiController이 올바르게 설정되어 있는지 확인 
                    EnsureActionIsAttributeRouted (동작); 

                    foreach는 ( var에 규칙 ActionModelConventions) 
                    {  
                        convention.Apply (행동);
                    } 
                } 
            } 
        } 

        개인  정적  무효 EnsureActionIsAttributeRouted (ActionModel actionModel) 
        { 
            경우 (! IsAttributeRouted (actionModel.Controller.Selectors) && 
                ! IsAttributeRouted (actionModel.Selectors가)) 
            { 
                // ApiControllerAttribute의 주석 컨트롤러와 라우팅 속성을 필요 
                var에 메시지 = (Resources.FormatApiController_AttributeRouteRequired 
                     actionModel.DisplayName, 
                    nameof (ApiControllerAttribute)); 
                던져  새로운 InvalidOperationException이 (메시지);
            }

             부울을IsAttributeRouted (IList의 <SelectorModel> selectorModel) 
            { 
                위해은 ( VAR은 난 = 0 ; I <selectorModel.Count; I ++ ) 
                { 
                    경우 (selectorModel [I] = .AttributeRouteModel! ) 
                    { 
                        반환  사실은 ; 
                    } 
                } 

                반환  거짓 ; 
            } 
        } 

        개인  정적  부울 IsApiController (ControllerModel 컨트롤러) 
        { 
            경우 (controller.Attributes.OfType <IApiBehaviorMetadata> () .ANY ()) 
            { 
                반환  ; 
            } 

            VAR controllerAssembly = controller.ControllerType.Assembly;
            VAR의 assemblyAttributes = controllerAssembly.GetCustomAttributes ();
             assemblyAttributes.OfType <IApiBehaviorMetadata> () .ANY (); 
        } 
    }

이 클래스는 측면의 webapi을 포함

 

 필터 및 관련 속성의 ActionModel 세트

 

추천

출처www.cnblogs.com/lanpingwang/p/12642751.html