streamlit 1.48.1__py3-none-any.whl → 1.49.0__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 (203) hide show
  1. streamlit/__init__.py +3 -10
  2. streamlit/commands/logo.py +4 -3
  3. streamlit/commands/navigation.py +1 -1
  4. streamlit/commands/page_config.py +4 -1
  5. streamlit/components/v1/custom_component.py +2 -2
  6. streamlit/config.py +82 -1
  7. streamlit/connections/snowflake_connection.py +3 -1
  8. streamlit/delta_generator.py +3 -0
  9. streamlit/elements/arrow.py +155 -70
  10. streamlit/elements/bokeh_chart.py +13 -3
  11. streamlit/elements/deck_gl_json_chart.py +0 -1
  12. streamlit/elements/dialog_decorator.py +7 -59
  13. streamlit/elements/form.py +10 -1
  14. streamlit/elements/graphviz_chart.py +57 -6
  15. streamlit/elements/heading.py +17 -16
  16. streamlit/elements/image.py +64 -37
  17. streamlit/elements/layouts.py +2 -2
  18. streamlit/elements/lib/built_in_chart_utils.py +2 -5
  19. streamlit/elements/lib/column_config_utils.py +18 -4
  20. streamlit/elements/lib/column_types.py +75 -30
  21. streamlit/elements/lib/dialog.py +3 -3
  22. streamlit/elements/lib/image_utils.py +19 -11
  23. streamlit/elements/lib/layout_utils.py +15 -2
  24. streamlit/elements/lib/utils.py +20 -41
  25. streamlit/elements/markdown.py +7 -6
  26. streamlit/elements/media.py +6 -13
  27. streamlit/elements/metric.py +78 -1
  28. streamlit/elements/pdf.py +192 -0
  29. streamlit/elements/plotly_chart.py +3 -2
  30. streamlit/elements/pyplot.py +53 -11
  31. streamlit/elements/toast.py +81 -5
  32. streamlit/elements/vega_charts.py +3 -8
  33. streamlit/elements/widgets/audio_input.py +0 -1
  34. streamlit/elements/widgets/button.py +0 -4
  35. streamlit/elements/widgets/button_group.py +5 -4
  36. streamlit/elements/widgets/camera_input.py +0 -1
  37. streamlit/elements/widgets/chat.py +11 -13
  38. streamlit/elements/widgets/checkbox.py +0 -1
  39. streamlit/elements/widgets/color_picker.py +0 -1
  40. streamlit/elements/widgets/data_editor.py +142 -62
  41. streamlit/elements/widgets/file_uploader.py +74 -37
  42. streamlit/elements/widgets/multiselect.py +0 -1
  43. streamlit/elements/widgets/number_input.py +0 -1
  44. streamlit/elements/widgets/radio.py +0 -1
  45. streamlit/elements/widgets/select_slider.py +0 -1
  46. streamlit/elements/widgets/selectbox.py +0 -1
  47. streamlit/elements/widgets/slider.py +0 -1
  48. streamlit/elements/widgets/text_widgets.py +0 -2
  49. streamlit/elements/widgets/time_widgets.py +0 -2
  50. streamlit/errors.py +11 -0
  51. streamlit/material_icon_names.py +1 -1
  52. streamlit/proto/Arrow_pb2.py +14 -8
  53. streamlit/proto/Arrow_pb2.pyi +11 -3
  54. streamlit/proto/Block_pb2.py +16 -16
  55. streamlit/proto/Block_pb2.pyi +2 -0
  56. streamlit/proto/ChatInput_pb2.py +3 -3
  57. streamlit/proto/ChatInput_pb2.pyi +2 -0
  58. streamlit/proto/FileUploader_pb2.py +2 -2
  59. streamlit/proto/FileUploader_pb2.pyi +5 -1
  60. streamlit/proto/GraphVizChart_pb2.py +4 -2
  61. streamlit/proto/GraphVizChart_pb2.pyi +1 -1
  62. streamlit/proto/Image_pb2.py +4 -2
  63. streamlit/proto/Image_pb2.pyi +1 -10
  64. streamlit/proto/Metric_pb2.py +8 -6
  65. streamlit/proto/Metric_pb2.pyi +34 -10
  66. streamlit/proto/Toast_pb2.py +2 -2
  67. streamlit/proto/Toast_pb2.pyi +10 -1
  68. streamlit/runtime/caching/__init__.py +14 -2
  69. streamlit/runtime/caching/cache_data_api.py +0 -17
  70. streamlit/runtime/caching/cache_resource_api.py +0 -16
  71. streamlit/runtime/caching/cached_message_replay.py +8 -20
  72. streamlit/runtime/caching/hashing.py +31 -1
  73. streamlit/runtime/credentials.py +4 -4
  74. streamlit/runtime/fragment.py +0 -42
  75. streamlit/runtime/websocket_session_manager.py +1 -1
  76. streamlit/static/index.html +2 -2
  77. streamlit/static/manifest.json +224 -252
  78. streamlit/static/static/css/{index.CJVRHjQZ.css → index.C8X8rNzw.css} +1 -1
  79. streamlit/static/static/css/index.COe1010n.css +1 -0
  80. streamlit/static/static/js/{ErrorOutline.esm.DjObtx4K.js → ErrorOutline.esm.u9XvzxL8.js} +1 -1
  81. streamlit/static/static/js/{FileDownload.esm.Bz9nxNC5.js → FileDownload.esm.CaRyZ-b2.js} +1 -1
  82. streamlit/static/static/js/FileHelper.Dk2SwIi3.js +5 -0
  83. streamlit/static/static/js/FormClearHelper.l_UPPvkg.js +1 -0
  84. streamlit/static/static/js/{Hooks.DEoLCfOE.js → Hooks.BxrVEftw.js} +1 -1
  85. streamlit/static/static/js/InputInstructions.C254RU9X.js +1 -0
  86. streamlit/static/static/js/Particles.DkY6FDnc.js +1 -0
  87. streamlit/static/static/js/ProgressBar.BPtSM82n.js +2 -0
  88. streamlit/static/static/js/Toolbar.BO_3WBaS.js +1 -0
  89. streamlit/static/static/js/{base-input.BmvSaPd2.js → base-input.egUI4LjJ.js} +4 -4
  90. streamlit/static/static/js/{checkbox.Cgxgc0et.js → checkbox.ButpszcE.js} +2 -2
  91. streamlit/static/static/js/createSuper.DYJA5xa6.js +1 -0
  92. streamlit/static/static/js/data-grid-overlay-editor.C9gQLEnU.js +1 -0
  93. streamlit/static/static/js/{downloader.M6jQeNDf.js → downloader.B3TjsSPZ.js} +1 -1
  94. streamlit/static/static/js/es6.BYSNuG4D.js +2 -0
  95. streamlit/static/static/js/iframeResizer.contentWindow.CNPHJsF2.js +1 -0
  96. streamlit/static/static/js/index.0tDq1WXk.js +1 -0
  97. streamlit/static/static/js/index.BBnWuh07.js +976 -0
  98. streamlit/static/static/js/index.BDZorv41.js +1 -0
  99. streamlit/static/static/js/{index.CbdWnLqS.js → index.BH79B25f.js} +3 -3
  100. streamlit/static/static/js/index.BeTC4Yl-.js +197 -0
  101. streamlit/static/static/js/index.BnOd05Ko.js +2 -0
  102. streamlit/static/static/js/index.BoJaJReB.js +1 -0
  103. streamlit/static/static/js/index.Bp1Of6L8.js +1 -0
  104. streamlit/static/static/js/index.Bpe4-O2W.js +1 -0
  105. streamlit/static/static/js/index.BrD9sbpx.js +1 -0
  106. streamlit/static/static/js/index.C1qCS-sd.js +1 -0
  107. streamlit/static/static/js/index.C3EXAI-u.js +1 -0
  108. streamlit/static/static/js/index.C77g9sAQ.js +3 -0
  109. streamlit/static/static/js/{index.BXDq9dj4.js → index.CFePF7s4.js} +1 -1
  110. streamlit/static/static/js/index.CFjU0x00.js +1 -0
  111. streamlit/static/static/js/index.Ca3y4ztK.js +1 -0
  112. streamlit/static/static/js/{index.CgZDfhN4.js → index.Cb9gN2T2.js} +2 -2
  113. streamlit/static/static/js/{index.tsvTLdio.js → index.CbwuUwu4.js} +9 -9
  114. streamlit/static/static/js/index.CeXLlclc.js +1 -0
  115. streamlit/static/static/js/index.CfiZGqj3.js +3 -0
  116. streamlit/static/static/js/index.CjQnYKID.js +1 -0
  117. streamlit/static/static/js/index.Cl_966eE.js +3858 -0
  118. streamlit/static/static/js/{index.Cqa4gqqN.js → index.CqSRo6zQ.js} +1 -1
  119. streamlit/static/static/js/index.CuEFSQ-o.js +1 -0
  120. streamlit/static/static/js/index.D4jR1m1z.js +1 -0
  121. streamlit/static/static/js/index.DGcW849X.js +1 -0
  122. streamlit/static/static/js/index.DKb-BAE2.js +1 -0
  123. streamlit/static/static/js/index.DP1rDFP0.js +1 -0
  124. streamlit/static/static/js/{index.D1EayrNh.js → index.DStzYLqM.js} +2 -2
  125. streamlit/static/static/js/index.DVKQKDLu.js +1 -0
  126. streamlit/static/static/js/index.DWedOrkQ.js +1 -0
  127. streamlit/static/static/js/index.DYbRPmVF.js +1 -0
  128. streamlit/static/static/js/index.DgpIMUsr.js +1 -0
  129. streamlit/static/static/js/index.DtwkPJs5.js +5367 -0
  130. streamlit/static/static/js/{index.D1jHqUJq.js → index.MQLQLR5Z.js} +1 -1
  131. streamlit/static/static/js/index.uInpwWAP.js +1 -0
  132. streamlit/static/static/js/index.z992t-BQ.js +7 -0
  133. streamlit/static/static/js/{input.DZd6EQlV.js → input.CbP5ZuQ7.js} +2 -2
  134. streamlit/static/static/js/{memory.ptkfuI71.js → memory.BuacVo2L.js} +1 -1
  135. streamlit/static/static/js/number-overlay-editor.BZb9zRl_.js +9 -0
  136. streamlit/static/static/js/{possibleConstructorReturn.Bd4ImlQ9.js → possibleConstructorReturn.DSM84rOS.js} +1 -1
  137. streamlit/static/static/js/{sandbox.DsH8LuID.js → sandbox.C480llMG.js} +1 -1
  138. streamlit/static/static/js/{timepicker.QVekV78C.js → timepicker.BunxCVp7.js} +4 -4
  139. streamlit/static/static/js/{toConsumableArray.BJvaP8gb.js → toConsumableArray.B4o8rEx1.js} +3 -3
  140. streamlit/static/static/js/uniqueId.tii0yosY.js +1 -0
  141. streamlit/static/static/js/{useBasicWidgetState.DB3vMS9V.js → useBasicWidgetState.Bnm4FD6K.js} +1 -1
  142. streamlit/static/static/js/{useTextInputAutoExpand.CBkGkaRt.js → useTextInputAutoExpand.Dgtwc1m0.js} +2 -2
  143. streamlit/static/static/js/useUpdateUiValue.DjXdMFGw.js +1 -0
  144. streamlit/static/static/js/withFullScreenWrapper.0cy2pVf5.js +1 -0
  145. streamlit/static/static/media/MaterialSymbols-Rounded.CBxVaFdk.woff2 +0 -0
  146. streamlit/user_info.py +3 -1
  147. streamlit/web/server/browser_websocket_handler.py +15 -0
  148. {streamlit-1.48.1.dist-info → streamlit-1.49.0.dist-info}/METADATA +4 -2
  149. {streamlit-1.48.1.dist-info → streamlit-1.49.0.dist-info}/RECORD +153 -156
  150. streamlit/static/static/css/index.CQt5TjGB.css +0 -1
  151. streamlit/static/static/js/FileHelper.BrQvUXVD.js +0 -5
  152. streamlit/static/static/js/FormClearHelper.DF4gFAOO.js +0 -1
  153. streamlit/static/static/js/InputInstructions.D8zoMog9.js +0 -1
  154. streamlit/static/static/js/Particles.CCFySwdL.js +0 -1
  155. streamlit/static/static/js/ProgressBar.COK9j1l0.js +0 -2
  156. streamlit/static/static/js/Toolbar.Dt4jIKlY.js +0 -1
  157. streamlit/static/static/js/createSuper.siQeagI2.js +0 -1
  158. streamlit/static/static/js/data-grid-overlay-editor.Ct51iCb_.js +0 -1
  159. streamlit/static/static/js/es6.CMaUdEZ5.js +0 -2
  160. streamlit/static/static/js/iframeResizer.contentWindow.C33BryyP.js +0 -1
  161. streamlit/static/static/js/index.8GJD0eeD.js +0 -1
  162. streamlit/static/static/js/index.8QEYHMQD.js +0 -1
  163. streamlit/static/static/js/index.Ay41Wnu9.js +0 -1
  164. streamlit/static/static/js/index.BLiKiJ7_.js +0 -1
  165. streamlit/static/static/js/index.BT78cJmU.js +0 -1
  166. streamlit/static/static/js/index.BdGvnhlM.js +0 -1
  167. streamlit/static/static/js/index.BfasrT0d.js +0 -1
  168. streamlit/static/static/js/index.CCdtFMFG.js +0 -1
  169. streamlit/static/static/js/index.CFRGZDz1.js +0 -1
  170. streamlit/static/static/js/index.CFSFYiPA.js +0 -5366
  171. streamlit/static/static/js/index.CeiIiXap.js +0 -1
  172. streamlit/static/static/js/index.CzX2xpyc.js +0 -1
  173. streamlit/static/static/js/index.D1ErX5go.js +0 -2
  174. streamlit/static/static/js/index.D5gweoL5.js +0 -7
  175. streamlit/static/static/js/index.DByVKZgq.js +0 -1
  176. streamlit/static/static/js/index.DEND45D1.js +0 -3
  177. streamlit/static/static/js/index.DKN5MVff.js +0 -781
  178. streamlit/static/static/js/index.DfoxW1gP.js +0 -3855
  179. streamlit/static/static/js/index.Dtf1Ac0x.js +0 -1
  180. streamlit/static/static/js/index.DxrLhpeO.js +0 -1
  181. streamlit/static/static/js/index.J7o-_HIh.js +0 -1
  182. streamlit/static/static/js/index.LU8juINp.js +0 -197
  183. streamlit/static/static/js/index.L_N2iylt.js +0 -1
  184. streamlit/static/static/js/index.PZUX2kRz.js +0 -3
  185. streamlit/static/static/js/index.ROjU6K0k.js +0 -1
  186. streamlit/static/static/js/index.WSNLkF94.js +0 -1
  187. streamlit/static/static/js/index.X5W3gJLn.js +0 -1
  188. streamlit/static/static/js/index.k9LYqfSL.js +0 -1
  189. streamlit/static/static/js/index.pnHtHv_c.js +0 -203
  190. streamlit/static/static/js/index.tPUXqsfW.js +0 -1
  191. streamlit/static/static/js/mergeWith.GRNk8iwv.js +0 -1
  192. streamlit/static/static/js/number-overlay-editor.DXS2qb1U.js +0 -9
  193. streamlit/static/static/js/threshold.DjX0wlsa.js +0 -1
  194. streamlit/static/static/js/timer.CAwTRJ_g.js +0 -1
  195. streamlit/static/static/js/uniqueId.D_5M8Dgf.js +0 -1
  196. streamlit/static/static/js/useUpdateUiValue.C7ZKpLQK.js +0 -1
  197. streamlit/static/static/js/value.CgPGBV_l.js +0 -1
  198. streamlit/static/static/js/withFullScreenWrapper.C-gXt0Rl.js +0 -1
  199. streamlit/static/static/media/MaterialSymbols-Rounded.DsbC8sYI.woff2 +0 -0
  200. {streamlit-1.48.1.data → streamlit-1.49.0.data}/scripts/streamlit.cmd +0 -0
  201. {streamlit-1.48.1.dist-info → streamlit-1.49.0.dist-info}/WHEEL +0 -0
  202. {streamlit-1.48.1.dist-info → streamlit-1.49.0.dist-info}/entry_points.txt +0 -0
  203. {streamlit-1.48.1.dist-info → streamlit-1.49.0.dist-info}/top_level.txt +0 -0
