본문 바로가기
카테고리 없음

SK네트웍스 Family 엔코아 멀티 AI 에이전트 개발자 국비지원 10일차 회고|Streamlit UI·대시보드·테마

by 랩보다 AI 더 잘해지기 2026. 7. 23.
728x90

 

오늘은 파이썬만으로 웹 화면을 만들 수 있는 Streamlit을 배웠다. 앞선 수업에서 FastAPI와 Supabase를 이용해 백엔드와 데이터베이스를 다뤘다면, 오늘은 사용자가 실제로 보고 조작할 수 있는 프론트엔드 화면을 만드는 과정에 집중했다.

Streamlit의 기본 실행 구조부터 문자·숫자 입력, 선택 상자, 이미지 출력, 화면 배치, 대시보드 구성과 테마 설정까지 단계적으로 실습했다.

Streamlit이란?

Streamlit은 파이썬 코드만으로 간단한 웹 애플리케이션을 만들 수 있게 도와주는 도구다.

일반적으로 웹 화면을 만들려면 HTML, CSS, JavaScript 같은 기술이 필요하다. 하지만 Streamlit을 사용하면 파이썬으로 입력창, 버튼, 이미지, 표, 대시보드 등을 비교적 빠르게 만들 수 있다.

따라서 다음과 같은 화면을 만들 때 활용하기 좋다.

  • AI 모델의 결과를 확인하는 화면
  • 데이터 분석 대시보드
  • 챗봇 테스트 화면
  • 포트폴리오용 시연 페이지
  • 간단한 사내 업무 도구

다만 세밀한 디자인이나 복잡한 화면을 만드는 데에는 한계가 있어, 빠르게 기능을 확인하는 프로토타입 제작에 특히 적합하다.

Streamlit 앱 실행하기

파이썬 파일에 Streamlit 코드를 작성한 후 터미널에서 다음과 같이 실행할 수 있다.

streamlit run 파일명.py

명령어를 실행하면 Streamlit 서버가 시작되고, 브라우저에서 앱 화면을 확인할 수 있다.

브라우저가 Streamlit 주소로 접속하면 서버에서 파이썬 코드가 실행되고, 그 결과가 화면에 표시된다. 사용자가 입력값을 바꾸거나 항목을 선택하면 코드가 다시 실행되면서 새로운 결과가 나타난다.

브라우저에서 앱 접속
→ Streamlit 서버에서 파이썬 코드 실행
→ 실행 결과를 브라우저에 표시
→ 사용자가 값을 입력하거나 선택
→ 코드가 다시 실행되면서 화면 갱신

복잡한 이벤트 처리 코드를 직접 작성하지 않아도 화면이 자동으로 바뀐다는 점이 Streamlit의 특징이다.

기본 텍스트와 안내 메시지 출력하기

Streamlit에서는 제목과 설명, 안내 문구 등을 간단한 코드로 표시할 수 있다.

import streamlit as st

st.title("Streamlit 실습")
st.header("기본 화면")
st.write("파이썬으로 만든 웹 화면입니다.")

상황에 따라 서로 다른 색상의 메시지도 출력할 수 있다.

st.success("정상적으로 처리됐습니다.")
st.info("안내할 내용입니다.")
st.warning("입력값을 확인해 주세요.")
st.error("오류가 발생했습니다.")

이러한 기능은 사용자에게 작업 결과나 입력 상태를 알려줄 때 유용하다.

문자와 숫자 입력받기

st.text_input()을 사용해 사용자의 이름을 입력받고, 값이 있는지에 따라 다른 메시지를 보여주는 실습을 진행했다.

name = st.text_input("이름을 입력하세요")

if name:
    st.write(f"안녕하세요, {name}님!")
else:
    st.info("이름을 입력해 주세요.")

입력한 문자는 name 변수에 저장된다. 값이 있으면 인사말을 출력하고, 아직 입력하지 않았다면 안내 문구를 보여준다.

숫자는 st.number_input()으로 입력받았다.

