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

Declare required and optional dependency #714

Merged
merged 20 commits into from
Oct 21, 2024
Merged
Show file tree
Hide file tree
Changes from 13 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
38 changes: 23 additions & 15 deletions pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -19,31 +19,38 @@ classifiers = [
"Topic :: Software Development :: Libraries :: Python Modules",
]
dependencies = [

"ruamel.yaml",
"numpy<2.0.0",
]
version = "2024.7.30"

[project.optional-dependencies]
ci = [
"pytest>=8",
"pytest-cov>=4",
"coverage",
"numpy<2.0.0",
"ruamel.yaml",
"msgpack",
"tqdm",
"pymongo",
"pandas",
"pint",
"orjson",
"types-orjson",
"types-requests",
"torch"
"coverage",
"monty[optional]",
"pytest>=8",
"pytest-cov>=4",
"types-orjson",
"types-requests",
]
# dev is for "dev" module, not for development
dev = ["ipython"]
docs = [
"sphinx",
"sphinx_rtd_theme",
]
json = [
"bson",
"orjson",
"pandas",
"pydantic",
"pint",
"torch",
]
multiprocessing = ["tqdm"]
optional = ["monty[dev,json,multiprocessing,serialization]"]
serialization = ["msgpack"]
task = ["requests", "invoke"]

[tool.setuptools.packages.find]
where = ["src"]
Expand Down Expand Up @@ -101,3 +108,4 @@ lint.select = [
]

lint.isort.required-imports = ["from __future__ import annotations"]
lint.isort.known-first-party = ["monty"]
2 changes: 1 addition & 1 deletion src/monty/dev.py
Original file line number Diff line number Diff line change
Expand Up @@ -232,7 +232,7 @@ def install_excepthook(hook_type: str = "color", **kwargs) -> int:
try:
from IPython.core import ultratb # pylint: disable=import-outside-toplevel
except ImportError:
warnings.warn("Cannot install excepthook, IPyhon.core.ultratb not available")
warnings.warn("Cannot install excepthook, IPython not installed")
return 1

# Select the hook.
Expand Down
6 changes: 1 addition & 5 deletions src/monty/io.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,11 +9,7 @@
import errno
import gzip
import io

try:
import lzma
except ImportError:
lzma = None # type: ignore[assignment]
import lzma
DanielYang59 marked this conversation as resolved.
Show resolved Hide resolved
import mmap
import os
import subprocess
Expand Down
5 changes: 1 addition & 4 deletions src/monty/itertools.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,10 +7,7 @@
import itertools
from typing import TYPE_CHECKING

try:
import numpy as np
except ImportError:
np = None
import numpy as np

if TYPE_CHECKING:
from typing import Iterable
Expand Down
46 changes: 20 additions & 26 deletions src/monty/json.py
Original file line number Diff line number Diff line change
Expand Up @@ -21,10 +21,8 @@
from typing import Any
from uuid import UUID, uuid4

try:
import numpy as np
except ImportError:
np = None
import numpy as np
from ruamel.yaml import YAML

try:
import pydantic
Expand All @@ -41,17 +39,11 @@
except ImportError:
bson = None

try:
from ruamel.yaml import YAML
except ImportError:
YAML = None

try:
import orjson
except ImportError:
orjson = None


try:
import torch
except ImportError:
Expand Down Expand Up @@ -599,23 +591,22 @@ def default(self, o) -> dict:
d["data"] = o.numpy().tolist()
return d

if np is not None:
if isinstance(o, np.ndarray):
if str(o.dtype).startswith("complex"):
return {
"@module": "numpy",
"@class": "array",
"dtype": str(o.dtype),
"data": [o.real.tolist(), o.imag.tolist()],
}
if isinstance(o, np.ndarray):
if str(o.dtype).startswith("complex"):
return {
"@module": "numpy",
"@class": "array",
"dtype": str(o.dtype),
"data": o.tolist(),
"data": [o.real.tolist(), o.imag.tolist()],
}
if isinstance(o, np.generic):
return o.item()
return {
"@module": "numpy",
"@class": "array",
"dtype": str(o.dtype),
"data": o.tolist(),
}
if isinstance(o, np.generic):
return o.item()

if _check_type(o, "pandas.core.frame.DataFrame"):
return {
Expand Down Expand Up @@ -668,7 +659,7 @@ def default(self, o) -> dict:
and dataclasses.is_dataclass(o)
):
# This handles dataclasses that are not subclasses of MSONAble.
d = dataclasses.asdict(o) # type: ignore[call-overload]
d = dataclasses.asdict(o) # type: ignore[call-overload, arg-type]
elif hasattr(o, "as_dict"):
d = o.as_dict()
elif isinstance(o, Enum):
Expand Down Expand Up @@ -813,7 +804,7 @@ def process_decoded(self, d):
).type(d["dtype"])
return torch.tensor(d["data"]).type(d["dtype"]) # pylint: disable=E1101

