Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(project)!: Remove "put-several" mechanic #1100

Merged
merged 1 commit into from
Jan 14, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
58 changes: 9 additions & 49 deletions skore/src/skore/project/project.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
"""Define a Project."""

import logging
from typing import Any, Optional, Union
from typing import Any

from skore.item import (
CrossValidationItem,
Expand All @@ -25,9 +25,6 @@
logger.setLevel(logging.INFO)


MISSING = object()


class Project:
"""
A collection of items arranged in views and stored in a storage.
Expand Down Expand Up @@ -80,44 +77,18 @@ def __init__(
self.item_repository = item_repository
self.view_repository = view_repository

def put(self, key: Union[str, dict[str, Any]], value: Optional[Any] = MISSING):
"""Add one or more key-value pairs to the Project.
def put(self, key: str, value: Any):
"""Add a key-value pair to the Project.

If an item with the same key already exists, its value is replaced by the new
one.

If ``key`` is a string, then :func:`~skore.Project.put` adds the single
``key``-``value`` pair mapping to the Project.
If ``key`` is a dict, it is interpreted as multiple key-value pairs to add to
the Project.

The dict format is equivalent to running :func:`~skore.Project.put`
for each individual key-value pair. In other words,

.. code-block:: python

project.put({"hello": 1, "goodbye": 2})

is equivalent to

.. code-block:: python

project.put("hello", 1)
project.put("goodbye", 2)

In particular, this means that if some key-value pair is invalid
(e.g. if a key is not a string, or a value's type is not supported),
then all the key-value pairs up to the first offending key-value pair will
be successfully inserted, *and then* an error will be raised.

Parameters
----------
key : str | dict[str, Any]
The key to associate with ``value`` in the Project,
or dict of key-value pairs to add to the Project.
value : Any, optional
key : str
The key to associate with ``value`` in the Project.
value : Any
The value to associate with ``key`` in the Project.
If ``key`` is a dict, this argument is ignored.

Raises
------
Expand All @@ -127,21 +98,10 @@ def put(self, key: Union[str, dict[str, Any]], value: Optional[Any] = MISSING):
NotImplementedError
If the value type is not supported.
"""
if value is not MISSING:
thomass-dev marked this conversation as resolved.
Show resolved Hide resolved
key_to_item = {key: value}
elif isinstance(key, dict):
key_to_item = key
else:
raise TypeError(
f"Bad parameters. "
f"When value is not specified, key must be a dict (found '{type(key)}')"
)

for key, value in key_to_item.items():
if not isinstance(key, str):
raise TypeError(f"Key must be a string (found '{type(key)}')")
if not isinstance(key, str):
raise TypeError(f"Key must be a string (found '{type(key)}')")

self.item_repository.put_item(key, object_to_item(value))
self.item_repository.put_item(key, object_to_item(value))

def put_item(self, key: str, item: Item):
"""Add an Item to the Project."""
Expand Down
30 changes: 0 additions & 30 deletions skore/tests/unit/project/test_project.py
Original file line number Diff line number Diff line change
Expand Up @@ -218,36 +218,6 @@ def test_list_view_keys(in_memory_project):
assert in_memory_project.list_view_keys() == ["view"]


def test_put_several_happy_path(in_memory_project):
in_memory_project.put({"a": "foo", "b": "bar"})
assert in_memory_project.list_item_keys() == ["a", "b"]


def test_put_several_some_errors(in_memory_project):
with pytest.raises(TypeError):
in_memory_project.put({0: "hello", 1: "hello", 2: "hello"})
assert in_memory_project.list_item_keys() == []


def test_put_several_nested(in_memory_project):
in_memory_project.put({"a": {"b": "baz"}})
assert in_memory_project.list_item_keys() == ["a"]
assert in_memory_project.get("a") == {"b": "baz"}


def test_put_several_error(in_memory_project):
"""If some key-value pairs are wrong, add all that are valid and print a warning."""
with pytest.raises(NotImplementedError):
in_memory_project.put(
{
"a": "foo",
"b": (lambda: "unsupported object"),
}
)

assert in_memory_project.list_item_keys() == ["a"]


def test_put_key_is_a_tuple(in_memory_project):
"""If key is not a string, warn."""
with pytest.raises(TypeError):
Expand Down
Loading