[Python / Django] 인증, 인가

jaylight·2020년 12월 13일
0

인증 (Authentication)

  • (정의) 회원가입과 로그인
  • (활용) 누가, 어떻게 우리 서비스를 활용하는지 추적하기 위해 활용
    • (장기적) 마케팅 타켓팅, 만족도 상승, 추가적 사업 발굴 등에 활용
    • (단기적) 유료/무료 고객 여부 등 파악
  • (필요사항) 아이디, 이메일주소, 비밀번호 등
    • 이 중 비밀번호가 가장 중요
    • 인증에 필요한 것은 아이디 대신 집 주소, 계좌번호, 주민등록번호 등을 활용할 수 있지만, 비밀번호는 필수적으로 가장 중요

[비밀번호 관리]

  • (법규상의 강제) 개인정보보호법을 통해 개인정보 암호화에 대한 구체적 규정이 마련되어 있음
  • 보통 백엔드 개발자가 관리는 하지만, 유출에 대해서 백엔드가 전체 책임을 지는 것은 아님
  • 윤리적 책임

[비밀번호 관리법]

  1. 복원이 불가능한 형태로 DB에 저장
    • 위 서버/DB를 개발한 백엔드 개발자조차 위의 코드를 해석해서 비밀번호를 알 수 없게 함
  2. 통신 시 개인정보를 주고받을 때 SSL을 적용하여 암호화(HTTPS)
    • 위 자물쇠 모양이 HTTPS로 전송되고 있다는 의미
    • 중요한 정보를 공유하는 사이트에서 위를 확인
      SSL인증, HTTP/HTTPS의 차이 등에 관해 추가적으로 search 해볼 것

[암호화 절차]

단방향 해쉬

해쉬(Hash)

  • 컴퓨터 공학의 자료 구조 중 하나로, 빠른 자료 검색, 데이터 위변조 체크를 위해 활용

  • Input을 다른 형태로 출력해주는 함수로 보면 됨

  • 단방향 Hash는 Output을 통해 Input을 다시 역산할 수 없는 구조이다.

    • 위의 특징을 활용하여 암호화에 활용하기 시작함
  • 기존 (MD5, SHA-1) 등을 활용했으나 함수이다 보니까, Super Computer 등을 통해 Input을 찾아내는 경우가 발견됨

  • 따라사 최근은 조금더 보안이 강화된 SHA-256을 활용

  • [문제점] 같은 Input에 대한 Output이 모두 같은 결과로 도출 됨 ⇒ 역추적의 가능성이 있음

    • 위와 같은 허점을 활용해 가능한 경우의 수를 모두 해시값으로 만들어서 판매하는 서비스도 존재(Rainbow Table) → 이를 활용한 비밀번호 유추 공격을 Rainbow Attack이라고 함

      ⇒ 위 허점을 보완하고자, Salting과 Key Stretching이라는 아이디어가 제안

    • 개발자가 Hash된 결과의 아웃풋의 임의의 값을 붙이는 방식

[Salting & KeyStretching]

  • (Salting) 입력한 비밀번호와 임의로 생성한 문자열(Salt)를 합쳐서 해싱해서 이 해시값을 저장하는 방법
    • 이 때 비교를 위해 해시값과 Salt값을 같이 저장
  • 물론 위 방식 또한 슈퍼컴을 통해 풀릴수는 있지만, 해시값 계산에 필요한 시간을 크게 늘림

현재 기술 기준, 10자리 비밀번호를 푸는데 약 100년이 걸린다고 알려져 있음

[bcrypt]

  • Salting & Key Stretching의 대표적 라이브러리
    • Salt언어는 한번 생길때마다 (회원가입, 비밀번호 변경 등) 매번 바뀜
    • 따라서, 사전에 미리 정해두지 않고 백엔드 개발자도 알 수 없음
  • 무료에 적용하기 쉽지만
  • 파이썬 버전 라이브러리를 사용할 예정
  • DB에는 위와 같은 형태로 비밀번호가 저장 됨
    • 2y2y: 어떤 알고리즘을 활용했는가 (SHA-256)
    • 10: Key Stretching 횟수
    • Salt
    • Hashed Password

