본문으로 건너뛰기

Caffeine License API

Phase 20에서 도입된 Licensing 시스템의 REST API 엔드포인트입니다.

라이선스 정책 안내

에디션별 기능·가격·활성화 절차는 **라이선스 & 가격 정책**을 참조하세요. 이 문서는 REST API 기술 사양만 다룹니다.

개요

License API는 라이선스 상태 조회, 하드웨어 ID 관리, 이력 추적, 토큰 업로드 기능을 제공합니다.

Base URL: http://localhost:5200/api/license

네임스페이스: Caffeine.Engine.Controllers 어셈블리: Caffeine.Engine.dll .NET 버전: .NET 10.0


인증

현재 License API는 공개 엔드포인트입니다. 프로덕션 환경에서는 JWT Bearer 토큰 인증을 권장합니다.

Authorization: Bearer <token>

엔드포인트 요약

메서드경로설명
GET/api/license/status라이선스 상태 조회
GET/api/license/hwid하드웨어 ID 조회
GET/api/license/features라이선스 기능 목록 조회
GET/api/license/history라이선스 이력 조회
POST/api/license/upload토큰 업로드
POST/api/license/revalidate라이선스 재검증

상세 엔드포인트

GET /status

현재 라이선스 상태를 조회합니다.

요청:

GET /api/license/status

응답 (200 OK):

{
"tier": "Professional",
"expiration": "2026-12-31T23:59:59Z",
"daysRemaining": 329,
"isValid": true,
"validationMessage": "Valid license",
"limits": {
"maxTags": 1000,
"maxDrivers": 10
},
"usage": {
"currentTags": 50,
"currentDrivers": 3
}
}

응답 필드:

필드타입설명
tierstring라이선스 등급 (Community, Professional, Enterprise)
expirationstring?만료일 (ISO 8601, null이면 무기한)
daysRemainingint남은 일수 (만료 시 0)
isValidbool유효성 여부
validationMessagestring검증 메시지
limits.maxTagsint최대 태그 수
limits.maxDriversint최대 드라이버 수
usage.currentTagsint현재 사용 중인 태그 수
usage.currentDriversint현재 사용 중인 드라이버 수

GET /hwid

시스템의 하드웨어 ID를 조회합니다. 라이선스 발급 요청 시 필요합니다.

요청:

GET /api/license/hwid

응답 (200 OK):

{
"machineId": "A1B2C3D4E5F67890ABCDEF1234567890",
"maskedId": "A1B2****7890"
}

응답 필드:

필드타입설명
machineIdstring전체 하드웨어 ID (라이선스 발급 시 필요)
maskedIdstring마스킹된 ID (UI 표시용)

GET /features

현재 라이선스에서 사용 가능한 기능 목록을 조회합니다.

요청:

GET /api/license/features

응답 (200 OK):

[
"BasicMonitoring",
"AdvancedAnalytics",
"MultiSiteSupport",
"CustomDrivers"
]

응답: 사용 가능한 기능명 문자열 배열


GET /history

라이선스 이벤트 이력을 조회합니다.

요청:

GET /api/license/history

응답 (200 OK):

[
{
"timestamp": "2026-02-06T10:30:00Z",
"eventType": "Loaded",
"message": "라이선스 로드 성공",
"details": "Tier: Professional"
},
{
"timestamp": "2026-02-05T14:00:00Z",
"eventType": "Validated",
"message": "라이선스 검증 완료",
"details": null
}
]

응답 필드:

필드타입설명
timestampstring이벤트 발생 시각 (ISO 8601, UTC)
eventTypestring이벤트 유형 (Loaded, Validated, Expired, Failed)
messagestring이벤트 메시지
detailsstring?상세 정보 (선택)

POST /upload

라이선스 토큰을 업로드하고 적용합니다.

요청:

POST /api/license/upload
Content-Type: application/json

{
"token": "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9..."
}

요청 필드:

필드타입필수설명
tokenstring라이선스 토큰 (JWT 형식)

응답 (200 OK - 성공):

{
"success": true,
"message": "라이선스가 성공적으로 적용되었습니다.",
"license": {
"tier": "Professional",
"expiration": "2026-12-31T23:59:59Z",
"daysRemaining": 329,
"isValid": true,
"validationMessage": "Valid license",
"limits": {
"maxTags": 1000,
"maxDrivers": 10
},
"usage": {
"currentTags": 0,
"currentDrivers": 0
}
}
}

응답 (400 Bad Request - 실패):

{
"success": false,
"message": "라이선스 검증 실패: HWID mismatch",
"license": null
}

응답 필드:

필드타입설명
successbool업로드 성공 여부
messagestring결과 메시지
licenseLicenseStatusDto?적용된 라이선스 정보 (성공 시)
토큰 자동 영속화 (v2.0.8+)

업로드 성공 시 토큰이 로컬 디스크에 자동 저장됩니다. 서버 재시작 시 저장된 토큰이 자동으로 로드되므로 재업로드가 필요 없습니다. 저장 경로는 appsettings.jsonLicensing.TokenStorePath로 설정합니다.


POST /revalidate

현재 라이선스를 재검증합니다.

요청:

POST /api/license/revalidate

응답 (200 OK - 성공):

{
"tier": "Professional",
"expiration": "2026-12-31T23:59:59Z",
"daysRemaining": 329,
"isValid": true,
"validationMessage": "Valid license",
"limits": {
"maxTags": 1000,
"maxDrivers": 10
},
"usage": {
"currentTags": 50,
"currentDrivers": 3
}
}

