아이넵
경력근거: DB 암호화와 통합 키 관리로 금융·공공 등 가장 엄격한 엔터프라이즈 환경에서 신뢰를 쌓아왔고
※ 실제 산출물이 아닌 AI 예측 시안입니다.
아이넵은 DB 암호화와 통합 키 관리로 금융·공공 기관의 신뢰를 쌓아 왔고, 지금은 변경 데이터 기반 DB 개인정보 검출에 집중한다고 공고에 적었습니다. 검출 제품이 찾은 개인정보 컬럼을 암호화 정책과 키 상태에 맞춰 보는 화면은 검출과 암호화, 키 관리를 함께 파는 회사에서 생기는 화면이고, 담당 업무의 관리 콘솔 UI·대용량 데이터 테이블·정책 설정 화면 개발이 이 화면에 그대로 닿습니다. 이 포트폴리오는 네 표를 컬럼 단위로 잇는 판정 차례 엔진과 그것을 고정하는 단위·통합 테스트, 실습 DB 를 직접 만들어 변경분 스캔을 돌리는 구성을 보여줍니다. 개인정보보호법 해석이나 암호 알고리즘 안전성 평가 전문성은 주장하지 않습니다.
공고는 지금 집중하는 기술로 변경 데이터 기반 DB 개인정보 검출을 들고, 회사의 바탕을 DB 암호화와 통합 키 관리로 적었습니다. 검출 제품이 찾은 개인정보 컬럼에 암호화 정책과 쓸 수 있는 키가 걸려 있는지 보는 화면은 세 제품을 함께 가진 회사에서만 생깁니다.
담당 업무에 관리 콘솔 UI, 대용량 데이터 테이블·차트·대시보드, 정책 설정 화면 개발이 있고 우대 사항에 관리자용 데이터 집약 화면 개발이 있습니다. 검출 컬럼을 판정별로 세우고 컬럼마다 정책·키·스캔 이력을 펼치는 화면이 이 업무에 닿습니다.
공고는 AI 가 만든 코드를 단위·통합 테스트로 검증하는 일을 가장 중요한 업무로 꼽고, 보안(암호화·키 관리) 개발 경험을 우대합니다. 판정 차례 규칙은 Claude Code 에 맡기되 날짜 경계와 두 사유가 겹친 컬럼을 담은 단위 테스트 40건, 실습 DB 에 평문 한 줄을 넣는 통합 테스트를 먼저 써 두고 통과한 코드만 받는 구성이 여기에 닿습니다.
아이넵은 컬럼 단위 DB 암호화 제품 디가드와 통합 키 관리, 변경 데이터 기반 DB 개인정보 검출을 금융·공공 기관에 납품합니다. 이 관리자 페이지는 검출 제품이 내놓은 개인정보 검출 결과, 디가드 정책 서버의 컬럼별 암호화 정책, 통합 키 관리의 키 목록, 기관의 암호화 기준표 네 표를 받아 DB 컬럼마다 판정 다섯 가지 중 하나를 붙입니다. 정책이 걸렸는지, 정책을 건 뒤의 스캔에서 평문이 나왔는지, 정책이 쓰는 키가 기준일에 살아 있는지, 그 개인정보 유형에 허용된 알고리즘인지를 차례로 따집니다. 은행·공공기관 개인정보보호 담당자는 이 판정으로 점검 보고서에 올릴 미조치 컬럼을 고르고, DB 관리자는 정책을 새로 걸거나 키를 바꿀 컬럼을 정합니다.
아이넵 관리 콘솔로 자기 기관 DB 의 개인정보 현황을 보는 은행·공공기관 개인정보보호 담당자와 DB 관리자. 같은 콘솔 화면을 보고 보호 담당자는 점검 보고서에 올릴 미조치 컬럼을, DB 관리자는 암호화 정책을 새로 걸거나 키를 바꿀 컬럼을 정한다
은행·공공기관에서 개인정보 검출 결과, 암호화 정책, 키 목록은 각각 다른 제품 화면에 있어서, 보호 담당자는 점검 때마다 세 화면을 내려받아 엑셀에서 컬럼 이름으로 맞춰 봅니다. 정책을 건 컬럼에 평문이 새로 들어오거나 정책이 쓰는 키가 만료돼도 세 화면은 각자 자기 값만 보여주므로, 점검에서 지적받거나 키를 바꾸다 복호화가 막힌 뒤에야 드러납니다. 네 표를 컬럼 단위로 잇고 기준일 하나로 판정하면 보호 담당자와 DB 관리자가 같은 목록을 보고 각자 할 일을 정합니다.
개인정보보호 담당자가 검출 결과·암호화 정책·키 목록·암호화 기준표 네 CSV 를 올리면 DB 컬럼마다 판정 다섯 가지 중 하나와 근거 값이 서는 React 관리자 페이지입니다. 정책 뒤 스캔만 골라 평문 행을 세고, 기준일과 키 만료일을 견주고, 개인정보 유형별 허용 알고리즘을 대는 규칙이 판정 차례대로 TypeScript 로 들어가고 단위 테스트 40건이 그 차례를 고정합니다. 이 주에는 내려받은 CSV 를 그대로 올리는 데서 시작하고 DB 직접 연결은 두지 않습니다.
Docker 로 띄운 PostgreSQL 에 Faker 의 ko_KR 로캘로 만든 가상 고객 5만 명을 넣고, pgcrypto 로 계좌·카드번호 컬럼을 AES-256·3DES 로 암호화하고 주민등록번호 컬럼 하나는 SHA-1 해시로 바꿉니다. updated_at 뒤 바뀐 행만 읽어 주민등록번호 형식과 검증 숫자, 계좌·카드번호 패턴을 세는 스캔 스크립트가 pii_detections 행을 쌓고, 암호화한 컬럼에 평문 한 줄을 넣으면 다음 스캔에서 그 컬럼이 평문 검출로 넘어가는 통합 테스트가 GitHub Actions 에서 돕니다. DB 관리자가 컬럼별 스캔 이력을 보는 탭이 열립니다.
보호 담당자가 걸린 컬럼을 고르면 컬럼마다 판정과 근거 값을 담은 조치 요청서가 마크다운과 엑셀로 나오고, Claude Sonnet 이 컬럼별 작업 문장을 씁니다. 새로 쓸 키 ID 와 작업 시각은 DB 관리자가 채우도록 비워 두고, 문장에 나온 컬럼명·키 ID·알고리즘이 근거 값과 다르면 그 문장을 버리고 근거 표만 남깁니다. 만료가 30일 안으로 다가온 키를 쓰는 컬럼을 미리 보여주는 키 만료 예정 탭도 이 주에 붙습니다.
개인정보보호 담당자가 네 CSV 를 올리면 새솔은행 DB 다섯 개의 검출 컬럼 11개가 판정 다섯 가지로 나뉘고, 주민등록번호 18,204행이 정책 없이 남은 CUSTDB TB_CUST_INFO.RRN_NO 가 맨 위에 섭니다. DB 관리자는 같은 화면에서 LOANDB TB_LOAN_APPL.PASSPORT_NO 를 펼쳐 키 K-2023-07 이 9월 30일에 만료됐다는 근거를 읽고 키를 바꿀 컬럼으로 정합니다.
판정 차례를 고정한 단위 테스트 40건이 모두 통과한 상태로 시연합니다. 폐기 키에 3DES 가 겹친 CARDDB TB_CARD_HIST.CARD_NO 는 쓸 수 없는 키 하나로 서고 3DES 는 펼침에 남으며, 만료일이 오늘인 K-2025-08 과 어제인 K-2025-05 는 하루 차이로 판정이 나뉩니다.
검출 결과 파일이 헤더만 있는 0행이어도 화면은 판정 묶음 다섯 칸을 0으로 세우고, 검출이 0행뿐인 HRDB 는 판정 컬럼 0개로 DB 목록에 남습니다. 만료일이 null 인 키 K-2026-02 는 만료일 없는 키로 읽고, matched_rows 에 문자가 든 줄은 그 줄만 판정에서 빼고 몇 번째 줄인지 화면 위에 띄웁니다.
위 수치는 더미데이터 자가채점이며, 실제 기관 DB 에서 검출 결과와 정책·키가 어긋나는 컬럼이 얼마나 되는지는 아이넵 검출 제품과 디가드 정책 서버, 통합 키 관리가 실제로 내보내는 기록이 있어야 측정됩니다. 네 표의 컬럼 이름은 검출 제품·정책 서버·키 관리가 내보내는 항목 이름에 맞춰 두어, 기관이 점검 때 내려받는 파일을 손으로 고치지 않고 올리게 합니다.
판정 다섯 가지의 기대값과 단위 테스트 40건의 정답은 제가 적은 것이라, 모두 통과해도 실제 기관 DB 에서 맞는다는 근거가 되지 않습니다. 40건이 지키는 것은 제가 정한 판정 차례와 기준일 비교가 코드에 그대로 옮겨졌다는 사실이고, 실제 은행 DB 의 검출 결과가 이 차례에 맞는지는 보호 담당자의 점검 기록을 받아 봐야 압니다.
검출 컬럼마다 사유가 하나씩만 걸리게 지으면 판정 차례가 틀려도 드러나지 않습니다. 폐기 키에 3DES 가 겹친 컬럼, 정책 뒤 1행 다음 0행이 나온 컬럼, 만료일이 오늘과 어제인 키, 만료일이 null 인 키를 일부러 넣었습니다. 알고리즘을 키보다 먼저 보면 TB_CARD_HIST.CARD_NO 가 허용되지 않은 알고리즘으로 뒤집히고, 만료일 비교를 '이하' 로 잘못 쓰면 LOANDB TB_LOAN_APPL.RRN_NO 가 쓸 수 없는 키로 넘어갑니다.
변경 데이터 기반 검출은 그 사이 바뀐 행만 보므로, 정책 뒤 0행이라는 결과가 컬럼 전체에 평문이 없다는 뜻은 아닙니다. 정책 뒤 한 번이라도 평문이 나온 컬럼은 이후 0행이 와도 판정을 풀지 않고, 풀려면 그 컬럼의 전수 스캔 결과가 있어야 합니다. 전수 스캔과 변경분 스캔을 가르는 컬럼은 실제 검출 기록 모양을 본 뒤 더할 도입 과제로 둡니다.
암호화 기준표의 허용 알고리즘 목록은 공개 해설서를 참고해 제가 만든 더미이고 기관마다 내부 기준이 다릅니다. 어느 개인정보에 어떤 알고리즘을 써도 되는지에 대한 법령 해석은 주장하지 않고, 실제 도입 때는 그 기관 보호 담당자가 쓰는 기준표로 갈아 끼웁니다.
pgcrypto 는 ARIA·SEED 를 지원하지 않아, 실습 DB 에서 허용 알고리즘으로 실제 암호화해 보는 것은 AES-256 하나입니다. ARIA·SEED 정책 줄은 정책 표와 기준표의 값으로만 판정을 시험합니다.
① 인라인 샘플 · ② seed.json 다운로드 · ③ 증강 프롬프트. 세 층 모두 동일한 schema 에서 파생.
아이넵의 변경 데이터 기반 DB 개인정보 검출 제품이 내보내는 검출 결과를 본뜬 표입니다. 스캔 한 번에 컬럼과 개인정보 유형마다 한 줄이고, 한 번 개인정보가 나온 컬럼은 이후 변경분 스캔에서 0행도 적습니다. 값은 작성자가 만든 더미이고, 2주차에는 지원자가 직접 만든 실습 DB 를 스캔해 같은 모양의 행을 얻습니다.
| detection_no | db_id | table_name | column_name | pii_type | matched_rows | scanned_at |
|---|---|---|---|---|---|---|
| DET-0101 | CUSTDB | TB_CUST_INFO | RRN_NO | 주민등록번호 | 18,204 | 2026-09-15T02:10:00+09:00 |
| DET-0102 | CUSTDB | TB_ACCT_HIST | ACCT_NO | 계좌번호 | 240,118 | 2026-09-01T02:10:00+09:00 |
| DET-0103 | CUSTDB | TB_ACCT_HIST | ACCT_NO | 계좌번호 | 312 | 2026-10-05T02:10:00+09:00 |
| DET-0104 | LOANDB | TB_LOAN_APPL | PASSPORT_NO | 여권번호 | 5,120 | 2025-02-28T03:00:00+09:00 |
| DET-0105 | LOANDB | TB_LOAN_APPL | PASSPORT_NO | 여권번호 | 0 | 2026-10-04T03:00:00+09:00 |
아래 JSON Schema 에 맞는 DB 개인정보 검출 결과 행을 더 만들어 주세요. {"type":"object","properties":{"detection_no":{"type":"string","description":"검출 결과 한 줄의 번호입니다."},"db_id":{"type":"string","description":"스캔한 DB 이름입니다."},"table_name":{"type":"string","description":"검출된 테이블 이름입니다."},"column_name":{"type":"string","description":"검출된 컬럼 이름입니다."},"pii_type":{"type":"string","description":"검출 패턴이 알아본 개인정보 유형입니다. pii_rules.pii_type 과 같은 이름을 씁니다."},"matched_rows":{"type":"integer","minimum":0,"description":"이번 스캔에서 개인정보 패턴에 걸린 행 수입니다. 한 번 개인정보가 나온 컬럼은 이후 스캔에서 0 도 적습니다."},"scanned_at":{"type":"string","format":"date-time","description":"스캔이 끝난 시각입니다. 변경 데이터 기반 스캔이라 직전 스캔 뒤 바뀐 행만 본 결과입니다."}},"required":["detection_no","db_id","table_name","column_name","pii_type","matched_rows","scanned_at"]} 은행·공공기관 DB 3~6개(계정계·여신·카드·웹·인사)에 걸쳐 컬럼 20~60개를 두고, 컬럼마다 정책 적용 전 최초 검출 한 줄과 이후 변경분 스캔 0~3줄을 시각 순서대로 만듭니다. 테이블·컬럼 이름은 TB_ 로 시작하는 대문자 영문으로, 개인정보 유형은 주민등록번호·여권번호·운전면허번호·외국인등록번호·계좌번호·신용카드번호·이메일·휴대전화번호 가운데서 고릅니다. 쉬운 데이터만 만들지 말 것 — 다음 하드 케이스를 의도적으로 섞어라: (1) 정책 적용 뒤 스캔에서 matched_rows 가 1 인 컬럼, (2) 정책 뒤 1 이상이 나온 다음 스캔에서 0 이 나온 컬럼, (3) 정책 뒤 스캔이 한 번도 없는 컬럼, (4) 검출이 0행뿐인 DB, (5) 암호화 의무가 없는 유형(이메일)만 나온 컬럼. 생성한 행은 위 스키마를 통과해야 하며, 형식을 깨뜨리는 시도는 별도로 3건만 표시해 두세요.{"type":"object","properties":{"detection_no":{"type":"string","description":"검출 결과 한 줄의 번호입니다."},"db_id":{"type":"string","description":"스캔한 DB 이름입니다."},"table_name":{"type":"string","description":"검출된 테이블 이름입니다."},"column_name":{"type":"string","description":"검출된 컬럼 이름입니다."},"pii_type":{"type":"string","description":"검출 패턴이 알아본 개인정보 유형입니다. pii_rules.pii_type 과 같은 이름을 씁니다."},"matched_rows":{"type":"integer","minimum":0,"description":"이번 스캔에서 개인정보 패턴에 걸린 행 수입니다. 한 번 개인정보가 나온 컬럼은 이후 스캔에서 0 도 적습니다."},"scanned_at":{"type":"string","format":"date-time","description":"스캔이 끝난 시각입니다. 변경 데이터 기반 스캔이라 직전 스캔 뒤 바뀐 행만 본 결과입니다."}},"required":["detection_no","db_id","table_name","column_name","pii_type","matched_rows","scanned_at"]}디가드 같은 DB 암호화 제품의 정책 서버에서 내려받은 컬럼별 암호화 정책을 본뜬 표입니다. 컬럼 하나에 정책 한 줄이고, applied_at 은 그 컬럼의 기존 값을 암호화하고 정책이 켜진 시각입니다. 작성자가 만든 더미입니다.
| enc_policy_no | db_id | table_name | column_name | algorithm | key_id | applied_at |
|---|---|---|---|---|---|---|
| EP-0101 | CUSTDB | TB_ACCT_HIST | ACCT_NO | AES-256 | K-2024-01 | 2026-09-12T21:00:00+09:00 |
| EP-0102 | LOANDB | TB_LOAN_APPL | PASSPORT_NO | ARIA-256 | K-2023-07 | 2025-03-10T22:00:00+09:00 |
| EP-0103 | CARDDB | TB_MEMBER | MEMBER_RRN | SHA-1 | K-2024-02 | 2024-06-01T23:00:00+09:00 |
| EP-0104 | LOANDB | TB_LOAN_APPL | RRN_NO | ARIA-256 | K-2025-08 | 2025-08-20T22:30:00+09:00 |
| EP-0105 | LOANDB | TB_GUARANTOR | RRN_NO | SEED | K-2025-05 | 2025-05-14T22:00:00+09:00 |
아래 JSON Schema 에 맞는 컬럼별 DB 암호화 정책 행을 더 만들어 주세요. {"type":"object","properties":{"enc_policy_no":{"type":"string","description":"암호화 정책 번호입니다."},"db_id":{"type":"string"},"table_name":{"type":"string"},"column_name":{"type":"string"},"algorithm":{"type":"string","description":"정책이 쓰는 암호화 알고리즘 이름입니다(예: ARIA-256, AES-256, SEED, 3DES, SHA-1)."},"key_id":{"type":"string","description":"정책이 쓰는 키의 ID 입니다."},"applied_at":{"type":"string","format":"date-time","description":"그 컬럼의 기존 값을 암호화하고 정책이 켜진 시각입니다."}},"required":["enc_policy_no","db_id","table_name","column_name","algorithm","key_id","applied_at"]} 검출 결과에 나온 컬럼 가운데 70~90% 에만 정책을 두고, 알고리즘은 ARIA-256·AES-256·SEED 를 주로 쓰되 오래된 정책에는 3DES·SHA-1·AES-128 을 섞습니다. 키 ID 는 K-연도-월 꼴로 씁니다. 쉬운 데이터만 만들지 말 것 — 다음 하드 케이스를 의도적으로 섞어라: (1) 키 목록에 없는 key_id 를 쓰는 정책, (2) 폐기된 키에 허용되지 않은 알고리즘까지 겹친 정책, (3) 만료일이 기준일 당일·전날인 키를 쓰는 정책, (4) 검출 결과에 개인정보가 나왔는데 정책이 없는 컬럼은 이 표에 넣지 않습니다. 생성한 행은 위 스키마를 통과해야 하며, 형식을 깨뜨리는 시도는 별도로 3건만 표시해 두세요.{"type":"object","properties":{"enc_policy_no":{"type":"string","description":"암호화 정책 번호입니다."},"db_id":{"type":"string"},"table_name":{"type":"string"},"column_name":{"type":"string"},"algorithm":{"type":"string","description":"정책이 쓰는 암호화 알고리즘 이름입니다(예: ARIA-256, AES-256, SEED, 3DES, SHA-1)."},"key_id":{"type":"string","description":"정책이 쓰는 키의 ID 입니다."},"applied_at":{"type":"string","format":"date-time","description":"그 컬럼의 기존 값을 암호화하고 정책이 켜진 시각입니다."}},"required":["enc_policy_no","db_id","table_name","column_name","algorithm","key_id","applied_at"]}통합 키 관리에서 내려받은 키 목록을 본뜬 표입니다. status 는 키 관리가 매기는 활성·비활성·폐기 셋이고, 만료일을 정하지 않은 키는 expires_at 이 null 입니다. 작성자가 만든 더미입니다.
| key_id | status | expires_at |
|---|---|---|
| K-2022-11 | 폐기 | 2025-11-30 |
| K-2023-07 | 활성 | 2026-09-30 |
| K-2024-01 | 활성 | 2027-03-31 |
| K-2024-02 | 활성 | 2026-12-31 |
| K-2025-03 | 비활성 | 2027-06-30 |
아래 JSON Schema 에 맞는 암호 키 목록 행을 더 만들어 주세요. {"type":"object","properties":{"key_id":{"type":"string"},"status":{"type":"string","enum":["활성","비활성","폐기"],"description":"통합 키 관리가 매기는 키 상태입니다."},"expires_at":{"type":["string","null"],"format":"date","description":"키 만료일입니다. 만료일을 정하지 않은 키는 null 입니다."}},"required":["key_id","status","expires_at"]} 키 10~30개를 만들고 대부분은 활성으로 둡니다. 만료일은 기준일 2026-10-06 앞뒤 2년 안에 흩어 놓습니다. 쉬운 데이터만 만들지 말 것 — 다음 하드 케이스를 의도적으로 섞어라: (1) status 는 활성인데 만료일이 기준일보다 이른 키, (2) 만료일이 기준일과 같은 키와 하루 이른 키, (3) expires_at 이 null 인 키, (4) 비활성·폐기 키. 생성한 행은 위 스키마를 통과해야 하며, 형식을 깨뜨리는 시도는 별도로 3건만 표시해 두세요.{"type":"object","properties":{"key_id":{"type":"string"},"status":{"type":"string","enum":["활성","비활성","폐기"],"description":"통합 키 관리가 매기는 키 상태입니다."},"expires_at":{"type":["string","null"],"format":"date","description":"키 만료일입니다. 만료일을 정하지 않은 키는 null 입니다."}},"required":["key_id","status","expires_at"]}개인정보 유형마다 암호화 의무와 허용 알고리즘을 적은 기관 기준표입니다. 개인정보의 안전성 확보조치 기준 해설서의 암호화 대상을 참고해 작성자가 만든 더미이고, 실제 도입 때는 그 기관이 쓰는 기준표로 갈아 끼웁니다.
| pii_type | encryption_required | allowed_algorithms |
|---|---|---|
| 주민등록번호 | true | ["ARIA-128","ARIA-256","SEED","AES-128","AES-256"] |
| 여권번호 | true | ["ARIA-128","ARIA-256","SEED","AES-128","AES-256"] |
| 운전면허번호 | true | ["ARIA-128","ARIA-256","SEED","AES-128","AES-256"] |
| 외국인등록번호 | true | ["ARIA-128","ARIA-256","SEED","AES-128","AES-256"] |
| 계좌번호 | true | ["ARIA-128","ARIA-256","SEED","AES-128","AES-256"] |
아래 JSON Schema 에 맞는 개인정보 유형별 암호화 기준 행을 더 만들어 주세요. {"type":"object","properties":{"pii_type":{"type":"string"},"encryption_required":{"type":"boolean","description":"이 유형이 DB 에 저장될 때 암호화해야 하는지입니다."},"allowed_algorithms":{"type":"array","items":{"type":"string"},"description":"이 유형에 쓸 수 있는 알고리즘 목록입니다. 암호화 의무가 없으면 빈 배열입니다."}},"required":["pii_type","encryption_required","allowed_algorithms"]} 고유식별정보·금융정보·비밀번호·연락처 계열을 고루 담고, 양방향 암호화 대상에는 블록 암호 이름을, 비밀번호에는 일방향 해시 이름만 넣습니다. 쉬운 데이터만 만들지 말 것 — 다음 하드 케이스를 의도적으로 섞어라: (1) 암호화 의무가 없고 allowed_algorithms 가 빈 배열인 유형, (2) 다른 유형에서는 허용되는 AES-256 이 허용 목록에 없는 비밀번호 유형. 생성한 행은 위 스키마를 통과해야 하며, 형식을 깨뜨리는 시도는 별도로 3건만 표시해 두세요.{"type":"object","properties":{"pii_type":{"type":"string"},"encryption_required":{"type":"boolean","description":"이 유형이 DB 에 저장될 때 암호화해야 하는지입니다."},"allowed_algorithms":{"type":"array","items":{"type":"string"},"description":"이 유형에 쓸 수 있는 알고리즘 목록입니다. 암호화 의무가 없으면 빈 배열입니다."}},"required":["pii_type","encryption_required","allowed_algorithms"]}| TypeScript | 네 표를 컬럼 단위로 잇고 판정 차례대로 하나를 남기는 규칙 엔진, 변경분 스캔 스크립트, 화면 코드의 언어입니다. |
| React | 판정별 컬럼 묶음, 컬럼을 누르면 열리는 정책·키·스캔 근거 펼침, 2주차 스캔 이력 차트를 그리는 관리자 페이지입니다. |
| 어드민 API | Node.js 로 네 CSV 를 받아 판정을 돌려주는 업로드·판정 API 를 만들고, 2주차부터 실습 DB 의 스캔 결과를 직접 읽습니다. |
| 단위 테스트·통합 테스트 | Vitest 로 판정 차례·만료일 당일과 전날·빈 만료일·폐기 키에 3DES 가 겹친 컬럼을 담은 단위 테스트 40건을 쓰고, 2주차에는 실습 PostgreSQL 에 평문을 넣고 지우며 판정이 바뀌는지 보는 통합 테스트를 더합니다. |
| 자동 빌드·테스트 환경 | GitHub Actions 가 커밋마다 PostgreSQL 컨테이너를 띄워 단위·통합 테스트를 돌리고, 하나라도 실패하면 배포를 멈춥니다. |
| Claude Code | 규칙 엔진·스캔 스크립트·화면 작업을 나눠 맡기고, 제가 먼저 써 둔 테스트를 통과한 코드만 받습니다. |
| MCP | 2주차에 실습 PostgreSQL 을 읽기 전용 MCP 서버로 Claude Code 에 연결해, 실제 테이블 구조를 보고 스캔 스크립트의 테스트 데이터를 만들게 합니다. |
| DB 튜닝 | 변경분 스캔이 updated_at 인덱스로 바뀐 행만 읽는지 EXPLAIN 으로 확인하고, 가상 고객 5만 명 테이블에서 전수 스캔과 걸린 시간을 견줍니다. |
| 암호화·키 관리 | pgcrypto 로 실습 DB 컬럼을 실제로 암호화·해시하고, 키 목록의 상태와 만료일로 정책이 쓰는 키가 기준일에 살아 있는지 판정합니다. |
| Linux/Unix | 실습 DB 와 스캔 스크립트를 Linux 컨테이너에서 cron 으로 돌려 매일 새벽 변경분 스캔을 쌓습니다. |
| Claude Sonnet | 3주차 조치 요청서의 컬럼별 작업 문장을 씁니다. |
✗ fail → 문서와 다른 판정이 나오면 판정 차례 단위 테스트부터 고치고, 두 사유가 겹친 컬럼은 펼침에 함께 걸린 사유가 보이는지 다시 봅니다.
✓ pass → 실습 PostgreSQL 과 변경분 스캔 스크립트로 2주차를 엽니다.
✗ fail → 스캔이 암호문을 주민등록번호로 잘못 세면 형식 패턴 뒤에 검증 숫자 확인을 붙이고 다시 스캔합니다.
✓ pass → 조치 요청서와 키 만료 예정 탭으로 3주차를 엽니다.
위 예측 UI 는 3주차까지 완주했을 때의 화면입니다. 1주차에 실제로 만드는 것은 아래 표시된 화면 하나입니다.
verdict사유 라벨 · column_ref + 한 줄 요약(근거 수치 포함)화면·코드·면접에서 이 단어를 그대로 씁니다. 키는 출력 스키마의 enum 과 같습니다.
암호화 정책 적용 중적용 중개인정보가 있는데 암호화 정책이 없음정책 없음정책 적용 뒤에도 평문이 검출됨평문 검출쓸 수 없는 키로 암호화 중쓸 수 없는 키허용되지 않은 알고리즘으로 암호화됨허용 안 된 알고리즘개인정보가 검출된 DB 컬럼 하나가 정책 유무, 정책 뒤 평문 검출, 키 유효기간·상태, 허용 알고리즘을 차례로 거쳐 어떤 판정을 받는지 남기는 형식입니다. 판정은 규칙 엔진이 내리고, 3주차 조치 요청서의 작업 문장만 모델이 씁니다.
{"type":"object","properties":{"column_ref":{"type":"string","description":"db_id.table_name.column_name 을 점으로 이은 컬럼 이름입니다. 화면의 줄 키입니다."},"as_of":{"type":"string","format":"date","description":"키 만료를 견주는 기준일입니다."},"db_id":{"type":"string"},"table_name":{"type":"string"},"column_name":{"type":"string"},"pii_type":{"type":"string"},"verdict":{"type":"string","enum":["암호화 정책 적용 중","개인정보가 있는데 암호화 정책이 없음","정책 적용 뒤에도 평문이 검출됨","쓸 수 없는 키로 암호화 중","허용되지 않은 알고리즘으로 암호화됨"]},"other_hits":{"type":"array","items":{"type":"string","enum":["개인정보가 있는데 암호화 정책이 없음","정책 적용 뒤에도 평문이 검출됨","쓸 수 없는 키로 암호화 중","허용되지 않은 알고리즘으로 암호화됨"]},"description":"판정 차례에서 verdict 뒤에 오는 조건 가운데 함께 성립한 판정입니다."},"enc_policy_no":{"type":["string","null"]},"algorithm":{"type":["string","null"]},"key_id":{"type":["string","null"]},"key_status":{"type":["string","null"],"description":"key_inventory.status 입니다. 정책이 없거나 키 목록에 그 key_id 가 없으면 null 입니다."},"key_expires_at":{"type":["string","null"]},"allowed_algorithms":{"type":"array","items":{"type":"string"}},"peak_matched_rows":{"type":"integer","minimum":1,"description":"이 컬럼 검출 행 matched_rows 의 최댓값입니다."},"scans_after_policy":{"type":["integer","null"],"minimum":0,"description":"scanned_at 이 applied_at 보다 나중인 검출 행 수입니다. 정책이 없으면 null 입니다."},"max_matched_after_policy":{"type":["integer","null"],"minimum":0,"description":"정책 뒤 검출 행 matched_rows 의 최댓값입니다. 정책 뒤 스캔이 없으면 null 입니다."},"evidence":{"type":"array","items":{"type":"object","properties":{"field":{"type":"string"},"agg":{"type":["string","null"],"enum":["count","sum","avg","min","max",null]},"value":{}},"required":["field","value"]}},"summary":{"type":"string"},"hedge":{"type":["string","null"]}},"required":["column_ref","as_of","db_id","table_name","column_name","pii_type","verdict","other_hits","enc_policy_no","algorithm","key_id","key_status","key_expires_at","allowed_algorithms","peak_matched_rows","scans_after_policy","max_matched_after_policy","evidence","summary"]}[
{
"column_ref": "CUSTDB.TB_CUST_INFO.RRN_NO",
"as_of": "2026-10-06",
"db_id": "CUSTDB",
"table_name": "TB_CUST_INFO",
"column_name": "RRN_NO",
"pii_type": "주민등록번호",
"verdict": "개인정보가 있는데 암호화 정책이 없음",
"other_hits": [],
"enc_policy_no": null,
"algorithm": null,
"key_id": null,
"key_status": null,
"key_expires_at": null,
"allowed_algorithms": [
"ARIA-128",
"ARIA-256",
"SEED",
"AES-128",
"AES-256"
],
"peak_matched_rows": 18204,
"scans_after_policy": null,
"max_matched_after_policy": null,
"evidence": [
{
"field": "detection_no",
"value": "DET-0101"
},
{
"field": "matched_rows",
"value": 18204
},
{
"field": "encryption_required",
"value": true
},
{
"field": "enc_policy_no",
"agg": "count",
"value": 0
}
],
"summary": "CUSTDB TB_CUST_INFO.RRN_NO 에서 주민등록번호 18,204행이 검출됐는데, 이 컬럼에 걸린 암호화 정책이 하나도 없습니다.",
"hedge": null
},
{
"column_ref": "LOANDB.TB_LOAN_APPL.PASSPORT_NO",
"as_of": "2026-10-06",
"db_id": "LOANDB",
"table_name": "TB_LOAN_APPL",
"column_name": "PASSPORT_NO",
"pii_type": "여권번호",
"verdict": "쓸 수 없는 키로 암호화 중",
"other_hits": [],
"enc_policy_no": "EP-0102",
"algorithm": "ARIA-256",
"key_id": "K-2023-07",
"key_status": "활성",
"key_expires_at": "2026-09-30",
"allowed_algorithms": [
"ARIA-128",
"ARIA-256",
"SEED",
"AES-128",
"AES-256"
],
"peak_matched_rows": 5120,
"scans_after_policy": 1,
"max_matched_after_policy": 0,
"evidence": [
{
"field": "enc_policy_no",
"value": "EP-0102"
},
{
"field": "key_id",
"value": "K-2023-07"
},
{
"field": "expires_at",
"value": "2026-09-30"
},
{
"field": "status",
"value": "활성"
}
],
"summary": "LOANDB TB_LOAN_APPL.PASSPORT_NO 는 ARIA-256 정책으로 암호화돼 있지만, 정책이 쓰는 키 K-2023-07 이 2026-09-30 에 만료돼 기준일 2026-10-06 에는 쓸 수 없습니다.",
"hedge": "키 목록에서는 상태가 아직 활성으로 남아 있어 만료일을 기준일과 견줘야 드러납니다. 키를 바꾸려면 이 컬럼 값을 새 키로 다시 암호화해야 합니다."
},
{
"column_ref": "CARDDB.TB_MEMBER.MEMBER_RRN",
"as_of": "2026-10-06",
"db_id": "CARDDB",
"table_name": "TB_MEMBER",
"column_name": "MEMBER_RRN",
"pii_type": "주민등록번호",
"verdict": "허용되지 않은 알고리즘으로 암호화됨",
"other_hits": [],
"enc_policy_no": "EP-0103",
"algorithm": "SHA-1",
"key_id": "K-2024-02",
"key_status": "활성",
"key_expires_at": "2026-12-31",
"allowed_algorithms": [
"ARIA-128",
"ARIA-256",
"SEED",
"AES-128",
"AES-256"
],
"peak_matched_rows": 81200,
"scans_after_policy": 1,
"max_matched_after_policy": 0,
"evidence": [
{
"field": "enc_policy_no",
"value": "EP-0103"
},
{
"field": "algorithm",
"value": "SHA-1"
},
{
"field": "pii_type",
"value": "주민등록번호"
},
{
"field": "key_id",
"value": "K-2024-02"
}
],
"summary": "CARDDB TB_MEMBER.MEMBER_RRN 은 주민등록번호를 SHA-1 로 바꿔 두었는데, 기준표가 주민등록번호에 허용한 알고리즘은 ARIA-128·ARIA-256·SEED·AES-128·AES-256 입니다.",
"hedge": "키 K-2024-02 는 2026-12-31 까지 활성이라 키 판정에는 걸리지 않았습니다."
},
{
"column_ref": "CUSTDB.TB_CUST_INFO.FRGN_REG_NO",
"as_of": "2026-10-06",
"db_id": "CUSTDB",
"table_name": "TB_CUST_INFO",
"column_name": "FRGN_REG_NO",
"pii_type": "외국인등록번호",
"verdict": "암호화 정책 적용 중",
"other_hits": [],
"enc_policy_no": "EP-0110",
"algorithm": "ARIA-256",
"key_id": "K-2025-10",
"key_status": "활성",
"key_expires_at": "2028-04-30",
"allowed_algorithms": [
"ARIA-128",
"ARIA-256",
"SEED",
"AES-128",
"AES-256"
],
"peak_matched_rows": 2310,
"scans_after_policy": 1,
"max_matched_after_policy": 0,
"evidence": [
{
"field": "enc_policy_no",
"value": "EP-0110"
},
{
"field": "algorithm",
"value": "ARIA-256"
},
{
"field": "key_id",
"value": "K-2025-10"
},
{
"field": "expires_at",
"value": "2028-04-30"
},
{
"field": "detection_no",
"value": "DET-0118"
},
{
"field": "matched_rows",
"value": 0
}
],
"summary": "CUSTDB TB_CUST_INFO.FRGN_REG_NO 는 ARIA-256 과 2028-04-30 까지 쓸 수 있는 키 K-2025-10 으로 암호화돼 있고, 정책 뒤 2026-10-05 스캔에서 평문이 0행입니다.",
"hedge": null
},
{
"column_ref": "LOANDB.TB_LOAN_APPL.RRN_NO",
"as_of": "2026-10-06",
"db_id": "LOANDB",
"table_name": "TB_LOAN_APPL",
"column_name": "RRN_NO",
"pii_type": "주민등록번호",
"verdict": "암호화 정책 적용 중",
"other_hits": [],
"enc_policy_no": "EP-0104",
"algorithm": "ARIA-256",
"key_id": "K-2025-08",
"key_status": "활성",
"key_expires_at": "2026-10-06",
"allowed_algorithms": [
"ARIA-128",
"ARIA-256",
"SEED",
"AES-128",
"AES-256"
],
"peak_matched_rows": 64300,
"scans_after_policy": 1,
"max_matched_after_policy": 0,
"evidence": [
{
"field": "enc_policy_no",
"value": "EP-0104"
},
{
"field": "key_id",
"value": "K-2025-08"
},
{
"field": "expires_at",
"value": "2026-10-06"
},
{
"field": "detection_no",
"value": "DET-0109"
},
{
"field": "matched_rows",
"value": 0
}
],
"summary": "LOANDB TB_LOAN_APPL.RRN_NO 의 키 K-2025-08 은 만료일이 기준일과 같은 2026-10-06 이라 오늘까지는 쓸 수 있는 키로 셉니다.",
"hedge": "만료일이 기준일보다 이를 때만 쓸 수 없는 키로 보므로 내일 판정부터 이 컬럼은 쓸 수 없는 키로 넘어갑니다. 하루 먼저 만료된 K-2025-05 를 쓰는 LOANDB TB_GUARANTOR.RRN_NO(EP-0105)는 이미 넘어가 있습니다."
},
{
"column_ref": "CARDDB.TB_CARD.CARD_NO",
"as_of": "2026-10-06",
"db_id": "CARDDB",
"table_name": "TB_CARD",
"column_name": "CARD_NO",
"pii_type": "신용카드번호",
"verdict": "암호화 정책 적용 중",
"other_hits": [],
"enc_policy_no": "EP-0106",
"algorithm": "AES-256",
"key_id": "K-2026-02",
"key_status": "활성",
"key_expires_at": null,
"allowed_algorithms": [
"ARIA-128",
"ARIA-256",
"SEED",
"AES-128",
"AES-256"
],
"peak_matched_rows": 512340,
"scans_after_policy": 0,
"max_matched_after_policy": null,
"evidence": [
{
"field": "enc_policy_no",
"value": "EP-0106"
},
{
"field": "applied_at",
"value": "2026-09-28T22:00:00+09:00"
},
{
"field": "key_id",
"value": "K-2026-02"
},
{
"field": "expires_at",
"value": null
},
{
"field": "scanned_at",
"agg": "count",
"value": 0
},
{
"field": "detection_no",
"value": "DET-0111"
}
],
"summary": "CARDDB TB_CARD.CARD_NO 는 2026-09-28 에 AES-256 정책을 걸었고, 키 K-2026-02 는 만료일을 정하지 않은 키라 쓸 수 있는 키로 셉니다.",
"hedge": "정책을 건 뒤 이 컬럼을 본 스캔이 0번이라 평문이 남았는지는 아직 모릅니다. 화면에는 적용 중 옆에 정책 뒤 스캔 없음 표시를 붙입니다."
},
{
"column_ref": "CARDDB.TB_CARD_HIST.CARD_NO",
"as_of": "2026-10-06",
"db_id": "CARDDB",
"table_name": "TB_CARD_HIST",
"column_name": "CARD_NO",
"pii_type": "신용카드번호",
"verdict": "쓸 수 없는 키로 암호화 중",
"other_hits": [
"허용되지 않은 알고리즘으로 암호화됨"
],
"enc_policy_no": "EP-0107",
"algorithm": "3DES",
"key_id": "K-2022-11",
"key_status": "폐기",
"key_expires_at": "2025-11-30",
"allowed_algorithms": [
"ARIA-128",
"ARIA-256",
"SEED",
"AES-128",
"AES-256"
],
"peak_matched_rows": 1830222,
"scans_after_policy": 0,
"max_matched_after_policy": null,
"evidence": [
{
"field": "enc_policy_no",
"value": "EP-0107"
},
{
"field": "key_id",
"value": "K-2022-11"
},
{
"field": "status",
"value": "폐기"
},
{
"field": "algorithm",
"value": "3DES"
}
],
"summary": "CARDDB TB_CARD_HIST.CARD_NO 는 폐기된 키 K-2022-11 로 암호화돼 있어 쓸 수 없는 키 판정입니다. 알고리즘 3DES 도 신용카드번호에 허용되지 않아 함께 걸린 사유로 남습니다.",
"hedge": "키를 바꾸려면 컬럼 값을 어차피 다시 암호화해야 하고 그때 알고리즘도 함께 바꾸게 되므로, 판정은 키 하나로 띄우고 3DES 는 펼침에서 보여줍니다."
},
{
"column_ref": "CUSTDB.TB_CUST_INFO.DRV_LIC_NO",
"as_of": "2026-10-06",
"db_id": "CUSTDB",
"table_name": "TB_CUST_INFO",
"column_name": "DRV_LIC_NO",
"pii_type": "운전면허번호",
"verdict": "정책 적용 뒤에도 평문이 검출됨",
"other_hits": [],
"enc_policy_no": "EP-0109",
"algorithm": "AES-256",
"key_id": "K-2024-01",
"key_status": "활성",
"key_expires_at": "2027-03-31",
"allowed_algorithms": [
"ARIA-128",
"ARIA-256",
"SEED",
"AES-128",
"AES-256"
],
"peak_matched_rows": 3400,
"scans_after_policy": 2,
"max_matched_after_policy": 1,
"evidence": [
{
"field": "enc_policy_no",
"value": "EP-0109"
},
{
"field": "applied_at",
"value": "2026-09-20T21:00:00+09:00"
},
{
"field": "detection_no",
"value": "DET-0115"
},
{
"field": "scanned_at",
"value": "2026-09-25T02:10:00+09:00"
},
{
"field": "matched_rows",
"value": 1
},
{
"field": "detection_no",
"value": "DET-0116"
},
{
"field": "matched_rows",
"value": 0
}
],
"summary": "CUSTDB TB_CUST_INFO.DRV_LIC_NO 는 2026-09-20 정책 적용 뒤 2026-09-25 스캔에서 운전면허번호 평문 1행이 나왔습니다.",
"hedge": "2026-10-05 스캔은 0행이지만 변경 데이터 기반 검출은 그 사이 바뀐 행만 보므로, 9월 25일의 1행이 고쳐졌다는 근거가 되지 않습니다. 판정을 풀려면 이 컬럼을 전수 스캔한 결과가 필요합니다."
}
][자동 검증 · 코드가 판정합니다] 1. verdict 가 암호화 정책 적용 중·개인정보가 있는데 암호화 정책이 없음·정책 적용 뒤에도 평문이 검출됨·쓸 수 없는 키로 암호화 중·허용되지 않은 알고리즘으로 암호화됨 다섯 값 중 하나인지, other_hits 의 값이 뒤의 네 값 안에 있는지 확인합니다. 2. column_ref·as_of·db_id·table_name·column_name·pii_type·verdict·other_hits·enc_policy_no·algorithm·key_id·key_status·key_expires_at·allowed_algorithms·peak_matched_rows·scans_after_policy·max_matched_after_policy·evidence·summary 필드가 빠짐없이 있는지 확인합니다. 3. peak_matched_rows 가 1 이상이고 scans_after_policy·max_matched_after_policy 가 null 이거나 0 이상인지 확인합니다. 4. peak_matched_rows 를 같은 db_id·table_name·column_name 검출 행의 matched_rows 최댓값으로, scans_after_policy 를 scanned_at 이 applied_at 보다 나중인 검출 행 수로, max_matched_after_policy 를 그 행들의 matched_rows 최댓값으로 다시 계산합니다. 5. 같은 db_id·table_name·column_name 의 encryption_policies 행이 0개이면 verdict 는 개인정보가 있는데 암호화 정책이 없음입니다. 6. 앞 조건에 걸리지 않고 max_matched_after_policy 가 1 이상이면 verdict 는 정책 적용 뒤에도 평문이 검출됨입니다. 7. 앞 두 조건에 걸리지 않고 key_id 가 key_inventory 에 없거나, status 가 비활성·폐기이거나, expires_at 이 as_of 보다 이르면 verdict 는 쓸 수 없는 키로 암호화 중입니다. expires_at 이 null 이면 만료일이 없는 키로 봅니다. 8. 앞 세 조건에 걸리지 않고 algorithm 이 그 pii_type 의 allowed_algorithms 에 없으면 verdict 는 허용되지 않은 알고리즘으로 암호화됨이고, 그렇지 않으면 암호화 정책 적용 중입니다. 9. verdict 뒤 차례의 조건이 함께 성립하면 other_hits 는 그 판정들을 담고, 함께 성립한 조건이 없으면 other_hits 는 빈 배열입니다. 10. evidence 의 field 이름이 네 데이터셋 가운데 하나에 있는 컬럼인지 대조합니다. 11. evidence 의 value 가 수록된 행의 원문 값과 같은지 확인합니다. 여러 행을 센 수는 agg 를 적습니다. 12. summary 가 존댓말로 끝나는지 확인합니다. [판정 대상 · 어느 컬럼을 판정하는가] encryption_required 가 참인 pii_type 으로 matched_rows 1 이상이 나온 검출 행이 한 번이라도 있는 컬럼만 판정합니다. WEBDB TB_USER.EMAIL(DET-0119)은 이메일이 암호화 의무 유형이 아니라 빠지고, HRDB TB_EMP.BANK_ACCT_NO(DET-0120)는 검출이 0행뿐이라 빠집니다. 그래서 HRDB 는 판정 컬럼 0개로 DB 목록에 남습니다. 검출 결과 파일이 헤더만 있는 0행이면 판정을 하나도 만들지 않고 화면은 빈 상태를 띄웁니다. [판정 차례 · 둘 이상 걸릴 때] 컬럼 하나에는 판정을 하나만 띄우고 나머지는 other_hits 로 펼침에 둡니다. ① 개인정보가 있는데 암호화 정책이 없음 → ② 정책 적용 뒤에도 평문이 검출됨 → ③ 쓸 수 없는 키로 암호화 중 → ④ 허용되지 않은 알고리즘으로 암호화됨 → ⑤ 암호화 정책 적용 중. 정책이 없으면 나머지는 따질 대상이 없고, 평문은 지금 DB 에 개인정보가 그대로 있는 상태라 키·알고리즘보다 앞에 둡니다. 알고리즘을 바꾸려면 쓸 수 있는 키로 다시 암호화해야 하므로 키를 알고리즘보다 앞에 둡니다. [하드 케이스 · 판정이 갈리는 이유] K-2025-08 은 만료일이 기준일 2026-10-06 과 같아 LOANDB TB_LOAN_APPL.RRN_NO 가 적용 중이고, 하루 이른 K-2025-05 를 쓰는 LOANDB TB_GUARANTOR.RRN_NO(EP-0105)는 쓸 수 없는 키입니다. K-2026-02 는 expires_at 이 null 이라 만료일이 없는 키로 보고, 그 키를 쓰는 CARDDB TB_CARD.CARD_NO 는 정책 뒤 스캔이 0번이라 적용 중으로 두되 평문 여부를 아직 모른다고 hedge 에 적습니다. CARDDB TB_CARD_HIST.CARD_NO 는 폐기 키 K-2022-11 과 3DES 가 함께 걸려 ③ 이 판정이고 ④ 는 other_hits 입니다. CUSTDB TB_CUST_INFO.DRV_LIC_NO 는 정책 뒤 DET-0115 에서 1행, DET-0116 에서 0행이 나왔는데, 변경분 스캔의 0행은 그 사이 바뀐 행만 본 결과라 평문 검출을 풀지 않습니다. CARDDB TB_MEMBER.PASSPORT_NO(EP-0108)의 K-2021-04 는 key_inventory 에 없는 키라 쓸 수 없는 키입니다. [확정 카드 판정식과 다른 점] 카드의 네 판정식은 그대로 씁니다. 카드가 정하지 않은 것 셋을 더했습니다. 첫째, 카드에 식이 없는 암호화 정책 적용 중은 네 조건 어디에도 걸리지 않은 컬럼으로 정했습니다. 둘째, 네 조건이 함께 걸릴 때의 차례를 위 ①~⑤ 로 정하고 함께 걸린 판정은 other_hits 에 남깁니다. 셋째, 카드의 '오늘' 은 as_of 기준일로 고정하고, 카드에 없는 expires_at 의 null 은 만료일이 없는 키로 읽습니다. [출처 · 공고에 없는 낱말] 공고에는 DB 암호화·통합 키 관리·변경 데이터 기반 DB 개인정보 검출까지만 나옵니다. 컬럼 단위 암호화, 주민등록번호 같은 개인정보 유형, 암호화 알고리즘, 키의 만료·비활성·폐기는 아이넵 홈페이지(https://www.inebsoft.com)의 디가드 DB 암호화(컬럼 단위 암호화·암호키 관리)와 통합 키 관리(키 생성·사용·만료·비활성·폐기) 제품 설명에서 가져온 낱말입니다. [평가 러너 · 2주차] 실습 PostgreSQL 에서 암호화한 컬럼에 평문 한 줄을 넣는 경우, 그 줄을 다시 암호화하는 경우, 정책을 지우는 경우, 키 상태를 폐기로 바꾸는 경우를 통합 테스트로 만들어, 스캔과 판정을 다시 돌린 뒤 그 컬럼의 verdict 가 기대한 값으로 바뀌는지 GitHub Actions 에서 매번 확인합니다. [수동 검증 · 사람이 봅니다] 1. 걸린 컬럼을 점검 보고서에 미조치로 올릴지는 개인정보보호 담당자가 정합니다. 2. 새로 쓸 키와 재암호화 작업 시각은 DB 관리자가 정합니다.
근거: DB 암호화와 통합 키 관리로 금융·공공 등 가장 엄격한 엔터프라이즈 환경에서 신뢰를 쌓아왔고