자동으로 설정되는 것들
광고를 제대로 운영하려면 여러 도구가 필요합니다. 구글 광고 계정, 분석 도구, 인스타그램 픽셀, 검색 등록까지. 이것들을 하나하나 직접 설정하려면 몇 주가 걸리고, 하나라도 잘못 설정하면 트래킹이 조용히 망가집니다.
레이니는 이 모든 작업을 도메인 연결 한 번으로 자동화했습니다.
자동으로 만들어지는 것들
도메인 DNS 인증이 완료되면 다음이 모두 자동으로 생성되고 연결됩니다.
| 서비스 | 해주는 일 |
|---|---|
| Google Ads 계정 | 구글 광고 캠페인 운영. 예약/채팅 전환 액션 자동 설정 |
| Google Analytics 4 | 홈페이지 방문자 분석. 어디서 얼마나 오는지 추적 |
| Meta 광고 계정 | 인스타그램/페이스북 광고 운영 |
| Meta 픽셀 | 인스타 광고를 본 사람이 예약했는지 추적 |
| Google Search Console | 구글 검색에 홈페이지가 잘 등록됐는지 확인 |
이 중 하나라도 빠지거나 잘못 연결되면 트래킹이 제대로 되지 않습니다. 레이니는 전체를 한 번에 올바르게 세팅합니다.
광고 계정은 레이니가 관리합니다
레이니는 마케팅 운영까지 포함하는 서비스이며, 광고 계정을 직접 만들고 관리합니다.
병원이 해야 할 일은 다음입니다.
- 월 광고 예산 상한 승인
- 광고 소재(로고, 클리닉 사진, 시술 정보) 제공
- 집행 전 광고 소재 최종 검토
캠페인 기획, 타겟 설정, 입찰 관리, 최적화는 레이니가 담당합니다.
나중에 다른 곳으로 옮기고 싶다면
레이니와 계약을 종료할 때 광고 계정은 병원에게 그대로 이전됩니다. 캠페인 이력, 전환 데이터, 광고 학습 결과가 모두 보존됩니다. 데이터 잠금(lock-in)은 없습니다.
광고 계정 소유·결제 모델 (기술 상세)
레이니 도입을 결정한 클리닉이 자주 묻는 질문:
"우리는 이미 Google Ads 계정과 Meta 광고 계정이 있는데, 그걸 그대로 쓰면 안 되나요?"
답: 레이니는 Plask MCC가 생성·관리하는 광고 계정만 사용합니다 (기존 계정 연결 옵션 없음). 결제 또한 Plask를 통해서 진행됩니다 (Google/Meta 직접 결제 옵션 없음). 레이니는 계정 생성·트래킹 인프라·캠페인 운영·결제 정산을 모두 포함하는 end-to-end 마케팅 서비스이기 때문에 이 구조가 필요합니다.
한눈에 보기
| 항목 | 레이니 모델 |
|---|---|
| 광고 계정 소유자 | Plask MCC 산하 child 계정 (Google Ads), Plask Business Manager 산하 ad account (Meta) |
| 계정 생성 시점 | 커스텀 도메인 DNS 인증 즉시 자동 생성 |
| 캠페인 운영 | Plask (기획·생성·입찰·최적화·소재 제작), 클리닉은 예산 상한 승인·소재 검토 |
| 트래킹 인프라 관리 | Plask (전환 액션, 픽셀, CAPI, Enhanced Conversions, Consent Mode) |
| 광고비 결제 | Plask가 Google/Meta에 직접 결제, 클리닉은 Plask에 월 정산 |
| 계정 이전 (클리닉 해지 시) | Move sub-account로 클리닉에 전체 이관, 계약상 30일 보장 |
기존 계정을 그대로 쓸 수 없는 이유
기존 계정을 그대로 쓰려고 하면 클리닉이 직접 처리해야 하는 작업들이 있습니다. 레이니는 이를 전부 제거합니다.
1. Developer Token 승인
Google Ads API를 사용하려면 모든 광고 계정이 Developer Token으로 인증해야 합니다. 이 토큰은 Google이 사람이 직접 검토해서 승인하는 자원이며, 의료 카테고리는 추가 검증이 요구됩니다.
클리닉이 본인 계정으로 직접 하려면: Google Cloud 프로젝트 생성 → Google Ads API 활성화 → Developer Token 신청서 작성 → Google 승인 대기 3일3주 → basic access (15,000 호출/일 제한) → standard access 신청 → 추가 12주 대기.
레이니: Plask는 이미 standard access developer token을 보유. 새 child 계정이 생성되는 즉시 API 호출 가능. 셋업 시간 0초.
2. OAuth2 동의와 refresh token 관리
Google Ads API는 OAuth2 refresh token 기반입니다. 본인 계정을 쓰려면 Google Cloud 프로젝트, OAuth client ID, OAuth consent screen 검증(추가 1~2주), 사용자 동의 화면, refresh token 저장을 클리닉이 직접 해야 합니다. 운영 중에 refresh token이 만료되면 모든 트래킹이 조용히 멈춥니다.
레이니: Plask가 1회 OAuth 동의 → refresh token이 fleet 전체를 커버. 클리닉 운영자는 Google Cloud Console을 한 번도 볼 일이 없습니다.
3. 전환 액션 카테고리의 정확성
Google Ads의 Smart Bidding은 전환 액션의 category 값에 따라 학습 모델을 다르게 적용합니다:
| 카테고리 | Smart Bidding의 반응 |
|---|---|
OTHER (대부분의 대행사 기본값) | 학습 신호를 약하게 처리 → 입찰 효율 저하 |
PURCHASE (예약을 구매로 잘못 분류) | 가치 기반 입찰이 잘못된 매출 추정으로 작동 |
SUBMIT_LEAD_FORM (정확) | Lead generation 모델로 학습 → 효율 최적화 |
기존 클리닉 계정 대부분에는 5~10개의 중복·broken 전환 액션이 쌓여 있고, 카테고리가 OTHER이며 가치(value)가 0으로 설정되어 있습니다. Smart Bidding이 이 불량 데이터로 학습한 결과가 낮은 ROAS입니다.
레이니: 자동 프로비저닝이 정확한 카테고리(SUBMIT_LEAD_FORM, ENGAGEMENT)와 가치(35,000 KRW Lead, 5,000 KRW Chat)로 전환 액션을 생성합니다. 잘못 설정할 여지가 없습니다.
4. Customer Data Terms — 1회 동의가 모든 클리닉에 전파
Enhanced Conversions for Leads (해시 이메일·전화 자동 업로드)를 활성화하려면 Customer Data Terms에 동의해야 합니다. Google Ads는 이 약관을 login-customer-id 헤더의 계정에서 검사합니다. 레이니는 모든 API 호출에서 login-customer-id = Plask MCC로 설정하므로:
- Plask MCC 1회 동의로 모든 child 클리닉에 영구 적용 (empirically verified)
- 새 클리닉은 0번의 클릭으로 Enhanced Conversions 활성화
5. 신규 클리닉 셋업 시간
| 모델 | 셋업 시간 |
|---|---|
| 레이니 (Plask MCC) | DNS 인증 후 수 초 |
| 기존 계정 연결 (가상) | 2~6주 (Google 승인 + 수동 셋업 + 검증) |
결제 흐름
Plask가 Google/Meta에 광고비를 직접 결제하고, 클리닉은 Plask에게 월 단위로 광고 집행액 + 서비스 이용료를 정산합니다. 광고비에는 mark-up이 없으며, Google/Meta 원본 인보이스를 요청 시 제공합니다.
해지 시 계정 이전 — Move sub-account
계약 해지 시 광고 계정은 클리닉에게 이전됩니다. Google Ads의 Move sub-account 기능으로 Plask MCC에서 클리닉이 지정한 다른 소유자(클리닉 본인 MCC, standalone 계정, 혹은 다른 대행사)로 이관할 수 있으며, 이 과정에서 다음이 모두 보존됩니다:
- 모든 캠페인 구조와 이력
- 모든 전환 액션과 이력 데이터
- Custom audience와 lookalike 모델
- Smart Bidding 학습 결과
- 광고 계정 ID (변경 안 됨)
- 광고비 결제 이력
Plask는 계약상 30일 이내 이전을 보장합니다. Meta Ads의 경우도 동일합니다. Plask Business Manager 산하 ad account를 클리닉 본인 Business Manager로 이전하는 Asset Transfer 기능을 제공합니다.
프로비저닝 상세 — 3단계 자동 생성
대시보드 설정 > 연동 > 커스텀 도메인에서 도메인을 추가하고 DNS 인증이 완료되면, 다음 3단계가 자동으로 실행됩니다.
Phase 1: 독립 계정 생성
DNS 인증 즉시, 서로 의존성이 없는 4개 리소스가 병렬로 생성됩니다.
Google Ads 고객 계정
| 항목 | 값 |
|---|---|
| API | Google Ads API customers/{MCC}:createCustomerClient |
| 생성 위치 | Plask MCC (Laney AI 464-669-1503) 하위 child 계정 |
| 통화 | KRW (현재 하드코딩, 향후 매개변수화 예정) |
| 시간대 | Asia/Seoul |
생성 후 child의 customer_id가 integrations.google_ads.customer_id에 저장됩니다.
MCC (Manager Customer Center) 계층 구조
레이니는 단일 MCC 모델을 사용합니다. Plask가 운영하는 1개의 MCC 아래에 모든 클리닉 child 계정이 있습니다.
Plask MCC: Laney AI (4646691503)
│
├─ child: 콜라겐닥터 (1665670449)
├─ child: 달임채한의원 (4403374997)
├─ child: 레이니 클리닉 (5439299119)
├─ child: 아이니의원 (7947660944)
├─ child: 오아로피부과 (3089615421)
└─ ... (각 클리닉마다 1개 child, 30+)모든 API 호출의 인증 패턴
레이니는 모든 Google Ads API 호출에서 동일한 헤더를 사용합니다:
Authorization: Bearer {OAuth2 access token, refresh token으로 mint}
developer-token: {Plask Google Ads developer token, MCC scope}
login-customer-id: {Plask MCC ID = 4646691503} ← 항상 MCC, 절대 child 아님URL path에는 작업 대상 child의 ID가 들어갑니다:
POST /v23/customers/1665670449:uploadClickConversions
└─ child customer ID (path)
Headers: login-customer-id: 4646691503
└─ MCC (auth context)이 패턴이 의미하는 것:
- OAuth2 동의 1회로 N개 클리닉 관리: Plask가 Google에 OAuth refresh token을 1회만 받음. 클리닉 운영자가 Google에 별도 OAuth 동의를 할 필요 없음.
- Developer token 1개로 fleet 전체 커버: Google이 developer token을 MCC 단위로 승인하므로, 한 번 승인받으면 모든 child 호출에 사용 가능.
- 하나의 quota pool 공유: 모든 클리닉의 conversion upload가 Plask MCC의 API quota를 공유.
- 중앙 관제: Plask가 MCC 대시보드에서 모든 클리닉의 광고 성과·에러·청구 상태를 한 화면에서 봄.
- 법적 합의도 1회: Customer Data Terms 같은 약관은
login-customer-id(MCC) 기준으로 검사되므로 MCC 1회 동의가 모든 child에 자동 전파.
일반 한국 대행사 셋업과의 차이
| 항목 | 일반 대행사 | 레이니 MCC 모델 |
|---|---|---|
| 클리닉당 OAuth 동의 | 매번 받음 (운영자 부담) | 1회 (Plask가 받음) |
| Developer token | 클리닉마다 신청 → 승인 대기 | Plask 1개로 전체 커버 |
| API quota | 클리닉마다 별도 할당, 작음 | MCC pool 공유, 큼 |
| 광고 성과 통합 보기 | 불가능 | MCC 대시보드 1화면 |
| 신규 클리닉 추가 시간 | 며칠~몇 주 (Google 승인 대기) | DNS 인증 즉시 (몇 초) |
| Customer Data Terms 동의 | 클리닉마다 (대부분 안 함) | MCC 1회로 모두 적용 |
Google Analytics 4 속성
| 항목 | 값 |
|---|---|
| API | GA4 Admin API properties.create |
| 업종 | HEALTHCARE |
| 데이터 스트림 | 웹 (커스텀 도메인 URL) |
속성 생성 후 웹 데이터 스트림이 추가되어 측정 ID(G-XXXXXXXXXX)가 발급됩니다. integrations.google_analytics.measurement_id에 저장됩니다.
Meta Ads 계정
| 항목 | 값 |
|---|---|
| API | Meta Marketing API /{business_id}/adaccount |
| 생성 위치 | Plask Business Manager 하위 |
| 시스템 사용자 | 자동 할당 (MANAGE, ADVERTISE, ANALYZE 권한) |
Google Search Console
| 항목 | 값 |
|---|---|
| API | Site Verification API v1 |
| 인증 방식 | META 태그 (<meta name="google-site-verification">) |
| 자동 배포 | 랜딩 페이지 <head>에 자동 삽입 |
인증 토큰이 integrations.google_search_console.verification_token에 저장되면, 랜딩 페이지의 generateMetadata()가 이를 <meta> 태그로 자동 삽입합니다. 다음 페이지 렌더링 시 Google이 인증을 완료합니다.
Phase 2: 의존 리소스 생성
Phase 1에서 Meta Ads 계정이 성공적으로 생성된 경우에만 실행됩니다.
Meta Pixel
| 항목 | 값 |
|---|---|
| API | /{ad_account_id}/adspixels |
| 이름 | {조직명} Pixel |
Pixel ID가 integrations.meta_pixel.pixel_id에 저장되면, 랜딩 페이지의 AnalyticsScripts 컴포넌트가 Meta Pixel 초기화 스크립트를 자동으로 삽입합니다.
Phase 3: 전환 액션 + 연결
Phase 1에서 Google Ads 계정과 GA4 속성이 모두 생성된 경우 실행됩니다.
Google Ads 전환 액션
각 조직에 Lead(폼 제출)와 Chat(채팅 시작) 2개의 전환 액션이 생성됩니다.
| 전환 유형 | 카테고리 | 기본 가치 | 통화 |
|---|---|---|---|
| Lead Form Submission | SUBMIT_LEAD_FORM | 35,000 | KRW |
| Chat Start | ENGAGEMENT | 5,000 | KRW |
전환 액션 생성 후 태그 스니펫에서 전환 라벨을 추출합니다. 이 라벨은 클라이언트 측 gtag('event', 'conversion', { send_to: 'AW-XXX/label' })에서 사용됩니다.
저장 형태:
{
"google_ads": {
"customer_id": "5439299119",
"conversion_id": "AW-5439299119",
"conversions": {
"lead": {
"action_id": "7558406363",
"label": "SOnpCNvBkJQcEIus16FD",
"value": 35000,
"currency": "KRW"
},
"chat": {
"action_id": "7558765374",
"label": "QUs4CL62ppQcEIus16FD",
"value": 5000,
"currency": "KRW"
}
}
}
}GA4 ↔ Google Ads 연결
| 항목 | 값 |
|---|---|
| API | GA4 Admin API properties/{id}/googleAdsLinks |
| 개인화 광고 | 활성화 (adsPersonalizationEnabled: true) |
이 연결을 통해:
- GA4에서 만든 **잠재고객(Audience)**을 Google Ads에서 리마케팅 타겟으로 사용 가능
- Google Ads 캠페인 데이터가 GA4 보고서에 표시
- 자동 태그 지정(auto-tagging)으로 캠페인 성과 분석 연동
Customer Data Terms — Plask MCC에 1회만, 모든 클리닉 영구 적용
Google Ads의 Customer Data Terms (고객 데이터 약관)는 Enhanced Conversions의 user_identifiers (해시 이메일·전화) 업로드를 활성화하는 1회성 법적 합의입니다.
이 약관은 login-customer-id 헤더의 계정에서 검사됩니다. 레이니는 모든 Google Ads API 호출에서 login-customer-id를 항상 Plask MCC (Laney AI 464-669-1503)로 설정합니다. 따라서:
- Plask MCC에서 1회 동의 → 모든 clinic child 계정에 영구 적용
- 새로 생성되는 clinic도 자동 적용 (별도 작업 0)
- 이미 동의 완료 (2026-04 기준)
empirically 검증됨: GAQL SELECT customer.conversion_tracking_setting.accepted_customer_data_terms FROM customer 쿼리 결과:
Laney AI MCC (4646691503): terms=true ← 활성
콜라겐닥터 (1665670449): terms=undefined ← child는 미설정이지만
달임채한의원 (4403374997): terms=undefined Enhanced Conversions
레이니 클리닉 (5439299119): terms=undefined 업로드는 정상 작동함
... (30+ clinic 모두 동일)child 계정은 자체 약관 설정이 없어도, MCC 약관이 캐리어 역할을 합니다.
클리닉 운영자가 직접 할 일: 없음. Plask가 MCC에 1회 동의함으로써 모든 클리닉이 자동으로 Enhanced Conversions를 사용합니다.
프로비저닝 결과: integrations JSONB
모든 프로비저닝이 완료되면, organizations.integrations JSONB 컬럼에 다음 구조가 저장됩니다:
{
"google_analytics": {
"measurement_id": "G-XXXXXXXXXX",
"property_id": "531057709",
"link_url": "https://analytics.google.com/..."
},
"google_ads": {
"customer_id": "1665670449",
"conversion_id": "AW-1665670449",
"link_url": "https://ads.google.com/...",
"conversions": {
"lead": { "action_id": "...", "label": "...", "value": 35000, "currency": "KRW" },
"chat": { "action_id": "...", "label": "...", "value": 5000, "currency": "KRW" }
}
},
"meta_ads": {
"account_id": "2582870765447150",
"link_url": "https://business.facebook.com/..."
},
"meta_pixel": {
"pixel_id": "1181102384178794"
},
"google_search_console": {
"verification_token": "YtN2gKqp...",
"verified": true,
"link_url": "https://search.google.com/..."
}
}개인정보 동의 처리 — Consent Mode v2
홈페이지에 방문한 환자의 광고 추적 동의를 어떻게 처리하는지에 대한 항목입니다.
광고 차단기·iOS ITP·동의 거부 사용자에게 픽셀이 차단되면 데이터를 잃습니다. Google은 2024년부터 Consent Mode v2가 없으면 EU 사용자에게 광고 노출 자체를 막는 정책을 도입했습니다.
레이니는 모든 테넌트 랜딩 페이지에 Consent Mode v2를 올바른 타이밍으로 활성화합니다.
Consent Mode v2의 4개 카테고리
Consent Mode v2는 광고·분석 도구가 사용자 데이터를 어떻게 다룰지를 4개의 독립된 동의 카테고리로 표현합니다.
| 카테고리 | denied가 되면... |
|---|---|
ad_storage | 광고 쿠키(_gcl_au 등) 저장 차단. Google Ads가 리마케팅 ID를 만들지 못함. 광고 클릭 어트리뷰션은 gclid URL 파라미터에 의존 |
analytics_storage | GA4 쿠키(_ga, _ga_*) 저장 차단. 클라이언트 ID 없음. GA4는 익명 집계 데이터만 수집 (cookieless ping) |
ad_user_data | Google에 사용자 데이터를 광고 목적으로 전송 금지. Enhanced Conversions의 hashed email/phone이 차단됩니다 |
ad_personalization | 리마케팅 오디언스, 개인화 광고 차단. 광고는 노출되지만 일반 광고로만 |
beforeInteractive 타이밍 — 왜 이게 결정적인가
Consent Mode v2의 핵심 규칙: gtag('consent', 'default')를 어떤 Google/Meta 태그보다 먼저 호출해야 합니다. 늦으면 태그가 legacy denied 모드로 작동하고, 나중에 grant해도 복구되지 않습니다.
레이니의 ConsentModeScripts 컴포넌트 (packages/tracking/src/react/consent-scripts.tsx):
<Script id="consent-defaults" strategy="beforeInteractive">
{`window.dataLayer=window.dataLayer||[];
function gtag(){dataLayer.push(arguments);}
gtag('consent','default',${JSON.stringify({
ad_storage: 'granted', // 또는 denied
analytics_storage: 'granted',
ad_user_data: 'granted',
ad_personalization: 'granted',
wait_for_update: 500
})});`}
</Script>strategy="beforeInteractive"는 Next.js가 이 스크립트를 <head> 안에 동기적으로 삽입하게 합니다. 페이지가 React로 hydrate되기 전, 다른 모든 afterInteractive 스크립트(GA4 gtag.js, Google Ads, Meta Pixel)가 로드되기 전에 실행됩니다.
타이밍 시퀀스:
1. <head> 파싱 시작
2. consent-defaults 스크립트 동기 실행 ✓ (gtag('consent', 'default', ...))
3. <body> 파싱
4. afterInteractive 스크립트 큐에 GA4 gtag.js, Meta Pixel, Google Ads 추가
5. React hydration
6. afterInteractive 스크립트들 실행 → 이 시점에 이미 dataLayer에 consent 상태가 있음
7. 각 태그가 dataLayer에서 consent를 읽어 자기 동작 결정만약 beforeInteractive가 아니라 afterInteractive로 했다면, 4번과 6번의 순서가 보장되지 않아서 race condition이 발생합니다.
wait_for_update: 500의 의미
gtag('consent', 'default', { ..., wait_for_update: 500 });이 값은 "동의 UI가 사용자 선택을 등록하는 데 걸릴 시간을 500ms 기다리겠다"는 의미입니다. 이 500ms 동안:
- 모든 태그가 큐에 쌓이고 실행되지 않음
- 동의 UI가
gtag('consent', 'update', { ad_storage: 'granted', ... })를 호출하면 → 큐가 즉시 flush - 500ms 안에 update가 안 오면 → 기본값으로 모든 태그가 firing 시작
레이니는 동의 UI가 없으므로 이 500ms는 사실상 무의미합니다 (기본값이 즉시 적용). 그러나 향후 동의 UI를 도입하면 이 값을 800~1000ms로 늘려 사용자에게 결정 시간을 주는 것이 표준입니다.
레이니의 현재 기본값 — granted (실용주의)
레이니의 두 consumer 모두 4개 카테고리 모두 granted로 override합니다:
<ConsentModeScripts
defaults={{
ad_storage: "granted",
analytics_storage: "granted",
ad_user_data: "granted",
ad_personalization: "granted"
}}
/>위치:
apps/landing/app/[tenant]/[locale]/layout.tsx:123— 멀티테넌트 클리닉 랜딩apps/laney-landing/src/components/providers.tsx:42— 레이니 자체 마케팅 사이트
패키지
@workspace/tracking의 기본값은denied(privacy-first)이며, 모든 consumer가 명시적으로 grant override를 합니다. 의도적인 설계로, 새 consumer가 실수로 default를 쓰면 안전 측(denied)으로 떨어지도록 한 것입니다.
granted 기본값의 trade-off
| 항목 | granted (현재) | denied (privacy-first) |
|---|---|---|
| 페이지 로드 시 이벤트 차단 | 없음 | 모든 광고/분석 태그 차단 |
| GA4 데이터 양 | 100% | 동의 UI 통과한 사용자만 ( |
| Google Ads 리마케팅 | 활성 | 동의 후 활성 |
| Meta Pixel 작동 | 정상 | 정상 (Consent Mode는 Meta를 통제 안 함) |
| EMQ 점수 | 7.0+ | 6.0~ (사용자 데이터 미전송으로) |
| 한국 트래픽 적합성 | 적합 | UX 마찰 큼 |
| EU/GDPR 트래픽 적합성 | 이론상 부적합 | 적합 |
Consent Mode가 통제하지 않는 것 — Meta Pixel
Consent Mode v2는 Google 도구(gtag.js, GA4, Google Ads)만 통제합니다. Meta Pixel은 별도의 동의 메커니즘(Limited Data Use, LDU)을 사용합니다.
// Meta LDU는 별도 호출
fbq('dataProcessingOptions', ['LDU'], 1, 1000); // CCPA (캘리포니아)레이니는 현재 Meta LDU를 활성화하지 않습니다. Meta는 EU/CCPA 영역 외에서는 LDU를 강제하지 않으므로, 한국 트래픽에는 영향 없습니다.
Region별 기본값 — 코드 인프라는 있고, 활성화는 향후
ConsentModeScripts 컴포넌트는 ISO 3166-2 코드 리스트를 받는 region prop을 지원합니다:
<ConsentModeScripts
defaults={{ ad_storage: "denied", ... }} // 이 region에 대한 기본값
region={["EU", "EEA", "GB", "CH"]} // 이 코드에 해당하는 사용자에게만 적용
/>레이니는 이 매개변수를 현재 사용하지 않습니다. 향후 EU 트래픽이 의미 있어지면 다음과 같이 활성화할 계획입니다.
{/* EU 지역: 명시적 동의 전까지 denied */}
<ConsentModeScripts
defaults={{ ad_storage: "denied", analytics_storage: "denied",
ad_user_data: "denied", ad_personalization: "denied" }}
region={["AT", "BE", "BG", "HR", "CY", "CZ", "DK", "EE", "FI", "FR",
"DE", "GR", "HU", "IE", "IT", "LV", "LT", "LU", "MT", "NL",
"PL", "PT", "RO", "SK", "SI", "ES", "SE", "GB", "CH", "NO", "IS", "LI"]}
/>
{/* 그 외 지역 (한국 포함): granted */}
<ConsentModeScripts
defaults={{ ad_storage: "granted", analytics_storage: "granted",
ad_user_data: "granted", ad_personalization: "granted" }}
/>동의 업데이트 메커니즘 — pushConsentUpdate
레이니는 동의 UI가 사용자 선택을 등록할 때 호출할 함수를 이미 export합니다 (packages/tracking/src/client/datalayer.ts:60):
import { pushConsentUpdate } from '@workspace/tracking/client/datalayer';
// 사용자가 cookie banner에서 "분석만 허용" 선택 시
pushConsentUpdate({
analytics_storage: 'granted',
ad_storage: 'denied',
ad_user_data: 'denied',
ad_personalization: 'denied'
});
// 또는 사용자가 "모두 허용" 선택 시
pushConsentUpdate({
ad_storage: 'granted',
analytics_storage: 'granted',
ad_user_data: 'granted',
ad_personalization: 'granted'
});이 함수는 내부적으로 gtag('consent', 'update', state)를 호출하며, 큐에 쌓여있던 모든 태그를 즉시 flush합니다.
현재는 어디서도 호출되지 않습니다. 동의 UI가 없기 때문이며, 향후 동의 banner 컴포넌트를 만들면 이 함수를 호출하기만 하면 됩니다.
Consent Mode 검증
1. 브라우저 DevTools에서 dataLayer 검사
// 개발자 도구 콘솔에서
window.dataLayer.filter(e => e[0] === 'consent')페이지 로드 직후 ['consent', 'default', { ad_storage: 'granted', ... }] 항목이 보여야 합니다.
2. Network 탭에서 consent 매개변수 확인
GA4 collect 요청 (collect?v=2&...) 의 query parameter에 gcs=G111 (모두 granted) 또는 gcs=G100 (denied 일부) 형태가 포함됩니다.
3. Google Tag Assistant Companion
Chrome 확장 Tag Assistant Companion을 설치하면 페이지의 모든 태그가 어떤 consent 상태로 동작하는지 시각적으로 확인할 수 있습니다.
셋업 비교
| 항목 | 표준 셋업 | 레이니 |
|---|---|---|
| Consent Mode v2 활성화 | 미설정 흔함 | 정상 활성화 |
gtag('consent', 'default') 호출 시점 | 안 함, 또는 너무 늦음 → 모든 태그가 legacy denied로 동작 | <head> 안에 동기 삽입 (beforeInteractive) |
| 4개 카테고리 분리 처리 | 미처리 | 4개 별도 처리 |
wait_for_update 설정 | 없음 | 500ms 기본 |
| Google EU 광고 정책 (2024+) 준수 | 위반 (광고 노출 거부될 수 있음) | 준수 |
| Smart Bidding 학습 신호 | 손실 30~50% | 손실 ~0% |
| Region별 기본값 (EU만 denied) | 미지원 | 코드 인프라 있음 (region prop), 향후 활성화 |
대시보드에서 확인
프로비저닝된 모든 연동은 설정 > 연동 페이지에서 확인할 수 있으며, 각 항목에 해당 플랫폼 대시보드로의 바로가기 링크가 제공됩니다.
- Google Analytics → GA4 보고서
- Google Ads → Ads 계정 관리
- Meta Ads → 광고 관리자
- Meta Pixel → 이벤트 관리자
- Google Search Console → Search Console 대시보드