인증 : JWT 사용 vs 세션


122

인증과 같은 상황에서 세션보다 JWT를 사용하면 어떤 이점이 있습니까?

독립 실행 형 접근 방식으로 사용됩니까 아니면 세션에서 사용됩니까?

답변:


213

JWT는 "세션"을 사용하는 것보다 이점이 없습니다. JWT는 서버에서 수행하는 대신 클라이언트에서 세션 상태를 유지하는 수단을 제공합니다.

사람들이이 질문을 할 때 종종 의미하는 것은 " 서버 측 세션 을 사용하는 것보다 JWT를 사용하는 것의 이점 "입니다.

서버 측 세션을 사용하면 세션 식별자를 데이터베이스에 저장하거나 메모리에 유지하고 클라이언트가 항상 동일한 서버에 연결되는지 확인해야합니다. 둘 다 단점이 있습니다. 데이터베이스 (또는 기타 중앙 집중식 스토리지)의 경우 병목 현상이 발생하고 유지 관리해야합니다. 본질적으로 모든 요청에 ​​대해 수행해야하는 추가 쿼리입니다.

인 메모리 솔루션을 사용하면 수평 확장이 제한되고 세션은 네트워크 문제 (WiFi와 모바일 데이터 사이를 로밍하는 클라이언트, 서버 재부팅 등)의 영향을받습니다.

세션을 클라이언트로 이동하는 것은 서버 측 세션에 대한 종속성을 제거하는 것을 의미하지만 자체 문제 세트를 부과합니다.

  • 토큰을 안전하게 보관
  • 안전하게 운반
  • JWT 세션은 때때로 무효화하기 어려울 수 있습니다.
  • 고객의 주장을 신뢰합니다.

이러한 문제는 JWT 및 기타 클라이언트 측 세션 메커니즘에서 모두 공유됩니다.

특히 JWT는 이들 중 마지막을 다룹니다. JWT가 무엇인지 이해하는 데 도움이 될 수 있습니다.

약간의 정보입니다. 사용자 세션의 경우 사용자 이름과 토큰이 만료되는 시간을 포함 할 수 있습니다. 그러나 세션 ID 또는 사용자의 전체 프로필 등 무엇이든 될 수 있습니다. (하지만 그렇게하지 마십시오) 악의적 인 당사자가 가짜 토큰을 생성하는 것을 방지하는 보안 서명이 있습니다. 쿠키 또는 Authorization헤더가 전송 되는 것처럼 모든 요청과 함께 전송합니다. 사실 그들은 일반적으로 HTTP Authorization헤더로 전송 되지만 쿠키를 사용하는 것도 좋습니다.

토큰이 서명되어 서버가 출처를 확인할 수 있습니다. 서버가 안전하게 서명 할 수있는 자체 능력을 신뢰한다고 가정합니다 (표준 라이브러리를 사용해야합니다. 직접 시도하지 말고 서버를 올바르게 보호하십시오).

토큰을 안전하게 전송하는 문제에 대한 대답은 일반적으로 암호화 된 채널 (일반적으로 httpS)을 통해 전송하는 것입니다.

클라이언트에 토큰을 안전하게 저장하는 것과 관련하여 악당이 토큰에 접근 할 수 없도록해야합니다. 이것은 (주로) 나쁜 웹 사이트의 JS가 토큰을 읽고 토큰을 다시 보내는 것을 방지하는 것을 의미합니다. 이는 다른 종류의 XSS 공격을 완화하는 데 사용되는 것과 동일한 전략을 사용하여 완화됩니다.

JWT를 무효화해야하는 경우이를 달성 할 수있는 확실한 방법이 있습니다. "다른 세션을 종료"하도록 요청한 사용자만을 위해 사용자 별 시대를 저장하는 것은 아마도 충분히 좋은 매우 효율적인 방법입니다. 애플리케이션에 세션 별 무효화가 필요한 경우 세션 ID를 동일한 방식으로 유지 관리 할 수 ​​있으며 "종료 된 토큰"테이블은 전체 사용자 테이블보다 훨씬 작게 유지 관리 할 수 ​​있습니다. 허용되는 가장 긴 토큰 수명.) 따라서 토큰을 무효화하는 기능은이 세션 종료 상태를 유지해야한다는 점에서 클라이언트 측 세션의 이점을 부분적으로 무효화합니다. 이것은 원래 세션 상태 테이블보다 훨씬 작은 테이블 일 가능성이 높으므로 조회는 여전히 더 효율적입니다.

