본문으로 건너뛰기
cccskills
무료GitHub에 공개한국어 소개

agent-runtime-hooks

에이전트 실행 단계, 도구 호출, 사람의 승인, 컨텍스트 압축, 하위 에이전트 호출에 훅을 등록하는 방법을 안내합니다. 이벤트를 관찰하고 로컬 도구 결과를 모의하거나 설정에 따라 웹훅으로 도구 호출을 허용 또는 거부할 수 있습니다.

원문원문 설명 보기

Use for agent lifecycle hooks, tool mocks, intervention, sub-agent calls and context compression.

lobehub/lobehub스타 83,500(GitHub 83,500 + cccskills 0)

실행 점수 미검증

설치 방법 보기

이럴 때 유용합니다

  • 에이전트 단계와 오류 기록
  • 테스트 중 도구 결과 모의
  • 웹훅으로 도구 호출 허용 또는 거부
  • 승인과 하위 에이전트 흐름 추적

한국어 소개

할 수 있는 일

이 가이드는 에이전트 실행 수명 주기의 여러 단계에 훅을 등록하고 이벤트를 처리하는 방법을 설명합니다. 단계의 시작과 완료, 도구 호출과 오류, 사람의 승인, 컨텍스트 압축, 하위 에이전트 호출, 최종 실행 상태를 관찰할 수 있습니다. 로컬 핸들러로 도구 결과를 모의할 수 있으며, 웹훅으로 이벤트를 알리거나 결정 기능을 설정해 도구 호출을 허용하거나 거부할 수 있습니다. 이벤트에 포함되는 실행 ID, 도구 정보, 결과와 웹훅 페이로드 및 전송 오류 동작도 다룹니다.

이럴 때 유용합니다

에이전트 실행을 관찰하거나 운영 중 개입하는 기능을 구현할 때 활용할 수 있습니다. 테스트를 위해 도구 결과를 바꾸거나 승인과 하위 에이전트가 포함된 흐름을 추적할 때도 도움이 됩니다.

사용 예시

  • “도구 실행 전에 권한을 확인하는 웹훅 훅을 설정해 주세요.”
  • “이 에이전트의 단계와 오류를 기록하는 훅을 추가해 주세요.”
  • “테스트 중 도구 결과를 로컬에서 모의해 주세요.”

주의 사항

웹훅을 설정하고 동작시키려면 대상 URL이 필요합니다. 헤더에 환경 변수를 사용할 경우 허용 목록을 지정해야 하며, 비밀 값은 설정 저장 시가 아니라 전송 시점에 해석됩니다. 웹훅만으로 등록한 훅은 프로세스를 다시 시작한 뒤 함수 핸들러를 복원할 수 없습니다.

이 소개문은 공개된 SKILL.md를 바탕으로 AI(OpenAI Codex)가 작성했습니다. 정확한 사양은 아래 원문을 확인하세요.

문서 점검

AI가 SKILL.md의 내용에서 주의가 필요한 작업과 도입 전제를 확인했습니다. 점수는 실제로 실행한 결과(실행 검증)만으로 매깁니다.

안전성전송·삭제·명령 실행 등을 명시하고 있는가
B일부 부족웹훅으로 실행을 허용하거나 거부할 수 있지만 실패 동작 설명이 여러 설정에 나뉩니다.
도입의 용이성필요한 도구나 API 키가 적고 적혀 있는가
B일부 부족웹훅에 대상 URL과 환경 변수 허용 목록이 필요하다고 명시합니다.

점수에는 넣지 않았습니다. 2026년 10월 26일 기준으로 AI(OpenAI Codex)가 판정했습니다. 참고용이므로 설치 전에 원문도 확인해 주세요.

평가가 다르다고 생각되면 재검토를 요청하기

어느 항목이 왜 다르다고 생각하는지 적어 주세요. 로그인은 필요 없습니다. SKILL.md와 대조해 평가를 다시 만들고 이곳에 반영합니다.

이 양식은 reCAPTCHA로 보호되며 Google 개인정보처리방침 및 서비스 약관이 적용됩니다.

포함된 파일(1)

  • SKILL.md15.9 KB