응답 (400 Bad Request - 실패): 검증 실패 시에도 동일한 DTO 구조가 반환되며, isValid: false와 함께 validationMessage에 실패 사유가 포함됩니다.


DTO 정의

LicenseStatusDto

public class LicenseStatusDto
{
public string Tier { get; set; } = "Community";
public DateTime? Expiration { get; set; }
public int DaysRemaining { get; set; }
public bool IsValid { get; set; }
public string ValidationMessage { get; set; } = string.Empty;
public LicenseLimitsDto Limits { get; set; } = new();
public LicenseUsageDto Usage { get; set; } = new();
}

LicenseLimitsDto

public class LicenseLimitsDto
{
public int MaxTags { get; set; }
public int MaxDrivers { get; set; }
}

LicenseUsageDto

public class LicenseUsageDto
{
public int CurrentTags { get; set; }
public int CurrentDrivers { get; set; }
}

HardwareIdDto

public class HardwareIdDto
{
public string MachineId { get; set; } = string.Empty;
public string MaskedId { get; set; } = string.Empty;
}

LicenseUploadRequest

public class LicenseUploadRequest
{
public string Token { get; set; } = string.Empty;
}

LicenseUploadResponse

public class LicenseUploadResponse
{
public bool Success { get; set; }
public string Message { get; set; } = string.Empty;
public LicenseStatusDto? License { get; set; }
}

LicenseHistoryEventDto

public class LicenseHistoryEventDto
{
public DateTime Timestamp { get; set; }
public string EventType { get; set; } = string.Empty;
public string Message { get; set; } = string.Empty;
public string? Details { get; set; }
}

에러 코드

HTTP 상태설명대응 방법
200성공-
400잘못된 요청 (토큰 누락, 검증 실패)요청 본문 확인
401인증 실패 (JWT 토큰 없음/만료)토큰 갱신
404엔드포인트 없음URL 확인
500서버 내부 오류로그 확인

라이선스 등급 (Tier)

등급최대 태그최대 드라이버기능
Community1002기본 모니터링
Professional1,00010고급 분석, 다중 사이트
Enterprise무제한무제한모든 기능, 기술 지원

전체 기능 비교는 에디션별 기능 비교를 참조하세요.


사용 예제

C# 예제

using System.Net.Http.Json;

var client = new HttpClient
{
BaseAddress = new Uri("http://localhost:5200")
};

// JWT 인증 (필요 시)
// client.DefaultRequestHeaders.Authorization =
// new AuthenticationHeaderValue("Bearer", token);

// 라이선스 상태 조회
var status = await client.GetFromJsonAsync<LicenseStatusDto>("/api/license/status");
Console.WriteLine($"Tier: {status?.Tier}");
Console.WriteLine($"Days Remaining: {status?.DaysRemaining}");
Console.WriteLine($"Valid: {status?.IsValid}");

// 하드웨어 ID 조회
var hwid = await client.GetFromJsonAsync<HardwareIdDto>("/api/license/hwid");
Console.WriteLine($"Machine ID: {hwid?.MachineId}");

// 토큰 업로드
var uploadResponse = await client.PostAsJsonAsync("/api/license/upload", new
{
Token = "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9..."
});
var result = await uploadResponse.Content.ReadFromJsonAsync<LicenseUploadResponse>();
Console.WriteLine($"Upload Success: {result?.Success}");
Console.WriteLine($"Message: {result?.Message}");

curl 예제

# 라이선스 상태 조회
curl http://localhost:5200/api/license/status

# 하드웨어 ID 조회
curl http://localhost:5200/api/license/hwid

# 기능 목록 조회
curl http://localhost:5200/api/license/features

# 이력 조회
curl http://localhost:5200/api/license/history

# 토큰 업로드
curl -X POST http://localhost:5200/api/license/upload \
-H "Content-Type: application/json" \
-d '{"token": "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9..."}'

# 라이선스 재검증
curl -X POST http://localhost:5200/api/license/revalidate

PowerShell 예제

# 라이선스 상태 조회
$status = Invoke-RestMethod -Uri "http://localhost:5200/api/license/status"
Write-Host "Tier: $($status.tier)"
Write-Host "Valid: $($status.isValid)"

# 하드웨어 ID 조회
$hwid = Invoke-RestMethod -Uri "http://localhost:5200/api/license/hwid"
Write-Host "Machine ID: $($hwid.machineId)"

# 토큰 업로드
$body = @{ token = "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9..." } | ConvertTo-Json
$result = Invoke-RestMethod -Uri "http://localhost:5200/api/license/upload" `
-Method Post -Body $body -ContentType "application/json"
Write-Host "Success: $($result.success)"

Swagger UI

개발 환경에서 Swagger UI를 통해 API를 테스트할 수 있습니다:

http://localhost:5200/swagger

v2.1.0 신규: AddCaffeineLicenseVerification()

Engine 외부에서 라이선스 검증만 필요한 경우 AddCaffeineLicenseVerification()을 사용하세요. ILicenseServiceIHardwareInfo만 등록되며, 라이선스 생성·서명 기능은 포함되지 않습니다.

builder.Services.AddCaffeineLicenseVerification();

자세한 내용: Infrastructure API — FIR-014

관련 문서


네임스페이스: Caffeine.Engine.Controllers DTO 네임스페이스: Caffeine.Engine.DTOs 어셈블리: Caffeine.Engine.dll (v2.1.0) .NET 플랫폼: .NET 10.0