토큰 인증 및 쿠키


141

쿠키를 사용한 토큰 인증과 인증의 차이점은 무엇입니까?

Ember Auth Rails 데모 를 구현하려고 하는데, "왜 토큰 인증?"질문 에 대한 Ember Auth FAQ 에 설명 된대로 토큰 인증을 사용해야 하는 이유를 이해하지 못합니다.


4
SPA 요청에 사용하기 위해 토큰을 모바일 앱에 제공하고 나중에 사용하기 위해 변수로 저장하거나 나중에 사용하거나 브라우저에서 JavaScript를 통해 저장할 수 있습니다. 쿠키는 일반적으로 브라우저에서 브라우저에 사용됩니다.
Tino Mclaren

2
2016 년에 작성된 기사 auth0.com/blog/cookies-vs-tokens-definitive-guide를 참조하십시오 .
Michael Freidgeim

답변:


34

일반적인 웹 앱은 요청 / 응답 특성으로 인해 대부분 상태 비 저장 입니다. HTTP 프로토콜은 상태 비 저장 프로토콜 의 가장 좋은 예입니다 . 그러나 대부분의 웹앱은 상태 를 유지하기 위해 서버와 클라이언트 사이 의 상태 를 유지하기 위해 서버가 모든 응답을 클라이언트로 다시 보낼 수 있도록 쿠키가 사용됩니다. 이는 클라이언트로부터의 다음 요청에이 쿠키가 포함되어 서버에서 인식됨을 의미합니다. 이런 식으로 서버는 상태 비 저장 클라이언트 와의 세션 을 유지하면서 대부분 앱 상태 에 대한 모든 것을 알고 있지만 서버에 저장됩니다. 이 시나리오에서 클라이언트는 즉시 보유하지 않습니다state . 이것은 Ember.js의 작동 방식이 아닙니다 .

Ember.js에서는 상황이 다릅니다. Ember.js는 서버에서 상태 데이터를 요구할 필요없이 해당 상태 에 대해 모든 순간에 알기 때문에 클라이언트에서 실제로 상태 를 유지하므로 프로그래머의 작업이 쉬워집니다 .

그러나 클라이언트에서 상태 를 유지하면 상태 비 저장 상황 에서는 표시되지 않는 동시성 문제가 발생할 수도 있습니다. 그러나 Ember.js는이 문제를 처리하며 특히 ember-data는이를 염두에두고 작성됩니다. 결론적으로 Ember.js는 상태 저장 클라이언트를 위해 설계된 프레임 워크입니다 .

Ember.js는 세션 , 상태 및 해당 쿠키가 서버에서 거의 완전히 처리 되는 일반적인 상태 비 저장 웹 앱 처럼 작동하지 않습니다 . Ember.js는 자바 스크립트 (클라이언트의 메모리에서, 다른 프레임 워크와 같은 DOM에서는 아님) 에서 상태를 완전히 유지 하며 세션을 관리하기 위해 서버가 필요하지 않습니다. 이로 인해 Ember.js는 앱이 오프라인 모드에있는 경우와 같이 여러 상황에서 더욱 다양합니다.

보안상의 이유로 인증 을 받기 위해 요청을 할 때마다 서버에 어떤 종류의 토큰 이나 고유 키 를 보내야 합니다 . 이렇게하면 서버가 송신 토큰 (서버에서 처음 발행 한)을 조회 할 수 있습니다. 클라이언트에게 응답을 다시 보내기 전에 유효한지 확인하십시오.

필자의 의견으로는 Ember Auth FAQ에 명시된 쿠키 대신 인증 토큰을 사용하는 주된 이유 는 주로 Ember.js 프레임 워크의 특성과 스테이트 풀 웹 앱 패러다임 에 더 적합하기 때문 입니다. 따라서 쿠키 메커니즘은 Ember.js 앱을 빌드 할 때 가장 좋은 방법은 아닙니다.

내 답변이 귀하의 질문에 더 많은 의미를 부여하기를 바랍니다.


