All checks were successful
Build And Test / build-and-push (push) Successful in 36s
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
672 lines
10 KiB
Markdown
672 lines
10 KiB
Markdown
# NHN Cloud API 명세서
|
|
|
|
## 기본 정보
|
|
|
|
- **Base URL**: `http://{server}:8900/api/nhn`
|
|
- **Swagger UI**: `http://{server}:8900/swagger/`
|
|
- **Content-Type**: `application/json`
|
|
|
|
---
|
|
|
|
## 인증 방식
|
|
|
|
모든 API 호출 시 아래 헤더를 포함해야 합니다:
|
|
|
|
| 헤더 | 필수 | 설명 |
|
|
|------|------|------|
|
|
| `X-NHN-Region` | O | NHN Cloud 리전 (`kr1`: 판교, `kr2`: 평촌) |
|
|
| `X-NHN-Token` | O | NHN Cloud API 토큰 |
|
|
| `X-NHN-Tenant-ID` | △ | 테넌트 ID (Compute API에서 필수) |
|
|
| `X-NHN-Storage-Account` | △ | 스토리지 계정 (Storage API에서 필수) |
|
|
|
|
---
|
|
|
|
## 1. Token API
|
|
|
|
### 1.1 토큰 생성
|
|
|
|
NHN Cloud API 인증 토큰을 발급받습니다.
|
|
|
|
```
|
|
POST /api/nhn/token/
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"tenant_id": "04a2c5b7de7e4d66b970ad950081a7c3",
|
|
"username": "user@example.com",
|
|
"password": "your-api-password"
|
|
}
|
|
```
|
|
|
|
**Response (200 OK)**
|
|
```json
|
|
{
|
|
"token": "gAAAAABm...",
|
|
"tenant_id": "04a2c5b7de7e4d66b970ad950081a7c3",
|
|
"expires_at": "2024-01-15T12:00:00Z"
|
|
}
|
|
```
|
|
|
|
**Error Response (401)**
|
|
```json
|
|
{
|
|
"error": "인증 실패 메시지",
|
|
"code": 401
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
## 2. Compute API
|
|
|
|
### 2.1 Flavor 목록 조회
|
|
|
|
```
|
|
GET /api/nhn/compute/flavors/
|
|
```
|
|
|
|
**Headers**
|
|
```
|
|
X-NHN-Region: kr2
|
|
X-NHN-Token: {token}
|
|
X-NHN-Tenant-ID: {tenant_id}
|
|
```
|
|
|
|
**Response (200 OK)**
|
|
```json
|
|
{
|
|
"flavors": [
|
|
{
|
|
"id": "flavor-id-123",
|
|
"name": "m2.c2m4",
|
|
"vcpus": 2,
|
|
"ram": 4096,
|
|
"disk": 0
|
|
}
|
|
]
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### 2.2 Keypair 목록 조회
|
|
|
|
```
|
|
GET /api/nhn/compute/keypairs/
|
|
```
|
|
|
|
**Response (200 OK)**
|
|
```json
|
|
{
|
|
"keypairs": [
|
|
{
|
|
"keypair": {
|
|
"name": "my-keypair",
|
|
"public_key": "ssh-rsa AAAA...",
|
|
"fingerprint": "xx:xx:xx..."
|
|
}
|
|
}
|
|
]
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### 2.3 이미지 목록 조회
|
|
|
|
```
|
|
GET /api/nhn/compute/images/
|
|
```
|
|
|
|
**Response (200 OK)**
|
|
```json
|
|
{
|
|
"images": [
|
|
{
|
|
"id": "image-id-123",
|
|
"name": "Ubuntu 20.04",
|
|
"status": "active",
|
|
"created_at": "2024-01-01T00:00:00Z"
|
|
}
|
|
]
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### 2.4 인스턴스 목록 조회
|
|
|
|
```
|
|
GET /api/nhn/compute/instances/
|
|
```
|
|
|
|
**Response (200 OK)**
|
|
```json
|
|
{
|
|
"servers": [
|
|
{
|
|
"id": "server-id-123",
|
|
"name": "my-instance",
|
|
"status": "ACTIVE",
|
|
"addresses": {
|
|
"Default Network": [
|
|
{"addr": "192.168.0.10", "version": 4}
|
|
]
|
|
},
|
|
"created": "2024-01-01T00:00:00Z"
|
|
}
|
|
]
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### 2.5 인스턴스 상세 조회
|
|
|
|
```
|
|
GET /api/nhn/compute/instances/{server_id}/
|
|
```
|
|
|
|
**Response (200 OK)**
|
|
```json
|
|
{
|
|
"server": {
|
|
"id": "server-id-123",
|
|
"name": "my-instance",
|
|
"status": "ACTIVE",
|
|
"flavor": {"id": "flavor-id"},
|
|
"image": {"id": "image-id"},
|
|
"addresses": {...},
|
|
"created": "2024-01-01T00:00:00Z"
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### 2.6 인스턴스 생성
|
|
|
|
```
|
|
POST /api/nhn/compute/instances/create/
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"name": "my-new-instance",
|
|
"image_id": "image-id-123",
|
|
"flavor_id": "flavor-id-123",
|
|
"subnet_id": "subnet-id-123",
|
|
"keypair_name": "my-keypair",
|
|
"volume_size": 50,
|
|
"security_groups": ["default"],
|
|
"availability_zone": "kr-pub-a"
|
|
}
|
|
```
|
|
|
|
| 필드 | 타입 | 필수 | 설명 |
|
|
|------|------|------|------|
|
|
| name | string | O | 인스턴스 이름 |
|
|
| image_id | string | O | 이미지 ID |
|
|
| flavor_id | string | O | Flavor ID |
|
|
| subnet_id | string | O | 서브넷 ID |
|
|
| keypair_name | string | O | Keypair 이름 |
|
|
| volume_size | integer | X | 볼륨 크기 (GB, 기본 50) |
|
|
| security_groups | array | X | 보안 그룹 (기본 ["default"]) |
|
|
| availability_zone | string | X | 가용 영역 |
|
|
|
|
**Response (201 Created)**
|
|
```json
|
|
{
|
|
"server": {
|
|
"id": "new-server-id",
|
|
"name": "my-new-instance",
|
|
...
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### 2.7 인스턴스 삭제
|
|
|
|
```
|
|
DELETE /api/nhn/compute/instances/{server_id}/
|
|
```
|
|
|
|
**Response (204 No Content)**
|
|
|
|
---
|
|
|
|
### 2.8 인스턴스 액션 (시작/정지/재부팅)
|
|
|
|
```
|
|
POST /api/nhn/compute/instances/{server_id}/action/
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"action": "start" // "start" | "stop" | "reboot"
|
|
}
|
|
```
|
|
|
|
**Response (200 OK)**
|
|
```json
|
|
{
|
|
"status": "success",
|
|
"action": "start"
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
## 3. VPC API
|
|
|
|
### 3.1 VPC 목록 조회
|
|
|
|
```
|
|
GET /api/nhn/vpc/
|
|
```
|
|
|
|
**Headers**
|
|
```
|
|
X-NHN-Region: kr2
|
|
X-NHN-Token: {token}
|
|
```
|
|
|
|
**Response (200 OK)**
|
|
```json
|
|
{
|
|
"vpcs": [
|
|
{
|
|
"id": "vpc-id-123",
|
|
"name": "my-vpc",
|
|
"cidrv4": "10.0.0.0/16",
|
|
"state": "available"
|
|
}
|
|
]
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### 3.2 VPC 생성
|
|
|
|
```
|
|
POST /api/nhn/vpc/create/
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"name": "my-new-vpc",
|
|
"cidr": "10.0.0.0/16"
|
|
}
|
|
```
|
|
|
|
**Response (201 Created)**
|
|
```json
|
|
{
|
|
"vpc": {
|
|
"id": "new-vpc-id",
|
|
"name": "my-new-vpc",
|
|
"cidrv4": "10.0.0.0/16"
|
|
}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### 3.3 VPC 상세 조회
|
|
|
|
```
|
|
GET /api/nhn/vpc/{vpc_id}/
|
|
```
|
|
|
|
---
|
|
|
|
### 3.4 VPC 삭제
|
|
|
|
```
|
|
DELETE /api/nhn/vpc/{vpc_id}/
|
|
```
|
|
|
|
**Response (204 No Content)**
|
|
|
|
---
|
|
|
|
### 3.5 서브넷 목록 조회
|
|
|
|
```
|
|
GET /api/nhn/subnet/
|
|
```
|
|
|
|
**Response (200 OK)**
|
|
```json
|
|
{
|
|
"vpcsubnets": [
|
|
{
|
|
"id": "subnet-id-123",
|
|
"name": "my-subnet",
|
|
"vpc_id": "vpc-id-123",
|
|
"cidr": "10.0.1.0/24",
|
|
"gateway": "10.0.1.1"
|
|
}
|
|
]
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### 3.6 서브넷 생성
|
|
|
|
```
|
|
POST /api/nhn/subnet/create/
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"vpc_id": "vpc-id-123",
|
|
"name": "my-new-subnet",
|
|
"cidr": "10.0.1.0/24"
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### 3.7 서브넷 상세 조회 / 삭제
|
|
|
|
```
|
|
GET /api/nhn/subnet/{subnet_id}/
|
|
DELETE /api/nhn/subnet/{subnet_id}/
|
|
```
|
|
|
|
---
|
|
|
|
### 3.8 Floating IP 목록 조회
|
|
|
|
```
|
|
GET /api/nhn/floatingip/
|
|
```
|
|
|
|
**Response (200 OK)**
|
|
```json
|
|
{
|
|
"floatingips": [
|
|
{
|
|
"id": "fip-id-123",
|
|
"floating_ip_address": "133.186.xxx.xxx",
|
|
"status": "ACTIVE",
|
|
"port_id": "port-id-123"
|
|
}
|
|
]
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
## 4. NKS (Kubernetes) API
|
|
|
|
### 4.1 지원 버전 조회
|
|
|
|
```
|
|
GET /api/nhn/nks/supports/
|
|
```
|
|
|
|
**Headers**
|
|
```
|
|
X-NHN-Region: kr2
|
|
X-NHN-Token: {token}
|
|
```
|
|
|
|
**Response (200 OK)**
|
|
```json
|
|
{
|
|
"supported_k8s": {
|
|
"v1.33.4": "True",
|
|
"v1.32.4": "True",
|
|
"v1.31.4": "True",
|
|
"v1.30.4": "False"
|
|
},
|
|
"supported_event_type": {...}
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### 4.2 클러스터 목록 조회
|
|
|
|
```
|
|
GET /api/nhn/nks/clusters/
|
|
```
|
|
|
|
**Headers**
|
|
```
|
|
X-NHN-Region: kr2
|
|
X-NHN-Token: {token}
|
|
```
|
|
|
|
**Response (200 OK)**
|
|
```json
|
|
{
|
|
"clusters": [
|
|
{
|
|
"uuid": "cluster-uuid-123",
|
|
"name": "my-cluster",
|
|
"status": "CREATE_COMPLETE",
|
|
"node_count": 3
|
|
}
|
|
]
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### 4.3 클러스터 상세 조회
|
|
|
|
```
|
|
GET /api/nhn/nks/clusters/{cluster_name}/
|
|
```
|
|
|
|
---
|
|
|
|
### 4.4 클러스터 kubeconfig 조회
|
|
|
|
```
|
|
GET /api/nhn/nks/clusters/{cluster_name}/config/
|
|
```
|
|
|
|
**Response (200 OK)**
|
|
```json
|
|
{
|
|
"config": "apiVersion: v1\nclusters:\n- cluster:..."
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### 4.5 클러스터 생성
|
|
|
|
```
|
|
POST /api/nhn/nks/clusters/create/
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"cluster_name": "my-k8s-cluster",
|
|
"vpc_id": "vpc-id-123",
|
|
"subnet_id": "subnet-id-123",
|
|
"instance_type": "m2.c4m8",
|
|
"keypair_name": "my-keypair",
|
|
"kubernetes_version": "v1.28.3",
|
|
"availability_zone": "kr-pub-a",
|
|
"is_public": true,
|
|
"external_network_id": "ext-net-id",
|
|
"external_subnet_id": "ext-subnet-id",
|
|
"node_count": 3,
|
|
"boot_volume_size": 50,
|
|
"boot_volume_type": "General SSD"
|
|
}
|
|
```
|
|
|
|
| 필드 | 타입 | 필수 | 설명 |
|
|
|------|------|------|------|
|
|
| cluster_name | string | O | 클러스터 이름 |
|
|
| vpc_id | string | O | VPC ID |
|
|
| subnet_id | string | O | 서브넷 ID |
|
|
| instance_type | string | O | 인스턴스 타입 (Flavor ID) |
|
|
| keypair_name | string | O | Keypair 이름 |
|
|
| kubernetes_version | string | O | K8s 버전 (예: v1.28.3) |
|
|
| availability_zone | string | O | 가용 영역 |
|
|
| is_public | boolean | X | Public 클러스터 여부 (기본 true) |
|
|
| external_network_id | string | △ | 외부 네트워크 ID (Public 필수) |
|
|
| external_subnet_id | string | △ | 외부 서브넷 ID (Public 필수) |
|
|
| node_count | integer | X | 노드 수 (기본 1) |
|
|
| boot_volume_size | integer | X | 부팅 볼륨 크기 (기본 50GB) |
|
|
| boot_volume_type | string | X | 볼륨 타입 (기본 General SSD) |
|
|
|
|
---
|
|
|
|
### 4.6 클러스터 삭제
|
|
|
|
```
|
|
DELETE /api/nhn/nks/clusters/{cluster_name}/
|
|
```
|
|
|
|
**Response (204 No Content)**
|
|
|
|
---
|
|
|
|
## 5. Object Storage API
|
|
|
|
### 5.1 컨테이너 목록 조회
|
|
|
|
```
|
|
GET /api/nhn/storage/containers/
|
|
```
|
|
|
|
**Headers**
|
|
```
|
|
X-NHN-Region: kr2
|
|
X-NHN-Token: {token}
|
|
X-NHN-Storage-Account: AUTH_xxxxxxxx
|
|
```
|
|
|
|
**Response (200 OK)**
|
|
```json
|
|
{
|
|
"containers": ["container1", "container2", "container3"]
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### 5.2 컨테이너 생성
|
|
|
|
```
|
|
POST /api/nhn/storage/containers/create/
|
|
```
|
|
|
|
**Request Body**
|
|
```json
|
|
{
|
|
"name": "my-new-container"
|
|
}
|
|
```
|
|
|
|
**Response (201 Created)**
|
|
```json
|
|
{
|
|
"status": 201,
|
|
"container": "my-new-container"
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### 5.3 컨테이너 오브젝트 목록 조회
|
|
|
|
```
|
|
GET /api/nhn/storage/containers/{container_name}/
|
|
```
|
|
|
|
**Response (200 OK)**
|
|
```json
|
|
{
|
|
"objects": ["file1.txt", "file2.png", "folder/file3.json"]
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
### 5.4 컨테이너 삭제
|
|
|
|
```
|
|
DELETE /api/nhn/storage/containers/{container_name}/
|
|
```
|
|
|
|
**Response (204 No Content)**
|
|
|
|
---
|
|
|
|
## 에러 응답
|
|
|
|
모든 API는 실패 시 아래 형식으로 에러를 반환합니다:
|
|
|
|
```json
|
|
{
|
|
"error": "에러 메시지",
|
|
"code": 400
|
|
}
|
|
```
|
|
|
|
| HTTP Status | 설명 |
|
|
|-------------|------|
|
|
| 400 | 잘못된 요청 (파라미터 오류) |
|
|
| 401 | 인증 실패 (토큰 없음/만료) |
|
|
| 403 | 권한 없음 |
|
|
| 404 | 리소스 없음 |
|
|
| 500 | 서버 내부 오류 |
|
|
|
|
---
|
|
|
|
## 프론트엔드 사용 예시 (JavaScript)
|
|
|
|
```javascript
|
|
// 1. 토큰 발급
|
|
const tokenResponse = await fetch('/api/nhn/token/', {
|
|
method: 'POST',
|
|
headers: { 'Content-Type': 'application/json' },
|
|
body: JSON.stringify({
|
|
tenant_id: 'your-tenant-id',
|
|
username: 'user@example.com',
|
|
password: 'your-password'
|
|
})
|
|
});
|
|
const { token, tenant_id } = await tokenResponse.json();
|
|
|
|
// 2. API 호출 (인스턴스 목록)
|
|
const instancesResponse = await fetch('/api/nhn/compute/instances/', {
|
|
headers: {
|
|
'X-NHN-Region': 'kr2',
|
|
'X-NHN-Token': token,
|
|
'X-NHN-Tenant-ID': tenant_id
|
|
}
|
|
});
|
|
const instances = await instancesResponse.json();
|
|
```
|
|
|
|
---
|
|
|
|
## 리전 정보
|
|
|
|
| 리전 코드 | 위치 |
|
|
|-----------|------|
|
|
| kr1 | 판교 |
|
|
| kr2 | 평촌 |
|