Salting은 기업마다 거의 동일한 방식 - 대부분 bcrypt를 활용함

단방향 해쉬라는 알고리즘 자체는 수학자들이 만들어낸다.
기업마다 개별적으로 단방향 해쉬 알고리즘을 개발하기에는 무리가 있다.
(Hash함수를 개발하는 것 자체가 매우 큰 Task)
알고리즘 자체가 발전이 빠르게 이루어져 있고 잘 만들어진 알고리즘을 모두가 같이 활용함
(오히려 기업이 개별적으로 개발하면 보안이 취약할 수 있음)

인가 (Authorization)

  • 사용자가 서버에 로그인하면 해당 사용자가 맞는지 확인하는 과정
    • 로그인한 사람이 추가적인 서비스를 이용할 때 서비스 이용을 허락하는 것
  • 개인에 대한 접근을 허락하는 개념
    • 사용자가 서비스에 본인을 증명하고 서비스 사용을 허가함
  • http의 특징
  1. request / response (요청 & 응답)
  2. Stateless한 성질 (저장하지 않음): 그 전의 활동을 기억하지 않음
  • 사용자가 로그인한 정보를 확인하는 방법: headers에 메타데이터를 보내서 확인
    • 서버에 로그인을 하면 Token을 발행함 ⇒ JWT (JSON Web Token)
      (백엔드 서버가 JWT 토큰을 발행하고, 프론트엔드 개발자에게 Return): 로그인을 해야 토큰을 넘긴다!
      [ 바디에 심어 준다고 이해하면 됨 ]
    • 프론트 개발자는 받은 Token을 브라우저의 (로컬 스토리지, 쿠키, 세션 스토리지 등)에 저장
    • 로그인 이후 다른 요청을 보낼 때, 해당 토큰과 함께 요청을 보냄으로써 서비스에 접근할 수 있도록 함
      (Request의 헤더에 담기게 됨 / Response에는 굳이 담기지 않음)

[JSON Web Token]

  • 3개의 구조로 나뉨

    • 헤더

      • 메타 데이터 (토큰 타입, 해시 알고리즘 정보 등)
        [JWS는 복호화(Input을 다시 찾아내는 것)를 해야하므로, 알고리즘 정보를 제공해야 함]
    • 내용(Payload)

      • 클라이너트 - 서버 간 협의하에 사용하는 비공개 클레임(유저정보)
      • 다른 사람이 볼 수 있는 내용이기 때문에 데이터 정보를 그대로 넣지 않고, 백엔드 상 저장된 유저 정보를 보냄
      • 너무 specific한 정보는 보내지 않고, 서버가 딱 알아들을 수 있는 정보를 담고 있음
      • 이 로그인을 얼마나 유지할 것인지에 대한 (금융권) 만료시간 등 정보를 담고 있음
    • 서명(signature)

      헤더와 내용은 크게 암호화 하지 않고 인코딩만 진행함 [인코딩: 문자의 타입만 바꿈]
      즉, 헤더와 내용에 개인정보를 그대로 담을 수 없음

      • 서명 부분은 암호화를 함 (즉, 헤더와 내용보다 중요한 정보)

      • 토큰을 발행하는 서비스(넷플릭스, 마켓컬리 등)가 있을 텐데, A 서비스 토큰을 가지고 B 서비스를 이용할 수 없도록 막아야함

      • 따라서 Signature는 해당 서비스의 고유한 정보가 암호화되어 들어감

        ⇒ 마치 계약서 위변조를 막기 위해 서로 사인하는 것과 같음

Token 보안 강화 방법

  • 한번 발행 된 토큰은 한 개 IP에서만 활용
  • 매번 로그인할 때마다 토큰이 리프레시 등 많은 방법을 활용

0개의 댓글