@@ -234,7 +234,6 @@ class CameraInputMixin:
234
234
  element_id = compute_and_register_element_id(
235
235
  "camera_input",
236
236
  user_key=key,
237
- form_id=current_form_id(self.dg),
238
237
  dg=self.dg,
239
238
  label=label,
240
239
  help=help,
@@ -32,7 +32,7 @@ from streamlit.elements.lib.file_uploader_utils import (
32
32
  normalize_upload_file_type,
33
33
  )
34
34
  from streamlit.elements.lib.form_utils import is_in_form
35
- from streamlit.elements.lib.image_utils import AtomicImage, WidthBehavior, image_to_url
35
+ from streamlit.elements.lib.image_utils import AtomicImage, image_to_url
36
36
  from streamlit.elements.lib.layout_utils import (
37
37
  LayoutConfig,
38
38
  Width,
@@ -147,7 +147,7 @@ def _process_avatar_input(
147
147
  try:
148
148
  return AvatarType.IMAGE, image_to_url(
149
149
  avatar,
150
- width=WidthBehavior.ORIGINAL,
150
+ layout_config=LayoutConfig(width="content"),
151
151
  clamp=False,
152
152
  channels="RGB",
153
153
  output_format="auto",
@@ -391,7 +391,7 @@ class ChatMixin:
391
391
  *,
392
392
  key: Key | None = None,
393
393
  max_chars: int | None = None,
394
- accept_file: Literal[True, "multiple"],
394
+ accept_file: Literal[True, "multiple", "directory"],
395
395
  file_type: str | Sequence[str] | None = None,
396
396
  disabled: bool = False,
397
397
  on_submit: WidgetCallback | None = None,
@@ -407,7 +407,7 @@ class ChatMixin:
407
407
  *,
408
408
  key: Key | None = None,
409
409
  max_chars: int | None = None,
410
- accept_file: bool | Literal["multiple"] = False,
410
+ accept_file: bool | Literal["multiple", "directory"] = False,
411
411
  file_type: str | Sequence[str] | None = None,
412
412
  disabled: bool = False,
413
413
  on_submit: WidgetCallback | None = None,
@@ -433,7 +433,7 @@ class ChatMixin:
433
433
  The maximum number of characters that can be entered. If this is
434
434
  ``None`` (default), there will be no maximum.
435
435
 
436
- accept_file : bool or str
436
+ accept_file : bool, "multiple", or "directory"
437
437
  Whether the chat input should accept files. This can be one of the
438
438
  following values:
439
439
 
@@ -442,9 +442,9 @@ class ChatMixin:
442
442
  - ``True``: The user can add a single file to their submission.
443
443
  - ``"multiple"``: The user can add multiple files to their
444
444
  submission.
445
-
446
- When the widget is configured to accept files, the accepted file
447
- types can be configured with the ``file_type`` parameter.
445
+ - ``"directory"``: The user can add multiple files to their
446
+ submission by selecting a directory. If ``file_type`` is set,
447
+ only files matching those type(s) will be uploaded.
448
448
 
449
449
  By default, uploaded files are limited to 200 MB each. You can
450
450
  configure this using the ``server.maxUploadSize`` config option.
@@ -614,9 +614,9 @@ class ChatMixin:
614
614
  writes_allowed=True,
615
615
  )
616
616
 
617
- if accept_file not in {True, False, "multiple"}:
617
+ if accept_file not in {True, False, "multiple", "directory"}:
618
618
  raise StreamlitAPIException(
619
- "The `accept_file` parameter must be a boolean or 'multiple'."
619
+ "The `accept_file` parameter must be a boolean or 'multiple' or 'directory'."
620
620
  )
621
621
 
622
622
  ctx = get_script_run_ctx()
@@ -624,8 +624,6 @@ class ChatMixin:
624
624
  element_id = compute_and_register_element_id(
625
625
  "chat_input",
626
626
  user_key=key,
627
- # chat_input is not allowed to be used in a form.
628
- form_id=None,
629
627
  dg=self.dg,
630
628
  placeholder=placeholder,
631
629
  max_chars=max_chars,
@@ -677,7 +675,7 @@ class ChatMixin:
677
675
  chat_input_proto.max_upload_size_mb = config.get_option("server.maxUploadSize")
678
676
 
679
677
  serde = ChatInputSerde(
680
- accept_files=bool(accept_file),
678
+ accept_files=accept_file in {True, "multiple", "directory"},
681
679
  allowed_types=file_type,
682
680
  )
683
681
  widget_state = register_widget( # type: ignore[misc]
@@ -342,7 +342,6 @@ class CheckboxMixin:
342
342
  element_id = compute_and_register_element_id(
343
343
  "toggle" if type == CheckboxProto.StyleType.TOGGLE else "checkbox",
344
344
  user_key=key,
345
- form_id=current_form_id(self.dg),
346
345
  dg=self.dg,
347
346
  label=label,
348
347
  value=bool(value),
@@ -219,7 +219,6 @@ class ColorPickerMixin:
219
219
  element_id = compute_and_register_element_id(
220
220
  "color_picker",
221
221
  user_key=key,
222
- form_id=current_form_id(self.dg),
223
222
  dg=self.dg,
224
223
  label=label,
225
224
  value=str(value),
@@ -33,6 +33,10 @@ from typing_extensions import TypeAlias
33
33
 
34
34
  from streamlit import dataframe_util
35
35
  from streamlit import logger as _logger
36
+ from streamlit.deprecation_util import (
37
+ make_deprecated_name_warning,
38
+ show_deprecation_warning,
39
+ )
36
40
  from streamlit.elements.lib.column_config_utils import (
37
41
  INDEX_IDENTIFIER,
38
42
  ColumnConfigMapping,
@@ -47,6 +51,12 @@ from streamlit.elements.lib.column_config_utils import (
47
51
  update_column_config,
48
52
  )
49
53
  from streamlit.elements.lib.form_utils import current_form_id
54
+ from streamlit.elements.lib.layout_utils import (
55
+ LayoutConfig,
56
+ Width,
57
+ validate_height,
58
+ validate_width,
59
+ )
50
60
  from streamlit.elements.lib.pandas_styler_utils import marshall_styler
51
61
  from streamlit.elements.lib.policies import check_widget_policies
52
62
  from streamlit.elements.lib.utils import Key, compute_and_register_element_id, to_key
@@ -60,7 +70,7 @@ from streamlit.runtime.state import (
60
70
  WidgetKwargs,
61
71
  register_widget,
62
72
  )
63
- from streamlit.type_util import is_type
73
+ from streamlit.type_util import is_list_like, is_type
64
74
  from streamlit.util import calc_md5
65
75
 
66
76
  if TYPE_CHECKING:
@@ -170,14 +180,14 @@ class DataEditorSerde:
170
180
 
171
181
 
172
182
  def _parse_value(
173
- value: str | int | float | bool | None,
183
+ value: str | int | float | bool | list[str] | None,
174
184
  column_data_kind: ColumnDataKind,
175
185
  ) -> Any:
176
186
  """Convert a value to the correct type.
177
187
 
178
188
  Parameters
179
189
  ----------
180
- value : str | int | float | bool | None
190
+ value : str | int | float | bool | list[str] | None
181
191
  The value to convert.
182
192
 
183
193
  column_data_kind : ColumnDataKind
@@ -194,9 +204,20 @@ def _parse_value(
194
204
  import pandas as pd
195
205
 
196
206
  try:
207
+ if column_data_kind == ColumnDataKind.LIST:
208
+ return list(value) if is_list_like(value) else [value] # ty: ignore
209
+
197
210
  if column_data_kind == ColumnDataKind.STRING:
198
211
  return str(value)
199
212
 
213
+ # List values aren't supported for anything else than list column data kind.
214
+ # To make the type checker happy, we raise a TypeError here. However,
215
+ # This isn't expected to happen.
216
+ if isinstance(value, list):
217
+ raise TypeError( # noqa: TRY301
218
+ "List values are only supported by list and string columns."
219
+ )
220
+
200
221
  if column_data_kind == ColumnDataKind.INTEGER:
201
222
  return int(value)
202
223
 
@@ -234,7 +255,7 @@ def _parse_value(
234
255
  if column_data_kind == ColumnDataKind.TIME:
235
256
  return datetime_value.time()
236
257
 
237
- except (ValueError, pd.errors.ParserError) as ex:
258
+ except (ValueError, pd.errors.ParserError, TypeError) as ex:
238
259
  _LOGGER.warning(
239
260
  "Failed to parse value %s as %s.",
240
261
  value,
@@ -247,7 +268,9 @@ def _parse_value(
247
268
 
248
269
  def _apply_cell_edits(
249
270
  df: pd.DataFrame,
250
- edited_rows: Mapping[int, Mapping[str, str | int | float | bool | None]],
271
+ edited_rows: Mapping[
272
+ int, Mapping[str, str | int | float | bool | list[str] | None]
273
+ ],
251
274
  dataframe_schema: DataframeSchema,
252
275
  ) -> None:
253
276
  """Apply cell edits to the provided dataframe (inplace).
@@ -278,7 +301,7 @@ def _apply_cell_edits(
278
301
  )
279
302
  else:
280
303
  col_pos = df.columns.get_loc(col_name)
281
- df.iloc[row_pos, col_pos] = _parse_value(
304
+ df.iat[row_pos, col_pos] = _parse_value(
282
305
  value, dataframe_schema[col_name]
283
306
  )
284
307
 
@@ -578,14 +601,14 @@ class DataEditorMixin:
578
601
  self,
579
602
  data: EditableData,
580
603
  *,
581
- width: int | None = None,
582
- height: int | None = None,
604
+ width: Width = "stretch",
605
+ height: int | Literal["auto"] = "auto",
583
606
  use_container_width: bool | None = None,
584
607
  hide_index: bool | None = None,
585
608
  column_order: Iterable[str] | None = None,
586
609
  column_config: ColumnConfigMappingInput | None = None,
587
610
  num_rows: Literal["fixed", "dynamic"] = "fixed",
588
- disabled: bool | Iterable[str] = False,
611
+ disabled: bool | Iterable[str | int] = False,
589
612
  key: Key | None = None,
590
613
  on_change: WidgetCallback | None = None,
591
614
  args: WidgetArgs | None = None,
@@ -599,14 +622,14 @@ class DataEditorMixin:
599
622
  self,
600
623
  data: Any,
601
624
  *,
602
- width: int | None = None,
603
- height: int | None = None,
625
+ width: Width = "stretch",
626
+ height: int | Literal["auto"] = "auto",
604
627
  use_container_width: bool | None = None,
605
628
  hide_index: bool | None = None,
606
629
  column_order: Iterable[str] | None = None,
607
630
  column_config: ColumnConfigMappingInput | None = None,
608
631
  num_rows: Literal["fixed", "dynamic"] = "fixed",
609
- disabled: bool | Iterable[str] = False,
632
+ disabled: bool | Iterable[str | int] = False,
610
633
  key: Key | None = None,
611
634
  on_change: WidgetCallback | None = None,
612
635
  args: WidgetArgs | None = None,
@@ -620,14 +643,14 @@ class DataEditorMixin:
620
643
  self,
621
644
  data: DataTypes,
622
645
  *,
623
- width: int | None = None,
624
- height: int | None = None,
646
+ width: Width = "stretch",
647
+ height: int | Literal["auto"] = "auto",
625
648
  use_container_width: bool | None = None,
626
649
  hide_index: bool | None = None,
627
650
  column_order: Iterable[str] | None = None,
628
651
  column_config: ColumnConfigMappingInput | None = None,
629
652
  num_rows: Literal["fixed", "dynamic"] = "fixed",
630
- disabled: bool | Iterable[str] = False,
653
+ disabled: bool | Iterable[str | int] = False,
631
654
  key: Key | None = None,
632
655
  on_change: WidgetCallback | None = None,
633
656
  args: WidgetArgs | None = None,
@@ -649,7 +672,7 @@ class DataEditorMixin:
649
672
  precedence over text and number formatting from ``pandas.Styler``.
650
673
  - Mixing data types within a column can make the column uneditable.
651
674
  - Additionally, the following data types are not yet supported for editing:
652
- ``complex``, ``list``, ``tuple``, ``bytes``, ``bytearray``,
675
+ ``complex``, ``tuple``, ``bytes``, ``bytearray``,
653
676
  ``memoryview``, ``dict``, ``set``, ``frozenset``,
654
677
  ``fractions.Fraction``, ``pandas.Interval``, and
655
678
  ``pandas.Period``.
@@ -658,18 +681,28 @@ class DataEditorMixin:
658
681
  default to uneditable, but this can be changed through column
659
682
  configuration.
660
683
 
661
- width : int or None
662
- Desired width of the data editor expressed in pixels. If ``width``
663
- is ``None`` (default), Streamlit sets the data editor width to fit
664
- its contents up to the width of the parent container. If ``width``
665
- is greater than the width of the parent container, Streamlit sets
666
- the data editor width to match the width of the parent container.
684
+ width : "stretch", "content", or int
685
+ The width of the data editor. This can be one of the following:
686
+
687
+ - ``"stretch"`` (default): The width of the editor matches the
688
+ width of the parent container.
689
+ - ``"content"``: The width of the editor matches the width of its
690
+ content, but doesn't exceed the width of the parent container.
691
+ - An integer specifying the width in pixels: The editor has a
692
+ fixed width. If the specified width is greater than the width of
693
+ the parent container, the width of the editor matches the width
694
+ of the parent container.
667
695
 
668
- height : int or None
669
- Desired height of the data editor expressed in pixels. If ``height``
670
- is ``None`` (default), Streamlit sets the height to show at most
671
- ten rows. Vertical scrolling within the data editor element is
672
- enabled when the height does not accommodate all rows.
696
+ height : int or "auto"
697
+ The height of the data editor. This can be one of the following:
698
+
699
+ - ``"auto"`` (default): Streamlit sets the height to show at most
700
+ ten rows.
701
+ - An integer specifying the height in pixels: The editor has a
702
+ fixed height.
703
+
704
+ Vertical scrolling within the data editor is enabled when the
705
+ height does not accommodate all rows.
673
706
 
674
707
  use_container_width : bool
675
708
  Whether to override ``width`` with the width of the parent
@@ -683,28 +716,42 @@ class DataEditorMixin:
683
716
  (default), the visibility of index columns is automatically
684
717
  determined based on the data.
685
718
 
686
- column_order : Iterable of str or None
687
- Specifies the display order of columns. This also affects which columns are
688
- visible. For example, ``column_order=("col2", "col1")`` will display 'col2'
689
- first, followed by 'col1', and will hide all other non-index columns. If
690
- None (default), the order is inherited from the original data structure.
719
+ column_order : Iterable[str] or None
720
+ The ordered list of columns to display. If this is ``None``
721
+ (default), Streamlit displays all columns in the order inherited
722
+ from the underlying data structure. If this is a list, the
723
+ indicated columns will display in the order they appear within the
724
+ list. Columns may be omitted or repeated within the list.
725
+
726
+ For example, ``column_order=("col2", "col1")`` will display
727
+ ``"col2"`` first, followed by ``"col1"``, and will hide all other
728
+ non-index columns.
729
+
730
+ ``column_order`` does not accept positional column indices and
731
+ can't move the index column(s).
691
732
 
692
733
  column_config : dict or None
693
- Configures how columns are displayed, e.g. their title, visibility, type, or
694
- format, as well as editing properties such as min/max value or step.
695
- This needs to be a dictionary where each key is a column name and the value
696
- is one of:
734
+ Configuration to customize how columns are displayed. If this is
735
+ ``None`` (default), columns are styled based on the underlying data
736
+ type of each column.
697
737
 
698
- - ``None`` to hide the column.
738
+ Column configuration can modify column names, visibility, type,
739
+ width, format, editing properties like min/max, and more. If this
740
+ is a dictionary, the keys are column names (strings) and/or
741
+ positional column indices (integers), and the values are one of the
742
+ following:
699
743
 
744
+ - ``None`` to hide the column.
700
745
  - A string to set the display label of the column.
746
+ - One of the column types defined under ``st.column_config``. For
747
+ example, to show a column as dollar amounts, use
748
+ ``st.column_config.NumberColumn("Dollar values", format="$ %d")``.
749
+ See more info on the available column types and config options
750
+ `here <https://docs.streamlit.io/develop/api-reference/data/st.column_config>`_.
701
751
 
702
- - One of the column types defined under ``st.column_config``, e.g.
703
- ``st.column_config.NumberColumn("Dollar values", format="$ %d")`` to show
704
- a column as dollar amounts. See more info on the available column types
705
- and config options `here <https://docs.streamlit.io/develop/api-reference/data/st.column_config>`_.
706
-
707
- To configure the index column(s), use ``_index`` as the column name.
752
+ To configure the index column(s), use ``"_index"`` as the column
753
+ name, or use a positional column index where ``0`` refers to the
754
+ first index column.
708
755
 
709
756
  num_rows : "fixed" or "dynamic"
710
757
  Specifies if the user can add and delete rows in the data editor.
@@ -712,11 +759,20 @@ class DataEditorMixin:
712
759
  add and delete rows in the data editor, but column sorting is disabled.
713
760
  Defaults to "fixed".
714
761
 
715
- disabled : bool or Iterable of str
716
- Controls the editing of columns. If True, editing is disabled for all columns.
717
- If an Iterable of column names is provided (e.g., ``disabled=("col1", "col2"))``,
718
- only the specified columns will be disabled for editing. If False (default),
719
- all columns that support editing are editable.
762
+ disabled : bool or Iterable[str | int]
763
+ Controls the editing of columns. This can be one of the following:
764
+
765
+ - ``False`` (default): All columns that support editing are editable.
766
+ - ``True``: All columns are disabled for editing.
767
+ - An Iterable of column names and/or positional indices: The
768
+ specified columns are disabled for editing while the remaining
769
+ columns are editable where supported. For example,
770
+ ``disabled=["col1", "col2"]`` will disable editing for the
771
+ columns named "col1" and "col2".
772
+
773
+ To disable editing for the index column(s), use ``"_index"`` as the
774
+ column name, or use a positional column index where ``0`` refers to
775
+ the first index column.
720
776
 
721
777
  key : str
722
778
  An optional string to use as the unique key for this widget. If this
@@ -737,6 +793,11 @@ class DataEditorMixin:
737
793
  is ``None`` (default), Streamlit will use a default row height,
738
794
  which fits one line of text.
739
795
 
796
+ .. deprecated::
797
+ ``use_container_width`` is deprecated and will be removed in a
798
+ future release. For ``use_container_width=True``, use
799
+ ``width="stretch"``.
800
+
740
801
  Returns
741
802
  -------
742
803
  pandas.DataFrame, pandas.Series, pyarrow.Table, numpy.ndarray, list, set, tuple, or dict.
@@ -839,6 +900,14 @@ class DataEditorMixin:
839
900
 
840
901
  key = to_key(key)
841
902
 
903
+ validate_width(width, allow_content=True)
904
+ validate_height(
905
+ height,
906
+ allow_content=False,
907
+ allow_stretch=False,
908
+ additional_allowed=["auto"],
909
+ )
910
+
842
911
  check_widget_policies(
843
912
  self.dg,
844
913
  key,
@@ -847,6 +916,23 @@ class DataEditorMixin:
847
916
  writes_allowed=False,
848
917
  )
849
918
 
919
+ if use_container_width is not None:
920
+ show_deprecation_warning(
921
+ make_deprecated_name_warning(
922
+ "use_container_width",
923
+ "width",
924
+ "2025-12-31",
925
+ "For `use_container_width=True`, use `width='stretch'`. "
926
+ "For `use_container_width=False`, use `width='content'`.",
927
+ include_st_prefix=False,
928
+ ),
929
+ show_in_browser=False,
930
+ )
931
+ if use_container_width:
932
+ width = "stretch"
933
+ elif not isinstance(width, int):
934
+ width = "content"
935
+
850
936
  if column_order is not None:
851
937
  column_order = list(column_order)
852
938
 
@@ -942,7 +1028,6 @@ class DataEditorMixin:
942
1028
  element_id = compute_and_register_element_id(
943
1029
  "data_editor",
944
1030
  user_key=key,
945
- form_id=current_form_id(self.dg),
946
1031
  dg=self.dg,
947
1032
  data=arrow_bytes,
948
1033
  width=width,
@@ -957,18 +1042,6 @@ class DataEditorMixin:
957
1042
  proto = ArrowProto()
958
1043
  proto.id = element_id
959
1044
 
960
- if use_container_width is None:
961
- # If use_container_width was not explicitly set by the user, we set
962
- # it to True if width was not set explicitly, and False otherwise.
963
- use_container_width = width is None
964
-
965
- proto.use_container_width = use_container_width
966
-
967
- if width:
968
- proto.width = width
969
- if height:
970
- proto.height = height
971
-
972
1045
  if row_height:
973
1046
  proto.row_height = row_height
974
1047
 
@@ -1005,6 +1078,13 @@ class DataEditorMixin:
1005
1078
 
1006
1079
  marshall_column_config(proto, column_config_mapping)
1007
1080
 
1081
+ # Create layout configuration
1082
+ # For height, only include it in LayoutConfig if it's not "auto"
1083
+ # "auto" is the default behavior and doesn't need to be sent
1084
+ layout_config = LayoutConfig(
1085
+ width=width, height=height if height != "auto" else None
1086
+ )
1087
+
1008
1088
  serde = DataEditorSerde()
1009
1089
 
1010
1090
  widget_state = register_widget(
@@ -1019,7 +1099,7 @@ class DataEditorMixin:
1019
1099
  )
1020
1100
 
1021
1101
  _apply_dataframe_edits(data_df, widget_state.value, dataframe_schema)
1022
- self.dg._enqueue("arrow_data_frame", proto)
1102
+ self.dg._enqueue("arrow_data_frame", proto, layout_config=layout_config)
1023
1103
  return dataframe_util.convert_pandas_df_to_data_format(data_df, data_format)
1024
1104
 
1025
1105
  @property