streamlit-nightly 1.43.2.dev20250307__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (563) hide show
  1. streamlit/__init__.py +306 -0
  2. streamlit/__main__.py +20 -0
  3. streamlit/auth_util.py +218 -0
  4. streamlit/cli_util.py +105 -0
  5. streamlit/column_config.py +56 -0
  6. streamlit/commands/__init__.py +13 -0
  7. streamlit/commands/echo.py +126 -0
  8. streamlit/commands/execution_control.py +238 -0
  9. streamlit/commands/experimental_query_params.py +169 -0
  10. streamlit/commands/logo.py +189 -0
  11. streamlit/commands/navigation.py +385 -0
  12. streamlit/commands/page_config.py +311 -0
  13. streamlit/components/__init__.py +13 -0
  14. streamlit/components/lib/__init__.py +13 -0
  15. streamlit/components/lib/local_component_registry.py +84 -0
  16. streamlit/components/types/__init__.py +13 -0
  17. streamlit/components/types/base_component_registry.py +99 -0
  18. streamlit/components/types/base_custom_component.py +150 -0
  19. streamlit/components/v1/__init__.py +31 -0
  20. streamlit/components/v1/component_arrow.py +141 -0
  21. streamlit/components/v1/component_registry.py +130 -0
  22. streamlit/components/v1/components.py +38 -0
  23. streamlit/components/v1/custom_component.py +243 -0
  24. streamlit/config.py +1513 -0
  25. streamlit/config_option.py +311 -0
  26. streamlit/config_util.py +177 -0
  27. streamlit/connections/__init__.py +28 -0
  28. streamlit/connections/base_connection.py +174 -0
  29. streamlit/connections/snowflake_connection.py +562 -0
  30. streamlit/connections/snowpark_connection.py +213 -0
  31. streamlit/connections/sql_connection.py +425 -0
  32. streamlit/connections/util.py +97 -0
  33. streamlit/cursor.py +210 -0
  34. streamlit/dataframe_util.py +1416 -0
  35. streamlit/delta_generator.py +602 -0
  36. streamlit/delta_generator_singletons.py +204 -0
  37. streamlit/deprecation_util.py +209 -0
  38. streamlit/development.py +21 -0
  39. streamlit/elements/__init__.py +13 -0
  40. streamlit/elements/alert.py +234 -0
  41. streamlit/elements/arrow.py +962 -0
  42. streamlit/elements/balloons.py +47 -0
  43. streamlit/elements/bokeh_chart.py +133 -0
  44. streamlit/elements/code.py +114 -0
  45. streamlit/elements/deck_gl_json_chart.py +546 -0
  46. streamlit/elements/dialog_decorator.py +267 -0
  47. streamlit/elements/doc_string.py +558 -0
  48. streamlit/elements/empty.py +130 -0
  49. streamlit/elements/exception.py +331 -0
  50. streamlit/elements/form.py +354 -0
  51. streamlit/elements/graphviz_chart.py +150 -0
  52. streamlit/elements/heading.py +302 -0
  53. streamlit/elements/html.py +105 -0
  54. streamlit/elements/iframe.py +191 -0
  55. streamlit/elements/image.py +196 -0
  56. streamlit/elements/json.py +139 -0
  57. streamlit/elements/layouts.py +879 -0
  58. streamlit/elements/lib/__init__.py +13 -0
  59. streamlit/elements/lib/built_in_chart_utils.py +1157 -0
  60. streamlit/elements/lib/color_util.py +263 -0
  61. streamlit/elements/lib/column_config_utils.py +542 -0
  62. streamlit/elements/lib/column_types.py +2188 -0
  63. streamlit/elements/lib/dialog.py +147 -0
  64. streamlit/elements/lib/dicttools.py +154 -0
  65. streamlit/elements/lib/event_utils.py +37 -0
  66. streamlit/elements/lib/file_uploader_utils.py +66 -0
  67. streamlit/elements/lib/form_utils.py +77 -0
  68. streamlit/elements/lib/image_utils.py +441 -0
  69. streamlit/elements/lib/js_number.py +105 -0
  70. streamlit/elements/lib/mutable_status_container.py +183 -0
  71. streamlit/elements/lib/options_selector_utils.py +250 -0
  72. streamlit/elements/lib/pandas_styler_utils.py +274 -0
  73. streamlit/elements/lib/policies.py +194 -0
  74. streamlit/elements/lib/streamlit_plotly_theme.py +207 -0
  75. streamlit/elements/lib/subtitle_utils.py +176 -0
  76. streamlit/elements/lib/utils.py +250 -0
  77. streamlit/elements/map.py +508 -0
  78. streamlit/elements/markdown.py +277 -0
  79. streamlit/elements/media.py +793 -0
  80. streamlit/elements/metric.py +301 -0
  81. streamlit/elements/plotly_chart.py +546 -0
  82. streamlit/elements/progress.py +156 -0
  83. streamlit/elements/pyplot.py +194 -0
  84. streamlit/elements/snow.py +47 -0
  85. streamlit/elements/spinner.py +113 -0
  86. streamlit/elements/text.py +76 -0
  87. streamlit/elements/toast.py +98 -0
  88. streamlit/elements/vega_charts.py +1984 -0
  89. streamlit/elements/widgets/__init__.py +13 -0
  90. streamlit/elements/widgets/audio_input.py +310 -0
  91. streamlit/elements/widgets/button.py +1123 -0
  92. streamlit/elements/widgets/button_group.py +1008 -0
  93. streamlit/elements/widgets/camera_input.py +263 -0
  94. streamlit/elements/widgets/chat.py +647 -0
  95. streamlit/elements/widgets/checkbox.py +352 -0
  96. streamlit/elements/widgets/color_picker.py +265 -0
  97. streamlit/elements/widgets/data_editor.py +983 -0
  98. streamlit/elements/widgets/file_uploader.py +486 -0
  99. streamlit/elements/widgets/multiselect.py +338 -0
  100. streamlit/elements/widgets/number_input.py +545 -0
  101. streamlit/elements/widgets/radio.py +407 -0
  102. streamlit/elements/widgets/select_slider.py +437 -0
  103. streamlit/elements/widgets/selectbox.py +366 -0
  104. streamlit/elements/widgets/slider.py +880 -0
  105. streamlit/elements/widgets/text_widgets.py +628 -0
  106. streamlit/elements/widgets/time_widgets.py +970 -0
  107. streamlit/elements/write.py +574 -0
  108. streamlit/emojis.py +34 -0
  109. streamlit/env_util.py +61 -0
  110. streamlit/error_util.py +105 -0
  111. streamlit/errors.py +452 -0
  112. streamlit/external/__init__.py +13 -0
  113. streamlit/external/langchain/__init__.py +23 -0
  114. streamlit/external/langchain/streamlit_callback_handler.py +406 -0
  115. streamlit/file_util.py +247 -0
  116. streamlit/git_util.py +173 -0
  117. streamlit/hello/__init__.py +13 -0
  118. streamlit/hello/animation_demo.py +82 -0
  119. streamlit/hello/dataframe_demo.py +71 -0
  120. streamlit/hello/hello.py +37 -0
  121. streamlit/hello/mapping_demo.py +114 -0
  122. streamlit/hello/plotting_demo.py +55 -0
  123. streamlit/hello/streamlit_app.py +55 -0
  124. streamlit/hello/utils.py +28 -0
  125. streamlit/logger.py +130 -0
  126. streamlit/material_icon_names.py +25 -0
  127. streamlit/navigation/__init__.py +13 -0
  128. streamlit/navigation/page.py +302 -0
  129. streamlit/net_util.py +125 -0
  130. streamlit/platform.py +33 -0
  131. streamlit/proto/Alert_pb2.py +29 -0
  132. streamlit/proto/Alert_pb2.pyi +90 -0
  133. streamlit/proto/AppPage_pb2.py +27 -0
  134. streamlit/proto/AppPage_pb2.pyi +64 -0
  135. streamlit/proto/ArrowNamedDataSet_pb2.py +28 -0
  136. streamlit/proto/ArrowNamedDataSet_pb2.pyi +57 -0
  137. streamlit/proto/ArrowVegaLiteChart_pb2.py +29 -0
  138. streamlit/proto/ArrowVegaLiteChart_pb2.pyi +84 -0
  139. streamlit/proto/Arrow_pb2.py +33 -0
  140. streamlit/proto/Arrow_pb2.pyi +188 -0
  141. streamlit/proto/AudioInput_pb2.py +28 -0
  142. streamlit/proto/AudioInput_pb2.pyi +58 -0
  143. streamlit/proto/Audio_pb2.py +27 -0
  144. streamlit/proto/Audio_pb2.pyi +58 -0
  145. streamlit/proto/AuthRedirect_pb2.py +27 -0
  146. streamlit/proto/AuthRedirect_pb2.pyi +41 -0
  147. streamlit/proto/AutoRerun_pb2.py +27 -0
  148. streamlit/proto/AutoRerun_pb2.pyi +45 -0
  149. streamlit/proto/BackMsg_pb2.py +29 -0
  150. streamlit/proto/BackMsg_pb2.pyi +105 -0
  151. streamlit/proto/Balloons_pb2.py +27 -0
  152. streamlit/proto/Balloons_pb2.pyi +43 -0
  153. streamlit/proto/Block_pb2.py +53 -0
  154. streamlit/proto/Block_pb2.pyi +322 -0
  155. streamlit/proto/BokehChart_pb2.py +27 -0
  156. streamlit/proto/BokehChart_pb2.pyi +49 -0
  157. streamlit/proto/ButtonGroup_pb2.py +36 -0
  158. streamlit/proto/ButtonGroup_pb2.pyi +169 -0
  159. streamlit/proto/Button_pb2.py +27 -0
  160. streamlit/proto/Button_pb2.pyi +71 -0
  161. streamlit/proto/CameraInput_pb2.py +28 -0
  162. streamlit/proto/CameraInput_pb2.pyi +58 -0
  163. streamlit/proto/ChatInput_pb2.py +31 -0
  164. streamlit/proto/ChatInput_pb2.pyi +111 -0
  165. streamlit/proto/Checkbox_pb2.py +30 -0
  166. streamlit/proto/Checkbox_pb2.pyi +90 -0
  167. streamlit/proto/ClientState_pb2.py +30 -0
  168. streamlit/proto/ClientState_pb2.pyi +90 -0
  169. streamlit/proto/Code_pb2.py +27 -0
  170. streamlit/proto/Code_pb2.pyi +55 -0
  171. streamlit/proto/ColorPicker_pb2.py +28 -0
  172. streamlit/proto/ColorPicker_pb2.pyi +67 -0
  173. streamlit/proto/Common_pb2.py +51 -0
  174. streamlit/proto/Common_pb2.pyi +293 -0
  175. streamlit/proto/Components_pb2.py +35 -0
  176. streamlit/proto/Components_pb2.pyi +172 -0
  177. streamlit/proto/DataFrame_pb2.py +56 -0
  178. streamlit/proto/DataFrame_pb2.pyi +397 -0
  179. streamlit/proto/DateInput_pb2.py +28 -0
  180. streamlit/proto/DateInput_pb2.pyi +83 -0
  181. streamlit/proto/DeckGlJsonChart_pb2.py +29 -0
  182. streamlit/proto/DeckGlJsonChart_pb2.pyi +102 -0
  183. streamlit/proto/Delta_pb2.py +31 -0
  184. streamlit/proto/Delta_pb2.pyi +74 -0
  185. streamlit/proto/DocString_pb2.py +29 -0
  186. streamlit/proto/DocString_pb2.pyi +93 -0
  187. streamlit/proto/DownloadButton_pb2.py +27 -0
  188. streamlit/proto/DownloadButton_pb2.pyi +70 -0
  189. streamlit/proto/Element_pb2.py +78 -0
  190. streamlit/proto/Element_pb2.pyi +312 -0
  191. streamlit/proto/Empty_pb2.py +27 -0
  192. streamlit/proto/Empty_pb2.pyi +36 -0
  193. streamlit/proto/Exception_pb2.py +27 -0
  194. streamlit/proto/Exception_pb2.pyi +72 -0
  195. streamlit/proto/Favicon_pb2.py +27 -0
  196. streamlit/proto/Favicon_pb2.pyi +40 -0
  197. streamlit/proto/FileUploader_pb2.py +28 -0
  198. streamlit/proto/FileUploader_pb2.pyi +78 -0
  199. streamlit/proto/ForwardMsg_pb2.py +53 -0
  200. streamlit/proto/ForwardMsg_pb2.pyi +293 -0
  201. streamlit/proto/GitInfo_pb2.py +29 -0
  202. streamlit/proto/GitInfo_pb2.pyi +83 -0
  203. streamlit/proto/GraphVizChart_pb2.py +27 -0
  204. streamlit/proto/GraphVizChart_pb2.pyi +53 -0
  205. streamlit/proto/Heading_pb2.py +27 -0
  206. streamlit/proto/Heading_pb2.pyi +56 -0
  207. streamlit/proto/Html_pb2.py +27 -0
  208. streamlit/proto/Html_pb2.pyi +42 -0
  209. streamlit/proto/IFrame_pb2.py +27 -0
  210. streamlit/proto/IFrame_pb2.pyi +59 -0
  211. streamlit/proto/Image_pb2.py +29 -0
  212. streamlit/proto/Image_pb2.pyi +84 -0
  213. streamlit/proto/Json_pb2.py +27 -0
  214. streamlit/proto/Json_pb2.pyi +53 -0
  215. streamlit/proto/LabelVisibilityMessage_pb2.py +29 -0
  216. streamlit/proto/LabelVisibilityMessage_pb2.pyi +68 -0
  217. streamlit/proto/LinkButton_pb2.py +27 -0
  218. streamlit/proto/LinkButton_pb2.pyi +58 -0
  219. streamlit/proto/Logo_pb2.py +27 -0
  220. streamlit/proto/Logo_pb2.pyi +51 -0
  221. streamlit/proto/Markdown_pb2.py +29 -0
  222. streamlit/proto/Markdown_pb2.pyi +86 -0
  223. streamlit/proto/Metric_pb2.py +32 -0
  224. streamlit/proto/Metric_pb2.pyi +101 -0
  225. streamlit/proto/MetricsEvent_pb2.py +30 -0
  226. streamlit/proto/MetricsEvent_pb2.pyi +200 -0
  227. streamlit/proto/MultiSelect_pb2.py +28 -0
  228. streamlit/proto/MultiSelect_pb2.pyi +81 -0
  229. streamlit/proto/NamedDataSet_pb2.py +28 -0
  230. streamlit/proto/NamedDataSet_pb2.pyi +59 -0
  231. streamlit/proto/Navigation_pb2.py +30 -0
  232. streamlit/proto/Navigation_pb2.pyi +84 -0
  233. streamlit/proto/NewSession_pb2.py +51 -0
  234. streamlit/proto/NewSession_pb2.pyi +481 -0
  235. streamlit/proto/NumberInput_pb2.py +30 -0
  236. streamlit/proto/NumberInput_pb2.pyi +121 -0
  237. streamlit/proto/PageConfig_pb2.py +33 -0
  238. streamlit/proto/PageConfig_pb2.pyi +126 -0
  239. streamlit/proto/PageInfo_pb2.py +27 -0
  240. streamlit/proto/PageInfo_pb2.pyi +43 -0
  241. streamlit/proto/PageLink_pb2.py +27 -0
  242. streamlit/proto/PageLink_pb2.pyi +63 -0
  243. streamlit/proto/PageNotFound_pb2.py +27 -0
  244. streamlit/proto/PageNotFound_pb2.pyi +42 -0
  245. streamlit/proto/PageProfile_pb2.py +31 -0
  246. streamlit/proto/PageProfile_pb2.pyi +127 -0
  247. streamlit/proto/PagesChanged_pb2.py +28 -0
  248. streamlit/proto/PagesChanged_pb2.pyi +48 -0
  249. streamlit/proto/ParentMessage_pb2.py +27 -0
  250. streamlit/proto/ParentMessage_pb2.pyi +46 -0
  251. streamlit/proto/PlotlyChart_pb2.py +31 -0
  252. streamlit/proto/PlotlyChart_pb2.pyi +131 -0
  253. streamlit/proto/Progress_pb2.py +27 -0
  254. streamlit/proto/Progress_pb2.pyi +43 -0
  255. streamlit/proto/Radio_pb2.py +28 -0
  256. streamlit/proto/Radio_pb2.pyi +84 -0
  257. streamlit/proto/RootContainer_pb2.py +27 -0
  258. streamlit/proto/RootContainer_pb2.pyi +56 -0
  259. streamlit/proto/Selectbox_pb2.py +28 -0
  260. streamlit/proto/Selectbox_pb2.pyi +80 -0
  261. streamlit/proto/SessionEvent_pb2.py +28 -0
  262. streamlit/proto/SessionEvent_pb2.pyi +62 -0
  263. streamlit/proto/SessionStatus_pb2.py +27 -0
  264. streamlit/proto/SessionStatus_pb2.pyi +57 -0
  265. streamlit/proto/Skeleton_pb2.py +29 -0
  266. streamlit/proto/Skeleton_pb2.pyi +71 -0
  267. streamlit/proto/Slider_pb2.py +32 -0
  268. streamlit/proto/Slider_pb2.pyi +142 -0
  269. streamlit/proto/Snow_pb2.py +27 -0
  270. streamlit/proto/Snow_pb2.pyi +43 -0
  271. streamlit/proto/Spinner_pb2.py +27 -0
  272. streamlit/proto/Spinner_pb2.pyi +49 -0
  273. streamlit/proto/TextArea_pb2.py +28 -0
  274. streamlit/proto/TextArea_pb2.pyi +80 -0
  275. streamlit/proto/TextInput_pb2.py +30 -0
  276. streamlit/proto/TextInput_pb2.pyi +107 -0
  277. streamlit/proto/Text_pb2.py +27 -0
  278. streamlit/proto/Text_pb2.pyi +46 -0
  279. streamlit/proto/TimeInput_pb2.py +28 -0
  280. streamlit/proto/TimeInput_pb2.pyi +74 -0
  281. streamlit/proto/Toast_pb2.py +27 -0
  282. streamlit/proto/Toast_pb2.pyi +45 -0
  283. streamlit/proto/VegaLiteChart_pb2.py +29 -0
  284. streamlit/proto/VegaLiteChart_pb2.pyi +71 -0
  285. streamlit/proto/Video_pb2.py +31 -0
  286. streamlit/proto/Video_pb2.pyi +117 -0
  287. streamlit/proto/WidgetStates_pb2.py +31 -0
  288. streamlit/proto/WidgetStates_pb2.pyi +126 -0
  289. streamlit/proto/__init__.py +15 -0
  290. streamlit/proto/openmetrics_data_model_pb2.py +60 -0
  291. streamlit/proto/openmetrics_data_model_pb2.pyi +522 -0
  292. streamlit/py.typed +0 -0
  293. streamlit/runtime/__init__.py +50 -0
  294. streamlit/runtime/app_session.py +982 -0
  295. streamlit/runtime/caching/__init__.py +98 -0
  296. streamlit/runtime/caching/cache_data_api.py +665 -0
  297. streamlit/runtime/caching/cache_errors.py +142 -0
  298. streamlit/runtime/caching/cache_resource_api.py +527 -0
  299. streamlit/runtime/caching/cache_type.py +33 -0
  300. streamlit/runtime/caching/cache_utils.py +523 -0
  301. streamlit/runtime/caching/cached_message_replay.py +290 -0
  302. streamlit/runtime/caching/hashing.py +637 -0
  303. streamlit/runtime/caching/legacy_cache_api.py +169 -0
  304. streamlit/runtime/caching/storage/__init__.py +29 -0
  305. streamlit/runtime/caching/storage/cache_storage_protocol.py +239 -0
  306. streamlit/runtime/caching/storage/dummy_cache_storage.py +60 -0
  307. streamlit/runtime/caching/storage/in_memory_cache_storage_wrapper.py +145 -0
  308. streamlit/runtime/caching/storage/local_disk_cache_storage.py +223 -0
  309. streamlit/runtime/connection_factory.py +436 -0
  310. streamlit/runtime/context.py +280 -0
  311. streamlit/runtime/credentials.py +364 -0
  312. streamlit/runtime/forward_msg_cache.py +296 -0
  313. streamlit/runtime/forward_msg_queue.py +240 -0
  314. streamlit/runtime/fragment.py +477 -0
  315. streamlit/runtime/media_file_manager.py +234 -0
  316. streamlit/runtime/media_file_storage.py +143 -0
  317. streamlit/runtime/memory_media_file_storage.py +181 -0
  318. streamlit/runtime/memory_session_storage.py +77 -0
  319. streamlit/runtime/memory_uploaded_file_manager.py +138 -0
  320. streamlit/runtime/metrics_util.py +486 -0
  321. streamlit/runtime/pages_manager.py +165 -0
  322. streamlit/runtime/runtime.py +792 -0
  323. streamlit/runtime/runtime_util.py +106 -0
  324. streamlit/runtime/script_data.py +46 -0
  325. streamlit/runtime/scriptrunner/__init__.py +38 -0
  326. streamlit/runtime/scriptrunner/exec_code.py +159 -0
  327. streamlit/runtime/scriptrunner/magic.py +273 -0
  328. streamlit/runtime/scriptrunner/magic_funcs.py +32 -0
  329. streamlit/runtime/scriptrunner/script_cache.py +89 -0
  330. streamlit/runtime/scriptrunner/script_runner.py +756 -0
  331. streamlit/runtime/scriptrunner_utils/__init__.py +19 -0
  332. streamlit/runtime/scriptrunner_utils/exceptions.py +48 -0
  333. streamlit/runtime/scriptrunner_utils/script_requests.py +307 -0
  334. streamlit/runtime/scriptrunner_utils/script_run_context.py +287 -0
  335. streamlit/runtime/secrets.py +534 -0
  336. streamlit/runtime/session_manager.py +394 -0
  337. streamlit/runtime/state/__init__.py +41 -0
  338. streamlit/runtime/state/common.py +191 -0
  339. streamlit/runtime/state/query_params.py +205 -0
  340. streamlit/runtime/state/query_params_proxy.py +218 -0
  341. streamlit/runtime/state/safe_session_state.py +138 -0
  342. streamlit/runtime/state/session_state.py +772 -0
  343. streamlit/runtime/state/session_state_proxy.py +153 -0
  344. streamlit/runtime/state/widgets.py +135 -0
  345. streamlit/runtime/stats.py +109 -0
  346. streamlit/runtime/uploaded_file_manager.py +148 -0
  347. streamlit/runtime/websocket_session_manager.py +167 -0
  348. streamlit/source_util.py +98 -0
  349. streamlit/static/favicon.png +0 -0
  350. streamlit/static/index.html +61 -0
  351. streamlit/static/static/css/index.Bmkmz40k.css +1 -0
  352. streamlit/static/static/css/index.DpJG_94W.css +1 -0
  353. streamlit/static/static/css/index.DzuxGC_t.css +1 -0
  354. streamlit/static/static/js/FileDownload.esm.Bp9m5jrx.js +1 -0
  355. streamlit/static/static/js/FileHelper.D_3pbilj.js +5 -0
  356. streamlit/static/static/js/FormClearHelper.Ct2rwLXo.js +1 -0
  357. streamlit/static/static/js/Hooks.BKdzj5MJ.js +1 -0
  358. streamlit/static/static/js/InputInstructions.DB3QGNJP.js +1 -0
  359. streamlit/static/static/js/ProgressBar.D40A5xc2.js +2 -0
  360. streamlit/static/static/js/RenderInPortalIfExists.DLUCooTN.js +1 -0
  361. streamlit/static/static/js/Toolbar.BiGGIQun.js +1 -0
  362. streamlit/static/static/js/UploadFileInfo.C-jY39rj.js +1 -0
  363. streamlit/static/static/js/base-input.CQBQT24M.js +4 -0
  364. streamlit/static/static/js/checkbox.Buj8gd_M.js +9 -0
  365. streamlit/static/static/js/createDownloadLinkElement.DZMwyjvU.js +1 -0
  366. streamlit/static/static/js/createSuper.CesK3I23.js +1 -0
  367. streamlit/static/static/js/data-grid-overlay-editor.B69OOFM4.js +1 -0
  368. streamlit/static/static/js/downloader.BZQhlBNT.js +1 -0
  369. streamlit/static/static/js/es6.D9Zhqujy.js +2 -0
  370. streamlit/static/static/js/iframeResizer.contentWindow.CAzcBpCC.js +1 -0
  371. streamlit/static/static/js/index.08vcOOvb.js +1 -0
  372. streamlit/static/static/js/index.0uqKfJUS.js +1 -0
  373. streamlit/static/static/js/index.B02M5u69.js +203 -0
  374. streamlit/static/static/js/index.B7mcZKMx.js +1 -0
  375. streamlit/static/static/js/index.BAQDHFA_.js +1 -0
  376. streamlit/static/static/js/index.BI60cMVr.js +2 -0
  377. streamlit/static/static/js/index.BLug2inK.js +1 -0
  378. streamlit/static/static/js/index.BM6TMY8g.js +2 -0
  379. streamlit/static/static/js/index.BZ9p1t7G.js +1 -0
  380. streamlit/static/static/js/index.BZqa87a1.js +2 -0
  381. streamlit/static/static/js/index.BcsRUzZZ.js +1 -0
  382. streamlit/static/static/js/index.BgVMiY_P.js +197 -0
  383. streamlit/static/static/js/index.BtuGy7By.js +6 -0
  384. streamlit/static/static/js/index.BuDuBmrs.js +1 -0
  385. streamlit/static/static/js/index.BvXU2oKV.js +1 -0
  386. streamlit/static/static/js/index.BxcwPacT.js +73 -0
  387. streamlit/static/static/js/index.CWX8KB81.js +1 -0
  388. streamlit/static/static/js/index.CXzZTo_q.js +1 -0
  389. streamlit/static/static/js/index.CcRWp_KL.js +1 -0
  390. streamlit/static/static/js/index.Cd-_xe55.js +3 -0
  391. streamlit/static/static/js/index.CdG2PXln.js +4537 -0
  392. streamlit/static/static/js/index.CjXvXmcP.js +1 -0
  393. streamlit/static/static/js/index.D1HZENZx.js +776 -0
  394. streamlit/static/static/js/index.D21Efo64.js +1617 -0
  395. streamlit/static/static/js/index.D9WgGVBx.js +7 -0
  396. streamlit/static/static/js/index.DEcsHtvb.js +12 -0
  397. streamlit/static/static/js/index.DFeMfr_K.js +1 -0
  398. streamlit/static/static/js/index.DHFBoItz.js +1 -0
  399. streamlit/static/static/js/index.D_PrBKnJ.js +3 -0
  400. streamlit/static/static/js/index.DmuRkekN.js +3855 -0
  401. streamlit/static/static/js/index.Do6eY8sf.js +1 -0
  402. streamlit/static/static/js/index.Dz3lP2P-.js +1 -0
  403. streamlit/static/static/js/index.Dz_UqF-s.js +1 -0
  404. streamlit/static/static/js/index.GkSUsPhJ.js +1 -0
  405. streamlit/static/static/js/index.H1U1IC_d.js +3 -0
  406. streamlit/static/static/js/index.g6p_4DPr.js +1 -0
  407. streamlit/static/static/js/index.g9x_GKss.js +1 -0
  408. streamlit/static/static/js/index.zo9jm08y.js +1 -0
  409. streamlit/static/static/js/input.DnaFglHq.js +2 -0
  410. streamlit/static/static/js/inputUtils.CQWz5UKz.js +1 -0
  411. streamlit/static/static/js/memory.Crb9x4-F.js +1 -0
  412. streamlit/static/static/js/mergeWith.ouAz0sK3.js +1 -0
  413. streamlit/static/static/js/number-overlay-editor._UaN-O48.js +9 -0
  414. streamlit/static/static/js/possibleConstructorReturn.CtGjGFHz.js +1 -0
  415. streamlit/static/static/js/sandbox.CBybYOhV.js +1 -0
  416. streamlit/static/static/js/sprintf.D7DtBTRn.js +1 -0
  417. streamlit/static/static/js/textarea.Cb_uJt5U.js +2 -0
  418. streamlit/static/static/js/threshold.DjX0wlsa.js +1 -0
  419. streamlit/static/static/js/timepicker.DKT7pfoF.js +4 -0
  420. streamlit/static/static/js/timer.CAwTRJ_g.js +1 -0
  421. streamlit/static/static/js/toConsumableArray.05Ikp13-.js +3 -0
  422. streamlit/static/static/js/uniqueId.D2FMWUEI.js +1 -0
  423. streamlit/static/static/js/useBasicWidgetState.urnZLANY.js +1 -0
  424. streamlit/static/static/js/useOnInputChange.BOKIIdJ1.js +1 -0
  425. streamlit/static/static/js/value.CgPGBV_l.js +1 -0
  426. streamlit/static/static/js/withFullScreenWrapper.C_N8J0Xx.js +1 -0
  427. streamlit/static/static/media/KaTeX_AMS-Regular.BQhdFMY1.woff2 +0 -0
  428. streamlit/static/static/media/KaTeX_AMS-Regular.DMm9YOAa.woff +0 -0
  429. streamlit/static/static/media/KaTeX_AMS-Regular.DRggAlZN.ttf +0 -0
  430. streamlit/static/static/media/KaTeX_Caligraphic-Bold.ATXxdsX0.ttf +0 -0
  431. streamlit/static/static/media/KaTeX_Caligraphic-Bold.BEiXGLvX.woff +0 -0
  432. streamlit/static/static/media/KaTeX_Caligraphic-Bold.Dq_IR9rO.woff2 +0 -0
  433. streamlit/static/static/media/KaTeX_Caligraphic-Regular.CTRA-rTL.woff +0 -0
  434. streamlit/static/static/media/KaTeX_Caligraphic-Regular.Di6jR-x-.woff2 +0 -0
  435. streamlit/static/static/media/KaTeX_Caligraphic-Regular.wX97UBjC.ttf +0 -0
  436. streamlit/static/static/media/KaTeX_Fraktur-Bold.BdnERNNW.ttf +0 -0
  437. streamlit/static/static/media/KaTeX_Fraktur-Bold.BsDP51OF.woff +0 -0
  438. streamlit/static/static/media/KaTeX_Fraktur-Bold.CL6g_b3V.woff2 +0 -0
  439. streamlit/static/static/media/KaTeX_Fraktur-Regular.CB_wures.ttf +0 -0
  440. streamlit/static/static/media/KaTeX_Fraktur-Regular.CTYiF6lA.woff2 +0 -0
  441. streamlit/static/static/media/KaTeX_Fraktur-Regular.Dxdc4cR9.woff +0 -0
  442. streamlit/static/static/media/KaTeX_Main-Bold.Cx986IdX.woff2 +0 -0
  443. streamlit/static/static/media/KaTeX_Main-Bold.Jm3AIy58.woff +0 -0
  444. streamlit/static/static/media/KaTeX_Main-Bold.waoOVXN0.ttf +0 -0
  445. streamlit/static/static/media/KaTeX_Main-BoldItalic.DxDJ3AOS.woff2 +0 -0
  446. streamlit/static/static/media/KaTeX_Main-BoldItalic.DzxPMmG6.ttf +0 -0
  447. streamlit/static/static/media/KaTeX_Main-BoldItalic.SpSLRI95.woff +0 -0
  448. streamlit/static/static/media/KaTeX_Main-Italic.3WenGoN9.ttf +0 -0
  449. streamlit/static/static/media/KaTeX_Main-Italic.BMLOBm91.woff +0 -0
  450. streamlit/static/static/media/KaTeX_Main-Italic.NWA7e6Wa.woff2 +0 -0
  451. streamlit/static/static/media/KaTeX_Main-Regular.B22Nviop.woff2 +0 -0
  452. streamlit/static/static/media/KaTeX_Main-Regular.Dr94JaBh.woff +0 -0
  453. streamlit/static/static/media/KaTeX_Main-Regular.ypZvNtVU.ttf +0 -0
  454. streamlit/static/static/media/KaTeX_Math-BoldItalic.B3XSjfu4.ttf +0 -0
  455. streamlit/static/static/media/KaTeX_Math-BoldItalic.CZnvNsCZ.woff2 +0 -0
  456. streamlit/static/static/media/KaTeX_Math-BoldItalic.iY-2wyZ7.woff +0 -0
  457. streamlit/static/static/media/KaTeX_Math-Italic.DA0__PXp.woff +0 -0
  458. streamlit/static/static/media/KaTeX_Math-Italic.flOr_0UB.ttf +0 -0
  459. streamlit/static/static/media/KaTeX_Math-Italic.t53AETM-.woff2 +0 -0
  460. streamlit/static/static/media/KaTeX_SansSerif-Bold.CFMepnvq.ttf +0 -0
  461. streamlit/static/static/media/KaTeX_SansSerif-Bold.D1sUS0GD.woff2 +0 -0
  462. streamlit/static/static/media/KaTeX_SansSerif-Bold.DbIhKOiC.woff +0 -0
  463. streamlit/static/static/media/KaTeX_SansSerif-Italic.C3H0VqGB.woff2 +0 -0
  464. streamlit/static/static/media/KaTeX_SansSerif-Italic.DN2j7dab.woff +0 -0
  465. streamlit/static/static/media/KaTeX_SansSerif-Italic.YYjJ1zSn.ttf +0 -0
  466. streamlit/static/static/media/KaTeX_SansSerif-Regular.BNo7hRIc.ttf +0 -0
  467. streamlit/static/static/media/KaTeX_SansSerif-Regular.CS6fqUqJ.woff +0 -0
  468. streamlit/static/static/media/KaTeX_SansSerif-Regular.DDBCnlJ7.woff2 +0 -0
  469. streamlit/static/static/media/KaTeX_Script-Regular.C5JkGWo-.ttf +0 -0
  470. streamlit/static/static/media/KaTeX_Script-Regular.D3wIWfF6.woff2 +0 -0
  471. streamlit/static/static/media/KaTeX_Script-Regular.D5yQViql.woff +0 -0
  472. streamlit/static/static/media/KaTeX_Size1-Regular.C195tn64.woff +0 -0
  473. streamlit/static/static/media/KaTeX_Size1-Regular.Dbsnue_I.ttf +0 -0
  474. streamlit/static/static/media/KaTeX_Size1-Regular.mCD8mA8B.woff2 +0 -0
  475. streamlit/static/static/media/KaTeX_Size2-Regular.B7gKUWhC.ttf +0 -0
  476. streamlit/static/static/media/KaTeX_Size2-Regular.Dy4dx90m.woff2 +0 -0
  477. streamlit/static/static/media/KaTeX_Size2-Regular.oD1tc_U0.woff +0 -0
  478. streamlit/static/static/media/KaTeX_Size3-Regular.CTq5MqoE.woff +0 -0
  479. streamlit/static/static/media/KaTeX_Size3-Regular.DgpXs0kz.ttf +0 -0
  480. streamlit/static/static/media/KaTeX_Size4-Regular.BF-4gkZK.woff +0 -0
  481. streamlit/static/static/media/KaTeX_Size4-Regular.DWFBv043.ttf +0 -0
  482. streamlit/static/static/media/KaTeX_Size4-Regular.Dl5lxZxV.woff2 +0 -0
  483. streamlit/static/static/media/KaTeX_Typewriter-Regular.C0xS9mPB.woff +0 -0
  484. streamlit/static/static/media/KaTeX_Typewriter-Regular.CO6r4hn1.woff2 +0 -0
  485. streamlit/static/static/media/KaTeX_Typewriter-Regular.D3Ib7_Hf.ttf +0 -0
  486. streamlit/static/static/media/MaterialSymbols-Rounded.DcZbplWk.woff2 +0 -0
  487. streamlit/static/static/media/SourceCodePro-Bold.CFEfr7-q.woff2 +0 -0
  488. streamlit/static/static/media/SourceCodePro-BoldItalic.C-LkFXxa.woff2 +0 -0
  489. streamlit/static/static/media/SourceCodePro-Italic.CxFOx7N-.woff2 +0 -0
  490. streamlit/static/static/media/SourceCodePro-Regular.CBOlD63d.woff2 +0 -0
  491. streamlit/static/static/media/SourceCodePro-SemiBold.CFHwW3Wd.woff2 +0 -0
  492. streamlit/static/static/media/SourceCodePro-SemiBoldItalic.Cg2yRu82.woff2 +0 -0
  493. streamlit/static/static/media/SourceSansPro-Bold.-6c9oR8J.woff2 +0 -0
  494. streamlit/static/static/media/SourceSansPro-BoldItalic.DmM_grLY.woff2 +0 -0
  495. streamlit/static/static/media/SourceSansPro-Italic.I1ipWe7Q.woff2 +0 -0
  496. streamlit/static/static/media/SourceSansPro-Regular.DZLUzqI4.woff2 +0 -0
  497. streamlit/static/static/media/SourceSansPro-SemiBold.sKQIyTMz.woff2 +0 -0
  498. streamlit/static/static/media/SourceSansPro-SemiBoldItalic.C0wP0icr.woff2 +0 -0
  499. streamlit/static/static/media/SourceSerifPro-Bold.8TUnKj4x.woff2 +0 -0
  500. streamlit/static/static/media/SourceSerifPro-BoldItalic.CBVO7Ve7.woff2 +0 -0
  501. streamlit/static/static/media/SourceSerifPro-Italic.DkFgL2HZ.woff2 +0 -0
  502. streamlit/static/static/media/SourceSerifPro-Regular.CNJNET2S.woff2 +0 -0
  503. streamlit/static/static/media/SourceSerifPro-SemiBold.CHyh9GC5.woff2 +0 -0
  504. streamlit/static/static/media/SourceSerifPro-SemiBoldItalic.CBtz8sWN.woff2 +0 -0
  505. streamlit/static/static/media/balloon-0.Czj7AKwE.png +0 -0
  506. streamlit/static/static/media/balloon-1.CNvFFrND.png +0 -0
  507. streamlit/static/static/media/balloon-2.DTvC6B1t.png +0 -0
  508. streamlit/static/static/media/balloon-3.CgSk4tbL.png +0 -0
  509. streamlit/static/static/media/balloon-4.mbtFrzxf.png +0 -0
  510. streamlit/static/static/media/balloon-5.CSwkUfRA.png +0 -0
  511. streamlit/static/static/media/fireworks.B4d-_KUe.gif +0 -0
  512. streamlit/static/static/media/flake-0.DgWaVvm5.png +0 -0
  513. streamlit/static/static/media/flake-1.B2r5AHMK.png +0 -0
  514. streamlit/static/static/media/flake-2.BnWSExPC.png +0 -0
  515. streamlit/static/static/media/snowflake.JU2jBHL8.svg +11 -0
  516. streamlit/string_util.py +203 -0
  517. streamlit/temporary_directory.py +56 -0
  518. streamlit/testing/__init__.py +13 -0
  519. streamlit/testing/v1/__init__.py +17 -0
  520. streamlit/testing/v1/app_test.py +1050 -0
  521. streamlit/testing/v1/element_tree.py +2083 -0
  522. streamlit/testing/v1/local_script_runner.py +180 -0
  523. streamlit/testing/v1/util.py +53 -0
  524. streamlit/time_util.py +75 -0
  525. streamlit/type_util.py +460 -0
  526. streamlit/url_util.py +122 -0
  527. streamlit/user_info.py +519 -0
  528. streamlit/util.py +72 -0
  529. streamlit/vendor/__init__.py +0 -0
  530. streamlit/vendor/pympler/__init__.py +0 -0
  531. streamlit/vendor/pympler/asizeof.py +2869 -0
  532. streamlit/version.py +18 -0
  533. streamlit/watcher/__init__.py +28 -0
  534. streamlit/watcher/event_based_path_watcher.py +406 -0
  535. streamlit/watcher/folder_black_list.py +82 -0
  536. streamlit/watcher/local_sources_watcher.py +233 -0
  537. streamlit/watcher/path_watcher.py +185 -0
  538. streamlit/watcher/polling_path_watcher.py +124 -0
  539. streamlit/watcher/util.py +207 -0
  540. streamlit/web/__init__.py +13 -0
  541. streamlit/web/bootstrap.py +353 -0
  542. streamlit/web/cache_storage_manager_config.py +38 -0
  543. streamlit/web/cli.py +369 -0
  544. streamlit/web/server/__init__.py +26 -0
  545. streamlit/web/server/app_static_file_handler.py +93 -0
  546. streamlit/web/server/authlib_tornado_integration.py +60 -0
  547. streamlit/web/server/browser_websocket_handler.py +246 -0
  548. streamlit/web/server/component_request_handler.py +116 -0
  549. streamlit/web/server/media_file_handler.py +141 -0
  550. streamlit/web/server/oauth_authlib_routes.py +176 -0
  551. streamlit/web/server/oidc_mixin.py +108 -0
  552. streamlit/web/server/routes.py +295 -0
  553. streamlit/web/server/server.py +479 -0
  554. streamlit/web/server/server_util.py +161 -0
  555. streamlit/web/server/stats_request_handler.py +95 -0
  556. streamlit/web/server/upload_file_request_handler.py +137 -0
  557. streamlit/web/server/websocket_headers.py +56 -0
  558. streamlit_nightly-1.43.2.dev20250307.data/scripts/streamlit.cmd +16 -0
  559. streamlit_nightly-1.43.2.dev20250307.dist-info/METADATA +207 -0
  560. streamlit_nightly-1.43.2.dev20250307.dist-info/RECORD +563 -0
  561. streamlit_nightly-1.43.2.dev20250307.dist-info/WHEEL +5 -0
  562. streamlit_nightly-1.43.2.dev20250307.dist-info/entry_points.txt +2 -0
  563. streamlit_nightly-1.43.2.dev20250307.dist-info/top_level.txt +1 -0