JWT 토큰을 사용하는 또 다른 이점은 예상 할 수있는 모든 언어로 제공되는 라이브러리를 사용하여 구현하는 것이 합리적으로 쉽다는 것입니다. 또한 초기 사용자 인증 체계와 완전히 분리되어 있습니다. 지문 기반 시스템으로 전환하는 경우 세션 관리 체계를 변경할 필요가 없습니다.

더 미묘한 이점 : JWT가 "정보"를 전달할 수 있고 클라이언트가이 정보에 액세스 할 수 있기 때문에 이제 몇 가지 현명한 작업을 시작할 수 있습니다. 예를 들어 사용자에게 로그 아웃하기 며칠 전에 세션이 만료 될 것임을 상기시켜 토큰의 만료 날짜를 기준으로 재 인증 옵션을 제공합니다. 당신이 상상할 수있는 무엇이든.

요약하자면 JWT는 다른 세션 기술의 몇 가지 질문과 단점에 답합니다.

  1. "저렴한"인증은 DB 왕복 (또는 적어도 쿼리 할 테이블이 훨씬 더 작음)을 제거 할 수 있기 때문에 수평 확장 성을 가능하게합니다.
  2. 변조 방지 클라이언트 측 클레임.

JWT는 보안 저장 또는 전송과 같은 다른 문제에 답하지 않지만 새로운 보안 문제를 소개하지는 않습니다.

JWT 주변에는 많은 부정적 요소가 존재하지만 다른 유형의 인증과 동일한 보안을 구현하면 괜찮습니다.

마지막 참고 사항 : 또한 쿠키 대 토큰이 아닙니다. 쿠키는 정보 비트를 저장하고 전송하기위한 메커니즘이며 JWT 토큰을 저장하고 전송하는 데에도 사용할 수 있습니다.


4
서버 측 세션도 서버에 정보를 저장할 필요가 없다는 점은 주목할 가치가 있습니다. 서버는 JWT와 동일한 방식으로 클라이언트를 저장소로 사용할 수 있습니다. 실제 차이점은 1) 쿠키 헤더가 아닌 요청 헤더로 값을 전달하여 브라우저 보안 규칙을 피하고 2) JWT로 표준화 된 형식을 갖는 것입니다.
Xeoncross

1
로컬 저장소에 jwt를 저장하는 것이 안전하다고 말씀 하시겠습니까? 그렇지 않은 경우 사용자가 로그인 상태를 유지하도록 저장할 수있는 안전한 장소는 어디입니까?
Jessica

1
예, localstorage는 일반적으로 클라이언트 측에 저장하기에 가장 정확한 장소입니다. 나는이 대답에서 웹 프로그래밍 전문가하지만 모양이 아니에요 - 당신은 XSS 처리해야합니까 stackoverflow.com/a/40376819/1810447 와 "어떻게 보호하기 위해 반대 XSS"를 검색
Tahaan

1
귀하의 의견에서 캐시 기반 솔루션 + 세션 토큰에 대해 이야기하지 않습니다. JWT + "killed tokens"테이블보다 "더 나은"것 같습니다.이 "killed tokens"테이블을 사용하면 어쨌든 DB 액세스가 필요하기 때문에 세션 + 캐시도 사용할 수 있습니다. 그리고 JWT를 지속하는 것은 세션을 지속하는 것보다 구현하기가 더 고통 스럽습니다. 왜냐하면 refresh_token을 가지고 플레이해야하기 때문입니다 (유지해야 할 두 개의 토큰) ... 어떤 코멘트라도 정말 감사 할 것입니다 ... 특히 JWT + kill_table은 세션 + 캐시보다 효율적입니다 ;-)
tobiasBora

2
@TheTahaan localStorage는 JWT를 저장하는 데 권장되지 않습니다. 공유 한 링크에도 언급되어 있습니다. 이 블로그 에는 JWT가 localStorage에 저장되지 않아야하는 이유에 대한 좋은 설명 이 있습니다.
Harke

40

짧은 대답은 없음입니다.

더 긴 버전은 다음과 같습니다.

