회원가입 | 고객센터 |
DESIGNONEX
DesignOneX CMS
로그인 회원가입
고객센터

DX Security — Authorization Bypass 보안 플러그인

D DX관리자
2026.09.04 01:38 5 0



DX Security — Authorization Bypass 방어 v1.0.0 안내서

PHP 5.6+ · IIS / Apache / Nginx 완전 호환 코어 수정 없음 — 훅으로만 동작



목차

  1. Authentication vs Authorization
  2. DXCMS 코어의 현재 방어 수준
  3. 이 플러그인의 역할
  4. 설치 방법
  5. 방어층 상세 설명
  6. 보안 로그 읽는 법
  7. 보안 강점 요약
  8. 개발자 API 가이드


1. Authentication vs Authorization

구분 질문
Authentication (11번) 누구인가? 김철수
Authorization (12번) 무엇을 할 수 있는가? 본인 게시글만 삭제 가능

로그인에 성공했다고 모든 기능을 사용할 수 있어서는 안 됩니다.

공격 예시:

수평적 권한 상승 (IDOR):
  /api/post/100/edit  (내 게시글)
  /api/post/101/edit  (타인 게시글) ← 수정 가능하면 취약

수직적 권한 상승:
  /admin/member/delete  (일반 회원이 직접 접근)

Mass Assignment:
  POST /mypage/update
  { "name": "홍길동", "role": "admin" }  ← role 주입


2. DXCMS 코어의 현재 방어 수준

코어가 이미 잘 하는 것

항목 방어 방식 평가
게시글 소유권 isAdmin() || user_id === member_id
댓글 소유권 isAdmin() || user_id === member_id
role Allowlist in_array(['member','manager','admin'])
mypage 허용 필드 $upd 배열 명시적 구성
관리자 URL 인증 Dispatcher::isAdmin()


코어가 하지 않는 것

항목 위험도
권한 거부 감사 로그 높음
IDOR/수평 권한 상승 탐지 높음
수직 권한 상승 탐지 높음
Mass Assignment 위험 필드 차단 높음
일괄 작업 권한 검증 API 중간
Fail Closed 정책 높음
플러그인 표준 권한 API 중간

3. 이 플러그인의 역할

코어의 권한 로직을 수정하거나 교체하지 않습니다. 코어가 하지 않는 탐지, 로깅, 표준 권한 API를 훅으로 보강합니다.



4. 설치 방법

(DXCMS 루트)/
└── plugins/
    └── dx-security-authz/
        ├── manifest.php
        └── plugin.php
관리자 → 플러그인 → dx-security-authz → 활성화


5. 방어층 상세 설명


AZ1. 권한 거부 감사 로그

모든 권한 관련 이벤트를 data/security.log에 기록합니다.



AZ2. IDOR / 수평적 권한 상승 탐지

같은 등급의 다른 사용자 리소스에 접근하는 시도를 탐지합니다.

탐지 방식:
  URL/POST의 member_id, user_id, uid 파라미터가
  현재 로그인 사용자 ID와 다를 때 → IDOR_SUSPECT 로그

예:
  로그인 사용자 ID: 42
  GET /api/member?member_id=43
  → IDOR_SUSPECT 로그 기록

WAF: 탐지·로그만 수행
실제 차단: 코어 소유권 검사 + dx_authz_owns() 담당


AZ3. 수직적 권한 상승 탐지

일반 회원이 관리자 기능 접근을 시도하는 패턴을 탐지합니다.

탐지 패턴:
  /admin/ 경로 직접 접근
  /api/admin/ 직접 접근
  ?action=admin 파라미터
  ?role=admin 파라미터
  ?is_admin=1 파라미터

→ VERTICAL_ESCALATION_ATTEMPT 로그

WAF: 탐지·로그만 수행
실제 차단: 코어 Dispatcher::isAdmin() 담당


AZ4. Mass Assignment 위험 필드 차단

사용자 요청에 보호 필드가 포함되면 해당 필드를 $_POST에서 제거합니다.

보호 필드 목록:
  role, is_admin, level, permission, status,
  verified, account_type, group_id, point, exp

처리 방식:
  권한 상승 패턴 (role=admin, is_admin=1 등) → 차단 + 로그
  단순 보호 필드 포함 → 필드 제거 + 로그

적용 대상:
  /auth/, /api/member, /mypage, /member/ 경로
  POST 요청, 일반 회원만 (관리자 제외)

예:
  POST /mypage/update
  { "name": "홍길동", "role": "admin" }
  → role 필드 제거 후 처리
  → MASS_ASSIGNMENT_FIELD 로그


AZ5. 일괄 작업 권한 검증

대량 처리 시 각 항목을 개별적으로 권한 검증합니다.

위험한 방식:
  첫 번째 ID 권한 확인 → 나머지 모두 처리

안전한 방식 (dx_authz_check_batch):
  ID 1 → 소유자 확인
  ID 2 → 소유자 확인
  ID 3 → 소유자 확인
  → 하나라도 실패 시 전체 거부


AZ6. Fail Closed

권한 시스템 오류 시 허용이 아닌 거부로 처리합니다.

잘못된 방식 (Fail Open):
  권한 확인 실패 → 일단 허용

이 플러그인 (Fail Closed):
  dx_authz_exception 훅 발동
  → HTTP 403
  → AUTHZ_EXCEPTION_FAIL_CLOSED 로그
  → exit