@@ -0,0 +1,1123 @@
1
+ # Copyright (c) Streamlit Inc. (2018-2022) Snowflake Inc. (2022-2025)
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+
15
+ from __future__ import annotations
16
+
17
+ import io
18
+ import os
19
+ from dataclasses import dataclass
20
+ from pathlib import Path
21
+ from textwrap import dedent
22
+ from typing import (
23
+ TYPE_CHECKING,
24
+ BinaryIO,
25
+ Final,
26
+ Literal,
27
+ TextIO,
28
+ Union,
29
+ cast,
30
+ )
31
+
32
+ from typing_extensions import TypeAlias
33
+
34
+ from streamlit import runtime
35
+ from streamlit.elements.lib.form_utils import current_form_id, is_in_form
36
+ from streamlit.elements.lib.policies import check_widget_policies
37
+ from streamlit.elements.lib.utils import (
38
+ Key,
39
+ compute_and_register_element_id,
40
+ save_for_app_testing,
41
+ to_key,
42
+ )
43
+ from streamlit.errors import (
44
+ StreamlitAPIException,
45
+ StreamlitMissingPageLabelError,
46
+ StreamlitPageNotFoundError,
47
+ )
48
+ from streamlit.file_util import get_main_script_directory, normalize_path_join
49
+ from streamlit.navigation.page import StreamlitPage
50
+ from streamlit.proto.Button_pb2 import Button as ButtonProto
51
+ from streamlit.proto.DownloadButton_pb2 import DownloadButton as DownloadButtonProto
52
+ from streamlit.proto.LinkButton_pb2 import LinkButton as LinkButtonProto
53
+ from streamlit.proto.PageLink_pb2 import PageLink as PageLinkProto
54
+ from streamlit.runtime.metrics_util import gather_metrics
55
+ from streamlit.runtime.pages_manager import PagesManager
56
+ from streamlit.runtime.scriptrunner import ScriptRunContext, get_script_run_ctx
57
+ from streamlit.runtime.state import (
58
+ WidgetArgs,
59
+ WidgetCallback,
60
+ WidgetKwargs,
61
+ register_widget,
62
+ )
63
+ from streamlit.string_util import validate_icon_or_emoji
64
+ from streamlit.url_util import is_url
65
+
66
+ if TYPE_CHECKING:
67
+ from streamlit.delta_generator import DeltaGenerator
68
+
69
+ FORM_DOCS_INFO: Final = """
70
+
71
+ For more information, refer to the
72
+ [documentation for forms](https://docs.streamlit.io/develop/api-reference/execution-flow/st.form).
73
+ """
74
+
75
+ DownloadButtonDataType: TypeAlias = Union[str, bytes, TextIO, BinaryIO, io.RawIOBase]
76
+
77
+
78
+ @dataclass
79
+ class ButtonSerde:
80
+ def serialize(self, v: bool) -> bool:
81
+ return bool(v)
82
+
83
+ def deserialize(self, ui_value: bool | None, widget_id: str = "") -> bool:
84
+ return ui_value or False
85
+
86
+
87
+ class ButtonMixin:
88
+ @gather_metrics("button")
89
+ def button(
90
+ self,
91
+ label: str,
92
+ key: Key | None = None,
93
+ help: str | None = None,
94
+ on_click: WidgetCallback | None = None,
95
+ args: WidgetArgs | None = None,
96
+ kwargs: WidgetKwargs | None = None,
97
+ *, # keyword-only arguments:
98
+ type: Literal["primary", "secondary", "tertiary"] = "secondary",
99
+ icon: str | None = None,
100
+ disabled: bool = False,
101
+ use_container_width: bool = False,
102
+ ) -> bool:
103
+ r"""Display a button widget.
104
+
105
+ Parameters
106
+ ----------
107
+ label : str
108
+ A short label explaining to the user what this button is for.
109
+ The label can optionally contain GitHub-flavored Markdown of the
110
+ following types: Bold, Italics, Strikethroughs, Inline Code, Links,
111
+ and Images. Images display like icons, with a max height equal to
112
+ the font height.
113
+
114
+ Unsupported Markdown elements are unwrapped so only their children
115
+ (text contents) render. Display unsupported elements as literal
116
+ characters by backslash-escaping them. E.g.,
117
+ ``"1\. Not an ordered list"``.
118
+
119
+ See the ``body`` parameter of |st.markdown|_ for additional,
120
+ supported Markdown directives.
121
+
122
+ .. |st.markdown| replace:: ``st.markdown``
123
+ .. _st.markdown: https://docs.streamlit.io/develop/api-reference/text/st.markdown
124
+
125
+ key : str or int
126
+ An optional string or integer to use as the unique key for the widget.
127
+ If this is omitted, a key will be generated for the widget
128
+ based on its content. No two widgets may have the same key.
129
+
130
+ help : str or None
131
+ A tooltip that gets displayed when the button is hovered over. If
132
+ this is ``None`` (default), no tooltip is displayed.
133
+
134
+ The tooltip can optionally contain GitHub-flavored Markdown,
135
+ including the Markdown directives described in the ``body``
136
+ parameter of ``st.markdown``.
137
+
138
+ on_click : callable
139
+ An optional callback invoked when this button is clicked.
140
+
141
+ args : tuple
142
+ An optional tuple of args to pass to the callback.
143
+
144
+ kwargs : dict
145
+ An optional dict of kwargs to pass to the callback.
146
+
147
+ type : "primary", "secondary", or "tertiary"
148
+ An optional string that specifies the button type. This can be one
149
+ of the following:
150
+
151
+ - ``"primary"``: The button's background is the app's primary color
152
+ for additional emphasis.
153
+ - ``"secondary"`` (default): The button's background coordinates
154
+ with the app's background color for normal emphasis.
155
+ - ``"tertiary"``: The button is plain text without a border or
156
+ background for subtly.
157
+
158
+ icon : str or None
159
+ An optional emoji or icon to display next to the button label. If ``icon``
160
+ is ``None`` (default), no icon is displayed. If ``icon`` is a
161
+ string, the following options are valid:
162
+
163
+ - A single-character emoji. For example, you can set ``icon="🚨"``
164
+ or ``icon="🔥"``. Emoji short codes are not supported.
165
+
166
+ - An icon from the Material Symbols library (rounded style) in the
167
+ format ``":material/icon_name:"`` where "icon_name" is the name
168
+ of the icon in snake case.
169
+
170
+ For example, ``icon=":material/thumb_up:"`` will display the
171
+ Thumb Up icon. Find additional icons in the `Material Symbols \
172
+ <https://fonts.google.com/icons?icon.set=Material+Symbols&icon.style=Rounded>`_
173
+ font library.
174
+
175
+ disabled : bool
176
+ An optional boolean that disables the button if set to ``True``.
177
+ The default is ``False``.
178
+
179
+ use_container_width : bool
180
+ Whether to expand the button's width to fill its parent container.
181
+ If ``use_container_width`` is ``False`` (default), Streamlit sizes
182
+ the button to fit its contents. If ``use_container_width`` is
183
+ ``True``, the width of the button matches its parent container.
184
+
185
+ In both cases, if the contents of the button are wider than the
186
+ parent container, the contents will line wrap.
187
+
188
+ Returns
189
+ -------
190
+ bool
191
+ True if the button was clicked on the last run of the app,
192
+ False otherwise.
193
+
194
+ Examples
195
+ --------
196
+
197
+ **Example 1: Customize your button type**
198
+
199
+ >>> import streamlit as st
200
+ >>>
201
+ >>> st.button("Reset", type="primary")
202
+ >>> if st.button("Say hello"):
203
+ ... st.write("Why hello there")
204
+ ... else:
205
+ ... st.write("Goodbye")
206
+ >>>
207
+ >>> if st.button("Aloha", type="tertiary"):
208
+ ... st.write("Ciao")
209
+
210
+ .. output::
211
+ https://doc-buton.streamlit.app/
212
+ height: 300px
213
+
214
+ **Example 2: Add icons to your button**
215
+
216
+ Although you can add icons to your buttons through Markdown, the
217
+ ``icon`` parameter is a convenient and consistent alternative.
218
+
219
+ >>> import streamlit as st
220
+ >>>
221
+ >>> left, middle, right = st.columns(3)
222
+ >>> if left.button("Plain button", use_container_width=True):
223
+ ... left.markdown("You clicked the plain button.")
224
+ >>> if middle.button("Emoji button", icon="😃", use_container_width=True):
225
+ ... middle.markdown("You clicked the emoji button.")
226
+ >>> if right.button("Material button", icon=":material/mood:", use_container_width=True):
227
+ ... right.markdown("You clicked the Material button.")
228
+
229
+ .. output::
230
+ https://doc-button-icons.streamlit.app/
231
+ height: 220px
232
+
233
+ """
234
+ key = to_key(key)
235
+ ctx = get_script_run_ctx()
236
+
237
+ # Checks whether the entered button type is one of the allowed options
238
+ if type not in ["primary", "secondary", "tertiary"]:
239
+ raise StreamlitAPIException(
240
+ 'The type argument to st.button must be "primary", "secondary", or "tertiary". '
241
+ f'\nThe argument passed was "{type}".'
242
+ )
243
+
244
+ return self.dg._button(
245
+ label,
246
+ key,
247
+ help,
248
+ is_form_submitter=False,
249
+ on_click=on_click,
250
+ args=args,
251
+ kwargs=kwargs,
252
+ disabled=disabled,
253
+ type=type,
254
+ icon=icon,
255
+ use_container_width=use_container_width,
256
+ ctx=ctx,
257
+ )
258
+
259
+ @gather_metrics("download_button")
260
+ def download_button(
261
+ self,
262
+ label: str,
263
+ data: DownloadButtonDataType,
264
+ file_name: str | None = None,
265
+ mime: str | None = None,
266
+ key: Key | None = None,
267
+ help: str | None = None,
268
+ on_click: WidgetCallback | Literal["rerun", "ignore"] | None = "rerun",
269
+ args: WidgetArgs | None = None,
270
+ kwargs: WidgetKwargs | None = None,
271
+ *, # keyword-only arguments:
272
+ type: Literal["primary", "secondary", "tertiary"] = "secondary",
273
+ icon: str | None = None,
274
+ disabled: bool = False,
275
+ use_container_width: bool = False,
276
+ ) -> bool:
277
+ r"""Display a download button widget.
278
+
279
+ This is useful when you would like to provide a way for your users
280
+ to download a file directly from your app.
281
+
282
+ Note that the data to be downloaded is stored in-memory while the
283
+ user is connected, so it's a good idea to keep file sizes under a
284
+ couple hundred megabytes to conserve memory.
285
+
286
+ If you want to prevent your app from rerunning when a user clicks the
287
+ download button, wrap the download button in a `fragment
288
+ <https://docs.streamlit.io/develop/concepts/architecture/fragments>`_.
289
+
290
+ Parameters
291
+ ----------
292
+ label : str
293
+ A short label explaining to the user what this button is for.
294
+ The label can optionally contain GitHub-flavored Markdown of the
295
+ following types: Bold, Italics, Strikethroughs, Inline Code, Links,
296
+ and Images. Images display like icons, with a max height equal to
297
+ the font height.
298
+
299
+ Unsupported Markdown elements are unwrapped so only their children
300
+ (text contents) render. Display unsupported elements as literal
301
+ characters by backslash-escaping them. E.g.,
302
+ ``"1\. Not an ordered list"``.
303
+
304
+ See the ``body`` parameter of |st.markdown|_ for additional,
305
+ supported Markdown directives.
306
+
307
+ .. |st.markdown| replace:: ``st.markdown``
308
+ .. _st.markdown: https://docs.streamlit.io/develop/api-reference/text/st.markdown
309
+
310
+ data : str, bytes, or file
311
+ The contents of the file to be downloaded.
312
+
313
+ To prevent unncecessary recomputation, use caching when converting
314
+ your data for download. For more information, see the Example 1
315
+ below.
316
+
317
+ file_name: str
318
+ An optional string to use as the name of the file to be downloaded,
319
+ such as ``"my_file.csv"``. If not specified, the name will be
320
+ automatically generated.
321
+
322
+ mime : str or None
323
+ The MIME type of the data. If this is ``None`` (default), Streamlit
324
+ sets the MIME type depending on the value of ``data`` as follows:
325
+
326
+ - If ``data`` is a string or textual file (i.e. ``str`` or
327
+ ``io.TextIOWrapper`` object), Streamlit uses the "text/plain"
328
+ MIME type.
329
+ - If ``data`` is a binary file or bytes (i.e. ``bytes``,
330
+ ``io.BytesIO``, ``io.BufferedReader``, or ``io.RawIOBase``
331
+ object), Streamlit uses the "application/octet-stream" MIME type.
332
+
333
+ For more information about MIME types, see
334
+ https://www.iana.org/assignments/media-types/media-types.xhtml.
335
+
336
+ key : str or int
337
+ An optional string or integer to use as the unique key for the widget.
338
+ If this is omitted, a key will be generated for the widget
339
+ based on its content. No two widgets may have the same key.
340
+
341
+ help : str or None
342
+ A tooltip that gets displayed when the button is hovered over. If
343
+ this is ``None`` (default), no tooltip is displayed.
344
+
345
+ The tooltip can optionally contain GitHub-flavored Markdown,
346
+ including the Markdown directives described in the ``body``
347
+ parameter of ``st.markdown``.
348
+
349
+ on_click : callable, "rerun", "ignore", or None
350
+ How the button should respond to user interaction. This controls
351
+ whether or not the button triggers a rerun and if a callback
352
+ function is called. This can be one of the following values:
353
+
354
+ - ``"rerun"`` (default): The user downloads the file and the app
355
+ reruns. No callback function is called.
356
+ - ``"ignore"``: The user downloads the file and the app doesn't
357
+ rerun. No callback function is called.
358
+ - A ``callable``: The user downloads the file and app reruns. The
359
+ callable is called before the rest of the app.
360
+ - ``None``: This is same as ``on_click="rerun"``. This value exists
361
+ for backwards compatibility and shouldn't be used.
362
+
363
+ args : tuple
364
+ An optional tuple of args to pass to the callback.
365
+
366
+ kwargs : dict
367
+ An optional dict of kwargs to pass to the callback.
368
+
369
+ type : "primary", "secondary", or "tertiary"
370
+ An optional string that specifies the button type. This can be one
371
+ of the following:
372
+
373
+ - ``"primary"``: The button's background is the app's primary color
374
+ for additional emphasis.
375
+ - ``"secondary"`` (default): The button's background coordinates
376
+ with the app's background color for normal emphasis.
377
+ - ``"tertiary"``: The button is plain text without a border or
378
+ background for subtly.
379
+
380
+ icon : str or None
381
+ An optional emoji or icon to display next to the button label. If ``icon``
382
+ is ``None`` (default), no icon is displayed. If ``icon`` is a
383
+ string, the following options are valid:
384
+
385
+ - A single-character emoji. For example, you can set ``icon="🚨"``
386
+ or ``icon="🔥"``. Emoji short codes are not supported.
387
+
388
+ - An icon from the Material Symbols library (rounded style) in the
389
+ format ``":material/icon_name:"`` where "icon_name" is the name
390
+ of the icon in snake case.
391
+
392
+ For example, ``icon=":material/thumb_up:"`` will display the
393
+ Thumb Up icon. Find additional icons in the `Material Symbols \
394
+ <https://fonts.google.com/icons?icon.set=Material+Symbols&icon.style=Rounded>`_
395
+ font library.
396
+
397
+ disabled : bool
398
+ An optional boolean that disables the download button if set to
399
+ ``True``. The default is ``False``.
400
+
401
+ use_container_width : bool
402
+ Whether to expand the button's width to fill its parent container.
403
+ If ``use_container_width`` is ``False`` (default), Streamlit sizes
404
+ the button to fit its contents. If ``use_container_width`` is
405
+ ``True``, the width of the button matches its parent container.
406
+
407
+ In both cases, if the contents of the button are wider than the
408
+ parent container, the contents will line wrap.
409
+
410
+ Returns
411
+ -------
412
+ bool
413
+ True if the button was clicked on the last run of the app,
414
+ False otherwise.
415
+
416
+ Examples
417
+ --------
418
+ **Example 1: Download a dataframe as a CSV file**
419
+
420
+ When working with a large dataframe, it's recommended to fetch your
421
+ data with a cached function. When working with a download button, it's
422
+ similarly recommended to convert your data into a downloadable format
423
+ with a cached function. Caching ensures that the app reruns
424
+ effeciently.
425
+
426
+ >>> import streamlit as st
427
+ >>> import pandas as pd
428
+ >>> import numpy as np
429
+ >>>
430
+ >>> @st.cache_data
431
+ >>> def get_data():
432
+ >>> df = pd.DataFrame(
433
+ ... np.random.randn(50, 20), columns=("col %d" % i for i in range(20))
434
+ ... )
435
+ >>> return df
436
+ >>>
437
+ >>> @st.cache_data
438
+ >>> def convert_for_download(df):
439
+ >>> return df.to_csv().encode("utf-8")
440
+ >>>
441
+ >>> df = get_data()
442
+ >>> csv = convert_for_download(df)
443
+ >>>
444
+ >>> st.download_button(
445
+ ... label="Download CSV",
446
+ ... data=csv,
447
+ ... file_name="data.csv",
448
+ ... mime="text/csv",
449
+ ... icon=":material/download:",
450
+ ... )
451
+
452
+ .. output::
453
+ https://doc-download-button-csv.streamlit.app/
454
+ height: 200px
455
+
456
+ **Example 2: Download a string as a text file**
457
+
458
+ If you pass a string to the ``data`` argument, Streamlit will
459
+ automatically use the "text/plain" MIME type.
460
+
461
+ When you have a widget (like a text area) affecting the value of your
462
+ download, it's recommended to use another button to prepare the
463
+ download. In this case, use ``on_click="ignore"`` in your download
464
+ button to prevent the download button from rerunning your app. This
465
+ turns the download button into a frontend-only element that can be
466
+ nested in another button.
467
+
468
+ Without a preparation button, a user can type something into the text
469
+ area and immediately click the download button. Because a download is
470
+ initiated concurrently with the app rerun, this can create a race-like
471
+ condition where the user doesn't see the updated data in their
472
+ download.
473
+
474
+ .. important::
475
+ Even when you prevent your download button from triggering a rerun,
476
+ another widget with a pending change can still trigger a rerun. For
477
+ example, if a text area has a pending change when a user clicks a
478
+ download button, the text area will trigger a rerun.
479
+
480
+ >>> import streamlit as st
481
+ >>>
482
+ >>> message = st.text_area("Message", value="Lorem ipsum.\nStreamlit is cool.")
483
+ >>>
484
+ >>> if st.button("Prepare download"):
485
+ >>> st.download_button(
486
+ ... label="Download text",
487
+ ... data=message,
488
+ ... file_name="message.txt",
489
+ ... on_click="ignore",
490
+ ... type="primary",
491
+ ... icon=":material/download:",
492
+ ... )
493
+
494
+ .. output::
495
+ https://doc-download-button-text.streamlit.app/
496
+ height: 250px
497
+
498
+ **Example 3: Download a file**
499
+
500
+ Use a context manager to open and read a local file on your Streamlit
501
+ server. Pass the ``io.BufferedReader`` object directly to ``data``.
502
+ Remember to specify the MIME type if you don't want the default
503
+ type of ``"application/octet-stream"`` for generic binary data. In the
504
+ example below, the MIME type is set to ``"image/png"`` for a PNG file.
505
+
506
+ >>> import streamlit as st
507
+ >>>
508
+ >>> with open("flower.png", "rb") as file:
509
+ ... st.download_button(
510
+ ... label="Download image",
511
+ ... data=file,
512
+ ... file_name="flower.png",
513
+ ... mime="image/png",
514
+ ... )
515
+
516
+ .. output::
517
+ https://doc-download-button-file.streamlit.app/
518
+ height: 200px
519
+
520
+ """
521
+ ctx = get_script_run_ctx()
522
+
523
+ if type not in ["primary", "secondary", "tertiary"]:
524
+ raise StreamlitAPIException(
525
+ 'The type argument to st.download_button must be "primary", "secondary", or "tertiary". \n'
526
+ f'The argument passed was "{type}".'
527
+ )
528
+
529
+ return self._download_button(
530
+ label=label,
531
+ data=data,
532
+ file_name=file_name,
533
+ mime=mime,
534
+ key=key,
535
+ help=help,
536
+ on_click=on_click,
537
+ args=args,
538
+ kwargs=kwargs,
539
+ type=type,
540
+ icon=icon,
541
+ disabled=disabled,
542
+ use_container_width=use_container_width,
543
+ ctx=ctx,
544
+ )
545
+
546
+ @gather_metrics("link_button")
547
+ def link_button(
548
+ self,
549
+ label: str,
550
+ url: str,
551
+ *,
552
+ help: str | None = None,
553
+ type: Literal["primary", "secondary", "tertiary"] = "secondary",
554
+ icon: str | None = None,
555
+ disabled: bool = False,
556
+ use_container_width: bool = False,
557
+ ) -> DeltaGenerator:
558
+ r"""Display a link button element.
559
+
560
+ When clicked, a new tab will be opened to the specified URL. This will
561
+ create a new session for the user if directed within the app.
562
+
563
+ Parameters
564
+ ----------
565
+ label : str
566
+ A short label explaining to the user what this button is for.
567
+ The label can optionally contain GitHub-flavored Markdown of the
568
+ following types: Bold, Italics, Strikethroughs, Inline Code, Links,
569
+ and Images. Images display like icons, with a max height equal to
570
+ the font height.
571
+
572
+ Unsupported Markdown elements are unwrapped so only their children
573
+ (text contents) render. Display unsupported elements as literal
574
+ characters by backslash-escaping them. E.g.,
575
+ ``"1\. Not an ordered list"``.
576
+
577
+ See the ``body`` parameter of |st.markdown|_ for additional,
578
+ supported Markdown directives.
579
+
580
+ .. |st.markdown| replace:: ``st.markdown``
581
+ .. _st.markdown: https://docs.streamlit.io/develop/api-reference/text/st.markdown
582
+
583
+ url : str
584
+ The url to be opened on user click
585
+
586
+ help : str or None
587
+ A tooltip that gets displayed when the button is hovered over. If
588
+ this is ``None`` (default), no tooltip is displayed.
589
+
590
+ The tooltip can optionally contain GitHub-flavored Markdown,
591
+ including the Markdown directives described in the ``body``
592
+ parameter of ``st.markdown``.
593
+
594
+ type : "primary", "secondary", or "tertiary"
595
+ An optional string that specifies the button type. This can be one
596
+ of the following:
597
+
598
+ - ``"primary"``: The button's background is the app's primary color
599
+ for additional emphasis.
600
+ - ``"secondary"`` (default): The button's background coordinates
601
+ with the app's background color for normal emphasis.
602
+ - ``"tertiary"``: The button is plain text without a border or
603
+ background for subtly.
604
+
605
+ icon : str or None
606
+ An optional emoji or icon to display next to the button label. If ``icon``
607
+ is ``None`` (default), no icon is displayed. If ``icon`` is a
608
+ string, the following options are valid:
609
+
610
+ - A single-character emoji. For example, you can set ``icon="🚨"``
611
+ or ``icon="🔥"``. Emoji short codes are not supported.
612
+
613
+ - An icon from the Material Symbols library (rounded style) in the
614
+ format ``":material/icon_name:"`` where "icon_name" is the name
615
+ of the icon in snake case.
616
+
617
+ For example, ``icon=":material/thumb_up:"`` will display the
618
+ Thumb Up icon. Find additional icons in the `Material Symbols \
619
+ <https://fonts.google.com/icons?icon.set=Material+Symbols&icon.style=Rounded>`_
620
+ font library.
621
+
622
+ disabled : bool
623
+ An optional boolean that disables the link button if set to
624
+ ``True``. The default is ``False``.
625
+
626
+ use_container_width : bool
627
+ Whether to expand the button's width to fill its parent container.
628
+ If ``use_container_width`` is ``False`` (default), Streamlit sizes
629
+ the button to fit its contents. If ``use_container_width`` is
630
+ ``True``, the width of the button matches its parent container.
631
+
632
+ In both cases, if the contents of the button are wider than the
633
+ parent container, the contents will line wrap.
634
+
635
+ Example
636
+ -------
637
+ >>> import streamlit as st
638
+ >>>
639
+ >>> st.link_button("Go to gallery", "https://streamlit.io/gallery")
640
+
641
+ .. output::
642
+ https://doc-link-button.streamlit.app/
643
+ height: 200px
644
+
645
+ """
646
+ # Checks whether the entered button type is one of the allowed options - either "primary" or "secondary"
647
+ if type not in ["primary", "secondary", "tertiary"]:
648
+ raise StreamlitAPIException(
649
+ 'The type argument to st.link_button must be "primary", "secondary", or "tertiary". '
650
+ f'\nThe argument passed was "{type}".'
651
+ )
652
+
653
+ return self._link_button(
654
+ label=label,
655
+ url=url,
656
+ help=help,
657
+ disabled=disabled,
658
+ type=type,
659
+ icon=icon,
660
+ use_container_width=use_container_width,
661
+ )
662
+
663
+ @gather_metrics("page_link")
664
+ def page_link(
665
+ self,
666
+ page: str | Path | StreamlitPage,
667
+ *,
668
+ label: str | None = None,
669
+ icon: str | None = None,
670
+ help: str | None = None,
671
+ disabled: bool = False,
672
+ use_container_width: bool | None = None,
673
+ ) -> DeltaGenerator:
674
+ r"""Display a link to another page in a multipage app or to an external page.
675
+
676
+ If another page in a multipage app is specified, clicking ``st.page_link``
677
+ stops the current page execution and runs the specified page as if the
678
+ user clicked on it in the sidebar navigation.
679
+
680
+ If an external page is specified, clicking ``st.page_link`` opens a new
681
+ tab to the specified page. The current script run will continue if not
682
+ complete.
683
+
684
+ Parameters
685
+ ----------
686
+ page : str, Path, or st.Page
687
+ The file path (relative to the main script) or an st.Page indicating
688
+ the page to switch to. Alternatively, this can be the URL to an
689
+ external page (must start with "http://" or "https://").
690
+
691
+ label : str
692
+ The label for the page link. Labels are required for external pages.
693
+ The label can optionally contain GitHub-flavored Markdown of the
694
+ following types: Bold, Italics, Strikethroughs, Inline Code, Links,
695
+ and Images. Images display like icons, with a max height equal to
696
+ the font height.
697
+
698
+ Unsupported Markdown elements are unwrapped so only their children
699
+ (text contents) render. Display unsupported elements as literal
700
+ characters by backslash-escaping them. E.g.,
701
+ ``"1\. Not an ordered list"``.
702
+
703
+ See the ``body`` parameter of |st.markdown|_ for additional,
704
+ supported Markdown directives.
705
+
706
+ .. |st.markdown| replace:: ``st.markdown``
707
+ .. _st.markdown: https://docs.streamlit.io/develop/api-reference/text/st.markdown
708
+
709
+ icon : str or None
710
+ An optional emoji or icon to display next to the button label. If ``icon``
711
+ is ``None`` (default), no icon is displayed. If ``icon`` is a
712
+ string, the following options are valid:
713
+
714
+ - A single-character emoji. For example, you can set ``icon="🚨"``
715
+ or ``icon="🔥"``. Emoji short codes are not supported.
716
+
717
+ - An icon from the Material Symbols library (rounded style) in the
718
+ format ``":material/icon_name:"`` where "icon_name" is the name
719
+ of the icon in snake case.
720
+
721
+ For example, ``icon=":material/thumb_up:"`` will display the
722
+ Thumb Up icon. Find additional icons in the `Material Symbols \
723
+ <https://fonts.google.com/icons?icon.set=Material+Symbols&icon.style=Rounded>`_
724
+ font library.
725
+
726
+ help : str or None
727
+ A tooltip that gets displayed when the link is hovered over. If
728
+ this is ``None`` (default), no tooltip is displayed.
729
+
730
+ The tooltip can optionally contain GitHub-flavored Markdown,
731
+ including the Markdown directives described in the ``body``
732
+ parameter of ``st.markdown``.
733
+
734
+ disabled : bool
735
+ An optional boolean that disables the page link if set to ``True``.
736
+ The default is ``False``.
737
+
738
+ use_container_width : bool
739
+ Whether to expand the link's width to fill its parent container.
740
+ The default is ``True`` for page links in the sidebar and ``False``
741
+ for those in the main app.
742
+
743
+ Example
744
+ -------
745
+ Consider the following example given this file structure:
746
+
747
+ >>> your-repository/
748
+ >>> ├── pages/
749
+ >>> │ ├── page_1.py
750
+ >>> │ └── page_2.py
751
+ >>> └── your_app.py
752
+
753
+ >>> import streamlit as st
754
+ >>>
755
+ >>> st.page_link("your_app.py", label="Home", icon="🏠")
756
+ >>> st.page_link("pages/page_1.py", label="Page 1", icon="1️⃣")
757
+ >>> st.page_link("pages/page_2.py", label="Page 2", icon="2️⃣", disabled=True)
758
+ >>> st.page_link("http://www.google.com", label="Google", icon="🌎")
759
+
760
+ The default navigation is shown here for comparison, but you can hide
761
+ the default navigation using the |client.showSidebarNavigation|_
762
+ configuration option. This allows you to create custom, dynamic
763
+ navigation menus for your apps!
764
+
765
+ .. |client.showSidebarNavigation| replace:: ``client.showSidebarNavigation``
766
+ .. _client.showSidebarNavigation: https://docs.streamlit.io/develop/api-reference/configuration/config.toml#client
767
+
768
+ .. output ::
769
+ https://doc-page-link.streamlit.app/
770
+ height: 350px
771
+
772
+ """
773
+
774
+ return self._page_link(
775
+ page=page,
776
+ label=label,
777
+ icon=icon,
778
+ help=help,
779
+ disabled=disabled,
780
+ use_container_width=use_container_width,
781
+ )
782
+
783
+ def _download_button(
784
+ self,
785
+ label: str,
786
+ data: DownloadButtonDataType,
787
+ file_name: str | None = None,
788
+ mime: str | None = None,
789
+ key: Key | None = None,
790
+ help: str | None = None,
791
+ on_click: WidgetCallback | Literal["rerun", "ignore"] | None = "rerun",
792
+ args: WidgetArgs | None = None,
793
+ kwargs: WidgetKwargs | None = None,
794
+ *, # keyword-only arguments:
795
+ type: Literal["primary", "secondary", "tertiary"] = "secondary",
796
+ icon: str | None = None,
797
+ disabled: bool = False,
798
+ use_container_width: bool = False,
799
+ ctx: ScriptRunContext | None = None,
800
+ ) -> bool:
801
+ key = to_key(key)
802
+
803
+ if on_click == "ignore" or on_click == "rerun":
804
+ on_click_callback = None
805
+ else:
806
+ on_click_callback = on_click
807
+
808
+ check_widget_policies(
809
+ self.dg,
810
+ key,
811
+ on_click_callback,
812
+ default_value=None,
813
+ writes_allowed=False,
814
+ )
815
+
816
+ element_id = compute_and_register_element_id(
817
+ "download_button",
818
+ user_key=key,
819
+ # download_button is not allowed to be used in a form.
820
+ form_id=None,
821
+ label=label,
822
+ icon=icon,
823
+ file_name=file_name,
824
+ mime=mime,
825
+ help=help,
826
+ type=type,
827
+ use_container_width=use_container_width,
828
+ )
829
+
830
+ if is_in_form(self.dg):
831
+ raise StreamlitAPIException(
832
+ f"`st.download_button()` can't be used in an `st.form()`.{FORM_DOCS_INFO}"
833
+ )
834
+
835
+ download_button_proto = DownloadButtonProto()
836
+ download_button_proto.id = element_id
837
+ download_button_proto.use_container_width = use_container_width
838
+ download_button_proto.label = label
839
+ download_button_proto.default = False
840
+ download_button_proto.type = type
841
+ marshall_file(
842
+ self.dg._get_delta_path_str(), data, download_button_proto, mime, file_name
843
+ )
844
+ download_button_proto.disabled = disabled
845
+
846
+ if help is not None:
847
+ download_button_proto.help = dedent(help)
848
+
849
+ if icon is not None:
850
+ download_button_proto.icon = validate_icon_or_emoji(icon)
851
+
852
+ if on_click == "ignore":
853
+ download_button_proto.ignore_rerun = True
854
+ else:
855
+ download_button_proto.ignore_rerun = False
856
+
857
+ serde = ButtonSerde()
858
+
859
+ button_state = register_widget(
860
+ download_button_proto.id,
861
+ on_change_handler=on_click_callback,
862
+ args=args,
863
+ kwargs=kwargs,
864
+ deserializer=serde.deserialize,
865
+ serializer=serde.serialize,
866
+ ctx=ctx,
867
+ value_type="trigger_value",
868
+ )
869
+
870
+ self.dg._enqueue("download_button", download_button_proto)
871
+ return button_state.value
872
+
873
+ def _link_button(
874
+ self,
875
+ label: str,
876
+ url: str,
877
+ help: str | None,
878
+ *, # keyword-only arguments:
879
+ type: Literal["primary", "secondary", "tertiary"] = "secondary",
880
+ icon: str | None = None,
881
+ disabled: bool = False,
882
+ use_container_width: bool = False,
883
+ ) -> DeltaGenerator:
884
+ link_button_proto = LinkButtonProto()
885
+ link_button_proto.label = label
886
+ link_button_proto.url = url
887
+ link_button_proto.type = type
888
+ link_button_proto.use_container_width = use_container_width
889
+ link_button_proto.disabled = disabled
890
+
891
+ if help is not None:
892
+ link_button_proto.help = dedent(help)
893
+
894
+ if icon is not None:
895
+ link_button_proto.icon = validate_icon_or_emoji(icon)
896
+
897
+ return self.dg._enqueue("link_button", link_button_proto)
898
+
899
+ def _page_link(
900
+ self,
901
+ page: str | Path | StreamlitPage,
902
+ *, # keyword-only arguments:
903
+ label: str | None = None,
904
+ icon: str | None = None,
905
+ help: str | None = None,
906
+ disabled: bool = False,
907
+ use_container_width: bool | None = None,
908
+ ) -> DeltaGenerator:
909
+ page_link_proto = PageLinkProto()
910
+
911
+ ctx = get_script_run_ctx()
912
+ if not ctx:
913
+ return self.dg._enqueue("page_link", page_link_proto)
914
+
915
+ page_link_proto.disabled = disabled
916
+
917
+ if label is not None:
918
+ page_link_proto.label = label
919
+
920
+ if icon is not None:
921
+ page_link_proto.icon = validate_icon_or_emoji(icon)
922
+
923
+ if help is not None:
924
+ page_link_proto.help = dedent(help)
925
+
926
+ if use_container_width is not None:
927
+ page_link_proto.use_container_width = use_container_width
928
+
929
+ if isinstance(page, StreamlitPage):
930
+ page_link_proto.page_script_hash = page._script_hash
931
+ page_link_proto.page = page.url_path
932
+ if label is None:
933
+ page_link_proto.label = page.title
934
+ else:
935
+ # Convert Path to string if necessary
936
+ if isinstance(page, Path):
937
+ page = str(page)
938
+
939
+ # Handle external links:
940
+ if is_url(page):
941
+ if label is None or label == "":
942
+ raise StreamlitMissingPageLabelError()
943
+ else:
944
+ page_link_proto.page = page
945
+ page_link_proto.external = True
946
+ return self.dg._enqueue("page_link", page_link_proto)
947
+
948
+ ctx_main_script = ""
949
+ all_app_pages = {}
950
+ ctx_main_script = ctx.main_script_path
951
+ all_app_pages = ctx.pages_manager.get_pages()
952
+
953
+ main_script_directory = get_main_script_directory(ctx_main_script)
954
+ requested_page = os.path.realpath(
955
+ normalize_path_join(main_script_directory, page)
956
+ )
957
+
958
+ # Handle retrieving the page_script_hash & page
959
+ for page_data in all_app_pages.values():
960
+ full_path = page_data["script_path"]
961
+ page_name = page_data["page_name"]
962
+ url_pathname = page_data["url_pathname"]
963
+ if requested_page == full_path:
964
+ if label is None:
965
+ page_link_proto.label = page_name
966
+ page_link_proto.page_script_hash = page_data["page_script_hash"]
967
+ page_link_proto.page = url_pathname
968
+ break
969
+
970
+ if page_link_proto.page_script_hash == "":
971
+ raise StreamlitPageNotFoundError(
972
+ page=page,
973
+ main_script_directory=main_script_directory,
974
+ uses_pages_directory=bool(PagesManager.uses_pages_directory),
975
+ )
976
+
977
+ return self.dg._enqueue("page_link", page_link_proto)
978
+
979
+ def _button(
980
+ self,
981
+ label: str,
982
+ key: str | None,
983
+ help: str | None,
984
+ is_form_submitter: bool,
985
+ on_click: WidgetCallback | None = None,
986
+ args: WidgetArgs | None = None,
987
+ kwargs: WidgetKwargs | None = None,
988
+ *, # keyword-only arguments:
989
+ type: Literal["primary", "secondary", "tertiary"] = "secondary",
990
+ icon: str | None = None,
991
+ disabled: bool = False,
992
+ use_container_width: bool = False,
993
+ ctx: ScriptRunContext | None = None,
994
+ ) -> bool:
995
+ key = to_key(key)
996
+
997
+ check_widget_policies(
998
+ self.dg,
999
+ key,
1000
+ on_click,
1001
+ default_value=None,
1002
+ writes_allowed=False,
1003
+ enable_check_callback_rules=not is_form_submitter,
1004
+ )
1005
+
1006
+ # Only the form submitter button needs a form ID at the moment.
1007
+ form_id = current_form_id(self.dg) if is_form_submitter else ""
1008
+ element_id = compute_and_register_element_id(
1009
+ "button",
1010
+ user_key=key,
1011
+ # Only the
1012
+ form_id=form_id,
1013
+ label=label,
1014
+ icon=icon,
1015
+ help=help,
1016
+ is_form_submitter=is_form_submitter,
1017
+ type=type,
1018
+ use_container_width=use_container_width,
1019
+ )
1020
+
1021
+ # It doesn't make sense to create a button inside a form (except
1022
+ # for the "Form Submitter" button that's automatically created in
1023
+ # every form). We throw an error to warn the user about this.
1024
+ # We omit this check for scripts running outside streamlit, because
1025
+ # they will have no script_run_ctx.
1026
+ if runtime.exists():
1027
+ if is_in_form(self.dg) and not is_form_submitter:
1028
+ raise StreamlitAPIException(
1029
+ f"`st.button()` can't be used in an `st.form()`.{FORM_DOCS_INFO}"
1030
+ )
1031
+ elif not is_in_form(self.dg) and is_form_submitter:
1032
+ raise StreamlitAPIException(
1033
+ f"`st.form_submit_button()` must be used inside an `st.form()`.{FORM_DOCS_INFO}"
1034
+ )
1035
+
1036
+ button_proto = ButtonProto()
1037
+ button_proto.id = element_id
1038
+ button_proto.label = label
1039
+ button_proto.default = False
1040
+ button_proto.is_form_submitter = is_form_submitter
1041
+ button_proto.form_id = form_id
1042
+ button_proto.type = type
1043
+ button_proto.use_container_width = use_container_width
1044
+ button_proto.disabled = disabled
1045
+
1046
+ if help is not None:
1047
+ button_proto.help = dedent(help)
1048
+
1049
+ if icon is not None:
1050
+ button_proto.icon = validate_icon_or_emoji(icon)
1051
+
1052
+ serde = ButtonSerde()
1053
+
1054
+ button_state = register_widget(
1055
+ button_proto.id,
1056
+ on_change_handler=on_click,
1057
+ args=args,
1058
+ kwargs=kwargs,
1059
+ deserializer=serde.deserialize,
1060
+ serializer=serde.serialize,
1061
+ ctx=ctx,
1062
+ value_type="trigger_value",
1063
+ )
1064
+
1065
+ if ctx:
1066
+ save_for_app_testing(ctx, element_id, button_state.value)
1067
+ self.dg._enqueue("button", button_proto)
1068
+
1069
+ return button_state.value
1070
+
1071
+ @property
1072
+ def dg(self) -> DeltaGenerator:
1073
+ """Get our DeltaGenerator."""
1074
+ return cast("DeltaGenerator", self)
1075
+
1076
+
1077
+ def marshall_file(
1078
+ coordinates: str,
1079
+ data: DownloadButtonDataType,
1080
+ proto_download_button: DownloadButtonProto,
1081
+ mimetype: str | None,
1082
+ file_name: str | None = None,
1083
+ ) -> None:
1084
+ data_as_bytes: bytes
1085
+ if isinstance(data, str):
1086
+ data_as_bytes = data.encode()
1087
+ mimetype = mimetype or "text/plain"
1088
+ elif isinstance(data, io.TextIOWrapper):
1089
+ string_data = data.read()
1090
+ data_as_bytes = string_data.encode()
1091
+ mimetype = mimetype or "text/plain"
1092
+ # Assume bytes; try methods until we run out.
1093
+ elif isinstance(data, bytes):
1094
+ data_as_bytes = data
1095
+ mimetype = mimetype or "application/octet-stream"
1096
+ elif isinstance(data, io.BytesIO):
1097
+ data.seek(0)
1098
+ data_as_bytes = data.getvalue()
1099
+ mimetype = mimetype or "application/octet-stream"
1100
+ elif isinstance(data, io.BufferedReader):
1101
+ data.seek(0)
1102
+ data_as_bytes = data.read()
1103
+ mimetype = mimetype or "application/octet-stream"
1104
+ elif isinstance(data, io.RawIOBase):
1105
+ data.seek(0)
1106
+ data_as_bytes = data.read() or b""
1107
+ mimetype = mimetype or "application/octet-stream"
1108
+ else:
1109
+ raise RuntimeError("Invalid binary data format: %s" % type(data))
1110
+
1111
+ if runtime.exists():
1112
+ file_url = runtime.get_instance().media_file_mgr.add(
1113
+ data_as_bytes,
1114
+ mimetype,
1115
+ coordinates,
1116
+ file_name=file_name,
1117
+ is_for_static_download=True,
1118
+ )
1119
+ else:
1120
+ # When running in "raw mode", we can't access the MediaFileManager.
1121
+ file_url = ""
1122
+
1123
+ proto_download_button.url = file_url