문서 작업 가이드
위험한 동작을 답습하지 않고 정적 HTML 뷰를 Pug로 옮기는 방법
레거시 HTML 뷰의 의존성을 조사하고 Pug로 변환한 뒤 활성 코드와 파서 경고를 해결하고 템플릿 데이터를 정의해 실제 렌더링 결과를 검증하는 절차입니다.
작성 및 검수 SimpleWebUtils게시일: 검토일:
이 작업 흐름을 검증한 방법
마크업 변환 워크벤치로 “전역 저장 핸들러를 명시적인 라우트와 클라이언트 계약으로 교체하기” 샘플 입력을 정확히 재현했습니다. 결과 비교에는 “현재 렌더링과 동작을 기준으로 남깁니다”, “소스를 변환하고 모든 경고를 조사합니다” 단계를 포함했습니다. 이어서 연결된 테스트 근거에서 “Pug가 허용한다는 이유로 인라인 이벤트 유지하기”, “편의를 위해 비이스케이프 Pug 보간 사용하기” 조건을 점검했습니다.
Pug 결과는 POST action, label, required name 필드와 escape되는 local 값을 유지했고, 전역 onclick 코드는 실행 결과가 아니라 명시적인 migration 작업으로 남겼습니다.
문제 상황
레거시 HTML 페이지는 전역 스크립트, 인라인 onclick 문자열, DOM ID, 상대 자산, 서버 주입값, 폼 엔드포인트, 상위 레이아웃이 불러오는 CSS에 의존하는 경우가 많습니다. 기계적 변환은 화면 구조를 유지하면서 위험 URL과 낡은 동작을 유효한 Pug 안에 그대로 가져올 수 있습니다. HTML 파서가 바꾼 구조를 놓치거나 데이터 출처를 정하기 전에 템플릿 로직부터 만들 위험도 있습니다. 안전한 이전은 문법 변환과 동작 재설계를 분리하고 실제 애플리케이션 안에서 최종 렌더링을 증명해야 합니다.
이럴 때 사용하세요
- 검토를 마친 정적 또는 서버 렌더링 HTML 뷰를 Pug를 사용하는 Express 애플리케이션으로 옮길 때
- 카드, 폼, 표, 내비게이션, 이메일 미리보기, SVG 조각 하나를 애플리케이션 데이터 연결 전에 Pug 초안으로 만들 때
- 레거시 템플릿의 인라인 이벤트, 활성 URL, 스크립트, 잘못된 중첩, 페이지 수준 의존성을 드러내야 할 때
- 생성된 템플릿을 정화되거나 완성된 코드로 오해하지 않고 여러 HTML 뷰를 반복해서 옮길 체크리스트가 필요할 때
단계
- 1단계
하나의 뷰를 고르고 모든 의존성을 목록화합니다
사용자 작업 하나를 완결하는 가장 작은 뷰나 조각을 선택합니다. 상위 레이아웃, 스타일시트, 스크립트, 폰트, 이미지, 상대 링크, 폼 action, 코드가 조회하는 ID, 브라우저 저장소, 전역 변수, 서버 값, 인증 가정, 오류 상태를 기록합니다. 변환 자료에서 비밀값, 고객 데이터, 사설 호스트, 운영 토큰을 제거합니다. doctype, html, head, body를 유지하기 전에 대상이 전체 문서를 소유하는지 include 조각을 소유하는지 결정합니다.
- 2단계
현재 렌더링과 동작을 기준으로 남깁니다
작동하는 환경에서 원본을 렌더링하고 제목 순서, 레이블, 대체 텍스트, 탭 순서, 키보드 동작, 폼 검증, 로딩 및 실패 상태, 좁은 화면 배치, 네트워크 요청을 기록합니다. 대표적인 assertion이나 스크린샷을 남깁니다. 잘못된 HTML은 이미 브라우저에서 보정될 수 있으므로 원본 파일과 브라우저가 파싱한 DOM을 함께 확인합니다. 이 기준으로 유지할 동작과 의도적으로 제거할 레거시 동작을 구분합니다.
- 3단계
소스를 변환하고 모든 경고를 조사합니다
마크업 변환 워크벤치에서 HTML → Pug 탭을 열어 검토한 소스를 변환합니다. 태그, 중첩, 텍스트 공백, 주석, 속성, SVG, template 내용, 문서 래퍼를 비교합니다. 파서 보정, 제거된 서식 공백, 레거시 doctype, script와 style, noscript, on 계열 이벤트 속성, javascript나 활성 data URL, 템플릿처럼 보이는 표식을 조사합니다. 문법 검사를 통과한 출력도 마이그레이션 초안일 뿐이므로 첫 렌더링이 비슷하다는 이유로 경고를 무시하지 않습니다.
- 4단계
보존된 활성 동작을 애플리케이션 설계로 교체합니다
인라인 이벤트 문자열과 전역 DOM 호출을 제거합니다. 동작을 명시적인 입력, 오류 처리, 테스트가 있는 이름 붙은 클라이언트 모듈이나 프레임워크 컴포넌트로 옮깁니다. javascript URL을 승인된 내비게이션으로 바꾸고 폼 목적지를 검증하며 스크립트를 레이아웃, 번들 클라이언트 진입점, 또는 제거 중 어디에 둘지 결정합니다. URL과 콘텐츠 신뢰 정책을 적용하고, 신뢰하지 않는 소스는 변환이 아니라 수집 경계에서 정화합니다.
- 5단계
Pug locals를 정의하고 동적 문법을 의도적으로 추가합니다
라우트가 제공하는 각 값의 타입, 필수 여부, 기본값, 이스케이프 규칙, 빈 상태와 오류 상태를 정의합니다. 이 계약에 필요한 곳에만 변수, 조건문, 반복문, include, mixin, 상속을 추가합니다. 사용자 제어 값은 이스케이프하고 문서화된 정화 과정 없이 비이스케이프 보간을 사용하지 않습니다. 누락값과 공격적인 값을 테스트하고, 단독 렌더링이 기준과 일치한 뒤에만 공통 레이아웃으로 이동합니다.
- 6단계
대상 뷰를 컴파일하고 렌더링해 검증합니다
프로젝트의 Pug 컴파일, 포매터, 린터, 테스트, 프로덕션 빌드를 실행합니다. Pug 소스만 스냅샷하지 말고 렌더링된 HTML을 파싱하거나 스냅샷합니다. 정상, 빈 값, 긴 값, 유니코드, 잘못된 값, 로딩, 실패 데이터를 시험하고 라우트, 자산, 폼, 키보드, 접근 가능한 이름, 포커스, 390px 모바일, CSP, 예상 네트워크 요청을 확인합니다. 병합이나 게시 전에 원본과 렌더링의 차이 및 활성 코드 해결 내역을 검토합니다.
예시
전역 저장 핸들러를 명시적인 라우트와 클라이언트 계약으로 교체하기
입력
<form class="profile" action="/profiles" method="post"><label for="name">이름</label><input id="name" name="name" value="Ada" required><button onclick="trackSave()" type="submit">저장</button></form>출력
구조를 변환하고 보존된 onclick 속성을 제거하며, 현재 이름은 이스케이프되는 Pug local로 제공합니다. 실제 label과 POST action을 유지하고 승인된 분석 동작은 애플리케이션 계층에 붙입니다. 이름 누락과 긴 값, 검증 실패, 키보드 제출, CSRF 처리, 서버 오류, 운영 CSP에서의 렌더링을 테스트합니다.흔한 실수
사이트 내보내기 전체를 하나의 템플릿으로 옮기기
전체 내보내기에는 서로 다른 뷰, 메타데이터, 스크립트, 페이지 장식이 섞여 있습니다. 소유권, 경고, 의존성을 검토할 수 있도록 라우트나 include 조각 하나씩 변환합니다.
Pug가 허용한다는 이유로 인라인 이벤트 유지하기
유효한 속성 문법이 전역 이벤트 문자열을 유지보수 가능하거나 안전하게 만들지는 않습니다. 애플리케이션이 소유하는 동작으로 바꾸고 상호작용과 실패 경로를 시험합니다.
편의를 위해 비이스케이프 Pug 보간 사용하기
비이스케이프 출력은 데이터를 실행 가능한 마크업으로 만들 수 있습니다. 사용자 제어 값은 이스케이프하고 의도적인 원시 HTML에는 문서화된 정화 도구와 신뢰 경계를 요구합니다.
locals를 정의하기 전에 반복문과 상속부터 추가하기
데이터 계약 없는 템플릿 기능은 숨은 undefined 상태와 중복 가정을 만듭니다. 먼저 라우트 입력, 기본값, 오류를 정의하고 필요한 최소 Pug 로직만 추가합니다.
Pug 소스만 검사하고 렌더링 HTML은 보지 않기
파서가 통과한 파일도 깨진 경로, 중복 ID, 접근할 수 없는 폼, 위험 URL, 누락 데이터를 렌더링할 수 있습니다. 대표 locals로 컴파일하고 최종 DOM, 동작, 네트워크를 검사합니다.
자주 묻는 질문
전체 HTML 문서는 Pug에서도 전체 문서로 유지해야 하나요?
대상 라우트가 응답 전체를 소유할 때만 그렇습니다. include나 하위 템플릿이라면 문서 래퍼를 제거하고 doctype, head 메타데이터, 스크립트, 공통 내비게이션은 상위 레이아웃이 소유하게 합니다.
변환 결과의 script와 onclick을 그대로 유지해도 되나요?
검토 자료로만 남기세요. 승인된 동작을 애플리케이션 클라이언트 코드로 옮기고 활성 URL을 교체하며 전역 문자열을 자동으로 답습하지 말고 CSP와 이벤트 동작을 검증합니다.
텍스트를 정적 등호 표현식으로 만드는 이유는 무엇인가요?
정적 문자열 표현식은 따옴표, 유니코드, 공백, Pug 보간처럼 보이는 표식을 템플릿 로직으로 바꾸지 않고 보존합니다. 의도한 동적 값은 나중에 명시적인 locals 계약으로 도입합니다.
로컬 변환이면 신뢰하지 않는 HTML도 안전해지나요?
아닙니다. 로컬 처리는 업로드를 피하고 변환 중 입력을 실행하지 않지만 활성 속성과 요소를 보존할 수 있습니다. 신뢰하지 않는 콘텐츠에는 애플리케이션 경계의 정화 도구, URL 정책, 이스케이프 규칙, CSP가 필요합니다.
마이그레이션 완료를 무엇으로 증명하나요?
의존성과 locals가 문서화되고 모든 경고가 해결되며 대상 빌드가 통과해야 합니다. 대표 데이터의 렌더링 HTML이 의도한 기준과 맞고 동작, 접근성, 모바일, 자산, 폼, 보안, 네트워크 검사도 깨끗해야 합니다.