API Reference
Core Functions¶
get_at ¶
get_at(data: Any, path: Union[str, List[Any]], default: Any = None) -> Any
Retrieve a value from a nested data structure.
Navigates through nested dictionaries, lists, and tuples using a path specified as either
a dot-notation string or a list of keys/indices. Returns default if the path does not
exist or an index is out of bounds (positive or negative). Supports negative indexing for
lists and tuples.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
data |
Any
|
The data structure to navigate (dict, list, tuple, or nested combinations). |
required |
path |
Union[str, List[Any]]
|
Path to the value. Accepts either a dot-separated string (e.g., "a.b.0.name") or a list of keys/indices (e.g., ["a", "b", 0, "name"]). Indices may be integers or strings representing integers (including negative indices). |
required |
default |
Any
|
Value to return if the path does not exist (default: None). |
None
|
Returns:
| Type | Description |
|---|---|
Any
|
The value at the specified path, or |
Raises:
| Type | Description |
|---|---|
PathError
|
If the path is malformed, empty, or contains empty keys. |
Examples:
>>> data = {"a": {"b": {"c": 5}}}
>>> get_at(data, "a.b.c")
5
>>> get_at(data, "a.b.d", default=99)
99
>>> data = {"items": [{"name": "apple"}, {"name": "banana"}]}
>>> get_at(data, "items.1.name")
'banana'
>>> get_at(data, "items.-1.name")
'banana'
>>> get_at(data, "items.-5.name", default="not found")
'not found'
>>> data = (10, 20, 30)
>>> get_at(data, "-1")
30
set_at ¶
set_at(data: Any, path: Union[str, List[Any]], value: Any, fill_strategy: Literal['auto', 'none', 'dict', 'list'] = 'auto') -> None
Set a value in a nested data structure, creating intermediate containers as needed.
Navigates to the specified path and sets the value, automatically creating missing
intermediate dictionaries or lists according to fill_strategy.
List indexing rules
- Non-negative indices can extend the list, filling gaps as needed.
- Negative indices can only modify existing elements (no extension allowed).
- Out-of-bounds negative indices raise PathError.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
data |
Any
|
The mutable data structure to modify (dict or list). Intermediate containers are created automatically, but the root must be mutable. |
required |
path |
Union[str, List[Any]]
|
Path where to set the value. Accepts either a dot-separated string (e.g., "a.b.0.name") or a list of keys/indices (e.g., ["a", "b", 0, "name"]). |
required |
value |
Any
|
The value to set at the specified path. |
required |
fill_strategy |
Literal['auto', 'none', 'dict', 'list']
|
Controls how missing intermediate containers are created. Must be one of: - 'auto' (default): creates {} for dict keys, [] for list indices, and None for sparse list gaps. - 'none': fills sparse list gaps with None. - 'dict': always creates dictionaries {} for missing containers. - 'list': always creates lists [] for missing containers. |
'auto'
|
Returns:
| Type | Description |
|---|---|
None
|
None. The function modifies |
Raises:
| Type | Description |
|---|---|
PathError
|
If the path is malformed, empty, attempts to modify a tuple, uses an invalid fill_strategy, or uses an out-of-bounds negative index. |
Note
When extending lists with gaps (e.g., setting index 5 on a list of length 2),
intermediate positions are filled based on fill_strategy ('auto' and 'none' use None;
'dict' uses {}; 'list' uses []).
Examples:
>>> data = {}
>>> set_at(data, "user.profile.name", "Alice")
>>> data
{'user': {'profile': {'name': 'Alice'}}}
>>> data = {}
>>> set_at(data, "items.0.name", "Item 1")
>>> data
{'items': [{'name': 'Item 1'}]}
>>> data = {}
>>> set_at(data, "items.5", "last", fill_strategy="none")
>>> data
{'items': [None, None, None, None, None, 'last']}
>>> data = {}
>>> set_at(data, "items.2.sub.value", 42) # 'auto' creates dict at target index, None for gaps
>>> data
{'items': [None, None, {'sub': {'value': 42}}]}
>>> data = [1, 2, 3]
>>> set_at(data, "5", 99) # extends with None gaps
>>> data
[1, 2, 3, None, None, 99]
>>> set_at(data, "-1", 100) # modifies existing last element
>>> data
[1, 2, 3, None, None, 100]
delete_at ¶
delete_at(data: Any, path: Union[str, List[Any]], *, allow_list_mutation: bool = False) -> Any
Delete a value from a nested data structure and return it.
Removes the item at the specified path. For dictionaries, the key-value pair is removed. For lists, deletion is disabled by default to prevent accidental index shifting that could break subsequent code.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
data |
Any
|
The mutable data structure to modify (dict or list). |
required |
path |
Union[str, List[Any]]
|
Path to the value to delete. Accepts either a dot-separated string (e.g., "a.b.0") or a list of keys/indices (e.g., ["a", "b", 0]). |
required |
allow_list_mutation |
bool
|
If True, allows deletion from lists using |
False
|
Returns:
| Type | Description |
|---|---|
Any
|
The deleted value. |
Raises:
| Type | Description |
|---|---|
PathError
|
If the path does not exist, is malformed, attempts deletion from a tuple,
attempts list deletion without |
Examples:
>>> data = {"a": {"b": 1, "c": 2}}
>>> delete_at(data, "a.b")
1
>>> data
{'a': {'c': 2}}
>>> data = {"items": [1, 2, 3]}
>>> delete_at(data, "items.1", allow_list_mutation=True)
2
>>> data
{'items': [1, 3]}
>>> delete_at(data, "items.-1", allow_list_mutation=True)
3
>>> data
{'items': [1]}
>>> delete_at(data, "items.0") # without allow_list_mutation=True
Traceback (most recent call last):
...
PathError: List deletion disabled. Set allow_list_mutation=True
exists_at ¶
exists_at(data: Any, path: Union[str, List[Any]]) -> bool
Check if a path exists in a nested data structure.
Navigates through nested dictionaries, lists, and tuples. Returns True if the full path exists, False otherwise (including for any out-of-bounds index, positive or negative). Supports negative indexing for lists and tuples.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
data |
Any
|
The data structure to navigate (dict, list, tuple, or nested combinations). |
required |
path |
Union[str, List[Any]]
|
Path to check. Accepts either a dot-separated string (e.g., "a.b.0.name") or a list of keys/indices (e.g., ["a", "b", 0, "name"]). |
required |
Returns:
| Type | Description |
|---|---|
bool
|
True if the path exists, False otherwise. |
Raises:
| Type | Description |
|---|---|
PathError
|
If the path is malformed, empty, or contains empty keys. |
Examples:
>>> data = {"a": {"b": {"c": 5}}}
>>> exists_at(data, "a.b.c")
True
>>> exists_at(data, "a.b.d")
False
>>> data = {"items": [{"name": "apple"}, {"name": "banana"}]}
>>> exists_at(data, "items.1.name")
True
>>> exists_at(data, "items.-1.name")
True
>>> exists_at(data, "items.-5.name")
False
>>> exists_at(data, "items.10.name")
False
>>> data = (10, 20, 30)
>>> exists_at(data, "2")
True
>>> exists_at(data, "5")
False