age = st.number_input(
    "나이를 입력하세요",
    min_value=0,
    max_value=120,
    value=20
)

st.write(f"내년 나이는 {age + 1}세입니다.")

min_value와 max_value로 입력 범위를 제한하고, value로 처음 표시되는 기본값을 정할 수 있다. 입력값이 숫자로 저장되기 때문에 곧바로 계산에 사용할 수 있었다.

선택 상자와 라디오 버튼 사용하기

st.selectbox()를 이용하면 목록 중 하나를 선택하는 드롭다운 메뉴를 만들 수 있다.

language = st.selectbox(
    "관심 있는 언어를 선택하세요",
    ["Python", "JavaScript", "SQL"]
)

st.radio()는 여러 항목을 화면에 보여주고 그중 하나를 선택할 때 사용한다.

level = st.radio(
    "현재 학습 수준을 선택하세요",
    ["입문", "기초", "중급"]
)

두 입력값과 조건문을 연결해 특정 조건을 만족할 때만 안내 메시지가 나타나도록 만들었다.

if language == "Python" and level == "입문":
    st.info("Streamlit 기초 실습을 추천합니다.")

이를 통해 화면에서 선택한 값도 일반적인 파이썬 변수처럼 조건문에 사용할 수 있다는 것을 확인했다.

여러 입력값을 이용한 학습 피드백 화면

문자 입력, 숫자 입력, 여러 줄 입력을 조합해 간단한 학습 피드백 화면도 만들었다.

name = st.text_input("이름")
score = st.number_input("오늘의 이해도", 0, 100, 70)
comment = st.text_area("오늘 배운 내용 한 줄 정리")

점수에 따라 서로 다른 피드백이 나오도록 조건문을 작성했다.

if score >= 80:
    message = "다음 실습으로 넘어가도 좋습니다."
elif score >= 50:
    message = "예제를 한 번 더 수정해 보세요."
else:
    message = "기초 예제부터 다시 확인해 보세요."

이름과 학습 내용이 모두 입력된 경우에만 최종 결과를 보여줬다.

if name and comment:
    st.success(f"{name}님의 피드백")
    st.write(message)
    st.caption(f"오늘의 정리: {comment}")
else:
    st.warning("이름과 학습 내용을 모두 입력해 주세요.")

하나의 입력만 처리하는 것에서 나아가, 여러 입력값이 모두 준비됐는지 확인한 다음 결과를 출력하는 흐름을 연습할 수 있었다.

폴더에 있는 이미지 자동으로 불러오기

pathlib의 Path를 이용해 특정 폴더에 있는 PNG, JPG, JPEG 파일을 자동으로 찾았다.

from pathlib import Path

current_file = Path(__file__).resolve()
image_dir = current_file.parent.parent / "imgs"

image_files = sorted(
    list(image_dir.glob("*.png"))
    + list(image_dir.glob("*.jpg"))
    + list(image_dir.glob("*.jpeg"))
)

찾은 파일들의 이름을 selectbox에 넣고, 사용자가 선택한 이미지를 화면에 출력했다.

selected_name = st.selectbox(
    "이미지를 선택하세요",
    [image_file.name for image_file in image_files]
)

selected_image = image_dir / selected_name

st.image(
    selected_image,
    caption=selected_name,
    use_container_width=True
)

목록에 표시되는 것은 실제 이미지가 아니라 이미지의 파일명이다. 사용자가 파일명을 선택하면 서버에서 해당 이미지를 찾아 브라우저로 전달한다.

이미지가 하나도 없을 때에는 프로그램이 멈추지 않도록 예외 처리도 추가했다.

if not image_files:
    st.warning("이미지가 없습니다.")

이 실습을 통해 폴더의 파일을 리스트에 담고, 사용자의 선택과 실제 파일 경로를 연결하는 과정을 이해할 수 있었다.

브라우저 캐시가 이미지를 빠르게 보여주는 원리

이미지를 처음 불러올 때보다 두 번째부터 빠르게 표시되는 이유도 배웠다.