84
나는 왜 토큰보다 쿠키가 더 나은지 다른지를 이해하지 못합니다. 어떤 방법으로 유효한 세션을 식별하는 API 서버로 무언가를 보냅니다. 단일 도메인에서 모든 것을 실행한다고 가정하고 (회원과 api가 다른 서버에 있더라도이를 달성하기 위해해야 ​​할 모든 것은 cdn 뒤에서 실행되며, 어쨌든해야합니다) 토큰이 제공하는 이점은 무엇입니까? 추가 설정 작업 및 타이밍 공격에 대한 추가 취약성?
Michael Johnston

46
마이클 존스턴과 동의. 이 답변은 토큰 기반 인증이 무엇인지 설명하지만 실제로 질문에 대답하지는 않았습니다. 내가 볼 수있는 가장 가까운 관련 정보는 "ember.js 프레임 워크의 특성으로 인해 상태 전체 웹 응용 프로그램 패러다임에 더 적합하기 때문에" 마지막 비트에 있지만 전혀 답이 아닙니다. 나도 같은 질문이 있습니다.
Daniel

5
나는 경찰 아웃의 비트입니다 사실, 내가 "는 타다 남은 방법"그 모든 느낌이 ... 여기에 코멘트 모두 동의
Grapho

3
솔직히 Statefulness는 쿠키와 다른 수단을 통해 제출 된 토큰과 관련하여 붉은 청어라고 생각합니다. 나는 그것이 사용자 증거의 개념을 다른 사용자 프로파일 정보와 혼동한다고 생각합니다. 토큰을 제출하기 위해 HTTP 헤더 또는 다른 채널과 동일한 쿠키를 사용할 수 있습니다. 쿠키의 단일 출처 정책과 관련된 문제를 해결하거나 백엔드의 기본 클라이언트에서 쿠키 컨테이너를 구현해야하는 부담을 덜어주는 것이 차이점이라고 생각합니다.
Michael Lang

15
ember.js에 질문 한 내용에 초점을 맞추지 마십시오. 무례하게되어 죄송합니다.
Vick_Pk

337

Http는 stateless입니다. 귀하에게 권한을 부여하려면 서버로 보내는 모든 단일 요청에 "서명"해야합니다.

토큰 인증

  • 서버에 대한 요청은 "토큰"으로 서명됩니다. 일반적으로 특정 http 헤더를 설정하는 것을 의미하지만 http 요청 (POST 본문 등)의 어느 부분으로나 보낼 수 있습니다.

  • 장점 :

    • 승인하려는 요청 만 승인 할 수 있습니다. (쿠키-인증 쿠키조차도 매 요청마다 전송됩니다.)
    • XSRF에 대한 면역 (XSRF의 간단한 예-이메일로 링크를 보내드립니다. <img src="http://bank.com?withdraw=1000&to=myself" />쿠키 인증을 통해 bank.com에 로그인 한 경우 bank.com에 XSRF의 수단이 없습니다. 브라우저에서 해당 URL에 대한 승인 된 GET 요청을 트리거한다는 사실만으로 계정에서 돈을 인출 할 수 있습니다.) 쿠키 기반 인증으로 수행 할 수있는 위조 방지 조치가 있지만이를 구현해야합니다.
    • 쿠키는 단일 도메인에 바인딩됩니다. 도메인 foo.com에서 생성 된 쿠키는 도메인 bar.com에서 읽을 수 없지만 원하는 도메인으로 토큰을 보낼 수 있습니다. 이 기능은 인증이 필요한 여러 서비스를 사용하는 단일 페이지 응용 프로그램에 특히 유용합니다. 따라서 myapp.com 도메인에 myservice1.com 및 myservice2.com에 대한 승인 된 클라이언트 측 요청을 수행 할 수있는 웹앱을 가질 수 있습니다.
  • 단점 :
    • 어딘가에 토큰을 저장해야합니다. 쿠키는 "즉시"저장됩니다. 기억해야 할 위치는 localStorage (con : 브라우저 창을 닫은 후에도 토큰이 유지됨), sessionStorage (pro : 브라우저 창을 닫은 후에는 토큰이 삭제됨, con : 새 탭에서 링크를 열면 해당 탭이 렌더링 됨) 익명) 및 쿠키 (Pro : 브라우저 창을 닫으면 토큰이 삭제됩니다. 세션 쿠키를 사용하는 경우 새 탭에서 링크를 열 때 인증되며 인증을 무시하므로 XSRF에 영향을받지 않습니다. 인증 쿠키, 당신은 단지 토큰 저장소로 사용하고 있습니다. 장소 : 쿠키는 모든 단일 요청에 대해 전송됩니다.이 쿠키가 https로 표시되지 않은 경우 중간 공격에 노출 될 수 있습니다.)
    • 토큰 기반 인증에 대해 XSS 공격을 수행하는 것이 약간 더 쉽습니다 (예 : 사이트에서 삽입 된 스크립트를 실행할 수있는 경우 토큰을 도용 할 수 있지만 쿠키 기반 인증은 은색 총알이 아닙니다. http-only는 클라이언트가 읽을 수 없으며 클라이언트는 여전히 권한 쿠키를 자동으로 포함하도록 귀하를 대신하여 요청할 수 있습니다.)
    • 인증 된 사용자에게만 적합한 파일 다운로드 요청에는 File API를 사용해야합니다. 쿠키 기반 인증을 위해 동일한 요청이 즉시 수행됩니다.

