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

New tests added #82

Closed
wants to merge 11 commits into from
91 changes: 91 additions & 0 deletions tests/test_calc_peak_time_range.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,91 @@
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
Created on Mon Aug 28 13:27:24 2023

@author: claudia
"""

import numpy as np
from ramp.core.stochastic_process import calc_peak_time_range
from ramp.core.core import User
from ramp.core.initialise import initialise_inputs
import pytest


def load_usecase(j=None, fname=None):
peak_enlarge, user_list, num_profiles = initialise_inputs(
j, fname, num_profiles=1
)
return user_list

class TestCalcPeakTimeRange:

# Tests that the peak time range is calculated correctly for a single user class with the default peak_enlarge value
def test_single_user_class_default_peak_enlarge(self):
user_list = [User(maximum_profile=np.array([1, 2, 3, 4, 5]))]
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

User class does not have argument maximum_profile this leads to an error when I run the tests locally. You probably locally changed the User class and forgot to commit and push this change.

peak_time_range = calc_peak_time_range(user_list)
assert isinstance(peak_time_range, np.ndarray)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As the return value of calc_peak_time_range is the return of np.arange() function I don't think it makes sense to test for np.ndarray here

assert peak_time_range.shape[0] > 0
assert peak_time_range.dtype == int
assert np.all(peak_time_range >= 0)

# Tests that the peak time range is calculated correctly for multiple user classes with the default peak_enlarge value
def test_multiple_user_classes_default_peak_enlarge(self):
user_list = [User(maximum_profile=np.array([1, 2, 3, 4, 5])),
User(maximum_profile=np.array([2, 3, 4, 5, 6]))]
peak_time_range = calc_peak_time_range(user_list)
assert isinstance(peak_time_range, np.ndarray)
assert peak_time_range.shape[0] > 0
assert peak_time_range.dtype == int
assert np.all(peak_time_range >= 0)

# Tests that the peak time range is calculated correctly for a single user class with a non-default peak_enlarge value
def test_single_user_class_non_default_peak_enlarge(self):
user_list = [User(maximum_profile=np.array([1, 2, 3, 4, 5]))]
peak_time_range = calc_peak_time_range(user_list, peak_enlarge=0.2)
assert isinstance(peak_time_range, np.ndarray)
assert peak_time_range.shape[0] > 0
assert peak_time_range.dtype == int
assert np.all(peak_time_range >= 0)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Those are the same assert than for all the other tests, shouldn't be the test more specific to the change of peak_enlarge value in this case?


# Tests that the peak time range is calculated correctly for multiple user classes with a non-default peak_enlarge value
def test_multiple_user_classes_non_default_peak_enlarge(self):
user_list = [User(maximum_profile=np.array([1, 2, 3, 4, 5])),
User(maximum_profile=np.array([2, 3, 4, 5, 6]))]
peak_time_range = calc_peak_time_range(user_list, peak_enlarge=0.2)
assert isinstance(peak_time_range, np.ndarray)
assert peak_time_range.shape[0] > 0
assert peak_time_range.dtype == int
assert np.all(peak_time_range >= 0)

# Tests that the peak time range is calculated correctly for a single user class with peak_enlarge=0
def test_single_user_class_peak_enlarge_0(self):
user_list = [User(maximum_profile=np.array([1, 2, 3, 4, 5]))]
peak_time_range = calc_peak_time_range(user_list, peak_enlarge=0)
assert isinstance(peak_time_range, np.ndarray)
assert peak_time_range.shape[0] > 0
assert peak_time_range.dtype == int
assert np.all(peak_time_range >= 0)

# Tests that the peak time range is calculated correctly for multiple user classes with peak_enlarge=0
def test_multiple_user_classes_peak_enlarge_0(self):
user_list = [User(maximum_profile=np.array([1, 2, 3, 4, 5])),
User(maximum_profile=np.array([2, 3, 4, 5, 6]))]
peak_time_range = calc_peak_time_range(user_list, peak_enlarge=0)
assert isinstance(peak_time_range, np.ndarray)
assert peak_time_range.shape[0] > 0
assert peak_time_range.dtype == int
assert np.all(peak_time_range >= 0)

def test_calc_peak_time_range_with_inputs(self):
j=1
peak_enlarge=0.15
user_list=load_usecase(j,peak_enlarge )
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
user_list=load_usecase(j,peak_enlarge )
user_list=load_usecase(j)

#call the function onder test
peak_time_range = calc_peak_time_range(user_list, peak_enlarge)
#perform assertions to validate the output
assert isinstance(peak_time_range, np.ndarray) # Check if the result is a NumPy array
assert peak_time_range.shape[0] > 0 # Check if the result array is not empty
assert peak_time_range.dtype == int # Check if the array contains integers
assert np.all(peak_time_range >= 0) # Check if all values are non-negative
39 changes: 39 additions & 0 deletions tests/test_peak_time_range.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
#!/usr/bin/env python3
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

How is this test different than test_calc_peak_time_range.py::test_calc_peak_time_range_with_inputs ?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks a lot for the review! I think the file [test_peak_time_range.py] was not supposed to be there, the real one was calc_peak_time_range.py. The first one needs to be deleted, sorry!

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No problems, this is what reviews are for :)

# -*- coding: utf-8 -*-
"""
Created on Wed May 31 10:04:56 2023

