---
title: "외부 앱 client_credential 발급 (APP_CREDENTIAL_SCHEMA §3-3)"
method: POST
path: "/v1/app-credentials"
tags: ["AppCredential"]
---

# 외부 앱 client_credential 발급 (APP_CREDENTIAL_SCHEMA §3-3)

`POST /v1/app-credentials`

## Request

- Base URL: `https://api.xdata.kr` (the document declares no server; this is the origin it was published from)
- URL: `https://api.xdata.kr/v1/app-credentials`
- Auth: one of:
  - HTTP basic
  - OAuth 2 (authorization code, authorization URL `https://api.xdata.kr/oauth/authorize`, token URL `https://api.xdata.kr/oauth/token`)

`POST /v1/app-credentials` 단일 진입점 (APP_CREDENTIAL_SCHEMA §3-3 + §6 1:1).

PR-N-3 (Phase 2 외부 표면 4호 본체 3단계). PR-J-3 의 `submit_job_v1` 패턴
1:1 재사용 (8 원칙 #1 공통모듈화). 정책 평가 + app_credentials INSERT +
`app_credential.issued` audit 적재 단일 트랜잭션.

응답 분기:
    - 정상 발급                              → 201 Created + 3필드 envelope
      ({client_id, client_secret, created_at})
    - 정책 거부 (AuthPolicyError)            → 401/402/403/422/429 (PR-M 정밀 매핑)
    - Service 거부 (AppCredentialIssueError) → 6 error_code 정밀 매핑:
        * PRINCIPAL_KIND_FORBIDDEN          → 403 AUTHZ_FORBIDDEN
        * PRINCIPAL_USER_ID_MISSING         → 500 INTERNAL_ERROR (운영 진단)
        * ORGANIZATION_ID_MISSING           → 400 VALIDATION_INVALID_FIELD
        * PRODUCTION_SCOPE_FORBIDDEN_V1     → 402 POLICY_PAID_REQUIRED
        * INVALID_LABEL_LENGTH              → 400 VALIDATION_INVALID_FIELD
        * INVALID_ENV_SCOPE                 → 400 VALIDATION_INVALID_FIELD
    - Repository ValueError                  → 500 INTERNAL_ERROR (Service 가 만든 행의
      사전 검증 실패 = 우리 결함. 고객 입력은 위 두 코드로 먼저 걸린다, 검수 1a0c5311804)
    - 그 외 예외                              → 500 INTERNAL_ERROR

Security (APP_CREDENTIAL_SCHEMA §10 금지):
    평문 `client_secret` 은 본 응답 body 에서 1회 노출 후 caller 가 즉시
    보관해야 한다. 서버는 본 함수가 응답 직렬화 직후 변수 reference 를
    새 dict 로 분리하여 best-effort 폐기 (Python str immutable). 평문은
    로그/메트릭/exception traceback 어디에도 진입하지 않는다.

## Query parameters

- `env_scope` 'production' | 'real_test' | 'sandbox', nullable: 환경을 고릅니다. 값은 production · real_test · sandbox 중 하나입니다. 경로 접두(/v1/sandbox/... · /v1/test/... · /v1/production/...) · X-Env-Scope 헤더 · env_scope 쿼리 가운데 한 통로로 반드시 보내야 합니다. 빼면 자동으로 채우지 않고 거절하며, 두 통로에 서로 다른 값을 담아도 거절합니다. 거절은 HTTP 422 이고 오류 코드는 VALIDATION_ENV_SCOPE_MISMATCH 입니다.

## Headers

- `Authorization` string, nullable
- `User-Agent` string, nullable
- `X-Env-Scope` 'production' | 'real_test' | 'sandbox', nullable: 환경을 고릅니다. 값은 production · real_test · sandbox 중 하나입니다. 경로 접두(/v1/sandbox/... · /v1/test/... · /v1/production/...) · X-Env-Scope 헤더 · env_scope 쿼리 가운데 한 통로로 반드시 보내야 합니다. 빼면 자동으로 채우지 않고 거절하며, 두 통로에 서로 다른 값을 담아도 거절합니다. 거절은 HTTP 422 이고 오류 코드는 VALIDATION_ENV_SCOPE_MISMATCH 입니다.

## Request body

- AppCredentialIssueRequest: `POST /v1/app-credentials` 요청 본문 (APP_CREDENTIAL_SCHEMA §6 + §3 1:1). 필드: label: 자격증명 라벨 (1~100자, human-readable, e.g. 'ERP-Prod-1'). allowed_env_scopes: 발급 허용 env_scope 목록. 누락/None → default ('sandbox') (Service 가 default 적용). real_test 는 ADR-043 APPROVED env_access_requests 후 approve append 또는 issue inherit. v1 'production' 포함 시 402 POLICY_PAID_REQUIRED 거부 (Plan §3-2.A — PAID 멤버십 통합 PR-N-6 PATCH 위임). Headers: Authorization: Bearer console_jwt 또는 admin_jwt (필수). client_credential/ legacy_api_key 는 §5-5 매트릭스 PR-N-3-pre 잠금으로 403 거부. X-Env-Scope: sandbox/real_test/production. production 진입은 §5-7 PAID 잠금 (AuthPolicyService 책임). X-Trace-Id / X-Request-Id: 운영 상관관계 (선택, 누락 시 자동 발급). X-Organization-Id: admin_user 위임 organization_id hint (선택, 누락 시 console_user 는 자기 조직 사용).
  - `label` string, required: 자격증명 라벨 (1~100자)
  - `allowed_env_scopes` string[], nullable: 발급 허용 env_scope. None → default ('sandbox'). real_test requires APPROVED env access request (ADR-043). v1 'production' 포함 시 402 POLICY_PAID_REQUIRED.
  - `integration_profile` string, nullable: Omit for standard_external (default ERP). desktop_agent for integrator SaaS keys — admin_user issuance only (ADR-XDATA-XSTAFF-001); console rejected at AppCredentialService.

## Response `201`

Successful Response

- unknown

## Other responses

- `422`: Validation Error

---

[API](https://skmtc.dev/xdata/apis/xboss-api.md) · [All operations](https://skmtc.dev/xdata/apis/xboss-api/llms.txt) · [OpenAPI document](https://skmtc.dev/xdata/apis/xboss-api/revisions/816de78950db?raw)