쿠키 인증

  • 서버에 대한 요청은 항상 권한 부여 쿠키로 로그인됩니다.
  • 장점 :
    • 쿠키는 "http-only"로 표시되어 클라이언트 측에서 읽을 수 없게합니다. 이것은 XSS 공격 보호에 더 좋습니다.
    • 기본 제공-클라이언트 측에서 코드를 구현할 필요가 없습니다.
  • 단점 :
    • 단일 도메인에 바인딩됩니다. (따라서 여러 서비스를 요청하는 단일 페이지 응용 프로그램이 있으면 리버스 프록시와 같은 미친 일을 끝낼 수 있습니다.)
    • XSRF에 취약합니다. 사이트 간 요청 위조로부터 사이트를 보호하려면 추가 조치를 구현해야합니다.
    • 모든 단일 요청에 대해 전송됩니다 (인증이 필요없는 요청에 대해서도).

전반적으로 토큰이 더 나은 유연성을 제공한다고 말하고 싶습니다 (단일 도메인에 바인딩되어 있지 않기 때문에). 단점은 스스로 코딩을해야한다는 것입니다.


56
이 답변은 정답보다 정식 답변에 훨씬 가깝습니다.
xlecoustillier 2016 년

3
감사합니다 @ ondrej-svejdar. 그것은 가장 좋은 대답입니다! 나는 단지 "일부 코딩"을 주장 할 뿐이다. 거의 모든 언어에 사용할 수있는 라이브러리가 많이 있습니다. 따라서 JWT 구현의 메커니즘을 실제로 알고 싶지 않으면 처음부터 시작할 필요가 없습니다.
FullStackForger

2
Are send out for every single request모든 요청에 ​​대한 토큰도 발송됩니다
Eugen Konkov

10
@EugenKonkov 번호 필연적으로. 헤더를 추가하는 경우에만. 쿠키는 원하거나 원하지 않는 경우 브라우저에서 전송됩니다
Royi Namir

2
@Zack-중요합니다. 쿠키 문제는 브라우저에서 자동으로 요청하기 위해 추가됩니다. 반면에 토큰은 Javascript에 의해 XHR 요청에 추가됩니다. evildomain.com이 mysite.com (btw. 토큰을 저장할 장소로 로컬 스토리지를 권장하지 않음) 또는 램 (토큰을 포함하는 자바 스크립트 변수를 의미한다고 가정)에 대한 로컬 스토리지에 액세스하는 것은 불가능합니다. 변수는 다른 브라우저 창에서 샌드 박스로 표시됩니다.
Ondrej Svejdar

