Streamlit은 데이터 사이언스와 머신러닝 프로젝트를 위한 파이썬 웹앱 프레임워크입니다. 이 튜토리얼에서는 Streamlit 1.10 버전에 도입된 멀티페이지 앱 기능을 활용해 기존 싱글페이지 데모 앱을 멀티페이지로 변환하는 과정을 단계별로 살펴보겠습니다.
싱글페이지 앱의 한계
Streamlit 1.10 이전에는 streamlit hello
명령어로 실행되는 데모 앱이 하나의 큰 싱글페이지로 구성되어 있었습니다. 멀티페이지를 지원하지 않았기 때문에 사이드바의 st.selectbox
를 사용해 플롯, 맵핑, 데이터프레임 데모 중 하나를 선택해 실행하는 방식이었죠.
이런 방식은 앱의 규모가 커질수록 코드 유지보수에 부담이 되고, 페이지 선택을 위한 UI가 st.selectbox
로 제한되며, 개별 페이지의 타이틀을 st.set_page_config
로 커스텀할 수 없는 등 여러 한계가 있습니다. 무엇보다 URL을 통한 페이지 간 이동이 불가능하죠.
멀티페이지로 앱 변환하기
이제 싱글페이지 앱의 한계를 극복하고 멀티페이지의 장점을 활용해 봅시다. 기존 앱을 멀티페이지로 변환하려면 다음과 같은 절차가 필요합니다.
- 엔트리포인트 파일(
hello.py
)과 동일한 경로에pages
폴더 생성 - 엔트리포인트 파일명을
Hello.py
로 변경해 사이드바 타이틀 대문자로 표시 pages
폴더에 각 데모별 파일 생성
pages/1_📈_Plotting_Demo.py
pages/2_🌍_Mapping_Demo.py
pages/3_📊_DataFrame_Demo.py
- 기존
plotting_demo
,mapping_demo
,data_frame_demo
함수의 내용을 3번에서 생성한 파일로 이동 streamlit run Hello.py
실행해 멀티페이지 앱 확인
이제 변환 과정의 각 단계별로 코드 변경 내용을 살펴보겠습니다.
엔트리포인트 파일 생성
Hello.py
를 앱의 엔트리포인트로 지정하고, 사이드바 타이틀을 대문자로 표시하며, 인트로 페이지의 코드만 포함하도록 합니다. 또한 st.set_page_config
를 사용해 브라우저 탭에 표시되는 페이지 타이틀과 파비콘을 지정할 수 있습니다.
import streamlit as st
st.set_page_config(
page_title="Hello",
page_icon="👋",
)
st.write("# Welcome to Streamlit! 👋")
st.sidebar.success("Select a demo above.")
st.markdown(
"""
Streamlit is an open-source app framework built specifically for
Machine Learning and Data Science projects.
**👈 Select a demo from the sidebar** to see some examples
of what Streamlit can do!
### Want to learn more?
- Check out [streamlit.io](https://streamlit.io)
- Jump into our [documentation](https://docs.streamlit.io)
- Ask a question in our [community forums](https://discuss.streamlit.io)
### See more complex demos
- Use a neural net to [analyze the Udacity Self-driving Car Image Dataset](https://github.com/streamlit/demo-self-driving)
- Explore a [New York City rideshare dataset](https://github.com/streamlit/demo-uber-nyc-pickups)
"""
)
아직 페이지를 생성하지 않았기 때문에 사이드바에 페이지 목록이 표시되지 않습니다.
여러 페이지 생성하기
페이지 생성 시 주의할 점은 다음과 같습니다.
- 파일명 앞에 숫자를 붙여 페이지 순서 지정 가능
- 파일명으로 앱 페이지명이 결정되므로 변경 시 주의
- 파일명에 이모지를 사용해 재미를 더할 수 있음
- 각 페이지는 파일명으로 정의되는 고유 URL을 갖게 됨
pages
폴더에 각 데모 페이지에 해당하는 파일을 생성하고 관련 코드를 옮깁니다.
pages/1_📈_Plotting_Demo.py
:
import streamlit as st
import time
import numpy as np
st.set_page_config(page_title="Plotting Demo", page_icon="📈")
st.markdown("# Plotting Demo")
st.sidebar.header("Plotting Demo")
st.write(
"""This demo illustrates a combination of plotting and animation with
Streamlit. We're generating a bunch of random numbers in a loop for around
5 seconds. Enjoy!"""
)
progress_bar = st.sidebar.progress(0)
status_text = st.sidebar.empty()
last_rows = np.random.randn(1, 1)
chart = st.line_chart(last_rows)
for i in range(1, 101):
new_rows = last_rows[-1, :] + np.random.randn(5, 1).cumsum(axis=0)
status_text.text("%i%% Complete" % i)
chart.add_rows(new_rows)
progress_bar.progress(i)
last_rows = new_rows
time.sleep(0.05)
progress_bar.empty()
# Streamlit widgets automatically run the script from top to bottom. Since
# this button is not connected to any other logic, it just causes a plain
# rerun.
st.button("Re-run")
pages/2_🌍_Mapping_Demo.py
:
import streamlit as st
import pandas as pd
import pydeck as pdk
from urllib.error import URLError
st.set_page_config(page_title="Mapping Demo", page_icon="🌍")
st.markdown("# Mapping Demo")
st.sidebar.header("Mapping Demo")
st.write(
"""This demo shows how to use
[`st.pydeck_chart`](https://docs.streamlit.io/library/api-reference/charts/st.pydeck_chart)
to display geospatial data."""
)
@st.cache_data
def from_data_file(filename):
url = (
"http://raw.githubusercontent.com/streamlit/"
"example-data/m