@author: claudia
"""

import os
import pytest
import numpy as np
import random
import math
from scipy.stats import norm

from ramp.core.core import User, Appliance
from ramp.core.core import UseCase
from ramp.core.initialise import initialise_inputs
from ramp.core.stochastic_process import calc_peak_time_range
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
import os
import pytest
import numpy as np
import random
import math
from scipy.stats import norm
from ramp.core.core import User, Appliance
from ramp.core.core import UseCase
from ramp.core.initialise import initialise_inputs
from ramp.core.stochastic_process import calc_peak_time_range
import numpy as np
from ramp.core.initialise import initialise_inputs
from ramp.core.stochastic_process import calc_peak_time_range

In the suggestion I removed the unused imports


def load_usecase(j=None, fname=None):
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If you reuse the same function several times then define it under tests/utils.py and import it. That way it is easier to maintain the tests on the long term

peak_enlarge, user_list, num_profiles = initialise_inputs(
j, fname, num_profiles=1
)
return user_list

class TestPeakTime:
def test_calc_peak_time_range(self):
j=1
peak_enlarge=0.15
user_list=load_usecase(j,peak_enlarge )
ClaudiaLSS marked this conversation as resolved.
Show resolved Hide resolved
#call the function onder test
peak_time_range = calc_peak_time_range(user_list, peak_enlarge)
#perform assertions to validate the output
assert isinstance(peak_time_range, np.ndarray) # Check if the result is a NumPy array
assert peak_time_range.shape[0] > 0 # Check if the result array is not empty
assert peak_time_range.dtype == int # Check if the array contains integers
assert np.all(peak_time_range >= 0) # Check if all values are non-negative

65 changes: 65 additions & 0 deletions tests/test_rand_total_time_of_use.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
Created on Mon Aug 28 15:40:12 2023

@author: claudia
"""

from ramp.core.utils import random_variation
from ramp.core.core import Appliance
from ramp.core.core import User


import pytest


@pytest.fixture
def appliance_instance():

# Create a User instance (you may need to provide the required arguments for User)
user = User(user_name="Test User", num_users=1)
appliance = Appliance(
user="Test User",
name="Test Appliance",
func_time=100, # Set an appropriate func_time
func_cycle=20,
time_fraction_random_variability=0.1
)
return appliance


# Define the test class for the Appliance class
class TestAppliance:

#Test that the method returns an integer
@pytest.mark.usefixtures("appliance_instance")
def test_returns_integer_value(self, appliance_instance):
result = appliance_instance.rand_total_time_of_use([0, 480], [600, 1080], [1200, 1440])
assert isinstance(result, int)