34
  • 토큰은 어딘가에 저장해야합니다 (로컬 / 세션 스토리지 또는 쿠키)

  • 토큰은 쿠키처럼 만료 될 수 있지만 더 많은 제어 권한이 있습니다

  • 로컬 / 세션 저장소가 도메인간에 작동하지 않습니다. 마커 쿠키를 사용하십시오.

  • 각 CORS 요청에 따라 프리 플라이트 요청이 전송됩니다.

  • 무언가를 스트리밍해야 할 경우 토큰을 사용하여 서명 된 요청을 받으십시오.

  • XSRF보다 XSS를 다루는 것이 더 쉽다

  • 모든 요청에 ​​따라 토큰이 전송되고 크기를 조심하십시오.

  • 기밀 정보를 저장하는 경우 토큰을 암호화하십시오.

  • JSON 웹 토큰은 OAuth에서 사용될 수 있습니다

  • 토큰은 은색 총알이 아닙니다. 인증 사용 사례를 신중하게 고려하십시오.

http://blog.auth0.com/2014/01/27/ten-things-you-should-know-about-tokens-and-cookies/

http://blog.auth0.com/2014/01/07/angularjs-authentication-with-cookies-vs-token/


14
귀하의 포인트가 쿠키 또는 토큰에 대한 것인지 확실하지 않습니다.
Pureferret

6
쿠키보다 쿠키에 대한 통제력이 높은 이유를 이해하지 못합니다.
Aaron

@onsmith 내가 이해하는 것에는 여기에 하나 이상의 글 머리 기호가 있습니다. 첫째, 쿠키는 모든 요청과 함께 전송됩니다. 토큰 전송은 자바 스크립트 코드에 의해 트리거됩니다. 자동으로 전송되지 않습니다. 또한, rfc 섹션 (4) 에 따르면, JWT는 당사자들 사이에 보안 클레임을 전달하는데 사용되는 컨테이너로서 설계되는 것처럼 보인다. 보다 세밀한 제어 기능을 제공 할뿐만 아니라 사용자를 대신하여 사용할 수있는 권한 세트로 타사에 대한 인증 토큰을 생성 할 수 있습니다.
FullStackForger

18

Google 직원의 경우 :

  • 상태 저장 메커니즘상태 저장 을 혼합하지 마십시오

전략

  • 상태 저장 = 서버 측에 인증 정보 저장, 이것은 전통적인 방법입니다
  • Stateless = 무결성을 보장하기 위해 서명과 함께 클라이언트 측에 인증 정보 저장

메커니즘

  • 쿠키 = 브라우저에 의한 특별한 처리 (접근, 저장, 만료, 보안, 자동 전송)가있는 특수 헤더
  • Custom Headers = 예 : Authorization특별한 대우가없는 헤더 일 뿐이므로 고객은 전송의 모든 측면을 관리해야합니다.
  • 기타 . 다른 전송 메커니즘이 사용될 수 있습니다. 예를 들어 쿼리 문자열은 한동안 인증 ID를 전송하도록 선택되었지만 보안 상 이유로 포기되었습니다.

전략적 비교

  • "상태 저장 권한"은 서버가 서버에 사용자 권한 정보를 저장하고 유지하여 권한을 응용 프로그램 상태의 일부로 만드는 것을 의미합니다.
  • 즉, 클라이언트는 "인증 ID"만 유지하면되고 서버는 데이터베이스에서 인증 정보를 읽을 수 있습니다.
  • 이는 서버가 활성 인증 풀 (로그인 한 사용자) 풀을 유지하고 모든 요청에 ​​대해이 정보를 쿼리 함을 의미합니다.
  • "상태 비 저장 인증"은 서버가 사용자 인증 정보를 저장 및 유지 관리하지 않으며 단순히 로그인 한 사용자를 알지 못하며 인증 정보를 생성하기 위해 클라이언트에 의존 함을 의미합니다.
  • 고객은 본인 (사용자 ID)과 같은 완전한 인증 정보 및 권한, 만료 시간 등을 저장합니다. 이는 인증 ID 이상의 것이기 때문에 새로운 이름 토큰 이 부여됩니다.
  • 분명히 클라이언트를 신뢰할 수 없으므로 인증 데이터는에서 생성 된 서명과 함께 저장됩니다 hash(data + secret key). 여기서 비밀 키는 서버에만 알려 지므로 토큰 데이터의 무결성을 확인할 수 있습니다
  • 토큰 메커니즘은 무결성을 보장하지만 기밀성을 보장하지는 않지만 클라이언트는이를 구현해야합니다.
  • 이는 또한 모든 요청 클라이언트가 완전한 토큰을 제출해야하므로 추가 대역폭이 발생 함을 의미합니다.

