개발 slecs

블로그 전체 포스트의 OG 태그와 canonical URL이 깨지던 변수

목차

Post.astro 안에서 _siteUrlAUTHOR_URL이 선언 누락된 채로 빌드가 통과되던 걸 발견해서 다시 선언해줬다.


왜 이게 문제였나

Astro 레이아웃 파일은 컴포넌트 단위로 분리되어 있어서, 상위에서 정의한 변수가 자식 컴포넌트로 자동 흘러들어오지 않는다. JavaScript 모듈 스코프와 동일한 개념인데, 문제는 이게 개발 환경에서 꽤 조용하게 실패한다는 점이다. 타입 추론이 느슨한 환경이거나, 빌드 타임에 정적으로 평가되는 값이라면 에러 없이 undefined로 넘어가서 HTML에 그대로 박혀버리는 경우가 생긴다.

_siteUrlAUTHOR_URL 두 값은 메타태그, OG 태그, canonical URL 같은 SEO 관련 마크업에서 쓰이는 경우가 많다. 이 값들이 undefined로 렌더링되면 실제 HTML에는 아무 에러도 안 뜨는데 크롤러가 잘못된 URL을 색인하거나, SNS 공유 미리보기가 깨지는 식의 증상이 나타난다. 바로 눈에 안 보이니까 방치되기 딱 좋은 버그다.


변수 누락이 레이아웃 파일에서 자주 터지는 이유

Astro의 layouts/ 폴더 하위 컴포넌트는 여러 페이지에서 공유되는 만큼, 처음 만들 때 "일단 여기서 쓸 것들만" 선언해두고 나중에 필요한 변수를 추가하다 보면 선언 위치가 뒤섞인다. 특히 이런 패턴이 위험하다.

---
// Post.astro
import { SITE } from '../config';

// _siteUrl, AUTHOR_URL 선언이 빠진 채로
// 하위 템플릿에서 그냥 사용 
---

<meta property="og:url" content={`${_siteUrl}/posts/${slug}`} />
<link rel="author" href={AUTHOR_URL} />

이 상태에서 빌드하면 TypeScript strict 모드가 켜져 있으면 에러가 나지만, .astro 파일 특성상 타입 체크가 느슨하게 설정된 프로젝트에선 그냥 통과된다. 팀원이 나중에 이 파일을 열면 "이 변수 어디서 왔지?" 하고 한참 따라가야 한다.

수정 후는 이렇게 됐다.

---
import { SITE } from '../config';

const _siteUrl = SITE.url;
const AUTHOR_URL = SITE.author.url;
---

<meta property="og:url" content={`${_siteUrl}/posts/${slug}`} />
<link rel="author" href={AUTHOR_URL} />

로컬 스코프에서 명시적으로 재선언해두면 이 파일만 읽어도 의존 관계가 한눈에 보인다. 코드 리뷰할 때도 "이 변수 어디서 오는 거야?"를 물어볼 필요가 없어진다.


팀 레벨에서 이 류의 버그가 반복되는 패턴

레이아웃 파일 관련 변수 누락은 혼자 작업할 때보다 여러 명이 같은 파일을 번갈아 수정할 때 훨씬 자주 생긴다. 누군가 config 구조를 리팩터링하면서 SITE.url 접근 방식을 바꿨는데, Post.astro에는 반영이 안 된 채 머지된다거나, 반대로 Post.astro를 고치면서 위에서 가져오던 변수를 실수로 지우는 경우.

체크리스트로 정리하면 이렇다.

  • layouts/ 수정 시 해당 파일 내 모든 변수 선언을 스코프 상단에 모아두는 관습 유지
  • config 구조 변경 시 layouts/ 파일 일괄 검색 필수 (grep -r "_siteUrl" src/)
  • OG 태그, canonical, author 링크는 빌드 후 HTML 직접 확인하는 스모크 테스트 루틴 추가
  • TypeScript strict 설정 또는 Astro의 타입 체크 옵션을 최대한 올려두기

이번 건 stat이 따로 없을 정도로 핀포인트 수정이었지만, 영향 범위는 작지 않았다. Post.astro는 블로그 글 전체에 적용되는 레이아웃이니까, 이 파일 하나가 잘못되면 모든 포스트 페이지의 메타 정보가 동시에 깨진다. 변경 라인 수가 적다고 리뷰를 가볍게 보면 안 되는 이유가 여기 있다.

레이아웃 컴포넌트는 수정 빈도가 낮은 대신 영향 반경이 넓다. 그래서 오히려 더 꼼꼼하게 봐야 하는 파일이다. 이번 fix를 계기로 layouts/ 하위 파일은 PR description에 "영향 받는 페이지 목록" 항목을 하나 추가해두기로 했다.

끝.


🛒 이 글과 어울리는 추천 상품

*위 링크는 쿠팡파트너스 활동의 일환이며, 일정액의 수수료를 제공받을 수 있습니다.

댓글 0

첫 댓글 달아줘.