diff --git a/py-polars/docs/source/reference/config.rst b/py-polars/docs/source/reference/config.rst index edc606a31e60..c190bfde5d3d 100644 --- a/py-polars/docs/source/reference/config.rst +++ b/py-polars/docs/source/reference/config.rst @@ -83,11 +83,37 @@ explicitly calling one or more of the available "set\_" methods on it... Use as a decorator ------------------ -In the same vein, you can also use ``Config`` as a function decorator to -temporarily set options for the duration of the function call: +In the same vein, you can also use a ``Config`` instance as a function decorator +to temporarily set options for the duration of the function call: .. code-block:: python - @pl.Config(set_ascii_tables=True) - def write_ascii_frame_to_stdout(df: pl.DataFrame) -> None: + cfg_ascii_frames = pl.Config(ascii_tables=True, apply_on_context_enter=True) + + @cfg_ascii_frames + def write_markdown_frame_to_stdout(df: pl.DataFrame) -> None: sys.stdout.write(str(df)) + +Multiple Config instances +------------------------- +You may want to establish related bundles of `Config` options for use in different +parts of your code. Usually options are set immediately on `Config` init, meaning +the `Config` instance cannot be reused; however, you can defer this so that options +are only invoked when entering context scope (which includes function entry if used +as a decorator)._ + +This allows you to create multiple *reusable* `Config` instances in one place, update +and modify them centrally, and apply them as needed throughout your codebase. + +.. code-block:: python + + cfg_verbose = pl.Config(verbose=True, apply_on_context_enter=True) + cfg_markdown = pl.Config(tbl_formatting="MARKDOWN", apply_on_context_enter=True) + + @cfg_markdown + def write_markdown_frame_to_stdout(df: pl.DataFrame) -> None: + sys.stdout.write(str(df)) + + @cfg_verbose + def do_various_things(): + ... diff --git a/py-polars/polars/api.py b/py-polars/polars/api.py index 11a61b63e570..1ee2c5165930 100644 --- a/py-polars/polars/api.py +++ b/py-polars/polars/api.py @@ -76,9 +76,9 @@ def register_expr_namespace(name: str) -> Callable[[type[NS]], type[NS]]: See Also -------- - register_dataframe_namespace: Register functionality on a DataFrame. - register_lazyframe_namespace: Register functionality on a LazyFrame. - register_series_namespace: Register functionality on a Series. + register_dataframe_namespace : Register functionality on a DataFrame. + register_lazyframe_namespace : Register functionality on a LazyFrame. + register_series_namespace : Register functionality on a Series. Examples -------- @@ -129,9 +129,9 @@ def register_dataframe_namespace(name: str) -> Callable[[type[NS]], type[NS]]: See Also -------- - register_expr_namespace: Register functionality on an Expr. - register_lazyframe_namespace: Register functionality on a LazyFrame. - register_series_namespace: Register functionality on a Series. + register_expr_namespace : Register functionality on an Expr. + register_lazyframe_namespace : Register functionality on a LazyFrame. + register_series_namespace : Register functionality on a Series. Examples -------- @@ -227,9 +227,9 @@ def register_lazyframe_namespace(name: str) -> Callable[[type[NS]], type[NS]]: See Also -------- - register_expr_namespace: Register functionality on an Expr. - register_dataframe_namespace: Register functionality on a DataFrame. - register_series_namespace: Register functionality on a Series. + register_expr_namespace : Register functionality on an Expr. + register_dataframe_namespace : Register functionality on a DataFrame. + register_series_namespace : Register functionality on a Series. Examples -------- @@ -328,9 +328,9 @@ def register_series_namespace(name: str) -> Callable[[type[NS]], type[NS]]: See Also -------- - register_expr_namespace: Register functionality on an Expr. - register_dataframe_namespace: Register functionality on a DataFrame. - register_lazyframe_namespace: Register functionality on a LazyFrame. + register_expr_namespace : Register functionality on an Expr. + register_dataframe_namespace : Register functionality on a DataFrame. + register_lazyframe_namespace : Register functionality on a LazyFrame. Examples -------- diff --git a/py-polars/polars/config.py b/py-polars/polars/config.py index dc5060c4e4c3..fd31a1e425d6 100644 --- a/py-polars/polars/config.py +++ b/py-polars/polars/config.py @@ -171,10 +171,15 @@ class Config(contextlib.ContextDecorator): ... pass """ + _context_options: ConfigParameters | None = None _original_state: str = "" def __init__( - self, *, restore_defaults: bool = False, **options: Unpack[ConfigParameters] + self, + *, + restore_defaults: bool = False, + apply_on_context_enter: bool = False, + **options: Unpack[ConfigParameters], ) -> None: """ Initialise a Config object instance for context manager usage. @@ -187,12 +192,19 @@ def __init__( restore_defaults set all options to their default values (this is applied before setting any other options). + apply_on_context_enter + defer applying the options until a context is entered. This allows you + to create multiple `Config` instances with different options, and then + reuse them independently as context managers or function decorators + with specific bundles of parameters. **options keyword args that will set the option; equivalent to calling the named "set_