Project 02 — Streamlit Log Dashboard
전체 소스코드는 GitHub에서 확인할 수 있습니다. hojjang98 / skshielders-rookies-28 — projects/week_02
개요
Streamlit Log Dashboard는 Week 1에서 구축한 Mini Security Log Monitor의 결과물(access.log)을 기반으로, 보안 로그를 데이터프레임 형태로 가공 -> 시각화 -> 대시보드화 하는 프로젝트다.
Week 1 코드를 단순 재사용하지 않고, 랜덤 사용자 및 랜덤 인증 반전 로직을 추가하여 보다 현실적인 로그 패턴을 자동 생성하도록 확장하였다. 이를 통해 Pie Chart · Bar Chart 에서 다양한 분포를 시각적으로 분석할 수 있는 구조를 완성했다.
주간 학습 요약
-
Day 1 (11.03) — Numpy 기초 및 벡터화 연산
- 로그 데이터의 벡터화 처리 및 고속 계산
-
Day 2 (11.04) — Pandas & EDA 기초
- 로그 적재, 결측 보정, DataFrame 변환
-
Day 3 (11.05) — Pandas 기반 로그 정규화
- 데이터 표준화, 타입 변환, 결측 처리
-
Day 4 (11.06) — Matplotlib · Seaborn 기반 시각화
- 그룹화, 통계형 시각화, 이상치 탐지 그래프
-
Day 5 (11.07) — Folium · Plotly · Streamlit 실습
- 인터랙티브 지도, 동적 그래프, 웹 대시보드 구성
주요 기능
- 랜덤 로그 자동 생성 — Week 1 모니터에 랜덤 사용자 · 인증 반전 로직 추가 (현실적 분포 확보)
- JSON 기반 데이터 로드 — access.log 의 JSON 라인을 필터링하여 Pandas DataFrame 으로 변환
- 통계 기반 시각화 — 성공 / 실패 비율(Pie), 사용자별 접근 분포(Bar) 표시
- Streamlit 대시보드 — 사이드바 필터, 메트릭, 그래프, 데이터 테이블 UI 구성
- 실시간 반영 — 로그 파일 갱신 시 수동 새로고침으로 즉시 반영
- 확장 가능 구조 — Folium 및 GeoIP 추가 시 지역 기반 공격 맵 시각화 가능
Week 1 -> Week 2 확장 포인트
Week 1의 secure_log_monitor.py 에서 달라진 핵심 부분은 랜덤 로그 생성 로직이다. 사용자 풀을 6명으로 늘리고, 50회 반복 실행하면서 매 시도마다 25% 확률로 인증 상태를 반전시킨다. 이를 통해 단순한 성공 / 실패 이분법이 아닌 불규칙한 실제 접근 패턴을 시뮬레이션한다.
users = [
User("admin", authenticated=True),
User("carol", authenticated=False),
User("root", authenticated=True),
User("guest", authenticated=False),
User("analyst", authenticated=True),
User("intern", authenticated=False)
]
for _ in range(50):
u = random.choice(users)
if random.random() < 0.25:
u.authenticated = not u.authenticated # 25% 확률로 인증 상태 반전
read_secure_log(u)
time.sleep(0.05) # 로그 생성 타이밍 분산 -> 시계열 분석 기반 마련
핵심 코드 설명 — dashboard.py
1. load_access_log — JSON 파싱 -> DataFrame 변환
access.log 에는 한 줄씩 JSON 형태로 로그가 쌓여 있다. 이 함수는 줄 단위로 읽어 { 로 시작하는 유효한 JSON 만 추출해 Pandas DataFrame 으로 반환한다. 파일이 없거나 JSON 파싱에 실패한 줄은 안전하게 건너뛴다.
def load_access_log(path="access.log"):
if not os.path.exists(path):
return pd.DataFrame()
records = []
with open(path, "r", encoding="utf-8") as f:
for line in f:
line = line.strip()
if not line or not line.startswith("{"):
continue
try:
records.append(json.loads(line))
except json.JSONDecodeError:
continue
return pd.DataFrame(records)
2. 사이드바 필터 — 사용자 · 결과 선택
st.sidebar.multiselect 를 사용해 사용자별, 결과(SUCCESS / FAIL)별 필터를 제공한다. 기본값으로 전체를 선택한 상태에서 시작하며, 선택 변경 즉시 하위 시각화에 반영된다.
user_filter = st.sidebar.multiselect("사용자 선택", df["user"].unique(), default=df["user"].unique())
result_filter = st.sidebar.multiselect("결과 선택", df["result"].unique(), default=df["result"].unique())
filtered = df[
(df["user"].isin(user_filter)) &
(df["result"].isin(result_filter))
]
3. 메트릭 — 총 시도 수 · 실패율 계산
필터링된 데이터 기준으로 총 접근 시도 수와 실패율(%) 을 계산해 상단에 요약 표시한다. 0으로 나누는 오류를 방지하는 안전 처리도 포함되어 있다.
st.metric("총 접근 시도", len(filtered))
fail_count = (filtered["result"] == "FAIL").sum()
fail_rate = (fail_count / len(filtered)) * 100 if len(filtered) > 0 else 0
st.metric("실패율 (%)", f"{fail_rate:.1f}")
4. Plotly 시각화 — Pie Chart & Bar Chart
Pie Chart 는 SUCCESS / FAIL 비율을, Bar Chart 는 사용자별 접근 시도 분포를 인터랙티브하게 표시한다. 두 그래프 모두 Plotly Express 를 사용해 마우스 호버 시 세부 수치가 표시된다.
fig_pie = px.pie(
filtered,
names="result",
title="Access Result Ratio",
color_discrete_sequence=px.colors.qualitative.Safe
)
st.plotly_chart(fig_pie, use_container_width=True)
fig_bar = px.bar(
filtered,
x="user",
color="result",
barmode="group",
title="Access Attempts per User"
)
st.plotly_chart(fig_bar, use_container_width=True)
대시보드 구성 요약
| 항목 | 내용 |
|---|---|
| 필터 (Sidebar) | 사용자 선택, 결과 선택 (SUCCESS / FAIL) |
| 메트릭 (상단 요약) | 총 접근 시도 수, 실패율 (%) |
| 그래프 ① | Pie Chart — 접근 결과 비율 (SUCCESS vs FAIL) |
| 그래프 ② | Bar Chart — 사용자별 접근 시도 및 결과 분포 |
| 데이터 테이블 | Raw Log Data — 필터링된 JSON 로그 목록 |
SOC 관점 연계
이번 프로젝트는 로그 -> 정제 -> 시각화 -> 인사이트 도출 과정을 보안관제(SOC) 의 기초 분석 사이클로 옮겨온 것이다.
- 로그 수집 (Collection) — Week 1 확장 버전에서 랜덤 로그 생성 및 수집
- 데이터 정제 (Preprocessing) — Pandas 기반 JSON 파싱 및 구조화
- 이벤트 시각화 (Visualization) — Plotly 로 성공 / 실패 분포 분석
- 대시보드 분석 (Dashboard) — Streamlit UI 로 사용자별 / 시간대별 필터링
- 보고 및 판단 (Reporting) — 보안 이벤트 패턴 및 실패율 시각화
학습 연결 포인트
- numpy, pandas => 로그 데이터 정규화 및 전처리
- random 모듈 => 인증 여부를 무작위로 전환하여 다양한 로그 패턴 생성
- groupby, pivot_table => 사용자별 / 시간대별 탐지 이벤트 집계
- matplotlib, seaborn => 탐지율 및 실패율 그래프 작성
- plotly.express => 인터랙티브 시각화 구현
- streamlit => 대시보드 UI 구성 및 필터 연동
- time.sleep() => 로그 생성 타이밍 분산으로 시계열 분석 기반 마련
확장 아이디어
- 시계열 분석 — 로그 생성 시각 기반 시간대별 접근 추이 Line Chart
- 실시간 업데이트 — st_autorefresh(interval=5000) 로 5초마다 자동 갱신
- 지도 시각화 — Folium + GeoIP 로 공격 발생 지역 표시
- 심화 집계 — Pandas 그룹화로 사용자별 실패율 / 평균 응답시간 계산
- 위협 인텔리전스 연계 — 외부 Threat Intelligence API 결합
Week 2 프로젝트는 Week 1의 탐지 엔진을 데이터 분석 레이어로 확장한 단계다. 로그를 “텍스트"가 아닌 “데이터” 로 바라보는 관점을 체득하는 것이 핵심이다.