개발자 도구 · Base64 인코더 및 디코더
HTTP 기본 인증 헤더가 Base64로 구축되고 디코딩되는 방식
· 작동 방식
베이스64 보안
Authorization: Basic 헤더는 Base64를 통해 실행되는 사용자 이름:비밀번호입니다. 이 게시물에서는 값이 어떻게 구축되는지, 요청 로그에서 값을 디코딩하는 방법, 인코딩이 아무 것도 숨기지 않는 이유를 보여줍니다.
자격 증명이 올바르더라도 지속되는 401 - 미묘하게 잘못된 문자열로 디코딩되는 헤더 값
HTTP API는 401 Unauthorized를 반환하고 Authorization: Basic 헤더를 기대합니다. 값은 구성 단어 Basic, 공백 1개 및 Base64 문자열입니다. 누락된 접두사, 인코딩된 접두사 또는 눈에 띄지 않는 줄 바꿈은 눈에 보이는 사용자 이름과 비밀번호가 정확해 보이는 경우에도 서버가 수신하는 내용을 변경합니다.
해당 문자열을 디코딩하면 사용자 이름:비밀번호(문자 그대로 둘 사이의 콜론)를 읽습니다. 바이트 사용자 이름:비밀번호는 UTF-8 인코딩된 다음 Base64로 인코딩되어 헤더 값을 생성합니다. 자격 증명이 admin:s3cret이고 UTF-8 바이트가 0x61 0x64 0x6D 0x69 0x6E 0x3A 0x73 0x33 0x63 0x72 0x65 0x74(ASCII 문자 + 콜론)인 경우 Base64 인코딩은 YWRtaW46czNjcmV0을 생성하고 헤더는 Authorization: Basic입니다. YWRtaW46czNjcmV0.
RFC의 레시피 7617: 'user:pass', UTF-8, Base64 — 콜론의 정확한 단계와 역할
이는 RFC 7617에 정의된 완전한 HTTP 기본 인증 체계입니다. 이는 간단하고 표준화되어 있으며 자체적으로 보안을 제공하지 않습니다. 헤더를 읽는 사람은 누구나 즉시 헤더를 해독하여 비밀번호를 읽을 수 있습니다. 이것이 기본 인증에 HTTPS가 필수인 이유입니다. 인코딩은 보안 기능이 아닌 전송 요구 사항입니다. 비밀번호는 다른 데이터와 마찬가지로 UTF-8 바이트로 이동합니다. Base64는 HTTP 프로토콜에 사용되는 표기법일 뿐입니다.
네트워크 로그에서 기본 헤더를 디코딩해야 하는 경우 프로세스는 간단합니다. 기본을 제거하고 나머지 Base64를 디코딩하면 사용자 이름:비밀번호가 있습니다. 콜론은 사용자 이름과 비밀번호 사이의 구분 기호입니다. RFC 7617은 자격 증명이 user-id:password이고 첫 번째 콜론이 구분 기호임을 지정합니다. 비밀번호에 콜론이 포함되어 있으면 두 번째 콜론은 비밀번호의 또 다른 문자입니다. 콜론은 수신자에게 하나의 명확한 경계가 필요하기 때문에 구조적입니다. 디코딩 후 첫 번째 콜론을 검색합니다. 사용자를 식별하기 전의 모든 것과 그 뒤의 모든 것이 비밀번호입니다. 따라서 누락된 콜론은 Base64 알파벳 문제가 아니라 잘못된 자격 증명 쌍을 나타냅니다.
작업된 예: admin:s3cret 인코딩 및 로그의 헤더 디코딩 — 후행 개행 버그를 포함하여 양방향
사용자 이름이 admin이고 비밀번호가 pass:word인 경우 자격 증명은 admin:pass:word이며 YWRtaW46cGFzczp3b3Jk로 인코딩됩니다. 디코딩할 때 첫 번째 콜론으로만 분할하여 사용자 이름 admin 및 비밀번호 pass:word를 제공해야 합니다. 모든 콜론을 분할하면 비밀번호가 잘못 분할됩니다. RFC 7617 상태 자격 증명의 charset 매개 변수는 UTF-8 인코딩됩니다. 이는 사용자 이름이나 비밀번호의 ASCII가 아닌 문자가 Base64 인코딩 전에 UTF-8바이트로 변환된다는 의미입니다.
사용자 이름이 카페(악센트 e)인 경우 UTF-8 바이트는 0x63 0x61 0x66 0xC3 0xA9(ASCII 문자의 경우 4바이트 + 악센트 문자의 경우 2바이트)이고 전체 자격 증명 Cafe:password에는 카페 바이트, 콜론 바이트 0x3A, 비밀번호 순으로 있습니다. Base64 출력은 모든 바이트를 충실하게 인코딩합니다. 디코더는 디코딩된 바이트를 라틴어-1가 아닌 UTF-8 텍스트로 해석해야 합니다.
콜론, 공백 및 비ASCII를 포함하는 비밀번호 — 첫 번째 콜론이 분할되는 이유 및 charset 매개변수의 용도
작업된 예: admin:s3cret으로 시작합니다. UTF-8 바이트로 변환: a=0x61, d=0x64, m=0x6D, i=0x69, n=0x6E, :=0x3A, s=0x73, 3=0x33, c=0x63, r=0x72, e=0x65, t=0x74. 십진수: (97, 100, 109, 105, 110, 58, 115, 51, 99, 114, 101, 116). Base64는 다음 12 바이트를 인코딩합니다. 3개씩 4개의 그룹으로 그룹화합니다(4개의 Base64 문자로 구성된 4개의 그룹 생성).
인코딩된 값은 YWRtaW46czNjcmV0입니다. 인증 헤더는 인증: 기본 YWRtaW46czNjcmV0입니다. 비밀번호 측에는 첫 번째 경계를 이동하지 않고도 다른 콜론을 포함할 수 있습니다. 두 피어가 텍스트 인코딩에 동의하면 공백과 비ASCII 텍스트도 유지됩니다. ToolAcre는 자신이 방출하는 UTF-8 바이트를 확인할 수 있지만 다른 문자 집합을 기대하는 이전 서버는 Base64 변환 외부의 상호 운용성 문제로 남아 있습니다.
TLS 없이는 안전하지 않은 이유 — 디코딩하면 헤더를 보는 모든 사람에게 비밀번호가 표시됩니다.
수신된 헤더를 디코딩하려면 Basic을 제거하고, Base64는 YWRtaW46czNjcmV0을 디코딩하여 바이트를 되찾고, UTF-8 텍스트로 해석하여 admin:s3cret을 얻고, 첫 번째 콜론을 분할하여 사용자 이름과 비밀번호를 추출합니다. 일반적인 실수는 echo에서 개행 문자가 뒤에 오는 것입니다. echo admin:s3cret |를 실행하면 | Unix 셸에서 base64를 사용하면 echo는 기본적으로 줄바꿈을 추가하므로 admin:s3cret을 줄바꿈(12 대신 13바이트)으로 인코딩합니다.
Base64 출력이 다릅니다: YWRtaW46czNjcmV0Cg== (패딩 및 추가 문자). 비밀번호에 개행 문자가 포함되어 있으므로 이 값을 사용하는 인증 헤더는 실패합니다. 수정은 echo -n을 사용하거나 printf를 통해 파이프하거나 개행 문자를 추가하지 않는 도구를 사용하는 것입니다. Base64 인코더 및 디코더는 이를 방지합니다. 숨겨진 줄 바꿈 없이 붙여넣은 내용을 정확하게 인코딩합니다. TLS는 자격 증명 형식이 아닌 전송 위협을 변경합니다. 보호된 연결 내에서 헤더는 요청의 나머지 부분과 함께 암호화됩니다. 소프트웨어가 이를 기록하거나 표시하면 Base64 값은 이를 디코딩할 수 있는 모든 사람에게 재사용 가능한 자격 증명을 다시 노출합니다. 편집은 모든 관찰 지점에서 여전히 중요합니다.
일반적인 실수 — 에코의 줄바꿈, 'Basic' 접두어 누락, 값 이중 인코딩
또 다른 오류에는 기본 접두사가 없습니다. 인증 헤더 값은 Base64만으로는 유효하지 않습니다. 스키마 이름(기본, 전달자 또는 기타)과 공백, 자격 증명이 차례로 옵니다. 일부 시스템은 YWRtaW46czNjcmV0을 자격 증명으로 인식하지 못하지만 기본 YWRtaW46czNjcmV0에서는 성공합니다. 401을 디버깅하는 경우 서버가 Authorization 헤더를 올바르게 구문 분석하고 있는지 확인하세요.
체계는 HTTP 표준에서 대소문자를 구분하지 않지만 많은 구현에서는 대소문자를 구분합니다. API 문서를 확인하세요. 이중 인코딩은 또 다른 실패 모드입니다. 이미 Base64로 인코딩된 문자열을 Base64로 인코딩하면 출력은 다른 문자열이 됩니다. YWRtaW46czNjcmV0을 인코딩하면 WVdkbWFXNDZjek5qY3JldA==(완전히 다름)가 생성됩니다. 일부 시스템에서는 실수로 인코딩을 두 번 적용할 수 있습니다. 자격 증명 설정 중에 한 번, 헤더를 구성할 때 다시 한 번. 셸 명령의 줄 바꿈은 Base64 주변의 공백으로 거부되지 않고 자격 증명의 일부로 인코딩될 수 있기 때문에 특히 놓치기 쉽습니다. 결과 헤더는 추가 바이트가 있는 비밀번호로 깔끔하게 디코딩되어 서버 측 인증 실패처럼 보이는 401을 생성합니다.
여기서 다루지 않는 내용 — 다이제스트 및 전달자 체계 및 브라우저 자격 증명 프롬프트
디코더는 Base64의 단일 레이어를 예상하므로 이중 인코딩으로 인해 불일치가 발생합니다. 이것이 Base64 형식(일반 텍스트 아님)의 자격 증명 값 로깅이 혼란스러울 수 있는 이유입니다. 누군가가 디코딩을 한 번 적용하면 사용자 이름과 비밀번호가 표시됩니다. 두 번 적용하면 난독화가 표시됩니다. 다이제스트 인증(RFC 7616) 및 전달자 인증(OAuth 토큰용)은 각각 서로 다른 자격 증명 형식을 가진 서로 다른 체계를 사용합니다.
다이제스트에서는 서버가 nonce를 보내고, 클라이언트가 해시를 계산하고, 헤더에 비밀번호가 아닌 해시와 사용자 이름을 포함해야 합니다. 전달자는 일반적으로 JSON 웹 토큰(JWT)입니다. 이는 Base64url로 인코딩되지만 사용자 이름 접두사가 붙지 않습니다. 기본 인증은 두 가지보다 간단하지만 자격 증명을 헤더에서 읽을 수 있기 때문에 TLS가 없으면 완전히 안전하지 않습니다. Digest와 Bearer는 동일한 Authorization 헤더 필드를 사용하지만 해당 값에 완전히 다른 의미를 할당합니다. 브라우저 자격 증명 프롬프트는 Basic 위에 사용자 인터페이스와 캐싱 동작을 추가합니다. 이 기사에서는 인증 시스템을 비교하기보다는 기본 자격 증명 페이로드를 구성하고 검사하는 데 중점을 둡니다.
요약: 기본 인증은 보호가 아닌 Base64입니다. Base64 인코더 및 디코더를 사용하면 자격 증명을 어디로든 보내지 않고도 로컬에서 헤더 값을 확인할 수 있습니다.
API가 여러 인증 체계를 지원하는 경우 가장 안전한 것을 선택하세요. Base64 인코더 및 디코더는 기본 인증 실패를 디버깅하는 데 도움이 될 수 있습니다. 자격 증명 문자열(사용자 이름, 콜론 및 비밀번호)을 붙여넣으면 도구가 즉시 Base64 값을 생성합니다. 결과를 헤더 전송과 비교하면 불일치가 표시됩니다. 반대로 네트워크 로그의 헤더 값을 붙여넣고 기본 접두사를 제거하고 디코딩하여 서버가 본 내용을 확인합니다.
학습을 위해 admin:s3cret을 붙여넣고 출력을 관찰한 다음 비밀번호를 수정하여 Base64가 어떻게 변경되는지 확인하세요. 헤더 작성 방법을 이해하면 디코딩에 RFC 형식을 알아야 하는 이유와 콜론이 Base64가 아닌 구조적 요소인 이유가 명확해집니다. 로컬 검사에서는 프로덕션에서 복사된 실제 비밀번호가 아닌 발명된 자격 증명을 사용해야 합니다. 쌍을 인코딩하고 출력을 다시 입력 패널로 이동한 다음 디코딩합니다. 일치하는 구두점과 정확한 후행 문자는 헤더가 어디로든 전송되기 전에 표현 왕복을 증명합니다.