Streamlit vs Shiny

expdpy ships two builds of the same no-code app, ExPdPy — one on Streamlit (expdpy.streamlit_app.ExPdPy) and one on Shiny for Python (expdpy.app.ExPdPy). Both sit on the same analytical core (the prepare_* functions) and the same framework-agnostic backend (sample pipeline, variable categorization, safe user-defined-variable evaluator, config I/O and notebook export), so they behave identically where it matters. This page reviews the feature set and the few deliberate differences.

Feature parity

Feature Streamlit ExPdPy Shiny ExPdPy
Descriptive / correlation / extreme-obs / regression tables ✅ native st.dataframe (Great Tables / etable available as a secondary view) ✅ Great Tables / etable
Histogram, bar, missing-values, scatter (color/size/LOESS) ✅ Plotly (identical figures) ✅ Plotly
Trends, quantile trends, by-group bar / violin / trend
Regression: fixed effects + clustered SEs (pyfixest)
Multi-sample switching, in-app upload (CSV/Excel/Parquet)
Subset-by-factor, outlier treatment (winsorize/truncate)
User-defined variables (safe expressions) ✅ launch-time and a live sidebar editor ✅ launch-time var_def
Config save/load (JSON) ✅ (byte-compatible — configs interchange)
Reproducible notebook + script + data export ✅ (identical zip)
Time-series components hidden for cross-sectional data
Layout sidebar + multipage navigation sidebar + stacked cards
One-click cloud deployment ✅ Streamlit Community Cloud (streamlit run streamlit_app.py)
Encrypted configs (store_encrypted) ➖ omitted

Deliberate differences

  • Tables. The Streamlit app renders tables natively with st.dataframe (sortable, theme-aware, good on mobile and the Cloud) directly from the DataFrame each prepare_* function returns, with the publication-quality Great Tables / pyfixest etable output one click away in an expander; the Shiny app shows that Great Tables / etable output directly.
  • Layout. The Streamlit app groups components into six pages with a navigation menu, which scales better as the analysis grows; the Shiny app stacks every component in one scrolling column.
  • Live user-defined variables. Both accept a launch-time var_def; the Streamlit app adds a sidebar editor so you can define variables interactively. The evaluator is the same restricted AST walker, so results — and saved configs — are identical.
  • Encryption. The Streamlit app writes plain JSON only; the Shiny app can additionally Fernet-encrypt saved configs (store_encrypted=True). Plain configs are interchangeable between the apps.

Which should I use?

  • Reach for the Streamlit app for a paginated layout, native interactive tables, or a shareable Streamlit Community Cloud deployment.
  • Reach for the Shiny app for a single-window, card-stack workflow, encrypted configs, or when you are already in the Shiny ecosystem.

Either way the analysis is reproducible: the Export notebook + data button turns whatever you built in the app into a runnable notebook and script of expdpy calls.