Skip to content

웹훅

동결된 서피스 (대시보드 UI)

클라우드 대시보드의 전용 웹훅 페이지는 명시적인 제품 결정(2026-07-04, 저장소의 docs/FROZEN_SURFACES.md 참조)에 의해 현재 동결 상태입니다: 사이드바 항목이 숨겨져 있고 /webhooks/dashboard로 리디렉션됩니다. 아래에 설명된 웹훅 API와 전달 파이프라인은 계속 운영 중이며 유지됩니다. 단, 동결이 해제될 때까지 새로운 웹훅 기능 작업은 계획되어 있지 않습니다. 여기에 문서화된 REST API 서피스를 통해 웹훅을 관리하세요.

클라우드 전용

웹훅은 클라우드 버전에서만 사용할 수 있습니다.

웹훅을 사용하면 ADHDev Cloud가 머신 및 에이전트 이벤트를 자체 HTTP 엔드포인트로 전송할 수 있습니다.

현재 주요 동작:

  • 웹훅 API는 운영 중입니다.
  • 전용 /webhooks 대시보드 페이지는 현재 안정적인 표준 탐색 서피스가 아닙니다.
  • 페이로드, 이벤트, 전달 히스토리 구조의 정식 계약은 REST API 레퍼런스를 사용하세요.
  • 웹훅 생성/토글/삭제/테스트 작업은 최근 로그인이 보호하는 클라우드 계정 작업으로, API 키가 아닌 신선한 대시보드 세션 JWT가 필요합니다.

웹훅 생성

현재 로그인된 클라우드 대시보드 세션에서 웹훅을 생성하세요. 요청 본문은 다음과 같습니다:

json
{
  "url": "https://example.com/hooks/adhdev",
  "events": ["agent:generating_completed", "agent:waiting_approval"]
}

만료된 브라우저 세션이나 API 키로 변경 웹훅 엔드포인트를 호출하면 서버는 훅을 프로비저닝하는 대신 403 RECENT_LOGIN_REQUIRED를 반환합니다.

생성 응답에는 다음이 포함됩니다:

  • 웹훅 레코드
  • 서명 검증을 위해 한 번만 표시되는 secret

모든 지원 이벤트를 구독하려면 events["*"]를 사용하세요.

이벤트

이벤트트리거
agent:generating_started에이전트가 응답 생성을 시작함
agent:generating_completed에이전트가 생성을 완료함
agent:waiting_approval에이전트가 승인을 기다리는 중
agent:error에이전트가 오류를 만남
webhook:test테스트 전달이 명시적으로 요청됨

페이로드 형식

json
{
  "event": "agent:generating_completed",
  "payload": {
    "chatTitle": "Claude Code · myproject",
    "ideType": "claude-code",
    "duration": 42,
    "timestamp": 1714000000000
  },
  "timestamp": 1714000000000
}

서명 검증

각 웹훅 요청에는 다음이 포함됩니다:

  • X-ADHDev-Signature
  • X-ADHDev-Event

서명 형식:

text
X-ADHDev-Signature: t=1714000000000,v1=a3f9c2b1...

원시 요청 본문을 기준으로 검증하세요.

js
import crypto from 'crypto'

function verifySignature(body, signature, secret) {
  const parts = Object.fromEntries(signature.split(',').map((p) => p.split('=')))
  const timestamp = parts.t
  const received = parts.v1
  const payload = `${timestamp}.${body}`
  const expected = crypto
    .createHmac('sha256', secret)
    .update(payload)
    .digest('hex')

  return crypto.timingSafeEqual(
    Buffer.from(received),
    Buffer.from(expected)
  )
}

// Express 예시
app.post('/webhook', express.raw({ type: 'application/json' }), (req, res) => {
  const sig = req.headers['x-adhdev-signature']
  const body = req.body.toString('utf8')
  if (!verifySignature(body, sig, process.env.WEBHOOK_SECRET)) {
    return res.status(401).send('Invalid signature')
  }
  const event = JSON.parse(body)
  // 이벤트 처리...
  res.sendStatus(200)
})
python
import hmac
import hashlib

def verify_signature(body: bytes, signature: str, secret: str) -> bool:
    parts = dict(p.split('=', 1) for p in signature.split(','))
    timestamp = parts.get('t', '')
    received = parts.get('v1', '')
    payload = f"{timestamp}.{body.decode('utf-8')}".encode()
    expected = hmac.new(secret.encode(), payload, hashlib.sha256).hexdigest()
    return hmac.compare_digest(received, expected)

# Flask 예시
@app.route('/webhook', methods=['POST'])
def webhook():
    sig = request.headers.get('X-ADHDev-Signature', '')
    if not verify_signature(request.data, sig, WEBHOOK_SECRET):
        return 'Invalid signature', 401
    event = request.get_json()
    # 이벤트 처리...
    return '', 200

웹훅 시크릿은 웹훅 생성 시 한 번만 표시됩니다 — 안전하게 저장하세요.

관리 엔드포인트

text
GET    /api/v1/webhooks
POST   /api/v1/webhooks
PATCH  /api/v1/webhooks/{webhookId}
DELETE /api/v1/webhooks/{webhookId}
GET    /api/v1/webhooks/{webhookId}/deliveries?limit=20
POST   /api/v1/webhooks/{webhookId}/test

GET 엔드포인트가 가장 안전한 자동화 서피스입니다. 변경 엔드포인트(POST, PATCH, DELETE, test)는 최근 로그인이 보호하는 대시보드 세션 작업입니다.

재시도 정책

실패한 전달은 지수 백오프로 최대 3회 재시도됩니다.

플랜 제한

플랜최대 웹훅 수
Free2
Pro10
Team50
Enterprise무제한

호스팅 클라우드 문서는 여기에 있습니다. 오픈소스 및 셀프호스트 문서는 OSS 레포지토리에 있습니다.