#Tests that the method returns a value greater than func_cycle
@pytest.mark.usefixtures("appliance_instance")
def test_rand_time_equal_or_greater_than_func_cycle(self, appliance_instance):
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think for such random function the test should run on at least 100 iteration of the method and make sure for none of these call is the rand_time < func_cycle

# Define windows with total available time
rand_window_1 = [0, 100]
rand_window_2 = [200, 300]
rand_window_3 = [400, 500]
appliance_instance.func_cycle = 50
# Call the method from the class
rand_time = appliance_instance.rand_total_time_of_use(rand_window_1, rand_window_2, rand_window_3)
assert rand_time >= appliance_instance.func_cycle, 'rand_time is not greater than func_cycle'

# Tests that the method returns a value less than or equal to 0.99 * total_time
@pytest.mark.usefixtures("appliance_instance")
def test_rand_time_less_than_99_percent_total_time(self, appliance_instance):
rand_window_1 = [0, 100]
rand_window_2 = [200, 300]
rand_window_3 = [400, 500]
appliance_instance.func_time = 200
appliance_instance.time_fraction_random_variability = 0.5
# Call the method from the class
rand_time = appliance_instance.rand_total_time_of_use(rand_window_1, rand_window_2, rand_window_3)
total_time = (rand_window_1[1] - rand_window_1[0]) + (rand_window_2[1] - rand_window_2[0]) + (rand_window_3[1] - rand_window_3[0])
assert rand_time <= 0.99 * total_time

56 changes: 56 additions & 0 deletions tests/test_switch_on.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
Created on Tue Sep 5 10:47:58 2023

@author: claudia
"""

from ramp.core.core import Appliance


import pytest

class TestRandSwitchOnWindow:

# Tests that the method returns a list of indexes within the available functioning windows when there are multiple available functioning windows and the random time is larger than the duration of the appliance's function cycle.
def test_happy_path(self):
appliance = Appliance(user=None, func_cycle=2)
appliance.free_spots = [slice(0, 5), slice(10, 15)]
indexes = appliance.rand_switch_on_window(rand_time=6)
assert all(index in range(0, 5) or index in range(10, 15) for index in indexes)

# Tests that the method returns None when there are no available functioning windows.
def test_edge_case_no_windows(self):
appliance = Appliance(user=None, func_cycle=2)
appliance.free_spots = []
indexes = appliance.rand_switch_on_window(rand_time=6)
assert indexes is None

# Tests that the method returns None when the available functioning window is smaller than the duration of the appliance's function cycle.
def test_edge_case_small_window(self):
appliance = Appliance(user=None, func_cycle=5)
appliance.free_spots = [slice(0, 3)]
indexes = appliance.rand_switch_on_window(rand_time=6)
assert indexes is None

# Tests that the method returns a list of indexes within the available functioning window when the available functioning window is equal to the duration of the appliance's function cycle.
def test_edge_case_equal_window(self):
appliance = Appliance(user=None, func_cycle=5)
appliance.free_spots = [slice(0, 5)]
indexes = appliance.rand_switch_on_window(rand_time=6)
assert all(index in range(0, 5) for index in indexes)

# Tests that the method returns a list of indexes within the available functioning window when the available functioning window is larger than the duration of the appliance's function cycle.
def test_edge_case_large_window(self):
appliance = Appliance(user=None, func_cycle=2)
appliance.free_spots = [slice(0, 10)]
indexes = appliance.rand_switch_on_window(rand_time=6)
assert all(index in range(0, 10) for index in indexes)

# Tests that the method returns a list of indexes within the available functioning windows when the appliance has multiple free spots.
def test_edge_case_multiple_free_spots(self):
appliance = Appliance(user=None, func_cycle=2)
appliance.free_spots = [slice(0, 5), slice(10, 15), slice(20, 25)]
indexes = appliance.rand_switch_on_window(rand_time=6)
assert all(index in range(0, 5) or index in range(10, 15) or index in range(20, 25) for index in indexes)