SKILL.md(원문)

설치하기 전에 에이전트에게 전달되는 지시 내용을 확인할 수 있습니다.

Agent Runtime Hooks

Register lifecycle hooks through execAgent({ hooks }). HookDispatcher stores them per operation and dispatches them in registration order.

Hook Types

16 hook types across 5 categories:

execAgent({ hooks })
  │
  ├─ beforeStep ──────────── Before each step executes
  │     │
  │     ├─ [call_llm]        LLM inference
  │     │
  │     ├─ [call_tool]
  │     │     ├─ beforeToolCall ── Before tool executes (supports mocking)
  │     │     ├─ (tool execution)
  │     │     ├─ afterToolCall ─── After tool completes (optional result control)
  │     │     └─ onToolCallError ─ Tool threw an exception
  │     │
  │     ├─ [request_human_approve]
  │     │     ├─ beforeHumanIntervention ── Before agent pauses
  │     │     ├─ afterHumanIntervention ─── After approve/reject + resume
  │     │     └─ onStopByHumanIntervention ── User rejected, agent halted
  │     │
  │     ├─ [compress_context]
  │     │     ├─ beforeCompact ──── Before compression starts
  │     │     ├─ afterCompact ───── After compression completes
  │     │     └─ onCompactError ─── Compression failed
  │     │
  │     ├─ [callAgent] (via execSubAgentTask)
  │     │     ├─ beforeCallAgent ── Before sub-agent starts
  │     │     ├─ afterCallAgent ─── After creation/start returns
  │     │     └─ onCallAgentError ── Sub-agent failed
  │     │
  │     └─ afterStep ──────────── After step completes
  │
  ├─ (next step...)
  │
  ├─ onComplete ───────────── Operation reaches terminal state
  └─ onError ──────────────── Error during execution

Key Files

FileRole
packages/agent-runtime/src/types/hooks.tsEvent types and required/optional fields
apps/server/src/services/agentRuntime/hooks/types.tsRegistration and webhook types
apps/server/src/services/agentRuntime/hooks/HookDispatcher.tsRegistration, dispatch, local mocks, HTTP/QStash delivery
apps/server/src/services/agentRuntime/hooks/webhookPayload.tsEvent projection and email enrichment
apps/server/src/modules/AgentRuntime/adapters/toolCallHookContext.tsShared tool-event context builder
apps/server/src/modules/AgentRuntime/adapters/ServerToolTransport.tsTool notifications and execution results
apps/server/src/modules/AgentRuntime/RuntimeExecutors.tsTool, compression and human-intervention execution
apps/server/src/services/agentRuntime/AgentRuntimeService/ (executeStep/, intervention.ts)Step events and human-intervention continuation
apps/server/src/services/agentRuntime/CompletionLifecycle/index.tsTerminal events
apps/server/src/services/aiAgent/subAgentRuns.tsSub-agent events

Registration

const hooks: AgentHook[] = [
  {
    id: 'observe-step',
    type: 'afterStep',
    handler: async (event) => {
      console.log(event.operationId, event.stepIndex);
    },
  },
];
await aiAgentService.execAgent({ agentId, prompt, hooks });

Completion cleans up registrations through hookDispatcher.unregister(operationId).

Webhook Hooks

Webhook-only hooks deliver in both local and queue modes. For hooks with both handler and webhook, local dispatch calls the handler; queue dispatch uses the serialized webhook. Only webhook configuration is persisted, so functions are unavailable after a process restart.