메커니즘 비교

  • "쿠키"는 헤더 일 뿐이지 만 브라우저에 미리로드 된 작업이 있습니다.
  • 쿠키는 서버에 의해 설정되고 클라이언트에 의해 자동 저장 될 수 있으며 동일한 도메인에 대해 자동 전송됩니다
  • 쿠키는 httpOnly클라이언트 JavaScript 액세스를 막는 것으로 표시 될 수 있습니다
  • 브라우저 이외의 플랫폼 (예 : 모바일)에서는 사전로드 된 작업을 사용할 수 없으므로 추가 노력이 필요할 수 있습니다.
  • "사용자 정의 헤더"는 사전로드 된 작업이없는 사용자 정의 헤더입니다.
  • 고객은 각 요청에 대해 사용자 정의 헤더 섹션을 수신, 저장, 보안, 제출 및 업데이트해야합니다. 이는 간단한 악성 URL 포함을 방지하는 데 도움이 될 수 있습니다

요약하면

  • 마법이 없으며 인증 상태는 서버 또는 클라이언트의 어딘가에 저장해야합니다
  • 쿠키 또는 다른 사용자 정의 헤더를 사용하여 상태 저장 / 상태 비 저장을 구현할 수 있습니다.
  • 사람들이 그 것들에 대해 이야기 할 때 기본 사고 방식은 주로 stateless = token + custom header, stateful = auth ID + cookie; 이것 만이 가능한 옵션은 아닙니다
  • 장단점이 있지만 암호화 된 토큰의 경우 민감한 정보를 저장해서는 안됩니다

링크


1
대단히 감사합니다. 질문에 대답하고 다른 답변에서 생성 된 모든 혼란은 갑자기 상태 저장에 대해 이야기합니다.
MDave

아주 아주 좋은. 자세한 내용을 제공하고 방법과 이유를 더 잘 설명합니다.
colinwong

8

나는 여기에 약간의 혼란이 있다고 생각합니다. 쿠키 기반 인증과 HTML5 Web Storage로 가능한 기능의 중요한 차이점은 브라우저가 쿠키를 설정 한 도메인에서 리소스를 요청할 때마다 쿠키 데이터를 보내도록 브라우저가 구축되어 있다는 것입니다. 쿠키를 끄지 않으면이를 막을 수 없습니다. 페이지의 코드가 보내지 않는 한 브라우저 는 Web Storage에서 데이터를 보내지 않습니다 . 그리고 페이지는 다른 페이지에 저장된 데이터가 아니라 저장된 데이터에만 액세스 할 수 있습니다.

따라서 사용자는 Google 또는 Facebook에서 쿠키 데이터를 사용하여 쿠키를 끌 수있는 방법에 대해 걱정했습니다. 그러나 광고주가 웹 스토리지를 사용하는 방법을 파악할 때까지 웹 스토리지를 해제 할 이유가 적습니다.

따라서 이는 쿠키 기반과 토큰 기반의 차이점이며 후자는 웹 스토리지를 사용합니다.


5

