—
로딩…
NocoDB는 팀의 공용 데이터베이스다. 에이전트가 데이터를 기록하고, 사람이 웹 UI로 조회한다.
| 항목 | 값 |
|---|---|
| URL | https://ttslab-nocodb.exe.xyz |
| 인증 | Secret Manager에서 자동 획득 (http://10.200.2.183:8900/secrets/nocodb) |
| API 헤더 | xc-token (xc-auth 아님) |
| API 버전 | v2 (/api/v2/tables/{id}/records) |
| Workspace | TTS Lab (id: wv7y2917) |
에이전트가 NocoDB API를 호출할 때 참고할 정보.
# 방법 1: Secret Manager (추천)
from tools._lib.secrets import get_secret
token = get_secret("nocodb/api_token")
# 방법 2: 직접 HTTP
import json, urllib.request
req = urllib.request.Request("http://10.200.2.183:8900/secrets/nocodb")
resp = urllib.request.urlopen(req)
secrets = json.loads(resp.read())
token = secrets["api_token"]
| 작업 | 메서드 | 경로 |
|---|---|---|
| 레코드 조회 | GET | /api/v2/tables/{table_id}/records |
| 레코드 생성 | POST | /api/v2/tables/{table_id}/records |
| 레코드 수정 | PATCH | /api/v2/tables/{table_id}/records |
| 레코드 삭제 | DELETE | /api/v2/tables/{table_id}/records |
| Workspace 목록 | GET | /api/v2/meta/workspaces |
| Base 목록 | GET | /api/v1/workspaces/{ws_id}/bases |
| Table 목록 | GET | /api/v2/meta/bases/{base_id}/tables |
| Table 메타 | GET | /api/v2/meta/tables/{table_id} |
| 컬럼 수정 | PATCH | /api/v2/meta/columns/{col_id} |
xc-token 이다. xc-auth는 401 에러 발생./api/v1/workspaces/{ws_id}/bases). v2 /api/v2/meta/bases/는 403./api/v2/meta/workspaces/{ws_id}/bases). v1은 404./api/v2/tables/{table_id}/records)./api/v2/meta/columns/{col_id}를 PATCH하여 colOptions.options에 추가한 뒤 레코드를 삽입해야 한다.에이전트가 매번 탐색하지 않도록, 변하지 않는 ID들을 여기에 기록한다. 새 base/table이 추가되면 이 섹션도 업데이트한다.
| 이름 | ID |
|---|---|
| TTS Lab | wv7y2917 |
| Base | ID | 용도 |
|---|---|---|
_meta | p4o78qz1uhkog7x | 메타데이터 — 에이전트 탐색 진입점 |
harness-ops | pipm9b2g2251scu | 하네스 운영 데이터 |
tts-data | pwj9nazglijhrxe | TTS 도메인 데이터 |
harness-radar | p996trjwlit255e | 기술 레이더 스카우팅 데이터 (experimental — contrib/experimental/tech-radar) |
| Base | Table | ID | 용도 |
|---|---|---|---|
_meta | bases_directory | mv5vojborzunqc9 | 모든 base의 목록과 용도 |
_meta | tables_directory | m1qjx4oal56k3oh | 모든 테이블의 목록, ID, 스키마 |
_meta | rules | mm2ew3qu7080o3c | NocoDB 운영 규칙 |
harness-ops | activity_log | mj19wnmsu4vrbmp | 팀/에이전트 활동 기록 |
harness-ops | skill_usage | m75vwsehqo6izkr | 스킬 사용 기록 |
harness-ops | daily_work_log | m0wj1eaen5maafy | 일일 작업 로그 |
harness-ops | meetings | mjqtpjz59o5wb8j | 회의록 본체. meeting-formatter 가 직접 적재(SoT, md 미러 폐기 2026-04-30). 컬럼: title, date, location, attendees, tags, agenda, discussion, decisions, synced_at, source_actor, action_items(Link). |
harness-ops | meeting_action_items | mif887khs9dyq7t | 회의 Action Items. meetings 와 hm/bt link. 컬럼: description, assignee_raw, assignee_type, status, due_date, source_meeting_date, created_at, completed_at, notes, meetings(bt). |
tts-data | speakers | mc26yuq98xp73np | 화자 정보 |
tts-data | recording_log | m00itzw58f79kzs | 녹음 세션 기록 |
tts-data | training_log | mk00z5kgcdbrslp | 모델 학습 이력 |
tts-data | deploy_speakers | mtwgedja5b3rofs | 배포용 화자 메타데이터 |
tts-data | deploy_models | m61jdr4n7ctmjes | 배포 준비된 TTS 모델별 README/화자 정보 (원본 repo의 GitHub Action이 동기화) |
tts-data | dataset_variants | meeukod33twsor6 | xdata registry 변종 마스터 (natural_key unique, processed_versions[], context_profile) |
tts-data | dataset_variant_changes | mryfgqxoe1643yg | dataset_variants 변경 감사 로그 (event_id unique, 8 이벤트 유형) |
harness-radar | tech_items | mvluf16i39wfn8w | 발견된 기술 아이템 (experimental) |
harness-radar | scout_runs | m3upfrirawo1u4v | 스카우트 run 기록 (experimental) |
위의 고정 ID 레지스트리를 참조하여 바로 접근한다. 대부분의 경우 이 방법으로 충분하다.
table_id = "m00itzw58f79kzs" # recording_log — 위 표에서 확인
req = urllib.request.Request(
f"https://ttslab-nocodb.exe.xyz/api/v2/tables/{table_id}/records",
headers={"xc-token": token}
)
새로운 테이블이거나 ID를 모르면 _meta를 통해 탐색한다.
1. _meta/tables_directory 조회 (table_id: m1qjx4oal56k3oh)
→ Table Name과 Table ID를 확인
2. 필요한 테이블의 ID로 직접 접근
이 문서의 고정 ID 레지스트리에 없는 테이블을 발견하면, 이 문서를 업데이트하여 다른 에이전트가 반복 탐색하지 않도록 한다.
에이전트가 NocoDB를 탐색하기 위한 진입점. wiki/INDEX.md와 같은 역할.
| 테이블 | 용도 |
|---|---|
bases_directory | 모든 base의 목록, 용도, 소유 그룹, 접근 수준 |
tables_directory | 모든 테이블의 목록, 용도, 테이블 ID, 업데이트 빈도 |
rules | NocoDB 운영 규칙 (네이밍, 스키마, 접근, 데이터 품질, 계층) |
주의: _meta는 read-only. harness-admin만 수정한다.
팀과 에이전트의 활동을 추적한다.
| 테이블 | 용도 | 기록자 |
|---|---|---|
activity_log | 누가 무엇을 했는지 (작업 기록) | 에이전트/사람 |
skill_usage | 어떤 스킬이 사용되었는지 | 에이전트 |
daily_work_log | 일일 작업 로그 (날짜, 담당자, 작업 내용) | 에이전트/사람 |
TTS 프로젝트의 핵심 데이터를 관리한다.
| 테이블 | 용도 | 기록자 |
|---|---|---|
speakers | 화자 정보 (코드, 언어, 성별, 상태) | 사람 |
recording_log | 녹음 세션 기록 (날짜, 수량, QA 결과) | 에이전트/사람 |
training_log | 모델 학습 이력 (모델명, epoch, loss, 상태) | 에이전트/사람 |
dataset_variants | 데이터 레지스트리 variant (natural_key = {speaker_id}/{language}/{utterance_style}/{phoneme_source}, ADR 0007/0008) | 에이전트 (xdata) |
NocoDB의 데이터 구조는 Workspace → Base → Table 계층이다.
Workspace: TTS Lab (wv7y2917)
├── _meta (메타 — 에이전트 탐색 전용)
├── harness-ops (운영 — 팀 공용)
├── tts-data (도메인 — TTS 데이터)
├── proj-* (프로젝트 한정 — 필요 시 생성)
└── ...
Base는 독립적인 업무 도메인 단위로 생성한다. 하나의 base 안에 있는 테이블들은 서로 관련된 데이터여야 한다.
| 상황 | 판단 |
|---|---|
| 기존 base의 테이블들과 같은 도메인 | → 기존 base에 테이블 추가 |
| 완전히 다른 도메인 | → 새 base 생성 |
| 판단이 어려움 | → 기존 base에 먼저 추가, 나중에 분리 |
| 접두사 | 용도 | 예시 |
|---|---|---|
(없음) _meta | 메타데이터 전용 | _meta |
harness- | 팀 공용 운영 데이터 | harness-ops |
tts- | TTS 도메인 데이터 | tts-data |
proj- | 특정 프로젝트 한정 | proj-customer-abc |
recording_log_2026)보다 하나의 테이블 + 날짜 컬럼을 우선_meta는 일반 데이터를 넣는 곳이 아니다. 에이전트가 NocoDB 구조를 파악하기 위한 카탈로그다.
_meta/bases_directory에 등록 필수_meta/tables_directory에 등록 필수_meta/rules에 반영kebab-case (예: harness-ops, tts-data)snake_case (예: recording_log, training_log)kebab-case (예: qa-pass, read-write)_meta/bases_directory에 등록 필수_meta/tables_directory에 등록 필수_meta base는 read-only (harness-admin만 수정)actor_type을 agent로 명시_meta/bases_directory 또는 _meta/tables_directory에 등록한다from tools._lib.secrets import get_secret
import json, urllib.request
token = get_secret("nocodb/api_token")
table_id = "m00itzw58f79kzs" # recording_log
req = urllib.request.Request(
f"https://ttslab-nocodb.exe.xyz/api/v2/tables/{table_id}/records",
headers={"xc-token": token}
)
resp = urllib.request.urlopen(req)
data = json.loads(resp.read())
print(data["list"])
row = {
"date": "2026-04-16",
"speaker_code": "KR_F02",
"utterance_count": 150,
"status": "recorded",
"recorded_by": "이녹음엔지니어"
}
data = json.dumps(row).encode()
req = urllib.request.Request(
f"https://ttslab-nocodb.exe.xyz/api/v2/tables/{table_id}/records",
data=data,
headers={"xc-token": token, "Content-Type": "application/json"},
method="POST"
)
# Workspace 목록 (v2)
req = urllib.request.Request(
"https://ttslab-nocodb.exe.xyz/api/v2/meta/workspaces",
headers={"xc-token": token}
)
# Workspace 내 Base 목록 (v1 — v2는 403)
req = urllib.request.Request(
f"https://ttslab-nocodb.exe.xyz/api/v1/workspaces/wv7y2917/bases",
headers={"xc-token": token}
)
# Base 내 Table 목록 (v2)
req = urllib.request.Request(
f"https://ttslab-nocodb.exe.xyz/api/v2/meta/bases/{base_id}/tables",
headers={"xc-token": token}
)
python -m tools.integrations.nocodb.client --table m00itzw58f79kzs --action list --json