const hook: AgentHook = {
  id: 'tool-notification',
  type: 'afterToolCall',
  matcher: '^fs/readFile$',
  webhook: {
    url: 'https://example.com/hooks',
    delivery: 'fetch',
    timeout: 5, // seconds; default 30
    headers: { Authorization: 'Bearer ${HOOK_TOKEN}' },
    allowedEnvVars: ['HOOK_TOKEN'],
  },
};
  • matcher is a regex against ${identifier}/${apiName}, supported only on tool events. Omitted, empty, or * matches all tools.
  • Header environment templates resolve only at send time from allowedEnvVars; persist templates, never resolved secrets.
  • Notifications ignore response content and may return HTTP 204.
  • beforeToolCall with responseHandling: 'toolCall' awaits an optional HTTP decision before tool execution. Return HTTP 2xx JSON with { "decision": "allow" } or { "decision": "deny", "reason": "禁止执行该操作" } to intervene. The type is { decision: 'allow' } | { decision: 'deny'; reason?: string }; a deny with an omitted or empty reason uses Blocked by beforeToolCall hook.. Denials preserve the reason in the tool result/card with classification hook_denied.
  • afterToolCall also accepts responseHandling: 'toolCall'. It synchronously checks the full request/result before archival and model consumption; deny replaces the original result with the receiver's optional reason in both content and blocked state. A deny with an omitted or empty reason uses Blocked by afterToolCall hook., following the same Blocked by ${type} hook. rule as beforeToolCall. The reason enters model context and the tool card, as with beforeToolCall. It does not undo tool side effects, retries, or charges. See the result-control contract for deferred completions and runtime boundaries.
  • Environment response modes are ignore (default notifications) and toolCall (optional decisions for both before and after). Only subscribed events are enabled. Replace removed toolResult/toolCallAndResult values with toolCall; use the events list to select after-only checking. Existing after responses with a valid decision now control results.
  • HTTP 204, empty successful bodies, invalid JSON, and JSON without a top-level decision (including arrays, scalars, null, or only the old nested hookSpecificOutput) are notification responses, even with onError: 'block'. Continue checking subsequent hooks; do not treat a notification as permission to skip later policies. Explicit invalid decisions, non-2xx status, oversized bodies, invalid UTF-8, network failures, and timeouts follow onError: 'continue' | 'block' (default continue); blocking uses hook_control_error as the tool-result content and reason for both before and after hooks. Cancellation never grants permission.
  • Extra response fields are allowed and discarded. Only decision and a deny's optional string reason are consumed; updatedInput/additionalContext do not change tool arguments or conversation context.
  • Configuration: packages/types/src/agentHook.ts; response parsing: packages/types/src/agentHookResponse.ts; HTTP delivery: apps/server/src/services/agentRuntime/hooks/httpWebhook.ts.

Hook configuration lifetime

  • Environment hooks (AGENT_HOOK_WEBHOOK_*) always come from the executing worker's current environment, including after human approval and deferred completion. Never persist their configuration or restore a previous environment's hooks.
  • Code-supplied webhook hooks (execAgent({ hooks })) retain the existing per-operation serialization and persistence. Recover these caller hooks from the runtime snapshot or durable operation record; preserve environment-variable templates without expanding secrets into storage.
  • Evaluate each operation's recovered caller hooks in order, then evaluate current environment hooks once in the final round. Do not deduplicate caller hook IDs across operations. Environment-only hooks do not require durable operation storage. Removing an environment hook stops it from controlling subsequent results; when no matching result control remains, allow the result. Do not freeze a previous environment policy across an approval or restart.
  • Deferred completion publishes into its empty placeholder once; duplicate callbacks retain that first final result, including a denial. Propagate caller-policy storage errors rather than treating failed reads as an empty hook list. Do not extend default allow to configured-hook delivery failures: those follow onError.
  • Cover environment removal/addition across approval and snapshot expiry, publication without review markers, and continued enforcement of persisted caller hooks in regression tests.

Publish after the result hook

  • Await result control before archival, message content/state writes, streaming, and model consumption. Persist the allowed result or the sanitized denial directly; do not add toolResultControl pending/allowed/blocked metadata or hide raw output through history projections.
  • Human approval sources claim the decision and retain the answer in their private resolution/outbox. MessageModel.resolveHumanApproval defaults to claim-only; only the runtime calls it with publishResult: true after result control. Stop/rejection receipts can publish directly because they contain no executed tool output.
  • Recover original caller hooks through the existing intervention operation identity or deferred callback's parent operation. Keep the in-memory hook verdict separate from tool-owned state; a tool returning type: 'blocked' is not a hook verdict.
  • Every deferred backfill, including a member that fails to start, follows the same hook-before-write order. Use the existing empty placeholder to arbitrate duplicate final writes; do not introduce a replacement review state machine.
  • When a thread has a sub-agent or group-member completion bridge, that bridge exclusively publishes its tool result. Thread lifecycle hooks update thread metadata only; never prefill the tool message with an ungated summary, including after approval recovery.
  • Cover an answer held while a hook runs, atomic publication and rollback, duplicate callbacks after policy removal, and partial member startup failure. History readers should need no result-review logic.

