SHIELDEX Policy Integration API Specification
※ Last updated: 2026-03-24
Document Information
| item | Content |
|---|---|
| Document Version | 6.2026.0324.01 |
| Writing | SOFTCAMP |
| Content-Type | application/json |
Environment Setup (Required)
This API isIP-based Access Controlis applied.
To use the API, the customer's company mustSource IP address of accessYou need to deliver it to SOFTCAMP in advance.
Customer Preparation Requirements
Please provide the following information about the server/system that will call the API.
Delivery Information
- Access source IP address (e.g:
192.168.1.50,10.10.12.100) - Usage (e.g., security portal server, batch job server)
How to Configure SOFTCAMP Engineer
SHIELDEX server'sWebConsoleApi.propertiesRegister allowed IPs in the file.
Configuration File Location
{SHIELDEX 설치 경로}/config/WebConsoleApi.properties
IP Allowlist Settings
| Setting Key | Description | example |
|---|---|---|
security.ip.allowed | IP Whitelist for Tokenless Calls (Comma Separated) | 10.10.12.43,10.10.12.44 |
Allow list(security.ip.allowedif a request is made from an IP not in __PH_0__Blockis returned as follows.
{
"timestamp": "2026-02-11T06:12:33.739+0000",
"status": 403,
"error": "Forbidden",
"message": "IP_ACCESS_DENIED",
"path": "/WebConsoleApi/policy/targets"
}
status:403error:Forbiddenmessage:IP_ACCESS_DENIED
After changing the settings, be sure toRestarting the SHIELDEX WebConsole ServiceThis is needed.
Base URL
http://{serverIp}:{serverPort}/WebConsoleApi
All API paths are called by appending them to the Base URL above.
example— Server IP is10.10.12.100, port is9000in case:
http://10.10.12.100:9000/WebConsoleApi/policy/targets/merged/preview/user001
API Resource Map
This is the list of APIs provided in this document.
Base URL: http://{serverIp}:{serverPort}/WebConsoleApi
/policy/targets
├── GET /policy/targets/merged/preview/{targetId} # 정책 통합 조회
├── POST /policy/targets # 정책 부분 업데이트
└── DELETE /policy/targets # 정책 선택 삭제
| Method | URI | Description |
|---|---|---|
| GET | /policy/targets/merged/preview/{targetId} | Merged Overall View of Company and Individual Policies |
| POST | /policy/targets | Add/modify only the requested policy (keep existing) |
| DELETE | /policy/targets | Release only the requested policy (restore to the parent policy) |
1. Common Rules
1.1 Response Structure
All API responses follow the format below.
{
"code": 0,
"codeMessage": "SUCCESS",
"data": { }
}
| field | Type | Description |
|---|---|---|
code | Integer | Processing Result Code |
codeMessage | String | Processing Result Message |
data | Object | Response Data (returned on GET requests, may be omitted on POST/DELETE) |
1.2 Response Code Definition
| code | codeMessage | Description | HTTP Status |
|---|---|---|---|
0 | SUCCESS | Normal processing completed | 200 |
1 | FAIL | Unable to process | 200 |
4000 | INVALID_REQUEST | Invalid request (missing required values, validation violations, body format/Content-Type errors, etc.) | 400 |
4404 | VALUE_NOT_FOUND | Non-existent target (targetId, policyId, etc.) | 404 |
5000 | INTERNAL_ERROR | Internal Server Error | 500 |
1.3 Timestamp Rules
All timestamp fields areepoch millisecondsIt is in units of (1/1000 seconds).
Unix epoch seconds (10 digits) is**No.**Please make sure to check the number of digits.
epoch seconds : 1761523200 (10자리) ← 이 단위가 아닙니다
epoch milliseconds: 1761523200000 (13자리) ← 이 API에서 사용하는 단위
When converting date/time to epoch milliseconds, always**KST (UTC+9, Asia/Seoul)**It must be converted based on the criteria.
When converted to UTC, there is a 9-hour difference, which results in an application that differs from the intended duration.
"2026-03-21 00:00:00" KST 기준 → 1774278000000 ← 올바른 값
"2026-03-21 00:00:00" UTC 기준 → 1774310400000 ← 9시간 밀림 (KST 09:00으로 적용됨)
- Java:
sdf.setTimeZone(TimeZone.getTimeZone("Asia/Seoul"))usage - JavaScript:
new Date('2026-03-21T00:00:00+09:00')usage TimeZone.getTimeZone("UTC")Prohibited
Fields related to Timestamp
| field | Type | Direction | Description |
|---|---|---|---|
startTimestamp | Long (int64) | Input/Output | Policy application start time (epoch ms,Based on KST). Applied immediately if omitted |
endTimestamp | Long (int64) | Input/Output | Policy application end time (epoch ms,KST Standard). If omitted, indefinite |
startTimestampText | String | Output only | KST conversion date (e.g:2025-12-04 09:52:33) |
endTimestampText | String | Output-only | KST conversion date. If indefinite,null |
Conversion Code Example
// JavaScript (KST 기준)
const start = Date.now(); // 현재 시각 (즉시 적용)
const end = new Date('2026-03-01T00:00:00+09:00').getTime(); // KST 2026-03-01 자정
// Java 1.7 (JDK 1.7) - SimpleDateFormat 사용
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.TimeZone;
public class PolicyTimestamp {
public static void main(String[] args) throws Exception {
// KST 기준 날짜 문자열 파싱
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
sdf.setTimeZone(TimeZone.getTimeZone("Asia/Seoul"));
// 현재 시각 (즉시 적용)
long start = System.currentTimeMillis();
// KST 기준 특정 날짜를 epoch milliseconds 로 변환
// 예: KST 2026-03-21 00:00:00 ~ 2026-03-21 23:59:59 (하루)
long dayStart = sdf.parse("2026-03-21 00:00:00").getTime();
long dayEnd = sdf.parse("2026-03-21 23:59:59").getTime();
System.out.println("startTimestamp: " + dayStart); // 1774278000000
System.out.println("endTimestamp: " + dayEnd); // 1774364399000
}
}
// Java 1.8 이상 (JDK 1.8+) - LocalDateTime + ZoneId 사용
import java.time.LocalDateTime;
import java.time.ZoneId;
public class PolicyTimestamp {
public static void main(String[] args) {
ZoneId kst = ZoneId.of("Asia/Seoul");
// 현재 시각 (즉시 적용)
long start = System.currentTimeMillis();
// KST 기준 특정 날짜를 epoch milliseconds 로 변환
// 예: KST 2026-03-21 00:00:00 ~ 2026-03-21 23:59:59 (하루)
long dayStart = LocalDateTime.of(2026, 3, 21, 0, 0, 0)
.atZone(kst).toInstant().toEpochMilli();
long dayEnd = LocalDateTime.of(2026, 3, 21, 23, 59, 59)
.atZone(kst).toInstant().toEpochMilli();
System.out.println("startTimestamp: " + dayStart); // 1774278000000
System.out.println("endTimestamp: " + dayEnd); // 1774364399000
}
}
The required value is **epoch milliseconds in KST (13-digit integer)**.
- Java 1.7 (JDK 1.7):
SimpleDateFormat,Date,CalendarGenerating epoch milliseconds with __PH_0__ - Java 1.8+ (JDK 1.8+):
InstantEasy Conversion with Classes
The above example is for reference, and it can also be used in a Java 1.7 environment.System.currentTimeMillis()You can also generate and use the same 13-digit millisecond value in various ways.
Reference: startTimestampText, endTimestampTextThis is a read-only field and cannot be used for input.
Validation Rules
- When both are specified
endTimestampastartTimestampmust be larger (in case of violation400 INVALID_REQUEST) - If both are omitted, it will be applied immediately and indefinitely.
1.4 Policy Priorities
The policy value is determined by the following priority. If a higher level exists, it overrides the lower level.
사용자 개별 정책 (User) ← 최우선
↓
소속 그룹 정책 (Group)
↓
전사 기본 정책 (Default) ← 최하위
1.5 Override Information
These are the fields included in each policy item of the query response. You can find out where the policy is set.
| field | Type | Description |
|---|---|---|
overridden | Boolean | When individual policies are appliedtrue, if the default is set to "transmission"false |
overriddenBy | String | Policy Source:"user" / "group" / "default" |
overriddenById | String | User ID or Group ID that set the policy (defaultIf sonull) |
1.6 Request Body Format (Content-Type) Rules
:::warning[ImportantPOST /policy/targets, DELETE /policy/targetsmust be **JSON body +Content-Type: application/json**must be called.]
text/plainRequests will be rejected if called in a format other than JSON.
- Recommended Header:
Content-Type: application/json - Discouraged example:
Content-Type: text/plain;charset=UTF-8(Request Denied)
Failure Response Example (Body Format Error)
{
"code": 4000,
"codeMessage": "INVALID_REQUEST"
}
2. Policy Integration Inquiry
GET /policy/targets/merged/preview/{targetId}
Enterprise policies and target individual policiesMergeTherefore, it returns the overall policy results that will be actually applied to the user.
Full URL Example
GET http://{serverIp}:{serverPort}/WebConsoleApi/policy/targets/merged/preview/user001
Path Parameters
| Parameter | Type | required | Description |
|---|---|---|---|
targetId | String | O | Target User ID |
Response Field
| field | Type | Description |
|---|---|---|
data.targetId | String | Target ID |
data.templates | Array | Policy List by Category |
data.templates[].categoryId | Integer | Category ID |
data.templates[].categoryName | String | Category name (e.g., Common, Exception, MS Office ...) |
data.templates[].policyList | Array | List of policy items in this category |
Policy Item (policyList) Field
| field | Type | Description |
|---|---|---|
policyId | String | Policy Unique Identifier (e.g.:SD_DOC_OP_MODE) |
policyName | String | Policy Display Name |
policyValue | StringorInteger | Current applied policy value |
policyDesc | String | Policy Detailed Description |
uiTypeCode | Integer | UI Type —1: Text input,2: Selectable |
uiOptions | Array | List of Selectable Options (uiTypeCode=2only exists when) |
overridden | Boolean | Application of Individual Policies |
overriddenBy | String | Policy Source (user / group / default) |
overriddenById | String | Subject ID that set the policy |
startTimestamp | Long | Start time of application (epoch ms) |
endTimestamp | Long | End time (epoch ms) |
curl example
curl -X GET "http://{serverIp}:{serverPort}/WebConsoleApi/policy/targets/merged/preview/user001" -H "Content-Type: application/json"
Response Example — 200 OK
{
"code": 0,
"codeMessage": "SUCCESS",
"data": {
"targetId": "user001",
"templates": [
{
"categoryId": 1,
"categoryName": "공통",
"policyList": [
{
"uiOrder": 1,
"uiTypeCode": 2,
"uiTypeDesc": "select",
"policyId": "SD_DOC_OP_MODE",
"policyName": "무해화 사용 설정",
"policyDesc": "문서 무해화 기능의 사용 여부를 설정합니다.\nON: 문서 무해화 기능을 사용합니다.\nOFF: 문서 무해화 기능을 사용하지 않습니다.\n'기록 모드' 설정 시 문서 무해화를 수행하지만, 반입 처리되며, 상세 로그가 기록됩니다.",
"uiOptions": [
{ "value": 0, "label": "사용 안함" },
{ "value": 1, "label": "사용 함" },
{ "value": 2, "label": "기록 모드" }
],
"policyValue": 2,
"overridden": true,
"overriddenBy": "user",
"overriddenById": "user001",
"startTimestamp": 1762300800000,
"endTimestamp": 1862300801000,
"startTimestampText": "2025-11-05 09:00:00",
"endTimestampText": "2029-01-15 09:00:01"
},
{
"uiOrder": 11,
"uiTypeCode": 2,
"uiTypeDesc": "select",
"policyId": "SD_NOSUP_EXT_MODE",
"policyName": "미지원 확장자 차단 설정",
"policyDesc": "서비스에서 지원하지 않는 확장자 및 '무해화 허용 확장자 필터'에 포함되지 않은 확장자에 대한 처리 방식을 설정합니다.\n'기록 모드' 설정 시 미지원 확장자로 탐지되더라도 반입 처리되며, 상세 로그가 기록됩니다.",
"uiOptions": [
{ "value": 0, "label": "차단" },
{ "value": 1, "label": "원본 반입" },
{ "value": 2, "label": "기록 모드" }
],
"policyValue": 2,
"overridden": true,
"overriddenBy": "user",
"overriddenById": "user001"
},
{
"uiOrder": 12,
"uiTypeCode": 2,
"uiTypeDesc": "select",
"policyId": "SD_EXT_MODE",
"policyName": "확장자 위변조 차단 설정",
"policyDesc": "파일 확장자와 실제 파일 형식이 일치하지 않는 경우, 위·변조로 간주하여 처리 방식을 설정합니다.\n'기록 모드' 설정 시 위·변조로 탐지되더라도 반입 처리되며, 상세 로그가 기록됩니다.",
"uiOptions": [
{ "value": 0, "label": "차단" },
{ "value": 1, "label": "원본 반입" },
{ "value": 2, "label": "기록 모드" }
],
"policyValue": 2,
"overridden": true,
"overriddenBy": "user",
"overriddenById": "user001"
}
]
},
{
"categoryId": 2,
"categoryName": "예외",
"policyList": [
{
"uiOrder": 6,
"uiTypeCode": 2,
"uiTypeDesc": "select",
"policyId": "SD_EXCEPTION_BYPASS",
"policyName": "무해화 오류 발생 시 원본 반입 설정",
"policyDesc": "무해화 엔진 오류, 처리 불가, 시스템 예외 등으로 인해 무해화가 정상적으로 완료되지 못한 경우의 처리 방식을 설정합니다.\n'기록 모드' 설정 시 무해화 오류가 발생하더라도 반입 처리되며, 상세 로그가 기록됩니다.",
"uiOptions": [
{ "value": 1, "label": "원본 반입" },
{ "value": 0, "label": "차단" },
{ "value": 2, "label": "기록 모드" }
],
"policyValue": 2,
"overridden": true,
"overriddenBy": "user",
"overriddenById": "user001"
},
{
"uiOrder": 2,
"uiTypeCode": 1,
"uiTypeDesc": "text",
"policyId": "CQMS_NOSUP_EXCEPT_EXT",
"policyName": "미지원 확장자 차단 예외 설정",
"policyDesc": "미지원 확장자는 '공통' 탭의 '미지원 확장자 차단 설정' 값에 의해 처리되지만,\n이 항목에서 예외로 지정된 확장자는 원본 반입을 허용합니다.\n입력 예시) log;tmp;",
"placeholder": "미지원 확장자 차단에서 예외될 확장자를 설정합니다.",
"policyValue": "log;tmp;dat;",
"overridden": true,
"overriddenBy": "user",
"overriddenById": "user001"
},
{
"uiOrder": 3,
"uiTypeCode": 1,
"uiTypeDesc": "text",
"policyId": "SD_EXCEPT_EXT",
"policyName": "확장자 위변조 차단 예외 설정",
"policyDesc": "확장자 위변조 파일은 '공통' 탭의 '확장자 위변조 차단 설정' 값에 의해 처리됩니다.\n이 항목에서 예외로 지정된 파일 확장자는 원본 반입을 허용합니다.\n입력 예시) docx;png;pptx;",
"placeholder": "확장자 차단이 된 경우 예외 처리하여 반입할 수 있습니다.",
"policyValue": "docx;xlsx;png;",
"overridden": true,
"overriddenBy": "user",
"overriddenById": "user001"
}
]
}
]
}
}
3. Policy Registration/Modification (Partial Update)
POST /policy/targets
Policy for Specific UserspartiallyRegister or modify.
Full URL Example
POST http://{serverIp}:{serverPort}/WebConsoleApi/policy/targets
- requestOnly included policieswill be added or updated.
- Previously registered**Maintain other policies as they are without modification.**It works.
- already exists
policyIdwill send the value/period of the corresponding policyOverwrite with new valueIt is done.
Action Example
기존 상태: A, B, C 정책이 등록되어 있음
POST 요청: policyList 에 C(새 값), D를 전달
결과: A, B 유지 + C 업데이트 + D 신규 추가
Request Body
| field | Type | required | Description |
|---|---|---|---|
targetId | String | O | Policy Target User ID |
manager_id | String | X | Policy Change Requester ID (for history identification, optional) |
updateReason | String | X | Reason for Change (For History Management) |
policyList | Array | O | List of Policies to be Updated |
policyList[].policyId | String | O | Policy Identifier (e.g.:SD_DOC_OP_MODE) |
policyList[].policyValue | StringorInteger | O | Policy values to set |
policyList[].startTimestamp | Long (int64) | X | Start time of application (epoch ms). If omitted, applies immediately. |
policyList[].endTimestamp | Long (int64) | X | End time (epoch ms). If omitted, it is indefinite. |
Required Conditions for Content-Type
POST /policy/targetsmust be requested with the header below.
Content-Type: application/json
text/plainError response when called with:
{
"code": 4000,
"codeMessage": "INVALID_REQUEST"
}
curl example
Switching to Decontamination Mode OFF (Setting Duration):
curl -X POST "http://{serverIp}:{serverPort}/WebConsoleApi/policy/targets" -H "Content-Type: application/json" -d '{
"targetId": "user001",
"manager_id": "portal-admin-01",
"updateReason": "무해화 모드 OFF 전환 (기간 설정)",
"policyList": [
{
"policyId": "SD_DOC_OP_MODE",
"policyValue": 0,
"startTimestamp": 1761523200000,
"endTimestamp": 1762128000000
}
]
}'
Switching the Decontamination Function Record Mode:
curl -X POST "http://{serverIp}:{serverPort}/WebConsoleApi/policy/targets" -H "Content-Type: application/json" -d '{
"targetId": "user001",
"manager_id": "portal-admin-01",
"updateReason": "무해화 기능 기록 모드 전환 (모니터링)",
"policyList": [
{
"policyId": "SD_DOC_OP_MODE",
"policyValue": 2
}
]
}'
Unsupported Extension Record Mode Switch:
curl -X POST "http://{serverIp}:{serverPort}/WebConsoleApi/policy/targets" -H "Content-Type: application/json" -d '{
"targetId": "user001",
"manager_id": "portal-admin-01",
"updateReason": "미지원 확장자 기록 모드 전환 (모니터링)",
"policyList": [
{
"policyId": "SD_NOSUP_EXT_MODE",
"policyValue": 2
}
]
}'
Switching Extension Tampering Record Mode:
curl -X POST "http://{serverIp}:{serverPort}/WebConsoleApi/policy/targets" -H "Content-Type: application/json" -d '{
"targetId": "user001",
"manager_id": "portal-admin-01",
"updateReason": "확장자 위변조 기록 모드 전환 (모니터링)",
"policyList": [
{
"policyId": "SD_EXT_MODE",
"policyValue": 2
}
]
}'
Switching to Decontamination Error Logging Mode:
curl -X POST "http://{serverIp}:{serverPort}/WebConsoleApi/policy/targets" -H "Content-Type: application/json" -d '{
"targetId": "user001",
"manager_id": "portal-admin-01",
"updateReason": "무해화 오류 기록 모드 전환 (모니터링)",
"policyList": [
{
"policyId": "SD_EXCEPTION_BYPASS",
"policyValue": 2
}
]
}'
Update for Blocking Exceptions for Unsupported File Extensions:
curl -X POST "http://{serverIp}:{serverPort}/WebConsoleApi/policy/targets" -H "Content-Type: application/json" -d '{
"targetId": "user001",
"manager_id": "portal-admin-01",
"updateReason": "미지원 확장자 예외 목록 갱신",
"policyList": [
{
"policyId": "CQMS_NOSUP_EXCEPT_EXT",
"policyValue": "log;tmp;"
}
]
}'
Update on Extension Spoofing Block Exception Settings:
curl -X POST "http://{serverIp}:{serverPort}/WebConsoleApi/policy/targets" -H "Content-Type: application/json" -d '{
"targetId": "user001",
"manager_id": "portal-admin-01",
"updateReason": "확장자 위변조 예외 목록 갱신",
"policyList": [
{
"policyId": "SD_EXCEPT_EXT",
"policyValue": "docx;png;pptx;"
}
]
}'
Simultaneous application of multiple recording modes:
curl -X POST "http://{serverIp}:{serverPort}/WebConsoleApi/policy/targets" -H "Content-Type: application/json" -d '{
"targetId": "user001",
"manager_id": "portal-admin-01",
"updateReason": "전체 기록 모드 전환 (모니터링)",
"policyList": [
{ "policyId": "SD_DOC_OP_MODE", "policyValue": 2 },
{ "policyId": "SD_NOSUP_EXT_MODE", "policyValue": 2 },
{ "policyId": "SD_EXT_MODE", "policyValue": 2 },
{ "policyId": "SD_EXCEPTION_BYPASS", "policyValue": 2 },
{ "policyId": "CQMS_NOSUP_EXCEPT_EXT","policyValue": "log;tmp;" },
{ "policyId": "SD_EXCEPT_EXT", "policyValue": "docx;png;pptx;" }
]
}'
Response — 200 OK
{
"code": 0,
"codeMessage": "SUCCESS"
}
Error Responses
| Situation | code | codeMessage |
|---|---|---|
targetIddoes not exist | 4404 | VALUE_NOT_FOUND |
policyIddoes not exist | 4404 | VALUE_NOT_FOUND |
endTimestampastartTimestampbelow | 4000 | INVALID_REQUEST |
Content-TypeThis is not JSON (text/plainetc.) | 4000 | INVALID_REQUEST |
4. Delete Policy
DELETE /policy/targets
Individual policies applied to specific usersDeselect optionallydoes.
The released policy is automatically applied according to the policy priority chain as **higher-level policies (affiliated group policies or enterprise defaults)**.
Full URL Example
DELETE http://{serverIp}:{serverPort}/WebConsoleApi/policy/targets
Request Body
| field | Type | required | Description |
|---|---|---|---|
targetId | String | O | Policy Target User ID |
policyList | Array | O | List of Policies to be Released |
policyList[].policyId | String | O | Policy Identifier |
Required Conditions for Content-Type
DELETE /policy/targetsSince there is a request body, please be sure to use the header below.
Content-Type: application/json
curl example
curl -X DELETE "http://{serverIp}:{serverPort}/WebConsoleApi/policy/targets" -H "Content-Type: application/json" -d '{
"targetId": "user001",
"policyList": [
{ "policyId": "SD_DOC_OP_MODE" },
{ "policyId": "SD_DOC_LIMIT_SIZE" }
]
}'
Response — 200 OK
{
"code": 0,
"codeMessage": "SUCCESS"
}
5. Integration Flow Summary
You can integrate in the following order.
| step | Method | URI | Description |
|---|---|---|---|
| 1 | GET | /policy/targets/merged/preview/{userId} | Check the list of all currently applied policies |
| 2 | POST | /policy/targets | Request only the policies to be changed (the rest will be automatically maintained) |
| 3 | DELETE | /policy/targets | Request only the policy to be lifted (restore to the parent policy) |
| 4 | GET | /policy/targets/merged/preview/{userId} | Recheck Status After Change |
- Step 1of the response retrieved from
policyIdUse the values as they are to modify/delete in steps 2-3. - Step 2 POSTSince this is a partial update, you only need to send the policies that need to be changed. There is no need to send the entire document.
- All changes are automatically recorded, allowing you to restore to a previous state if needed.
- When making POST/DELETE calls, it is essential to
Content-Type: application/jsonSpecify.