8000 Check Functions do not display datetime comparisons helpfully · Issue #98 · PyFixate/Fixate · GitHub
[go: up one dir, main page]
More Web Proxy on the site http://driver.im/
Skip to content

Check Functions do not display datetime comparisons helpfully #98

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

Open
pazzarpj opened this issue Apr 1, 2019 · 7 comments
Open

Check Functions do not display datetime comparisons helpfully #98

pazzarpj opened this issue Apr 1, 2019 · 7 comments

Comments

@pazzarpj
Copy link
Collaborator
pazzarpj commented Apr 1, 2019

Comparing datetime functions in a chk_* will show .3g instead of the repr for the datetime object. This could overflow into other object time comparisons that are not float or integer based.

@christopherwallis
Copy link
Collaborator

Had a go at replicating this issue but without any luck. Ended up writing some tests for chk_smaller.
They're in my fix-time-checks fork in Fixate/test/core/test_checks.py if it helps.

@clint-lawrence
8000
Copy link
Collaborator

@pazzarpj, have you got a script that shows the error? or can you write a failing test?

@pazzarpj
Copy link
Collaborator Author
pazzarpj commented Apr 5, 2019
from datetime import datetime, timedelta
from fixate.core.checks import CheckClass, _in_range
from fixate.ui_cmdline.cmd_line import _print_comparisons
chk1 = CheckClass(_min=2, _max=3, test_val=2.5, target=_in_range)
date_thing = datetime(2019, 1, 1, 0, 0)
chk2 = CheckClass(_min=date_thing - timedelta(seconds=2), _max=datetime.now() + timedelta(seconds=2), test_val=date_thing, target=_in_range)

_print_comparisons(True, chk1, 1, None)
_print_comparisons(True, chk2, 2, None)

Expected output

Check 1: PASS when comparing 2.5 in range 2 - 3 :
Check 2: PASS when comparing 2019-01-01 00:00:00 in range 2018-12-31 23:59:58 - 2019-01-01 00:00:02 :

Actual

Check 1: PASS when comparing 2.5 in range 2 - 3 :
Check 2: PASS when comparing .3g in range .3g - .3g :

@christopherwallis
Copy link
Collaborator

There seems to be an issue with timestruct objects as well in that script. They're displayed with their data but always pass:

t = time.localtime(time.time())
chk3 = CheckClass(_min=time.localtime(1545925760), _max=time.localtime(1545925777), test_val=t, target=_in_range)

_print_comparisons(True, chk3, 3, None)
Check 3: PASS when comparing time.struct_time(tm_year=2019, tm_mon=4,
tm_mday=5, tm_hour=19, tm_min=50, tm_sec=33, tm_wday=4, tm_yday=95,
tm_isdst=1) in range time.struct_time(tm_year=2018, tm_mon=12, tm_mday=28,
tm_hour=2, tm_min=49, tm_sec=20, tm_wday=4, tm_yday=362, tm_isdst=1) -
time.struct_time(tm_year=2018, tm_mon=12, tm_mday=28, tm_hour=2, tm_min=49,
tm_sec=37, tm_wday=4, tm_yday=362, tm_isdst=1)

However the issue doesn't seem to occur when using chk_in_range for either timestruct or datetime objects as the following tests pass:

def test_time_struct_check_true():
    t = time.localtime(1545925765)
    chk = chk_in_range(t, time.localtime(1545925760), time.localtime(1545925777), "Time is in range")
    assert chk


def test_time_struct_check_false():
    with pytest.raises(CheckFail):
        t = time.localtime(1554452763)
        chk = chk_in_range(t, time.localtime(1545925760), time.localtime(1545925777), "Time is NOT in range")


def test_datetime_struct_check_true():
    t_min = datetime.now()
    time.sleep(1)
    t = datetime.now()
    time.sleep(1)
    t_max = datetime.now()
    chk = chk_in_range(t, t_min, t_max, "DateTime is in range")
    assert chk


def test_datetime_struct_check_false():
    with pytest.raises(CheckFail):
        t_min = datetime.now()
        time.sleep(1)
        t_max = datetime.now()
        time.sleep(1)
        t = datetime.now()
        chk = chk_in_range(t, t_min, t_max, "DateTime is not in range")
        assert chk

@pazzarpj
Copy link
Collaborator Author
pazzarpj commented Apr 5, 2019

The script I provided was to demonstrate the display issue, the CheckClass doesn't actually run the check.

_print_comparisons first parameter determines if it displays as pass/fail.

The issue is that the _print_comparisons function assumes a number with the {:.3g} string formatter.

@christopherwallis
Copy link
Collaborator

Riiight, i finally get it now. I'll stop barking up the wrong tree. Will look into it when i get a chance. Thanks for slow walking me there.

@christopherwallis
Copy link
Collaborator

Issue found in ui_cmdline\cmd_line.py line 304:

def round_to_3_sig_figures(chk):
    """
    Tries to round elements to 3 significant figures for formatting
    :param chk:
    :return:
    """
    ret_dict = {}
    for element in ["_min", "_max", "test_val", "nominal", "tol"]:
        ret_dict[element] = getattr(chk, element, None)
        try:
            ret_dict[element] = "{:.3g}".format(ret_dict[element])
        except:
            pass
    return ret_dict

format with decimal places does not produce the desired output but does not raise an error when datetime object is used.

Adding an assert math.isclose within the try: rejects the change of format, allowing the original formatting (standard datetime object output) to be shown:

Check 1: PASS when comparing 2.5 in range 2 - 3 :

Check 2: PASS when comparing 2019-01-01 00:00:00 in range 2018-12-31
23:59:58 - 2019-04-08 21:52:25.021197 :

Will run a few more tests and upload the code.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants
0