Skip to content

Instantly share code, notes, and snippets.

@coordt
Created May 8, 2023 18:00
Show Gist options
  • Save coordt/61ec5eb315ebd33cd9fb86657460835d to your computer and use it in GitHub Desktop.
Save coordt/61ec5eb315ebd33cd9fb86657460835d to your computer and use it in GitHub Desktop.

Revisions

  1. coordt created this gist May 8, 2023.
    26 changes: 26 additions & 0 deletions immutable.py
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,26 @@
    """Functions to make things immutable."""
    from collections import OrderedDict
    from collections.abc import Hashable
    from typing import Any

    from immutabledict import immutabledict
    from pydantic import BaseModel


    def freeze_data(obj: Any) -> Any:
    """Check type and recursively return a new read-only object."""
    if isinstance(obj, (str, int, float, bytes, type(None), bool)):
    return obj
    elif isinstance(obj, tuple) and type(obj) != tuple: # assumed namedtuple
    return type(obj)(*(freeze_data(i) for i in obj))
    elif isinstance(obj, (tuple, list)):
    return tuple(freeze_data(i) for i in obj)
    elif isinstance(obj, (dict, OrderedDict, immutabledict)):
    return immutabledict({k: freeze_data(v) for k, v in obj.items()})
    elif isinstance(obj, (set, frozenset)):
    return frozenset(freeze_data(i) for i in obj)
    elif isinstance(obj, BaseModel):
    return freeze_data(obj.dict())
    elif isinstance(obj, Hashable):
    return obj
    raise ValueError(obj)