AZ7. 플러그인 표준 권한 API

플러그인 개발자가 일관된 방식으로 권한을 검사할 수 있는 표준 함수를 제공합니다.



6. 보안 로그 읽는 법

이벤트 타입

타입 의미
AUTHZ:PRIVILEGE_ESCALATION_BLOCKED 권한 상승 시도 차단
AUTHZ:MASS_ASSIGNMENT_FIELD 보호 필드 제거
AUTHZ:VERTICAL_ESCALATION_ATTEMPT 수직 권한 상승 시도 탐지
AUTHZ:IDOR_SUSPECT IDOR 의심 탐지
AUTHZ:ACCESS_DENIED_403 403 거부
AUTHZ:AUTHZ_DENIED_NOT_LOGIN 미로그인 접근 거부
AUTHZ:AUTHZ_DENIED_NOT_ADMIN 비관리자 접근 거부
AUTHZ:AUTHZ_DENIED_NOT_OWNER 소유권 없는 접근 거부
AUTHZ:BATCH_OWNERSHIP_DENIED 일괄 작업 소유권 거부
AUTHZ:FILTER_BLOCKED_FIELD 필드 필터링으로 차단
AUTHZ:AUTHZ_EXCEPTION_FAIL_CLOSED 권한 예외 — Fail Closed


로그 예시

# Mass Assignment 차단
[2026-09-03 09:00:01][AUTHZ:PRIVILEGE_ESCALATION_BLOCKED][IP:45.33.x.x][...][UID:42][POST /mypage/update]
field=role value=admin uri=/mypage/update

# IDOR 탐지
[2026-09-03 14:22:10][AUTHZ:IDOR_SUSPECT][IP:58.29.x.x][...][UID:42][GET /api/member]
user_id=42 param=member_id target_id=43 uri=/api/member

# 일괄 작업 소유권 거부
[2026-09-03 16:45:03][AUTHZ:BATCH_OWNERSHIP_DENIED][IP:121.131.x.x][...][UID:42][POST /api/post/bulk]
user_id=42 denied_ids=100,101 context=bulk_delete


7. 보안 강점 요약

공격 결과 방어 레이어
role=admin POST 주입 필드 제거 + 차단 AZ4
is_admin=1 POST 주입 필드 제거 + 차단 AZ4
IDOR (타인 게시글 수정) 코어 소유권 검사 + IDOR 탐지 로그 코어 + AZ2
수직 권한 상승 시도 코어 Dispatcher 차단 + 탐지 로그 코어 + AZ3
일괄 작업 권한 우회 dx_authz_check_batch()로 개별 검증 AZ5
권한 시스템 오류 Fail Closed (403) AZ6
정상 mypage 수정 통과 (보호 필드 없으면 영향 없음)


8. 개발자 API 가이드

로그인 여부 확인

if (!dx_authz_check('login', 0, 0, 'my_plugin')) {
    http_response_code(401);
    exit(json_encode(array('success' => false, 'message' => '로그인이 필요합니다.')));
}


관리자 권한 확인

if (!dx_authz_check('admin', 0, 0, 'my_plugin_admin')) {
    http_response_code(403);
    exit(json_encode(array('success' => false, 'message' => '관리자만 사용할 수 있습니다.')));
}


소유권 확인 (게시글 수정 등)

// 게시글 조회
$post = $db->row("SELECT * FROM posts WHERE id=?", array($postId));
if (!$post) { dx_error('게시글을 찾을 수 없습니다.', 404); }

// 소유권 확인
if (!dx_authz_owns($post['member_id'], 'post_edit')) {
    dx_error('수정 권한이 없습니다.', 403);
}

// 수정 처리


Mass Assignment 방어

// 허용 필드만 추출
$allowed = array('name', 'email', 'intro', 'phone');
$safe = dx_authz_filter_fields($_POST, $allowed, 'mypage_update');

// 안전한 데이터만 DB 업데이트
$db->updateRow('members', $safe, array('id' => $memberId));


일괄 작업 권한 검증

$ids = isset($_POST['ids']) ? (array)$_POST['ids'] : array();

// 각 게시글의 소유자 조회
$ownerships = array();
foreach ($ids as $id) {
    $post = $db->row("SELECT id, member_id FROM posts WHERE id=?", array((int)$id));
    if ($post) $ownerships[$post['id']] = (int)$post['member_id'];
}

// 일괄 소유권 검증
if (!dx_authz_check_batch($ids, $ownerships, 'bulk_delete')) {
    dx_error('일부 게시글에 대한 권한이 없습니다.', 403);
}

// 삭제 처리


권한 감사 로그 직접 기록

dx_authz_log('MY_PLUGIN_DENIED', 'resource=invoice target_id=' . $invoiceId);

DX Security — Authorization Bypass 방어 v1.0.0 — DesignOneX https://designonex.com
 

라이선스

디자인원엑스 라이선스 참고
https://designonex.com/notice/view/1787577858493247

 

첨부파일 1개 회원전용

댓글0

로그인 후 댓글을 작성할 수 있습니다.
Plugin 53
45
전체 회원
1,391
전체 게시글
2,748
전체 댓글
80
오늘 방문
53,598
전체 방문
0
현재 접속
인기글 7일 이내
최신글
최신댓글
내 플레이리스트
플레이리스트가 비어있습니다
스튜디오 게시판에서
플레이리스트에 담기 버튼을
눌러보세요
목록
목록