Voila
- 장점: 노트북에서 쉽게 프로토타입을 만들 수 있음
- 단점: 대시보드처럼 레이아웃을 잡기 어려움
- 기존 코드를 조금만 수정해서 웹 서비스를 만드는 것이 목표
웹 서비스를 만드는 과정
- 데이터 분석가가 웹 서비스를 작업하는 Flow
- Jupyter notebook에서 코드 만들기
- Python script에서 복붙
- Flask app을 사용, HTTP 요청, callback, JS...등등
- 유지하기 힘들다
- 데이터 Product로 중요하게 된다면 프론트엔드/PM 조직과 협업
- requirements 작성
- 웹 화면 Layout
- HTML, css, python, react 등으로 앱을 코드업한다.
- 수정이 힘들다
다른 조직의 도움 없이 빠르게 웹서비스를 만드는 방법: Streamlit!
- Streamlit의 대안
- R의 Shiny
- Flask, Fast API: 백엔드 직접 구성 + 프론트엔드 작업도 진행
- Dash: 제일 기능이 풍부한 Python 대시보드 라이브러리
- Voila: Jupyter notebook 시각화 가능
Streamlit
장점
- 파이썬 스크립트 코드를 조금만 수정하면 웹을 띄울 수 있음
- 백엔드 개발이나 http 요청을 구현하지 않아도 됨
- 다양한 component 제공
- streamlit cloud도 존재해서 쉽게 배포 가능
- 화면 녹화 기능 존재
- albumentations 데모도 streamlit으로 만들어짐
Streamlit 실행
- 설치: pip install streamlit
- 실행: streamlit run streamlit-basic.py
button ,checkbox, df
import streamlit as st
import pandas as pd
import numpy as np
import time
st.title("Title")
st.header("Header")
st.subheader("subheader")
#버튼
if st.button("버튼 클릭하면"):
st.write("클릭하면 보이는 메시지")
#체크박스
checkbox_btn=st.checkbox("체크박스 버튼",value=True)
if checkbox_btn:
st.write("체크박스 버튼 클릭")
#st.dataframe: 컬럼 클릭, 정렬 가능
df=pd.DataFrame(df.style.highlight_max(axis=0)) #max값 색칠
st.markdown("======")
st.write(df)
st.dataframe(df)
st.table
#streamlit Metric, JSON
st.metric("my metric",42,2)
st.json(df.to_json())
Chart
# line chart
chart_data=pd.DataFrame(np.random.randn(20,3),columns=['a','b','c'])
st.line_chart(chart_data)
# map chart
map_data=pd.DataFrame(np.random.randn(1000,2)/[50,50]+[37.76,-122.4, columns=['lat','lon'])
st.map(map_data)
Radio button, select box 등
#radio button
selected_item=st.radio("radio part",("A","B","C"))
if selected_item=="A":
st.write("All")
elif ....~
#selectbox
option=st.selectbox('please select in selectbox',('a','b','c'))
# slider
values=st.slider('select range of values',0.0, 100.0, (25.0,70.0))
#input box
text_input=st.text_input("텍스트 입력해주세요")
#caption
st.caption("This is caption")
#code
st.code("a=123")
#latex
st.latex()
Streamlit Layout
#sidebar: method 앞에 sidebar 붙이면 sidebar가 보임
st.sidebar.button("hi")
# columns: 여러 칸으로 나눠서 component 추가하고 싶은 경우
col1,col2,col3,col4=st.columns(4)
col1.write(~)
col2.write(~~)
# streamlit spinner: 연산이 진행되는 도중 메시지를 보여주고 싶은 경우
with st.spinner("please wait.."):
time.sleep(5)
# file uploader
upload_file=st.file_uploader("choose a file",type=['png','jpg','jpeg'])
Session State
- streamlit의 데이터 flow로 인해 매번 코드가 재실행되며 중복 이벤트 불가
- global variable처럼 서로 공유할 수 있는 변수가 필요
- session_state_value에 변수 저장해서 활용하는 방식
if 'count' not in st.session_state:
st.session_state.count=0
increment=st.button('increment1')
if increment:
st.session_state.count+=1
decrement=st.button('decrement1')
if decrement:
st.session_state.count-=1
Streamlit Cache -@st.cache
- 데이터도 매번 다시 읽을 수 있음
- @st.cache 데코레이터를 사용해 캐싱(성능을 위해 메모리에 저장)하면 좋음
- 데이터를 읽는 함수를 만들고, 데코레이터 적용