정적 블로그에 댓글 기능 달기 — giscus로 GitHub Discussions 연동
첫 포스트 마지막에 이런 말을 남겼었는데요,
💡 ps. 댓글 기능을 넣을지 말지 고민 중이에요…
결론부터 말하면, 넣기로 했습니다! 🫣
사실 댓글 다는 사람이 몇이나 될까 싶긴 한데… 그래도 혹시 누군가 제 글에 공감하거나, 다른 의견이 있다면 편하게 남길 수 있는 공간 정도는 있어야 하지 않을까 싶어서 ㅎㅎ
그런데 이 블로그, Astro 기반의 정적 사이트거든요. 서버가 따로 없으니 DB에 댓글을 저장하는 건 불가능하고… 어떻게 해야 할까 고민하다가 찾은 게 giscus입니다 👊
giscus가 뭔데?
giscus는 GitHub Discussions를 댓글 저장소로 활용하는 오픈소스 댓글 위젯이에요.
작동 원리는 간단합니다:
- 블로그에 방문자가 댓글을 작성
- GitHub 계정으로 로그인
- 연결된 리포지토리의 Discussions에 자동으로 스레드가 생성
- 댓글이 해당 스레드에 저장
즉, GitHub Discussions = 댓글 DB 역할을 하는 거죠 🥸
왜 giscus를 선택했나?
찾아보니까 giscus 외에도 댓글 시스템을 달 수 있는 선택지가 몇 가지 있더라고요
| 서비스 | 기반 | 비고 |
|---|---|---|
| giscus | GitHub Discussions | 무료, 리액션/답글 지원 |
| utterances | GitHub Issues | 무료, giscus의 전신 |
| Disqus | 자체 서비스 | 무료 플랜에 광고, 무거움 |
| Cusdis | 자체 호스팅 | 경량, 셀프호스팅 필요 |
개발 블로그니까 방문자 대부분이 GitHub 계정이 있을 거고, Discussions 기반이라 답글 스레드, 리액션 이모지 같은 기능도 지원하고, 무엇보다 무료에 광고가 없다는 게 베리굿 👍
설정 과정
저는 블로그 소스코드와 댓글 데이터를 분리하고 싶어서, 별도의 댓글 전용 리포지토리를 새로 만들어 사용했어요. 물론 블로그 소스 리포지토리에 바로 연결해도 됩니다.
1단계 — 저장소 준비 (사전 조건 3가지)
-
저장소가 Public(공개) 상태여야 함
-
giscus 앱이 이 저장소에 설치되어 있어야 함
- 저장소에 Discussions 기능이 활성화 되어 있어야 함 (Settings -> General -> Discussions 체크 ✅)
2단계 — giscus.app에서 설정값 생성
giscus.app/ko에 접속한 뒤, 저장소 입력란에 본인의 저장소 이름을 입력해주세요.
카테고리는 Announcements로 설정했습니다.
카테고리를 General로 두면 외부인도 임의로 Discussion을 생성할 수 있어서 스팸이나 무관한 글이 섞일 수 있어요. Announcements는 Discussion 생성 권한이 저장소 소유자(= 본인)와 giscus 봇에게만 있어서, 블로그 포스트마다 정확히 1개의 Discussion이 깔끔하게 관리됩니다.
| General | Announcements | |
|---|---|---|
| 새 Discussion 생성 | 누구나 | 관리자만 |
| 댓글 작성 | 누구나 | 누구나 |
| 블로그 댓글 적합성 | 보통 | ✅ 최적 |
블로그 댓글용으로는 Announcements를 강력 추천합니다 !
💡 추가 팁: giscus 설정 페이지에서 “이 카테고리에서만 Discussion 찾기” 체크박스도 함께 활성화하면, 다른 카테고리에 동일 경로의 Discussion이 있어도 충돌 없이 동작합니다.
그리고 기능(Features) 섹션에서 아래 4가지 옵션을 설정할 수 있어요.
-
메인 포스트에 반응 남기기 (기본값: 켜짐)
- 댓글 목록 위에 👍 👎 😄 🎉 😕 ❤️ 🚀 👀 같은 이모지 반응 버튼을 표시합니다. 방문자가 댓글을 쓰지 않아도 간단히 반응을 남길 수 있어 참여율을 높여줍니다.
-
Discussion 메타데이터 보내기 (기본값: 꺼짐)
- Discussion의 메타데이터(댓글 수, 반응 수 등)를 부모 페이지(내 블로그)로 전달합니다. 이 데이터를 받아서 JavaScript로 커스텀 UI를 만들고 싶을 때 사용하는 개발자용 고급 옵션입니다.
-
댓글 위에 댓글 상자 배치 (기본값: 꺼짐)
- 기본적으로 댓글 입력창은 댓글 목록 아래에 있습니다. 이 옵션을 켜면 입력창이 댓글 목록 위로 올라옵니다. 댓글이 많아서 맨 아래까지 스크롤하기 번거로울 때 유용하지만, 초기 블로그라면 굳이 켤 필요는 없습니다.
-
댓글 느리게 불러오기 (기본값: 꺼짐)
- 페이지 로드 시 댓글을 바로 불러오지 않고, 방문자가 댓글 영역 근처로 스크롤할 때 불러옵니다. 페이지 초기 로딩 속도를 개선할 수 있어요. 저는 이 옵션도 활성화했습니다.
블로그용 추천 설정:
| 옵션 | 추천 |
|---|---|
| 메인 포스트에 반응 남기기 | ✅ 켜기 |
| Discussion 메타데이터 보내기 | ⬜ 끄기 |
| 댓글 위에 댓글 상자 배치 | 취향껏 |
| 댓글 느리게 불러오기 | ✅ 켜기 (성능 최적화) |
그러면 페이지 하단에 아래 값들이 자동으로 채워진 <script> 태그가 생성됩니다.
| 설정 키 | 설명 |
|---|---|
| data-repo | username/repo (본인 저장소) |
| data-repo-id | GitHub API로 자동 조회되는 저장소 ID |
| data-category | Discussion 카테고리 이름 (예: Announcements) |
| data-category-id | 카테고리 ID (자동 조회) |
| data-mapping | 페이지 ↔ Discussion 연결 방식 |
| data-theme | 테마 설정 |
3단계 — 스크립트 복사 & 붙여넣기
여기서 한 가지 주의할 점이 있어요. giscus의 data-theme에 preferred_color_scheme을 써도 되지만, 블로그에 별도로 다크모드 토글이 있는 경우 시스템 테마와 블로그 테마가 달라서 처음 로드 시 싱크가 안 맞는 문제가 생길 수 있습니다 🚨
그래서 저는 giscus <script> 태그를 정적으로 박아두는 대신, JavaScript로 동적으로 생성하는 방식을 택했어요
이렇게 하면 로드 시점에 현재 테마를 읽어 data-theme에 바로 주입할 수 있거든요
<!-- HTML에는 빈 div만 둘 -->
<div id="giscus-container"></div>
// 페이지 로드 시 현재 테마를 읽어 giscus 스크립트 동적 생성
const isDark = document.documentElement.classList.contains('dark');
const script = document.createElement('script');
script.src = 'https://giscus.app/client.js';
script.setAttribute('data-repo', 'username/repo'); // 본인 저장소
script.setAttribute('data-repo-id', 'REPO_ID'); // giscus.app에서 자동 조회
script.setAttribute('data-category', 'Announcements');
script.setAttribute('data-category-id', 'CATEGORY_ID'); // giscus.app에서 자동 조회
script.setAttribute('data-mapping', 'pathname');
script.setAttribute('data-theme', isDark ? 'dark' : 'light'); // 현재 테마 주입!
script.setAttribute('data-lang', 'ko');
script.setAttribute('data-loading', 'lazy');
script.setAttribute('crossorigin', 'anonymous');
script.async = true;
document.getElementById('giscus-container').appendChild(script);
💡 핵심 포인트
data-repo-id와data-category-id는 직접 입력하는 것이 아니라, giscus.app에서 저장소 이름을 입력하는 순간 GitHub GraphQL API를 통해 자동으로 조회해서 채워줍니다. 따라서 별도로 ID를 찾아볼 필요가 없습니다.
4단계 (선택): 다크모드 연동
블로그에 다크모드 토글이 있다면, 토글할 때 giscus 테마도 함께 바꿔줘야 해요! giscus는 iframe으로 렌더링되기 때문에, 테마를 바꾸려면 postMessage를 통해 메시지를 보내야 해요.
그래서 저는 CustomEvent 로 두 컴포넌트를 연결했슴다
1. ThemeToggle에서 테마 변경 시 이벤트 발행
// ThemeToggle.jsx
const toggleTheme = () => {
// ... classList/localStorage 업데이트
// giscus 등 구독자에게 테마 변경 알림
window.dispatchEvent(
new CustomEvent('themechange', { detail: { theme: newTheme } })
);
};
2. [slug].astro에서 이벤트 수신 후 giscus에 전달
window.addEventListener('themechange', (e) => {
const iframe = document.querySelector('iframe.giscus-frame');
if (!iframe) return;
iframe.contentWindow.postMessage(
{ giscus: { setConfig: { theme: e.detail.theme } } },
'https://giscus.app'
);
});
이렇게 하면 토글 시 giscus 테마도 실시간으로 함께 바뀌어요 👍
결과
이제 각 블로그 포스트 하단에 댓글 영역이 생겼습니다! GitHub 계정만 있으면 누구나 댓글을 달 수 있고, 리액션 이모지도 남길 수 있어요!
정적 사이트인데도 서버 하나 없이 댓글 기능을 붙이다니!! 세상 참 편해졌네요!!
혹시 댓글 기능이 잘 작동하는지 궁금하시다면…
👇 아래에 테스트 댓글 한 번 남겨주세요! 👇