Events

EventTiming and payload
beforeStepBefore a step; AgentHookEvent
afterStepAfter a step; content, tool calls/results and usage totals
onCompleteTerminal state; reason such as done, error, interrupted, max_steps or cost_limit
onErrorOperation error; errorMessage, errorDetail and available error metadata
beforeToolCallBefore tool execution; shared tool context and local mock() callback
afterToolCallAfter tool execution; structured result and mocked
onToolCallErrorTool execution throws; shared tool context and error
beforeHumanInterventionBefore approval; pendingTools, operationId, stepIndex
afterHumanInterventionApproval decision and continuation; action, optional toolCallId and rejectionReason
onStopByHumanInterventionHuman rejection stops the run; optional toolCallId and rejectionReason
beforeCompactBefore compression; messageCount, tokenCount, stepIndex
afterCompactAfter compression; groupId, messagesBefore, messagesAfter, summary
onCompactErrorCompression error; error, tokenCount, stepIndex
beforeCallAgentBefore sub-agent creation; agentId, instruction
afterCallAgentCreation/start returns; agentId, subOperationId, success, optional threadId
onCallAgentErrorSub-agent call fails; agentId, error

CallAgent events dispatch on the parent operation identified by parentOperationId. An isolated child supplies threadId; shared group members use the shared conversation. Child completion is reported by the child's onComplete event.

Tool Context

Use buildToolCallHookContext() for the three tool events.

  • Required fields: native toolCallId, assistantMessageId, identifier, apiName, effective args, callIndex, stepIndex, operationId and executor.
  • Optional associations come from the run context: agent, topic, session, thread, group, task, workspace, document, source/tool message and parent operation IDs.
  • userId uses runtime.userId ?? origin.userId.
  • toolSource identifies the tool's origin; executor identifies the server/client dispatch route. executionTarget and activeDeviceId describe the run's execution plan and device selection.
  • afterToolCall.result carries content, success, optional executionTime and error/state data such as state.type: 'blocked'. mocked marks results supplied by a local hook.

Sandbox and MCP tools use the same event path. Filter with identifier, apiName or toolSource.

Local Mocking

dispatchBeforeToolCall() exposes event.mock(result). The first accepted mock wins and short-circuits the remaining mock handlers. The method returns { isMocked: true, result } for a mock, or null to continue execution.

event.mock({ content: '{"items":[]}', success: true });

Tool observation payloads use BeforeToolCallObservationEvent; the callback belongs to the in-memory handler event. dispatchBeforeToolCall() does not deliver webhooks.

Webhook Payloads

createWebhookPayloadBuilder() selects eventFields, adds hookId/hookType, then merges webhook.body. The body determines the final value of overlapping fields. Tool-result notification payloads use redactResultForEvents() to trim raw skill Work data; controls receive the full result. Work registration retains the full in-process result. finalState is available to local handlers; serialized payloads carry the event's data fields.

When email is selected, the builder resolves userEmail from the final effective userId, replacing supplied email values. Email-only projections use the event ID. An explicit invalid ID, missing email or lookup error leaves email omitted.

Email queries share a per-dispatcher cache of up to 1,000 users for five minutes. Query timeouts belong to the database layer. The builder's optional fourth { signal } argument lets a waiter cancel independently; cancellation returns undefined so the caller can stop delivery. Fetch and QStash use the enriched payload.

Delivery Errors

Dispatch awaits each handler or webhook. Ordinary errors are logged and dispatch continues. Webhooks with fallback: 'none' accumulate a CriticalHookDeliveryError, which is thrown after sibling hooks have run. QStash delivery defaults to a fetch fallback; use fallback: 'none' for QStash-signed endpoints.

리뷰

아직 리뷰가 없습니다. 사용해 본 소감을 남겨 주세요.

