source

AngularJS Web API 위조 방지토큰 CSRF

ittop 2023. 3. 28. 22:36
반응형

AngularJS Web API 위조 방지토큰 CSRF

나는 Angular를 가지고 있다.ASP가 호스트하는 JS Single Page Application(SPA; 싱글 페이지응용 프로그램).NET MVC 어플리케이션
백엔드는 ASP.NET Web API

CSRF 공격으로부터 데이터를 보호하고,AntiForgeryTokenASP에 있습니다.NET MVC 파트를 AngularJS에 전달하고 Web Api에 의해 검증됩니다.AntiForgeryToken후속 Angular에서 수신됨JS

CSRF(Cross-Site Request Formature)는 최종 사용자가 현재 인증되어 있는 웹 응용 프로그램에서 원하지 않는 액션을 실행하도록 하는 공격입니다.CSRF 공격은 공격자가 위조 요구에 대한 응답을 확인할 방법이 없기 때문에 데이터 도난이 아닌 상태 변경 요구를 대상으로 합니다.공격자는 소셜 엔지니어링(전자 메일 또는 채팅으로 링크 보내기 등)의 약간의 도움을 받아 웹 응용 프로그램 사용자를 속여 공격자가 선택한 작업을 실행할 수 있습니다.피해자가 일반 사용자인 경우 CSRF 공격이 성공하면 사용자는 자금 이체, 이메일 주소 변경 등의 상태 변경 요청을 수행해야 할 수 있습니다.피해자가 관리 계정일 경우 CSRF는 웹 애플리케이션 전체를 손상시킬 수 있습니다.
- 웹 어플리케이션 보안 프로젝트(OWASP) 열기

ASP에 추가합니다.Angular를 지원하는 NET MVCViewJS SPA라고 합시다.Views\Home\Index.cshtml, 를 생성하는HTML 도우미AntiForgeryToken.

@Html.AntiForgeryToken();

각도 설정JS가 상기 생성에 합격AntiForgeryToken[ Request Header ](요구 헤더)로 지정합니다.

angular.module('app')
.run(function ($http) {
    $http.defaults.headers.common['X-XSRF-Token'] =
        angular.element('input[name="__RequestVerificationToken"]').attr('value');
});

GET 이외의 모든 요청을 검증하기 위한 커스텀 Web API 필터를 만듭니다(PUT,PATCH,POST,DELETE).

여기에서는, 모든 유저가GET요청은 안전하고 보호할 필요가 없습니다.
그렇지 않은 경우,if (actionContext.Request.Method.Method != "GET")제외.

using System;
using System.Linq;
using System.Net.Http;
using System.Web.Helpers;
using System.Web.Http.Filters;

namespace Care.Web.Filters
{
    public sealed class WebApiValidateAntiForgeryTokenAttribute : ActionFilterAttribute
    {
        public override void OnActionExecuting(
            System.Web.Http.Controllers.HttpActionContext actionContext)
        {
            if (actionContext == null)
            {
                throw new ArgumentNullException("actionContext");
            }

            if (actionContext.Request.Method.Method != "GET")
            {
                var headers = actionContext.Request.Headers;
                var tokenCookie = headers
                    .GetCookies()
                    .Select(c => c[AntiForgeryConfig.CookieName])
                    .FirstOrDefault();

                var tokenHeader = string.Empty;
                if (headers.Contains("X-XSRF-Token"))
                {
                    tokenHeader = headers.GetValues("X-XSRF-Token").FirstOrDefault();
                }

                AntiForgery.Validate(
                    tokenCookie != null ? tokenCookie.Value : null, tokenHeader);
            }

            base.OnActionExecuting(actionContext);
        }
    }
}

새로 생성된 필터를 글로벌 필터로 등록합니다.Global.asax.cs.

    private static void RegisterWebApiFilters(HttpFilterCollection filters)
    {
        filters.Add(new WebApiValidateAntiForgeryTokenAttribute());
    }

또는 이 필터를 글로벌하게 추가하지 않으려면 다음과 같은 특정 웹 API 작업에만 추가할 수 있습니다.

[WebApiValidateAntiForgeryToken]

물론, 이 방법은 필요한 작업에 속성을 적용하는 것을 잊어버릴 가능성이 있기 때문에 보안성이 떨어집니다.

또, 다음의 기능이 있는 것에 주의해 주세요.Microsoft.AspNet.WebApi.Core접근하기 위한 패키지System.Web.Http네임스페이스.NuGet을 통해 설치할 수 있습니다.Install-Package Microsoft.AspNet.WebApi.Core.

이 게시물은 이 블로그 게시물에서 많은 영감을 받았습니다.

__RequestVerificationToken form form to 。

 var formData = new FormData();
    formData.append("__RequestVerificationToken", token);
    formData.append("UserName", $scope.kullaniciAdi);
    formData.append("Password", $scope.sifre);

    $http({
        method: 'POST',
        url: '/Login/Login',
        data: formData,
        transformRequest: angular.identity, 
        headers: { 'Content-Type': undefined }

    }).then(function successCallback(response) {
      


    }, function errorCallback(response) {

    });

ASP에 추가합니다.NET MVC 뷰

<Form ng-submit="SubmitForm(FormDataObject)">
        @Html.AntiForgeryToken()
        .....
        ...
        .
</Form>

그런 다음 AngularJs 컨트롤러에서

angular.module('myApp', []).controller('myController', function ($scope, $http, $httpParamSerializerJQLike) {

        $scope.antiForgeryToken = angular.element('input[name="__RequestVerificationToken"]').attr('value');

        $scope.SubmitForm = function (formData) {
            var dataRequest = {
                __RequestVerificationToken: $scope.antiForgeryToken,
                formData: angular.toJson(formData)
            };

            $http.post("/url/...", $httpParamSerializerJQLike(dataRequest), { headers: { 'Content-Type': 'application/x-www-form-urlencoded; charset=UTF-8' } }).then(function (response) {
                $scope.result = JSON.parse(response.data);
            });
        }
    });

$httpParamSerializer를 선택하는 이유JQLike(데이터 요구)이러한 AngularJs가 없으면 다음과 같이 데이터를 직렬화할 수 있습니다.

{__RequestVerificationToken: blablabla, formData: blablabla}

및 ASP.NET MVC 컨트롤러가 필요한 위조 방지 폼 필드 '_RequestVerification'을 슬로우합니다.토큰"이 존재하지 않습니다.

단, $httpParamSerializer를 사용하여 요청 데이터를 시리얼화하면JQLike(dataRequest), AngularJs는 다음과 같이 직렬화됩니다.

__RequestVerificationToken: blablabla
formData: blablabla

및 ASP.NET MVC 컨트롤러는 토큰을 오류 없이 인식할 수 있습니다.

언급URL : https://stackoverflow.com/questions/32460196/angularjs-web-api-antiforgerytoken-csrf

반응형