브라우저는 서버에서 받은 이미지를 캐시라는 임시 저장 공간에 보관한다. 같은 이미지가 다시 필요하면 서버에서 매번 내려받지 않고, 저장된 이미지를 활용할 수 있기 때문에 더 빠르게 표시된다.

처음 선택한 이미지
→ 서버에 이미지 요청
→ 서버가 이미지 전달
→ 브라우저가 이미지 저장

같은 이미지를 다시 선택
→ 브라우저 캐시에서 이미지 불러오기
→ 더 빠르게 화면에 표시

화면에 이미지가 보인다고 해서 이미지가 처음부터 브라우저 안에 있던 것은 아니라는 점이 중요했다.

columns로 화면 영역 나누기

st.columns()를 사용해 화면을 좌우로 나누는 실습을 진행했다.

left_col, right_col = st.columns(2)

with left_col:
    st.header("입력 영역")
    name = st.text_input("이름")

with right_col:
    st.header("결과 영역")

    if name:
        st.write(f"{name}님, 환영합니다.")
    else:
        st.write("왼쪽에서 이름을 입력하세요.")

with를 이용하면 각각의 영역에 어떤 요소를 배치할지 구분할 수 있다.

columns는 입력과 결과를 나란히 보여주거나, 여러 통계 수치를 한눈에 비교하는 대시보드를 만들 때 유용하다.

tabs와 sidebar로 화면 정리하기

한 화면에 모든 내용을 길게 배치하지 않고 st.tabs()를 이용해 주제별로 구분했다.

tab_summary, tab_detail, tab_memo = st.tabs(
    ["요약", "상세", "메모"]
)

각 탭에는 서로 다른 기능을 넣을 수 있다.

with tab_memo:
    memo = st.text_area("메모를 입력하세요")
    st.write("입력한 메모:", memo)

st.sidebar를 이용해서는 사용자 설정이나 검색 조건을 메인 화면과 분리했다.

with st.sidebar:
    user_name = st.text_input("사용자 이름")
    mode = st.selectbox(
        "화면 모드",
        ["기본", "집중", "요약"]
    )

사이드바는 과정 선택, 필터, 로그인 정보, 모델 설정처럼 결과 화면과 구분할 필요가 있는 입력 기능을 배치할 때 활용할 수 있다.

기본 대시보드 만들기

배운 기능을 조합해 학습 과정을 확인하는 기본 대시보드를 만들었다.

st.set_page_config(
    page_title="기본 대시보드",
    layout="wide"
)

layout="wide"를 적용하면 브라우저 화면을 넓게 사용할 수 있다.

사이드바에서는 과정과 진도율을 선택했다.

with st.sidebar:
    course = st.selectbox(
        "과정",
        ["Python Basic", "Streamlit Basic", "FastAPI Backend"]
    )

    progress = st.slider(
        "진도율",
        min_value=0,
        max_value=100,
        value=60
    )

메인 화면에서는 st.metric()과 st.progress()로 선택한 과정과 진도율을 보기 쉽게 표시했다.

st.metric("선택 과정", course)
st.metric("진도율", f"{progress}%")
st.progress(progress)

진도율에 따라 안내 메시지가 바뀌도록 조건문도 연결했다.

if progress >= 80:
    st.success("마무리 점검 단계입니다.")
elif progress >= 40:
    st.info("꾸준히 진행 중입니다.")
else:
    st.warning("기초 예제부터 다시 확인하세요.")

이를 통해 입력 위젯과 조건문, 화면 배치 기능을 하나의 앱으로 조합하는 방법을 연습했다.

버튼을 눌렀을 때 결과 출력하기

앞선 예제에서는 입력값이 바뀔 때마다 화면이 자동으로 갱신됐다. 이번에는 st.button()을 이용해 사용자가 버튼을 눌렀을 때만 결과가 나타나도록 만들었다.

if st.button("선택 내용 확인"):
    st.success(f"선택 항목: {topic} / 화면 모드: {mode}")

    if memo.strip():
        st.write("메모:", memo)
    else:
        st.warning("메모를 입력하지 않았습니다.")