토큰 기반 인증은 상태 비 저장이므로 서버는 세션에 사용자 정보를 저장할 필요가 없습니다. 이를 통해 사용자가 어디에 로그인했는지 걱정하지 않고도 응용 프로그램을 확장 할 수 있습니다. 쿠키 기반 웹 서버 프레임 워크 선호도는 있지만 토큰 기반 문제는 아닙니다. 따라서 동일한 토큰을 사용하여 로그인 한 도메인 이외의 도메인에서 다른 uid / pwd 인증을 피하는 보안 리소스를 가져올 수 있습니다.

여기 아주 좋은 기사 :

http://www.toptal.com/web/cookie-free-authentication-with-json-web-tokens-an-example-in-laravel-and-angularjs


3

다음과 같은 경우 토큰 사용

연합이 바람직합니다. 예를 들어, 하나의 제공자 (토큰 분배기)를 토큰 발행자로 사용하고 API 서버를 토큰 유효성 검증기로 사용하려고합니다. 앱은 토큰 Dispensor를 인증하고 토큰을받은 다음 해당 토큰을 API 서버에 제시하여 확인할 수 있습니다. (Google 로그인 또는 Paypal 또는 Salesforce.com 등에서도 동일하게 작동)

비동기가 필요합니다. 예를 들어, 클라이언트가 요청을 보낸 다음 해당 요청을 어딘가에 저장하여 별도의 시스템 "나중"에 의해 작동되기를 원합니다. 이 별도의 시스템은 클라이언트에 대한 동기 연결을 갖지 않으며 중앙 토큰 약국에 직접 연결되지 않을 수 있습니다. 비동기 처리 시스템이 JWT를 읽어 작업 항목이 나중에 수행 될 수 있는지 여부를 판별 할 수 있습니다. 이것은 어떤 방식으로 위의 연합 아이디어와 관련이 있습니다. JWT가 만료되었습니다. 작업 항목을 보유한 큐가 JWT의 수명 내에 처리되지 않으면 클레임을 더 이상 신뢰하지 않아야합니다.

Cient Signed 요청이 필요합니다. 여기서 요청은 개인 키를 사용하여 클라이언트에 의해 서명되며 서버는 이미 등록 된 클라이언트의 공개 키를 사용하여 유효성을 검사합니다.


1

주요 차이점 중 하나는 쿠키는 동일 출처 정책의 적용을받는 반면 토큰은 그렇지 않다는 것입니다. 이것은 모든 종류의 다운 스트림 효과를 만듭니다.

쿠키는 호스트가 특정 호스트와 만주고 받기 때문에 해당 호스트는 사용자 인증에 대한 부담을 부담해야하며 사용자는 확인하기 위해 해당 호스트와 보안 데이터가있는 계정을 만들어야합니다.

반면에 토큰은 발행되며 동일한 원산지 정책이 적용되지 않습니다. 발급자는 말 그대로 누구나 가능하며 어떤 발급자를 신뢰할 것인지 결정하는 것은 호스트의 몫입니다. Google 및 Facebook과 같은 발급자는 일반적으로 신뢰할 수 있으므로 호스트는 사용자 인증의 부담 (모든 사용자 보안 데이터 저장 포함)을 다른 당사자에게 이전 할 수 있으며 사용자는 특정 발급자에 따라 개인 데이터를 통합 할 수 있으며 상호 작용하는 각 호스트에 대해 서로 다른 암호 모음.

이를 통해 사용자 경험의 전반적인 마찰을 줄이는 싱글 사인온 시나리오가 가능합니다. 이론적으로, 전문 아이덴티티 공급자가 모든 웹 사이트에서 자체적으로 구운 절반의 인증 시스템을 회전시키는 대신 인증 서비스를 제공함에 따라 웹의 보안이 더욱 강화됩니다. 그리고 이러한 제공 업체는 매우 기본적인 리소스 트렌드에 대한 안전한 웹 리소스를 제로로 제공하는 비용을 발생시킵니다.

따라서 일반적으로 토큰은 인증 제공과 관련된 마찰과 비용을 줄이고 보안 웹의 다양한 측면의 부담을 보안 시스템을 구현하고 유지 관리 할 수있는 중앙 집중식 당사자로 이동시킵니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.