[PonsLink] 서버가 미디어를 나르지 않을 때 남는 책임
서버가 미디어를 나르지 않으면 편해질 줄 알았다. 트래픽 비용이 줄고 인코딩 부담도 클라이언트 쪽으로 가니 운영이 단순해 보였다. 그 문장은 절반만 맞았다.
막상 해보니 사라지는 건 미디어 운반뿐이었다. 세션 권한, 기능 허용, 중계 자격, 업로드 주소, 방 권한, 실패 문장 번역은 그대로 남았다. 미디어를 안 나를수록 제어면 경계가 더 선명해야 제품이 안전해졌다.

미디어를 안 나르면 무엇을 나르나
처음 시선은 서버가 가벼워진다는 문장에 고정돼 있었다. 실제 남는 책임 목록을 적어 보니 가벼움과는 거리가 있었다.
세션 권한과 기능 허용 발급, 중계 자격 발급과 만료, 업로드 주소 발급, 방 권한과 연결 수락, 실패를 사용자 문장으로 번역, 감사 가능한 결정 기록이 남았다.
이 중 하나라도 브라우저에 넘기면 보안 경계가 얇아진다. 서버가 미디어를 안 나르는 만큼 제어면은 더 단단해야 한다.
가벼운 서버라는 말 대신 얇은 미디어 경로, 두꺼운 제어 경로라고 부르는 편이 정직했다.
프론트에 권한을 줬던 첫 설계
초기에는 프론트가 방 설정을 알고 패널을 직접 그렸다. 속도는 빨랐다. 화면 토글 하나 넣는 데 서버 왕복이 필요 없었다.
대가는 분명했다. 공급자 비밀값이나 관리자 성격 값이 브라우저 쪽으로 스며들 위험이 커졌다.
같은 링크인데 브라우저마다 다른 화면이 보이면 권한 판단이 클라이언트에 일부 내려갔다는 신호다.
화면은 열리는데 실제 기능 허용은 없는 상태, 또는 그 반대 상태는 사용자 신뢰를 빠르게 무너뜨린다.

백엔드를 유일한 권한자로 둔 이유
다시 그은 경계는 백엔드가 제어면의 유일한 권한자라는 선언이다. 브라우저는 런타임 설정만 받고 허용 결과에 따라 화면을 그린다.
| 서버 | 브라우저 |
|---|---|
| 세션 토큰 발급 | 런타임 설정 수신 |
| 기능 허용 결정 | 허용 기준 화면 렌더 |
| 자격 발급 | 자격 사용만 |
| 실패 번역 | 상태 문장 표시 |
공개 가능한 설정만 내려보내고 진짜 판단은 서버 경계 안에서만 일어난다. 비밀값이 브라우저에 없어야 유출 사고가 프론트 실수로 번지지 않는다.
이 구조는 계정 없는 만남과도 충돌하지 않는다. 계정 없음은 신원 수집을 줄이는 선택이지 권한 부재가 아니다.
미디어 경로와 제어 경로를 섞지 않기
미디어 경로는 지연과 대역과 끊김을 다룬다. 제어 경로는 권한과 만료와 감사와 설명 가능성을 다룬다. 목적 함수가 다르다.
둘을 한 파이프에 욱여넣으면 장애 해석이 불가능해진다. 화면이 끊긴 건지 자격이 만료된 건지 방 권한이 거절된 건지 한 번에 섞인다.
서버가 미디어를 안 나른다는 문장은 끝이 아니라 시작이다. 다음 문장은 그러면 서버는 무엇을 판단하는가여야 한다.
실패 코드도 경로별로 나눈다. 한 코드로 모든 실패를 퉁치면 지원과 개발이 같은 표를 볼 수 없다.
마치며
서버가 미디어를 나르지 않는 건 자유가 아니라 제어면에 더 엄격한 책임을 지우는 일이다.
수치로 포장하지 않아도 된다. 순서와 책임 경계만 고정하면 된다.
그 경계가 서버에 남아 있을 때 비로소 계정 없는 빠른 만남이 안전한 약속이 된다.
다음에 제어면을 다시 만지면 백엔드 단일 권한자를 전제로 시작하겠다.