댓글

로그인 없이 쓸 수 있습니다. 사용 후기, 질문, 작동하지 않은 환경 등을 편하게 남겨 주세요.

아직 댓글이 없습니다. 첫 댓글을 남겨 보세요.

보내면 바로 공개됩니다. 이메일 주소나 전화번호 같은 개인 정보는 쓰지 마세요. URL은 2개까지입니다.

0 / 1,000자

이 양식은 reCAPTCHA로 보호되며 Google 개인정보처리방침 및 서비스 약관이 적용됩니다.

같은 저장소의 스킬

acceptance

무료요약 있음

실제 제품을 적절한 조작 환경에서 실행해 변경 사항을 검증하고, 사용자가 확인할 수 있는 증거를 모아 인수 보고서로 게시합니다. 기존 검증 계획을 확인하거나 점검 항목을 만들고, `lh` CLI로 결과를 게시할 수 있습니다.

  • 변경된 제품 동작을 실제로 확인하기
  • 스크린샷 등 검증 증거 수집하기
  • 검증 계획과 보고서 작성하기
lobehub/lobehub8.4만2026년 10월 26일 업데이트

add-model-provider

무료요약 있음

LobeHub에 AI 모델 제공자를 추가하는 과정을 안내합니다. 런타임 연동, 모델 정보와 설정, 브랜드 표시, 문서화 및 인수 확인을 다루며, 기존 제공자에 모델만 추가하는 경우와 새 연동이 필요한 경우를 구분합니다.

  • LobeHub에 새 AI 모델 제공자 추가하기
  • 제공자의 설정 안내나 설명 갱신하기
  • 모델 추가에 새 제공자 연동이 필요한지 판단하기
lobehub/lobehub8.4만2026년 10월 26일 업데이트

add-setting-env

무료요약 있음

서버 환경 변수로 사용자 설정의 기본값을 지정하도록 구현하는 절차를 안내합니다. 변수 검증, 서버 설정 구성, 사용자 저장소 반영부터 예시 환경 파일과 셀프 호스팅 문서 갱신까지 다룹니다.

  • 환경 변수로 사용자 설정 기본값 지정
  • 설정을 서버 구성과 사용자 저장소에 연결
  • 환경 변수 예시와 문서 갱신
lobehub/lobehub8.4만2026년 10월 26일 업데이트

agent-signal

무료요약 있음

에이전트의 이벤트 기반 백그라운드 작업을 설계하고 구현하도록 돕습니다. 소스, 시그널, 액션, 정책의 역할을 나누고 비동기 처리, 중복 실행 방지, 완료 기록과 관측 기능을 다룹니다.

  • 이벤트로 시작되는 백그라운드 작업 추가
  • 대화 요청과 작업을 분리
  • 액션의 중복 실행 방지
lobehub/lobehub8.4만2026년 10월 26일 업데이트

agent-testing-bot

무료요약 있음

실제 데스크톱 채팅 앱에서 봇 채널의 인수 테스트를 진행합니다. Discord, Slack, Telegram, WeChat, Lark, QQ에서 메시지를 보내고 응답을 기다린 뒤 결과 화면을 캡처합니다. iMessage는 BlueBubbles 브리지를 사용합니다.

  • 실제 Discord 채널에서 봇 응답 확인하기
  • Slack이나 Telegram 대화 경로 테스트하기
  • macOS 앱의 작업 결과 화면으로 기록하기
lobehub/lobehub8.4만2026년 10월 26일 업데이트

agent-tracing

무료요약 있음

작업 ID로 에이전트 실행 기록을 살펴 실패한 도구 호출과 인수·결과, 사용 가능한 도구, 실행 문맥과 대규모 언어 모델 입력을 확인합니다. 문맥 지도와 다른 모델로 기록을 재생해 비교하는 기능도 제공합니다.

  • 실패한 도구 호출 조사
  • 대규모 언어 모델에 전달된 문맥 확인
  • 작업별 도구와 결과 추적
lobehub/lobehub8.4만2026년 10월 26일 업데이트

lobehub의 스킬 모두 보기

이 스킬의 문제 신고