GraphQL 문서 에서이 권장 사항을 읽은 후 세션 관리를 위해 JWT를 구현했습니다 .

이러한 인증 메커니즘에 익숙하지 않은 경우 향후 유연성을 희생하지 않고 간단하므로 express-jwt를 사용하는 것이 좋습니다.

구현은 약간의 복잡성 만 추가했기 때문에 실제로 간단했습니다. 그러나 얼마 후, 나는 (당신처럼) 혜택이 무엇인지 궁금해하기 시작했습니다. 이 블로그 게시물에서 자세히 설명하는 것처럼 세션 관리가 진행되는 한 JWT에 대해 매우 적거나없는 것으로 나타났습니다.

세션에 JWT 사용 중지


0

내 2 센트는 joepie91의 유명한 블로그 게시물과 대조를 이룹니다.

현재 (그리고 미래의) 애플리케이션이 (대부분) 클라우드 네이티브
라는 점을 고려하면 애플리케이션이 확장됨에 따라 확장되는 Stateless JWT 인증 에는 경제적 이점
이 있습니다 . 클라우드 애플리케이션은 숨을 쉴 때마다 비용이 발생합니다 .
이 비용은 사용자가 더 이상 세션 저장소 "에 대해"인증 할 필요가 없을 때 줄어 듭니다.

처리
세션 저장소를 연중 무휴로 운영하려면 비용이 듭니다.
포드는 일시적이기 때문에 K8S의 세계에서 메모리 기반 솔루션을 사용할 수 없습니다.
고정 세션은 똑같은 이유로 잘 작동하지 않습니다.

스토리지
데이터 저장에는 비용이 듭니다. SSD에 데이터를 저장하는 데 더 많은 비용이 듭니다.
세션 관련 작업은 신속하게 해결해야하므로 광학 드라이브는 옵션이 아닙니다.

I / O
일부 클라우드 제공 업체는 디스크 관련 I / O에 대해 비용을 청구합니다.

대역폭
일부 클라우드 공급자는 서버 인스턴스 간의 네트워크 활동에 대해 요금을 부과합니다.
이는 API와 세션 저장소가 별도의 인스턴스라는 것이 거의 확실하기 때문에 적용됩니다.

세션 저장소 클러스터링
비용은 앞서 언급 한 모든 비용을 더욱 증가시킵니다.


"포드는 일시적이기 때문에 K8S의 세계에서 메모리 기반 솔루션으로 벗어날 수 없습니다."이것이 무엇을 의미하는지 확실하지 않습니다. Redis는 확실히 K8S 환경에서 작동하며 사용자에게 영향을 미칠만큼 자주 실패하는 redis 포드는 거의 발생하지 않습니다.
quietContest

@quietContest 저는 개인적으로 소프트웨어를 만들 때 가능성을 다루지 않는 것을 선호합니다. BTW, 솔루션 안정성은 제쳐두고 공격으로 인해 소프트웨어가 실패하고 포드가 다시 시작되어 세션이 손실 될 수 있습니다. 그런 이유로 JWT 기반 솔루션을 선택합니다.
Eyal Perry

1
"저는 개인적으로 소프트웨어를 만들 때 가능성을 다루지 않는 것을 선호합니다." 저는 우리 모두가 그것을 선호 할 것이라고 생각합니다. 그렇기 때문에 인 메모리 데이터 저장소에 의존하는 시스템을 설계해서는 안됩니다. 그 가능성이 상당히 높기 때문입니다. 다른 요점에 관해서는, 지속적으로 redis 인스턴스를 종료 할 수있는 공격자가 있다면, 그에 대한 해결책은 아마도 JWT 사용을 포함 할 필요가 없을 것입니다.
quietContest

@quietContest는 일관되게 또는 일생에 한 번이 측면에서 나에게 동일합니다. 즉, 잘 배치 된 DDoS 공격으로 인해 서버가 "사용자를 로그 아웃"할 수 있습니다. 이것은 소프트웨어의 신뢰성 평판에 좋지 않습니다. 어쨌든 redis는 세션 관리에 과잉이라고 생각합니다. 비용과 확장이 필요하지만 쿠키에 JWT를 (안전하게) 저장하는 것은 그렇지 않습니다.
Eyal Perry

1
@quietContest 귀하의 의견에 감사드립니다. 토론을 좋아하십시오!
Eyal Perry

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