elif np is not None and modname == "numpy" and classname == "array":
elif modname == "numpy" and classname == "array":
if d["dtype"].startswith("complex"):
return np.array(
[
Expand Down Expand Up @@ -936,7 +927,8 @@ def jsanitize(
)
for i in obj
]
if np is not None and isinstance(obj, np.ndarray):

if isinstance(obj, np.ndarray):
try:
return [
jsanitize(
Expand All @@ -950,8 +942,10 @@ def jsanitize(
]
except TypeError:
return obj.tolist()
if np is not None and isinstance(obj, np.generic):

if isinstance(obj, np.generic):
return obj.item()

if _check_type(
obj,
(
Expand Down
6 changes: 2 additions & 4 deletions src/monty/multiprocessing.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,8 @@

try:
from tqdm.autonotebook import tqdm
except ImportError:
tqdm = None
except ImportError as exc:
raise ImportError("tqdm must be installed for this function.") from exc


def imap_tqdm(nprocs: int, func: Callable, iterable: Iterable, *args, **kwargs) -> list:
Expand All @@ -28,8 +28,6 @@ def imap_tqdm(nprocs: int, func: Callable, iterable: Iterable, *args, **kwargs)
Returns:
Results of Pool.imap.
"""
if tqdm is None:
raise ImportError("tqdm must be installed for this function.")
data = []
with Pool(nprocs) as pool:
try:
Expand Down
5 changes: 1 addition & 4 deletions src/monty/serialization.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,10 +9,7 @@
import os
from typing import TYPE_CHECKING

try:
from ruamel.yaml import YAML
except ImportError:
YAML = None # type: ignore[arg-type]
from ruamel.yaml import YAML

from monty.io import zopen
from monty.json import MontyDecoder, MontyEncoder
Expand Down
1 change: 1 addition & 0 deletions tasks.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@

import requests
from invoke import task

from monty import __version__ as ver
from monty.os import cd

Expand Down
1 change: 1 addition & 0 deletions tests/test_collections.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
import os

import pytest

from monty.collections import AttrDict, FrozenAttrDict, Namespace, frozendict, tree

TEST_DIR = os.path.join(os.path.dirname(__file__), "test_files")
Expand Down
1 change: 1 addition & 0 deletions tests/test_design_patterns.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
from typing import Any

import pytest

from monty.design_patterns import cached_class, singleton


Expand Down
1 change: 1 addition & 0 deletions tests/test_dev.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
from unittest.mock import patch

import pytest

from monty.dev import deprecated, install_excepthook, requires

# Set all warnings to always be triggered.
Expand Down
1 change: 1 addition & 0 deletions tests/test_fractions.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
from __future__ import annotations

import pytest

from monty.fractions import gcd, gcd_float, lcm


Expand Down
1 change: 1 addition & 0 deletions tests/test_functools.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
import unittest

import pytest

from monty.functools import (
TimeoutError,
lazy_property,
Expand Down
1 change: 1 addition & 0 deletions tests/test_io.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
from unittest.mock import patch

import pytest

from monty.io import (
FileLock,
FileLockException,
Expand Down
36 changes: 15 additions & 21 deletions tests/test_json.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,10 +8,19 @@
from enum import Enum
from typing import Union

try:
import numpy as np
except ImportError:
np = None
import numpy as np
import pytest

from monty.json import (
MontyDecoder,
MontyEncoder,
MSONable,
_load_redirect,
jsanitize,
load,
)

from . import __version__ as TESTS_VERSION

try:
import pandas as pd
Expand All @@ -38,18 +47,6 @@
except ImportError:
ObjectId = None

import pytest
from monty.json import (
MontyDecoder,
MontyEncoder,
MSONable,
_load_redirect,
jsanitize,
load,
)

from . import __version__ as tests_version

TEST_DIR = os.path.join(os.path.dirname(os.path.abspath(__file__)), "test_files")


Expand Down Expand Up @@ -320,7 +317,7 @@ def test_unsafe_hash(self):
def test_version(self):
obj = self.good_cls("Hello", "World", "Python")
d = obj.as_dict()
assert d["@version"] == tests_version
assert d["@version"] == TESTS_VERSION

def test_nested_to_from_dict(self):
GMC = GoodMSONClass
Expand Down Expand Up @@ -564,7 +561,6 @@ def test_nan(self):
d = json.loads(djson)
assert isinstance(d[0], float)

@pytest.mark.skipif(np is None, reason="numpy not present")
def test_numpy(self):
x = np.array([1, 2, 3], dtype="int64")
with pytest.raises(TypeError):
Expand Down Expand Up @@ -872,9 +868,7 @@ def test_jsanitize_pandas(self):
clean = jsanitize(s)
assert clean == s.to_dict()

@pytest.mark.skipif(
np is None or ObjectId is None, reason="numpy and bson not present"
)
@pytest.mark.skipif(ObjectId is None, reason="bson not present")
def test_jsanitize_numpy_bson(self):
d = {
"a": ["b", np.array([1, 2, 3])],
Expand Down
1 change: 1 addition & 0 deletions tests/test_os.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
from pathlib import Path

import pytest

from monty.os import cd, makedirs_p
from monty.os.path import find_exts, zpath

Expand Down
6 changes: 3 additions & 3 deletions tests/test_serialization.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,14 +7,14 @@

import pytest

from monty.serialization import dumpfn, loadfn
from monty.tempfile import ScratchDir

try:
import msgpack
except ImportError:
msgpack = None

from monty.serialization import dumpfn, loadfn
from monty.tempfile import ScratchDir


class TestSerial:
@classmethod
Expand Down
1 change: 1 addition & 0 deletions tests/test_shutil.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
from pathlib import Path

import pytest

from monty.shutil import (
compress_dir,
compress_file,
Expand Down
1 change: 1 addition & 0 deletions tests/test_tempfile.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
import shutil

import pytest

from monty.tempfile import ScratchDir

TEST_DIR = os.path.join(os.path.dirname(os.path.abspath(__file__)), "test_files")
Expand Down
Loading