세이가쿠샤코리아
경력근거: Claude Code, Codex, OpenCode 등을 활용해 업무 효율화 도구/애플리케이션을 개발한 경험 보유자
※ 실제 산출물이 아닌 AI 예측 시안입니다.
이 회사는 산업특화 온프레미스 LLM 부터 Agent RAG 와 노코드 앱 빌더까지 다루고, 대표 고객사가 미쓰이스미토모 파이낸셜그룹·도쿄메트로·히타치제작소·NTT도코모처럼 망을 나눠 쓰는 일본 대기업입니다. 그런 현장에서 Solutions Architect 가 처음 부딪히는 벽은 모델 성능이 아니라 전산실 방화벽이고, 자격요건이 TCP/IP·DNS·HTTP·VPN·방화벽 지식과 *NIX 숙련도를 나란히 요구하는 이유도 거기 있습니다. 다만 이 포트폴리오는 통신 요구를 규칙과 맞춰 문서로 떨어뜨리는 도구를 보여주는 것이고, 금융이나 철도 같은 고객사 업종의 보안 규정 전문성은 주장하지 않습니다. 모르는 깊이는 면접에서 모른다고 말하는 편이 낫습니다.
Claude Code·Codex·OpenCode 로 업무 효율화 도구를 개발한 경험을 자격요건에 못 박아 두어, 현장에서 실제로 돌려 쓰는 CLI 한 벌이 서류에서 바로 읽힙니다.
TCP/IP·DNS·HTTP·VPN·방화벽 지식과 *NIX 숙련도를 함께 요구하는데, 온프레미스 도입에서 실제로 시간을 잡아먹는 자리가 바로 그 통신 개방이라 도구가 붙을 곳이 분명합니다.
고객과 협업해 과제를 정의하고 요건을 기술적 성과물로 구체화하는 것이 주요업무라, 담당자가 말로 준 요구를 문서로 떨어뜨리는 산출물이 직무와 겹칩니다.
온프레미스 LLM 도입에 필요한 통신 요구 목록과 방화벽 팀이 내려준 현재 규칙 두 파일을 받아, 이미 열려 있는 통신과 새로 신청해야 하는 통신을 나눠 신청서 초안 문서를 내는 CLI 도구입니다. 판정 근거로 쓴 규칙 번호를 줄마다 적어, 담당자가 방화벽 팀에 그대로 들고 갑니다.
일본 고객사 전산실에 온프레미스 LLM 서버를 올려 놓고, 정작 모델 저장소 내려받기와 사내 인증 서버 호출이 막혀 사흘을 기다리던 도입 담당자입니다. 무엇이 이미 열려 있는지는 방화벽 팀 엑셀에 있고 무엇이 필요한지는 자기 머릿속에 있어서, 둘을 맞춰 보는 일을 현장마다 손으로 되풀이합니다.
어느 통신이 되고 어느 통신이 막히는지는 출발지·목적지·포트·프로토콜을 현재 규칙에 맞춰 보면 끝나는 결정론적 판정입니다. 그 판정을 CLI 로 옮기면 담당자는 막히는 것만 추린 신청서를 첫날에 넘기고, 사흘을 기다리는 자리가 사라집니다.
도입 담당자가 통신 요구 목록과 현재 규칙 파일을 넣고 명령을 한 줄 치면, 이미 열린 통신과 신청이 필요한 통신을 가른 신청서 초안 문서가 파일로 남습니다.
정답을 붙인 통신 26건으로 판정 일치를 자동으로 재는 러너와, 포트가 비었거나 호스트를 못 붙인 줄만 담당자 확인 목록으로 따로 내는 명령입니다.
폐쇄망을 흉내 낸 컨테이너 두 대를 띄워 신청서에 적은 통신이 실제로 오가는지 확인하고, 그 결과를 신청서 문서 뒤에 붙이는 형상입니다.
도입 담당자가 통신 요구 목록과 현재 규칙 파일을 넣고 명령을 한 줄 치면 신청서 초안 문서가 파일로 남습니다. 요구 14건과 규칙 12건을 합친 26건에서 이미 열린 통신과 신청이 필요한 통신이 갈립니다.
포트가 비어 있는 줄과 호스트 이름 표기가 흔들린 줄을 일부러 섞은 입력에서도 실행이 멈추지 않습니다. 규칙 쪽에 짝이 없는 호스트는 미매핑으로 신청서 아래 확인 목록에 남습니다.
정답을 붙인 통신 26건으로 판정 일치를 냅니다. 단, 정답도 데이터도 작성자가 만든 합성 기준이라 성능 검증이 아니라 데모 조건 동작입니다.
요구 14건을 한 번 판정하는 데 걸리는 시간을 실행 로그로 잽니다. 측정은 개발 장비의 실행 로그이고 표본은 연속 10회 실행입니다.
위 수치는 더미데이터 자가채점이며 실제 판정 정확도는 고객사의 실 방화벽 규칙과 실제 전산실 구성이 있어야 측정됩니다. 이 포트폴리오는 그 측정을 바로 돌릴 수 있는 상태로 만듭니다.
수치는 합성 데이터 자가채점이라 성능 증명이 아닙니다. 면접에서는 데모 동작과 실측 준비 상태로 솔직히 설명합니다.
정답을 작성자가 만들었으니 잘 맞는 것이 당연합니다. 포트가 비어 있는 줄, 호스트 표기가 흔들린 줄, 규칙 쪽에 짝이 없는 호스트, 만료일이 지난 규칙을 더미에 일부러 섞어 쉬운 문제만 푸는 함정을 피합니다.
신청서가 나왔다는 사실이 곧 통신이 열린다는 뜻은 아닙니다. 실제 개방은 고객사 보안 심의를 거치므로, 도구는 신청 대상을 추리는 데까지만 하고 승인 여부는 사람의 자리로 남깁니다.
실제 도입에서는 고객사마다 규칙 export 형식과 구간 표기 방식이 다릅니다. 읽기 규칙을 코드에서 빼 설정 파일로 옮겨야 하며, 그것은 도입 단계 과제로 분리합니다.
이 포트폴리오는 통신 요구를 규칙과 맞춰 문서로 떨어뜨리는 도구를 보여줍니다. 금융·철도 같은 고객사 업종의 보안 규정 깊이는 주장하지 않습니다.
① 인라인 샘플 · ② seed.json 다운로드 · ③ 증강 프롬프트. 세 층 모두 동일한 schema 에서 파생.
온프레미스 LLM 을 올리는 데 필요한 통신을 도입 담당자가 정리한 요구 목록입니다. 판정의 왼쪽 축이고, 포트를 아직 못 적은 줄과 같은 호스트를 다르게 적은 줄이 섞여 있습니다.
| flow_no | src_host_raw | src_host_id | dst_host_raw | dst_port | protocol_raw | purpose | zone_raw | requested_by |
|---|---|---|---|---|---|---|---|---|
| REQ-1101 | llm-infer01.corp.local | H-2001 | hub-registry.corp.local | 443 | TCP | 모델 가중치 내려받기 | DMZ | 사토 |
| REQ-1102 | llm-infer01.corp.local | H-2001 | HUB-REGISTRY.CORP.LOCAL | 443 | tcp | 모델 갱신본 내려받기 | DMZ | 김도윤 |
| REQ-1103 | llm-infer01.corp.local | H-2001 | idp-auth.corp.local | 636 | TCP | 사내 계정 인증 조회 | 내부망 | 사토 |
| REQ-1104 | llm-app01.corp.local | H-2002 | llm-infer01.corp.local | 8,080 | TCP | 추론 요청 전달 | 내부망 | 사토 |
| REQ-1105 | llm-app01.corp.local | H-2002 | pg-meta01.corp.local | 5,432 | TCP | 대화 이력 저장 | 내부망 | 김도윤 |
아래 JSON Schema 에 정확히 맞는 온프레미스 LLM 도입 통신 요구 20건을 JSON 배열로 생성해 주세요. {"type":"object","properties":{"flow_no":{"type":"string"},"src_host_raw":{"type":"string"},"src_host_id":{"type":["string","null"]},"dst_host_raw":{"type":"string"},"dst_port":{"type":["integer","null"],"minimum":1,"maximum":65535},"protocol_raw":{"type":"string"},"purpose":{"type":"string"},"zone_raw":{"type":"string"},"requested_by":{"type":"string"}},"required":["flow_no","src_host_raw","dst_host_raw","protocol_raw","purpose","zone_raw","requested_by"]} 조건: flow_no 는 REQ-11NN 형식으로 서로 다르게 쓰고, 호스트 이름은 corp.local 도메인을 씁니다. 쉬운 데이터만 만들지 말 것 — 다음 하드 케이스를 의도적으로 섞어라: 같은 호스트를 소문자와 대문자로 다르게 적은 줄 2건, dst_port 가 null 인 줄 1건, src_host_id 가 null 인 미등록 서버 줄 2건, 규칙 쪽에 짝이 없을 호스트를 가리키는 줄 2건. 형식을 깨뜨리는 시도(포트 칸에 '80,443' 처럼 두 값 넣기, 프로토콜을 'TCP/UDP' 로 적기, 열 이름을 일본어로 바꾼 CSV)는 데이터가 아니라 별도 3건의 파일로 만들어 읽기 계층을 시험합니다. JSON 배열만 출력해 주세요.{"type":"object","properties":{"flow_no":{"type":"string"},"src_host_raw":{"type":"string"},"src_host_id":{"type":["string","null"]},"dst_host_raw":{"type":"string"},"dst_port":{"type":["integer","null"],"minimum":1,"maximum":65535},"protocol_raw":{"type":"string"},"purpose":{"type":"string"},"zone_raw":{"type":"string"},"requested_by":{"type":"string"}},"required":["flow_no","src_host_raw","dst_host_raw","protocol_raw","purpose","zone_raw","requested_by"]}방화벽 팀이 내려준 현재 허용 규칙 export 입니다. 판정의 오른쪽 축이고, 만료일이 비어 있는 규칙과 이미 지난 규칙이 섞여 있습니다.
| rule_no | src_raw | dst_raw | port_from | port_to | protocol_raw | action | expires_on |
|---|---|---|---|---|---|---|---|
| FWR-2201 | llm-infer01.corp.local | hub-registry.corp.local | 443 | 443 | TCP | allow | — |
| FWR-2202 | llm-infer01.corp.local | idp-auth.corp.local | 636 | 636 | TCP | allow | 2026-12-31 |
| FWR-2203 | llm-app01.corp.local | llm-infer01.corp.local | 8,000 | 8,099 | TCP | allow | — |
| FWR-2204 | llm-app01.corp.local | pg-meta01.corp.local | 5,432 | 5,432 | TCP | allow | 2026-06-30 |
| FWR-2205 | llm-infer01.corp.local | ntp-pool.corp.local | 123 | 123 | UDP | allow | — |
아래 JSON Schema 에 정확히 맞는 방화벽 허용 규칙 16건을 JSON 배열로 생성해 주세요. {"type":"object","properties":{"rule_no":{"type":"string"},"src_raw":{"type":"string"},"dst_raw":{"type":"string"},"port_from":{"type":"integer","minimum":1,"maximum":65535},"port_to":{"type":"integer","minimum":1,"maximum":65535},"protocol_raw":{"type":"string"},"action":{"type":"string","enum":["allow","deny"]},"expires_on":{"type":["string","null"]}},"required":["rule_no","src_raw","dst_raw","port_from","port_to","protocol_raw","action"]} 조건: rule_no 는 FWR-22NN 형식으로 서로 다르게 쓰고, 호스트 이름은 통신 요구 목록과 같은 corp.local 도메인을 씁니다. 쉬운 데이터만 만들지 말 것 — 다음 하드 케이스를 의도적으로 섞어라: 요구한 포트보다 좁은 구간만 허용하는 규칙 1건, expires_on 이 이미 지난 규칙 1건, action 이 deny 인 규칙 1건, expires_on 이 null 인 무기한 규칙 3건. 형식을 깨뜨리는 시도(포트 구간을 '8000-8099' 한 칸에 넣기, action 을 '허용' 으로 적기)는 데이터가 아니라 별도 2건의 파일로 만들어 읽기 계층을 시험합니다. JSON 배열만 출력해 주세요.{"type":"object","properties":{"rule_no":{"type":"string"},"src_raw":{"type":"string"},"dst_raw":{"type":"string"},"port_from":{"type":"integer","minimum":1,"maximum":65535},"port_to":{"type":"integer","minimum":1,"maximum":65535},"protocol_raw":{"type":"string"},"action":{"type":"string","enum":["allow","deny"]},"expires_on":{"type":["string","null"]}},"required":["rule_no","src_raw","dst_raw","port_from","port_to","protocol_raw","action"]}| Python | 엑셀과 규칙 export 를 읽어 통신 요구를 현재 규칙에 맞춰 보는 판정 엔진을 씁니다 |
| *NIX(Linux) | 명령을 표준 입출력으로 이어 붙여 다른 도구와 파이프로 엮이게 만듭니다 |
| TCP/IP | 출발지·목적지·포트·프로토콜 네 값을 판정의 기본 단위로 삼습니다 |
| DNS | 호스트 이름 표기가 흔들려도 같은 대상인지 정규화해 붙입니다 |
| HTTP | 모델 저장소와 사내 인증 서버 호출처럼 실제로 필요한 통신의 목적을 분류합니다 |
| VPN·방화벽 | 현재 규칙의 허용 구간과 만료일을 읽어 신청이 필요한 줄을 가릅니다 |
| LLM Agent | 판정 결과를 받아 신청서 문구를 만드는 단계를 도구 호출로 묶습니다 |
| Claude Code | 이 CLI 자체를 만들고 고치는 개발 환경이며, 명령 추가와 회귀 확인을 같은 자리에서 돌립니다 |
| Kubernetes | 폐쇄망을 흉내 낸 컨테이너 두 대를 띄워 신청한 통신이 실제로 오가는지 확인합니다 |
| PostgreSQL | 현장별 판정 이력을 쌓아 지난 현장의 신청 내용을 다시 꺼냅니다 |
✓ pass → 여기서 멈춰도 완결입니다. 더 키우려면 판정이 맞았는지 재는 러너와 확인 목록을 붙입니다.
✓ pass → 여기서 멈춰도 완결입니다. 더 키우려면 컨테이너를 띄워 신청한 통신이 실제로 오가는지 확인합니다.
통신 요구 한 줄이 신청서에서 어떤 줄이 되는지를 담습니다. 판정 근거로 쓴 규칙 번호를 그대로 실어, 담당자가 방화벽 팀에 근거를 대고 말합니다.
{"type":"object","properties":{"flow_no":{"type":"string"},"status":{"type":"string","enum":["already_allowed","request_needed","port_widen_needed","rule_expired","host_unresolved","port_missing"]},"matched_rule_no":{"type":["string","null"]},"request_sentence":{"type":["string","null"]},"summary":{"type":"string"},"evidence":{"type":"array","items":{"type":"object","properties":{"dataset":{"type":"string"},"field":{"type":"string"},"quote":{"type":"string"},"value":{"type":["number","string","null"]}},"required":["dataset","field"]}}},"required":["flow_no","status","summary","evidence"]}[
{
"flow_no": "REQ-1101",
"status": "already_allowed",
"matched_rule_no": "FWR-2201",
"request_sentence": null,
"summary": "모델 가중치 내려받기 통신은 무기한 허용 규칙에 이미 들어 있어 신청하지 않아도 됩니다.",
"evidence": [
{
"dataset": "required_flows",
"field": "dst_host_raw",
"quote": "hub-registry.corp.local",
"value": "hub-registry.corp.local"
},
{
"dataset": "approved_rules",
"field": "rule_no",
"quote": "FWR-2201",
"value": "FWR-2201"
}
]
},
{
"flow_no": "REQ-1102",
"status": "already_allowed",
"matched_rule_no": "FWR-2201",
"request_sentence": null,
"summary": "호스트를 대문자로 적었을 뿐 같은 대상이라 갱신본 내려받기도 기존 허용 규칙으로 이미 열려 있습니다.",
"evidence": [
{
"dataset": "required_flows",
"field": "dst_host_raw",
"quote": "HUB-REGISTRY.CORP.LOCAL",
"value": "HUB-REGISTRY.CORP.LOCAL"
},
{
"dataset": "approved_rules",
"field": "dst_raw",
"quote": "hub-registry.corp.local",
"value": "hub-registry.corp.local"
}
]
},
{
"flow_no": "REQ-1112",
"status": "port_widen_needed",
"matched_rule_no": "FWR-2208",
"request_sentence": "llm-app01.corp.local 에서 idp-auth.corp.local 636 포트로 나가는 TCP 통신을 열어 주십시오. 기존 규칙 FWR-2208 은 389 포트만 허용합니다.",
"summary": "관리자 로그인 인증은 636 포트가 필요한데 기존 규칙이 389 포트만 열어 두어 구간을 넓혀야 합니다.",
"evidence": [
{
"dataset": "required_flows",
"field": "dst_port",
"quote": "636",
"value": 636
},
{
"dataset": "approved_rules",
"field": "port_to",
"quote": "389",
"value": 389
}
]
},
{
"flow_no": "REQ-1108",
"status": "rule_expired",
"matched_rule_no": "FWR-2206",
"request_sentence": "llm-ops01.corp.local 에서 llm-infer01.corp.local 9100 포트로 나가는 TCP 통신을 다시 열어 주십시오. 기존 규칙 FWR-2206 은 만료됐습니다.",
"summary": "지표 수집 통신을 열어 두던 규칙의 만료일이 지나 다시 신청해야 합니다.",
"evidence": [
{
"dataset": "approved_rules",
"field": "expires_on",
"quote": "2026-02-28",
"value": "2026-02-28"
},
{
"dataset": "required_flows",
"field": "dst_port",
"quote": "9100",
"value": 9100
}
]
},
{
"flow_no": "REQ-1106",
"status": "port_missing",
"matched_rule_no": null,
"request_sentence": null,
"summary": "첨부 파일 보관 통신은 포트가 비어 있어 판정하지 못했습니다. 스토리지 팀에 포트를 물어야 합니다.",
"evidence": [
{
"dataset": "required_flows",
"field": "dst_port",
"value": null
},
{
"dataset": "required_flows",
"field": "purpose",
"quote": "첨부 파일 보관, 포트는 스토리지 팀 확인 필요",
"value": "첨부 파일 보관, 포트는 스토리지 팀 확인 필요"
}
]
},
{
"flow_no": "REQ-1114",
"status": "host_unresolved",
"matched_rule_no": null,
"request_sentence": null,
"summary": "가속기 라이선스 서버가 현재 규칙 어디에도 없어 어느 구간을 넓히는 신청인지 정하지 못했습니다.",
"evidence": [
{
"dataset": "required_flows",
"field": "dst_host_raw",
"quote": "gpu-lic01.corp.local",
"value": "gpu-lic01.corp.local"
},
{
"dataset": "required_flows",
"field": "zone_raw",
"quote": "내부망",
"value": "내부망"
}
]
},
{
"flow_no": "REQ-1110",
"status": "request_needed",
"matched_rule_no": "FWR-2210",
"request_sentence": "llm-app01.corp.local 에서 smtp-relay.corp.local 25 포트로 나가는 TCP 통신을 열어 주십시오. 기존 규칙 FWR-2210 은 차단으로 잡혀 있습니다.",
"summary": "실패 알림 메일 전송은 현재 차단 규칙에 걸려 있어 예외 신청이 필요합니다.",
"evidence": [
{
"dataset": "approved_rules",
"field": "action",
"quote": "deny",
"value": "deny"
},
{
"dataset": "required_flows",
"field": "purpose",
"quote": "실패 알림 메일 전송",
"value": "실패 알림 메일 전송"
}
]
}
][자동 검증 · 러너가 매 실행마다 겁니다] 1. status 값이 여섯 값 목록에 있는지 확인합니다. 2. flow_no·status·summary·evidence 필수 필드가 모두 존재하는지 확인합니다. 3. status 가 already_allowed 이면 matched_rule_no 필드가 존재하고 request_sentence 는 null 인지 확인합니다. 4. evidence 의 field 가 datasets 컬럼에 실재하는지 확인합니다. 5. evidence 의 quote 가 datasets 샘플의 원문 그대로인지 확인합니다. 6. dst_port 와 port_from·port_to 가 1 이상 65535 이하 범위인지 확인합니다. 7. summary 가 존댓말 한 문장인지 확인합니다. [수동 검증 · 사람이 한 번 봅니다] 신청 문구가 방화벽 팀이 그대로 읽을 만한 문장인지, 판정 근거로 든 규칙이 실제로 그 통신을 덮는 규칙이 맞는지를 표본 열 건에서 눈으로 봅니다. [평가 러너 · 2주차] 정답을 붙인 통신 26건으로 판정 상태가 정답과 얼마나 겹치는지 재고, 이미 열려 있는데 신청 대상으로 잘못 올린 줄이 몇 건인지 따로 셉니다.