본문으로 건너뛰기
cccskills
무료GitHub에 공개

fetch-cadmus-logs

Fetch Cadmus application logs from Loki by run ID. Use when asked to look up logs for a specific run, debug a device session, or find log output for a given run ID.

한국어 요약은 준비 중입니다. 원문 설명을 표시하고 있습니다.

설치 방법 보기

포함된 파일(1)

  • SKILL.md6.8 KB

SKILL.md(원문)

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

Fetch Cadmus Logs by Run ID

Context

Cadmus logs are shipped to Loki under the stream label service_name="cadmus". The run ID is stored as a JSON field named resources_cadmus_run_id — it is not a Loki stream label, so it cannot be used in the stream selector {}. It must be filtered with | json | resources_cadmus_run_id="<id>" in the LogQL pipeline.

Two separate observability sources

Cadmus uses two distinct pipelines:

SourceWhat it containsHow to query
Loki (http://localhost:3100)tracing-bridge log records (third-party crate logs like reqwest, i18n_embed)LogQL via /loki/api/v1/query_range
Tempo (http://localhost:3200)Spans and span events from #[tracing::instrument] — this is where cadmus-core importer, library, db spans live/api/traces/<traceID>

Important: Cadmus application logic (cadmus_core::*) emits structured spans via tracing::instrument, not log records. These appear in Tempo, not Loki. Loki for a cadmus run will mostly contain noise from reqwest::retry, i18n_embed, etc. — not importer or library logic.

To debug application behaviour (import scan, db inserts, errors), query Tempo. To find third-party log noise or connectivity errors, query Loki.

Loki

Base URL

http://localhost:3100

Override with the LOKI_URL environment variable if the instance is elsewhere.

Query logs for a run ID

LOKI_URL="${LOKI_URL:-http://localhost:3100}"
RUN_ID="<run-id>"

curl -sG "${LOKI_URL}/loki/api/v1/query_range" \
  --data-urlencode 'query={service_name="cadmus"} | json | resources_cadmus_run_id="'"${RUN_ID}"'"' \
  --data-urlencode 'limit=1000' \
  --data-urlencode 'direction=forward' \
  | jq -r '.data.result[].values[] | .[1] | fromjson | .body // .msg // .'

This prints the body field of each JSON log line in chronological order.

Filter to cadmus-core log records only

Add | instrumentation_scope_name="log" to isolate records that went through the log bridge (as opposed to span events). Even then, most records will be from third-party crates. To further narrow to cadmus-core targets:

curl -sG "${LOKI_URL}/loki/api/v1/query_range" \
  --data-urlencode 'query={service_name="cadmus"} | json | resources_cadmus_run_id="'"${RUN_ID}"'" | instrumentation_scope_name="log"' \
  --data-urlencode 'limit=1000' \
  --data-urlencode 'direction=forward' \
  | jq -r '.data.result[].values[] | .[1] | fromjson | select(.attributes["log.target"] | startswith("cadmus")) | .body'

Filter by log level

Loki attaches a level stream label (lowercase) derived from the severity JSON field. Filter by level two ways:

Stream label (preferred — fast, evaluated before parsing):

{service_name="cadmus", level="error"} | json | resources_cadmus_run_id="<id>"

JSON field filter:

{service_name="cadmus"} | json | resources_cadmus_run_id="<id>" | severity="ERROR"

Valid level stream label values: trace, debug, info, warn, error. Valid severity JSON field values: TRACE, DEBUG, INFO, WARN, ERROR.

Paginate large result sets

Loki returns at most limit entries per request. Keep limit ≤ 1000 — larger values may return empty results. Paginate using the last timestamp:

LAST_TS=$(echo "$RESPONSE" | jq -r '.data.result[-1].values[-1][0]')

curl -sG "${LOKI_URL}/loki/api/v1/query_range" \
  --data-urlencode 'query={service_name="cadmus"} | json | resources_cadmus_run_id="'"${RUN_ID}"'"' \
  --data-urlencode "start=$((LAST_TS + 1))" \
  --data-urlencode 'limit=1000' \
  --data-urlencode 'direction=forward'

Common Loki patterns

GoalLogQL
All logs for a run{service_name="cadmus"} | json | resources_cadmus_run_id="<id>"
Errors only{service_name="cadmus", level="error"} | json | resources_cadmus_run_id="<id>"
cadmus-core targets onlyadd | instrumentation_scope_name="log" then filter .attributes["log.target"] in jq
Count entriesUse /loki/api/v1/query with count_over_time(...)

Tempo (spans and span events)

Tempo Base URL

http://localhost:3200

Find a trace by run ID

curl -sG "http://localhost:3200/api/search" \
  --data-urlencode "tags=cadmus.run_id=<run-id>" \
  --data-urlencode "limit=5" \
  | jq -r '.traces[] | "\(.traceID) \(.rootName)"'

Fetch a full trace

TRACE_ID="<traceID>"
curl -s "http://localhost:3200/api/traces/${TRACE_ID}" \
  | jq -r '.batches[].scopeSpans[].spans[] | "\(.name) | \(.attributes[] | "\(.key)=\(.value.stringValue // .value.intValue)")"'

Find error spans

curl -s "http://localhost:3200/api/traces/${TRACE_ID}" | jq -r '
  .batches[].scopeSpans[].spans[]
  | select(.status.code == "STATUS_CODE_ERROR")
  | {name, status, events: .events}
'

Span events carry the actual error message. Check .events[].attributes for fields like error which contain the database error string.

Filter spans by name

curl -s "http://localhost:3200/api/traces/${TRACE_ID}" | jq -r '
  .batches[].scopeSpans[].spans[]
  | select(.name | test("scan_entries|flush_to_db|batch_insert|run"))
  | "\(.name) | \(.attributes[] | select(.key | test("count|library_id|home")) | "\(.key)=\(.value.stringValue // .value.intValue)")"
'

Convert nanosecond timestamps

Tempo span timestamps are Unix nanoseconds:

python3 -c "import datetime; print(datetime.datetime.fromtimestamp(<ns>/1e9, tz=datetime.timezone.utc))"

Loki API reference

  • GET /loki/api/v1/query_range — range query (fetching log lines)
  • GET /loki/api/v1/query — instant query (metric expressions)
  • GET /loki/api/v1/labels — list available label names
  • GET /loki/api/v1/label/{name}/values — list values for a label

All parameters are passed as query string values and should be URL-encoded. Timestamps can be Unix epoch nanoseconds (integer) or RFC3339 strings.

리뷰

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

댓글

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

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

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

0 / 1,000자

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

같은 저장소의 스킬

Build Cadmus on Linux and macOS hosts using cadmuscli. Use when asked how to compile, test, lint, or run the project locally.

한국어 요약은 준비 중입니다. 원문 설명을 표시하고 있습니다.

OGKevin/cadmus502026년 10월 23일 업데이트

Build, test, and lint Cadmus from a jj sibling workspace that has no .git (non-colocated checkout). Use when jj workspace root is a sibling tmp/agent workspace and builds fail with git submodule or .gitmodules errors, empty thirdparty/ sources, cache-marker misses, or missing sqlite.

한국어 요약은 준비 중입니다. 원문 설명을 표시하고 있습니다.

OGKevin/cadmus502026년 10월 23일 업데이트

Cross-compile Cadmus for Kobo e-reader devices (ARM Linux). Use this when asked to build a Kobo release, cross-compile for ARM, or prepare a device binary.

한국어 요약은 준비 중입니다. 원문 설명을 표시하고 있습니다.

OGKevin/cadmus502026년 10월 23일 업데이트

Run clippy locally and report only issues in the current diff, matching the CI reviewdog flow. Use when asked how to lint changed code or get clippy feedback on a branch before pushing.

한국어 요약은 준비 중입니다. 원문 설명을 표시하고 있습니다.

OGKevin/cadmus502026년 10월 23일 업데이트

Resolve failed Renovate or Dependabot dependency update PRs by fixing version constraints, API breaking changes, and verifying build/test/format compliance. Use when a dependency bump PR fails CI, Cargo cannot select versions, or a crate update requires code migration.

한국어 요약은 준비 중입니다. 원문 설명을 표시하고 있습니다.

OGKevin/cadmus502026년 10월 23일 업데이트

docs

무료

Build the full Cadmus documentation website (mdBook + cargo doc + Storybook + Next.js). Use this when asked to build, preview, or update the documentation site.

한국어 요약은 준비 중입니다. 원문 설명을 표시하고 있습니다.

OGKevin/cadmus502026년 10월 23일 업데이트

OGKevin의 스킬 모두 보기

이 스킬의 문제 신고