이 구조를 이용하면 여러 입력값을 작성한 다음 제출 버튼을 눌러 한 번에 처리하는 화면으로 발전시킬 수 있다.

config.toml로 테마 변경하기

.streamlit/config.toml 파일을 이용해 앱 전체의 색상과 글꼴을 바꾸는 실습도 진행했다.

[theme]
base = "dark"
primaryColor = "#eb2525"
backgroundColor = "#06e706"
secondaryBackgroundColor = "#4f05ef"
textColor = "#d80909"
font = "sans serif"

각 설정은 다음과 같은 역할을 한다.

  • base: 밝은 테마와 어두운 테마 설정
  • primaryColor: 버튼과 선택 항목의 강조색
  • backgroundColor: 메인 화면의 배경색
  • secondaryBackgroundColor: 사이드바와 입력 영역의 배경색
  • textColor: 기본 글자색
  • font: 화면에서 사용하는 글꼴

테마 설정 파일이 실습 폴더 안에 있다면 해당 폴더로 이동한 뒤 Streamlit을 실행해야 한다.

cd 실습폴더경로
streamlit run .\01_theme-preview.py

다른 위치에서 파일 경로만 지정해 실행하면 .streamlit/config.toml을 찾지 못해 테마가 적용되지 않을 수 있다. 설정을 바꾼 후에는 서버를 종료하고 다시 실행해야 변경 사항을 정확하게 확인할 수 있었다.

실습을 통해 이해한 점

오늘은 Streamlit의 개별 기능을 배우는 데 그치지 않고, 여러 입력값과 조건문을 연결해 실제 웹 애플리케이션의 기본 흐름을 만들어 봤다.

특히 다음 내용을 이해할 수 있었다.

  • 파이썬 코드가 Streamlit 서버에서 실행되는 과정
  • 사용자의 입력값이 변수에 저장되는 원리
  • 입력값이 바뀌면 화면이 다시 만들어지는 방식
  • 폴더의 이미지 파일을 자동으로 검색하는 방법
  • 선택한 파일명과 실제 이미지 경로를 연결하는 과정
  • columns, tabs, sidebar를 이용한 화면 구성
  • metric과 progress를 활용한 대시보드 제작
  • config.toml을 이용한 전체 테마 변경

처음에는 Streamlit 화면이 일반적인 웹페이지처럼 브라우저 안에서만 실행되는 것으로 생각하기 쉽다. 하지만 실제로는 브라우저가 서버에 요청을 보내고, 서버에서 파이썬 코드와 데이터를 처리해 결과를 전달한다는 흐름을 이해하는 것이 중요했다.

오늘의 회고

오늘 수업을 통해 파이썬으로도 생각보다 빠르게 웹 화면을 만들 수 있다는 것을 알게 됐다. 문자와 숫자를 입력받는 간단한 예제에서 시작해 이미지 선택, 화면 분할, 탭, 사이드바, 대시보드와 테마 설정까지 단계적으로 확장하면서 각 기능이 어떻게 연결되는지 확인할 수 있었다.

아직은 화면을 구성하는 기본 기능을 따라 해본 단계이므로, 각 위젯에서 받은 값이 어떤 자료형으로 저장되는지와 입력값 변경 시 코드가 다시 실행되는 흐름을 더 복습해야겠다. 이미지 경로를 만드는 Path, 파일 목록을 만드는 리스트 컴프리헨션도 다시 직접 작성해 보면 도움이 될 것 같다.

앞으로 Streamlit에서 입력받은 값을 FastAPI 백엔드로 보내고, Supabase에 저장된 데이터나 LLM의 응답을 다시 화면에 출력한다면 실제 AI 서비스에 가까운 구조를 만들 수 있을 것 같다.

#해시태그

#SK네트웍스Family #엔코아 #멀티AI에이전트 #AI개발자국비지원 #Streamlit #파이썬웹개발 #Streamlit대시보드 #파이썬프론트엔드 #Streamlit테마 #AI서비스개발

댓글