Skip to content

Commit

Permalink
add utils testing and coverage
Browse files Browse the repository at this point in the history
  • Loading branch information
mmahacek committed Jan 10, 2024
1 parent b83102b commit fcdf731
Show file tree
Hide file tree
Showing 5 changed files with 152 additions and 7 deletions.
2 changes: 2 additions & 0 deletions .coveragerc
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
[report]
omit = ./venv*,./tests/*,./examples/*
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
* Revert nodes get functions to default components to `NodeComponents.NONE` instead of `ALL`.
* Added `Enlkind` endpoint and models.
* Update testing/linting configuration.
* Add testing for `utils` methods.

**Full Changelog**: https://github.com/mmahacek/PyONMS/compare/v0.1.2...v0.1.3

Expand Down
21 changes: 14 additions & 7 deletions pyonms/utils/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,14 @@
"""Helper Utilities"""

from collections import OrderedDict
from datetime import datetime, timezone
from datetime import datetime, timezone, tzinfo
from typing import Union

import pytz
import xmltodict

LINK_TIME_PATTERN = "%m/%d/%y, %I:%M:%S %p"


def convert_time(time: int, zone: str = None) -> datetime:
"""Convert epoch to `datetime`"""
Expand All @@ -18,27 +20,32 @@ def convert_time(time: int, zone: str = None) -> datetime:
time_stamp = datetime.fromtimestamp(time / 1000)
if isinstance(zone, str):
time_stamp.replace(tzinfo=pytz.timezone(zone))
elif isinstance(zone, timezone):
elif isinstance(zone, Union[timezone, tzinfo]):
time_stamp.replace(tzinfo=zone)
elif zone:
raise ValueError("Timezone is not a valid type")
return time_stamp
else:
raise ValueError
raise ValueError("Time value not an integer")


def convert_link_time(time: str, zone: Union[str, timezone] = None) -> datetime:
"""Convert enlinkd time to `datetime`"""
if not time:
return None
if isinstance(time, str):
pattern = "%m/%d/%y, %I:%M:%S %p"
link_time = datetime.strptime(time, pattern)
link_time = datetime.strptime(time, LINK_TIME_PATTERN)
if isinstance(zone, str):
link_time.replace(tzinfo=pytz.timezone(zone))
elif isinstance(zone, timezone):
elif isinstance(zone, Union[timezone, tzinfo]):
link_time.replace(tzinfo=zone)
elif zone:
raise ValueError("Timezone is not a valid type")
return link_time
else:
raise ValueError
raise ValueError(
f"time data '{time}' does not match format '{LINK_TIME_PATTERN}'"
)


def convert_xml(data: str) -> dict:
Expand Down
1 change: 1 addition & 0 deletions requirements.txt
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ requests
python-dotenv
pytz
pytest
pytest-cov
pytest-vcr
xmltodict
tqdm
Expand Down
134 changes: 134 additions & 0 deletions tests/test_utils.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,134 @@
# tests.test_utils.py

# pylint: disable=C0114,C0116,W0621,W0212

from collections import OrderedDict
from datetime import datetime
from xml.parsers.expat import ExpatError

import pytest
import pytz

from pyonms import utils


def test_convert_time_null():
assert utils.convert_time(time=None) == None


def test_convert_time_valid():
converted_time = utils.convert_time(time=1704904715000)
assert isinstance(converted_time, datetime)


def test_convert_time_with_zone_valid():
converted_time = utils.convert_time(time=1704904715000, zone="US/Eastern")
assert isinstance(converted_time, datetime)
converted_time = utils.convert_time(
time=1704904715000, zone=pytz.timezone("US/Eastern")
)
assert isinstance(converted_time, datetime)


def test_convert_time_with_zone_invalid():
with pytest.raises(pytz.exceptions.UnknownTimeZoneError, match="'Neverland'"):
utils.convert_time(time=1704904715000, zone="Neverland")
with pytest.raises(ValueError, match="Timezone is not a valid type"):
utils.convert_time(time=1704904715000, zone=1245)


def test_convert_time_invalid():
with pytest.raises(ValueError, match="Time value not an integer"):
utils.convert_time(time="now")


def test_convert_link_time_null():
assert utils.convert_link_time(time=None) == None


def test_convert_link_time_valid():
converted_time = utils.convert_link_time(time="01/01/24, 12:00:00 am")
assert isinstance(converted_time, datetime)


def test_convert_link_time_with_zone_valid():
converted_time = utils.convert_link_time(
time="01/01/24, 12:00:00 am", zone="US/Eastern"
)
assert isinstance(converted_time, datetime)
converted_time = utils.convert_link_time(
time="01/01/24, 12:00:00 am", zone=pytz.timezone("US/Eastern")
)
assert isinstance(converted_time, datetime)


def test_convert_link_time_with_zone_invalid():
with pytest.raises(pytz.exceptions.UnknownTimeZoneError, match="'Neverland'"):
utils.convert_link_time(time="01/01/24, 12:00:00 am", zone="Neverland")
with pytest.raises(ValueError, match="Timezone is not a valid type"):
utils.convert_link_time(time="01/01/24, 12:00:00 am", zone=12345)


def test_convert_link_time_invalid():
time_values = ["now", 1704904715000]
for time_value in time_values:
with pytest.raises(
ValueError,
match=f"time data '{time_value}' does not match format '{utils.LINK_TIME_PATTERN}'",
):
utils.convert_link_time(time=time_value)


def test_convert_xml_valid():
source = '<nodes><node label="name"><interface>int1</interface><interface>int2</interface></node><node label="name2"></node></nodes>'
destination = {
"nodes": {
"node": [
{"interface": ["int1", "int2"], "label": "name"},
{"label": "name2"},
]
}
}
conversion = utils.convert_xml(data=source)
assert isinstance(conversion, dict)
assert conversion == destination


def test_convert_xml_invalid():
with pytest.raises(ExpatError):
assert utils.convert_xml("hello")


def test_normailize_dict():
source = OrderedDict(
{
"nodes": {
"node": [
OrderedDict({"@label": "name", "interface": ["int1", "int2"]}),
OrderedDict({"@label": "name2"}),
]
}
}
)
destination = {
"nodes": {
"node": [
{"label": "name", "interface": ["int1", "int2"]},
{"label": "name2"},
]
}
}

assert utils.normalize_dict(source) == destination
assert utils.normalize_dict(["a", "b"]) == ["a", "b"]
assert utils.normalize_dict(["@a", "@b"]) == ["@a", "@b"]
assert utils.normalize_dict(["a@", "b@"]) == ["a@", "b@"]


def test_normalize_key():
assert utils.normalize_key(key="testing") == "testing"
assert utils.normalize_key(key="this_is_a_test") == "this_is_a_test"
assert utils.normalize_key(key="this-is-a-test") == "this_is_a_test"
assert utils.normalize_key(key="@testing") == "testing"
assert utils.normalize_key(key="@testing@things") == "testing@things"
assert utils.normalize_key(key="testing") == "testing"

0 comments on commit fcdf731

Please sign in to comment.