1158 lines
41 KiB
Python
1158 lines
41 KiB
Python
import unittest
|
|
from unittest.mock import MagicMock
|
|
|
|
from helix.calculators.ebom_calculator import EbomCalculator, ModuleType
|
|
from helix.constants.inverter_type import InverterType
|
|
from helix.constants.parts import *
|
|
from helix.constants.system_type import SystemType
|
|
from test.test_helpers import assert_dictionary_equal
|
|
|
|
|
|
class EbomCalculatorTest(unittest.TestCase):
|
|
def setUp(self):
|
|
self.user_values = MagicMock()
|
|
self.subject = EbomCalculator(self.user_values, 171, 98)
|
|
|
|
def test_computes_ebom_without_aux_plugs(self):
|
|
self.user_values.power_stations.return_value = [
|
|
{
|
|
'power_station_id': '1',
|
|
'power_station_description': 'Panel Board 1',
|
|
'power_station_quantity': 1,
|
|
'ac_run_length': 109,
|
|
'inverter_quantity': 2,
|
|
'inverters': [
|
|
{
|
|
'model': InverterType.SMA.MODEL_12KW,
|
|
'strings_per_inverter': 2,
|
|
'sunshade': False,
|
|
'dc_switch': True,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_15KW,
|
|
'strings_per_inverter': 5,
|
|
'sunshade': True,
|
|
'dc_switch': False,
|
|
}
|
|
]
|
|
},
|
|
{
|
|
'power_station_id': '2',
|
|
'power_station_description': 'Panel Board 2',
|
|
'power_station_quantity': 3,
|
|
'ac_run_length': 355,
|
|
'inverter_quantity': 4,
|
|
'inverters': [
|
|
{
|
|
'model': InverterType.SMA.MODEL_20KW,
|
|
'strings_per_inverter': 6,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 7,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
}
|
|
]
|
|
}
|
|
]
|
|
self.user_values.standalone_inverters.return_value = [
|
|
{
|
|
'standalone_inverter_id': 'key_1',
|
|
'ac_run_length': 57,
|
|
'model': InverterType.SMA.MODEL_20KW,
|
|
'strings_per_inverter': 5,
|
|
'sunshade': True,
|
|
'dc_switch': False,
|
|
'attachment_point': ('Panel Board 1', '1')
|
|
},
|
|
{
|
|
'standalone_inverter_id': 'key_2',
|
|
'ac_run_length': 200,
|
|
'model': InverterType.SMA.MODEL_12KW,
|
|
'strings_per_inverter': 3,
|
|
'sunshade': False,
|
|
'dc_switch': True,
|
|
'attachment_point': ('Switch Gear', None)
|
|
},
|
|
{
|
|
'standalone_inverter_id': 'key_3',
|
|
'ac_run_length': 0,
|
|
'model': InverterType.SMA.MODEL_12KW,
|
|
'strings_per_inverter': 3,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
'attachment_point': ('Panel Board 1', '1')
|
|
},
|
|
]
|
|
|
|
self.user_values.power_monitors.return_values = []
|
|
|
|
self.user_values.system_type.return_value = SystemType.dualTilt
|
|
self.user_values.module_type.return_value = ModuleType.Cell96
|
|
expected_output = {
|
|
flat_washer: 100,
|
|
star_washer: 12,
|
|
channel_nut: 16,
|
|
phillips_screw: 12,
|
|
hex_nut_quarter_20: 8,
|
|
hex_nut_three_eighths_16: 100,
|
|
flat_washer_quarter_inch: 8,
|
|
flat_washer_6: 12,
|
|
hex_bolt_quarter_20: 8,
|
|
stump: 102+181,
|
|
wire_clip_large: 2907,
|
|
cable_support_lid: 368,
|
|
cable_support: 368,
|
|
rear_skirt: -140,
|
|
dc_switch_bracket: 2,
|
|
front_legs: 23,
|
|
back_legs: 23,
|
|
inverter_link: 46,
|
|
inverter_rail: 23,
|
|
sma_20kw_inverter: 4,
|
|
sunshade: 2,
|
|
hex_bolt_3_4: 50,
|
|
panel_board_4: 4,
|
|
ac_inverter_bracket: 3,
|
|
rubber_foot: 69,
|
|
harness_3_string_fm: 13,
|
|
harness_3_string_mf: 13,
|
|
harness_2_string_fm: 3,
|
|
harness_2_string_mf: 3,
|
|
harness_4_string_fm: 15,
|
|
harness_4_string_mf: 15,
|
|
harness_ac_inner: 8,
|
|
harness_ac_outer: 8,
|
|
sma_24kw_inverter: 9,
|
|
sma_12kw_inverter: 3,
|
|
sma_15kw_inverter: 1,
|
|
comm_cable: 12,
|
|
dc_switch_box: 2,
|
|
hex_bolt_1_2: 362,
|
|
whip_tray: 19,
|
|
ac_switch: 3,
|
|
ac_splice_box: 2,
|
|
ethernet_plug: 12.600000000000001,
|
|
mounting_back_plate: 23,
|
|
sunshade_bolt: 4,
|
|
sunshade_washer: 4,
|
|
}
|
|
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output)
|
|
|
|
def test_computes_ebom_with_delta_inverters(self):
|
|
self.user_values.standalone_inverters.return_value = [
|
|
{
|
|
'standalone_inverter_id': 'key_1',
|
|
'ac_run_length': 57,
|
|
'model': InverterType.DELTA.MODEL_36KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
'splice_box': True,
|
|
'attachment_point': ('Switch Gear', None)
|
|
},
|
|
{
|
|
'standalone_inverter_id': 'key_2',
|
|
'ac_run_length': 200,
|
|
'model': InverterType.DELTA.MODEL_42KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
'splice_box': False,
|
|
'attachment_point': ('Switch Gear', None)
|
|
},
|
|
{
|
|
'standalone_inverter_id': 'key_3',
|
|
'ac_run_length': 0,
|
|
'model': InverterType.DELTA.MODEL_60KW,
|
|
'strings_per_inverter': 12,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
'splice_box': True,
|
|
'attachment_point': ('Switch Gear', None)
|
|
},
|
|
]
|
|
|
|
self.user_values.system_type.return_value = SystemType.singleTilt
|
|
self.user_values.module_type.return_value = ModuleType.Cell96
|
|
expected_output = {
|
|
stump: 65,
|
|
wire_clip_large: 513,
|
|
cable_support_lid: 0,
|
|
cable_support: 0,
|
|
rear_skirt: 0,
|
|
rubber_foot: 9,
|
|
delta_inverter_leg: 9,
|
|
harness_4_string_mf: 4,
|
|
harness_4_string_fm: 4,
|
|
delta_36kw_inverter: 1,
|
|
delta_42kw_inverter: 1,
|
|
delta_60kw_inverter: 1,
|
|
delta_splice_box: 2,
|
|
delta_kit_inverter_mount: 3,
|
|
}
|
|
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output)
|
|
|
|
def test_computes_ebom_with_delta_inverters_dual_tilt(self):
|
|
self.user_values.standalone_inverters.return_value = [
|
|
{
|
|
'standalone_inverter_id': 'key_1',
|
|
'ac_run_length': 0,
|
|
'model': InverterType.DELTA.MODEL_42KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
'splice_box': False,
|
|
'attachment_point': ('Switch Gear', None)
|
|
},
|
|
]
|
|
|
|
self.user_values.system_type.return_value = SystemType.dualTilt
|
|
self.user_values.module_type.return_value = ModuleType.Cell96
|
|
expected_output = {
|
|
stump: 0,
|
|
wire_clip_large: 171,
|
|
cable_support_lid: 0,
|
|
cable_support: 0,
|
|
rear_skirt: 0,
|
|
rubber_foot: 3,
|
|
delta_inverter_leg: 3,
|
|
harness_4_string_mf: 2,
|
|
harness_4_string_fm: 2,
|
|
delta_42kw_inverter: 1,
|
|
delta_kit_inverter_mount_dt: 1,
|
|
}
|
|
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output)
|
|
|
|
def test_computes_ebom_with_aux_plugs(self):
|
|
self.user_values.power_stations.return_value = [
|
|
{
|
|
'power_station_description': 'Panel Board 1',
|
|
'power_station_id': 'panel_board_uuid_1',
|
|
'power_station_quantity': 1,
|
|
'ac_run_length': 0,
|
|
'inverter_quantity': 2,
|
|
'inverters': [
|
|
{
|
|
'model': InverterType.SMA.MODEL_12KW,
|
|
'strings_per_inverter': 2,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_15KW,
|
|
'strings_per_inverter': 5,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
}
|
|
]
|
|
},
|
|
{
|
|
'power_station_description': 'Panel Board 2',
|
|
'power_station_id': 'panel_board_uuid_2',
|
|
'power_station_quantity': 2,
|
|
'ac_run_length': 0,
|
|
'inverter_quantity': 4,
|
|
'inverters': [
|
|
{
|
|
'model': InverterType.SMA.MODEL_20KW,
|
|
'strings_per_inverter': 6,
|
|
'sunshade': True,
|
|
'dc_switch': True,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': True,
|
|
'dc_switch': True,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 7,
|
|
'sunshade': False,
|
|
'dc_switch': True,
|
|
}
|
|
]
|
|
},
|
|
{
|
|
'power_station_description': 'Panel Board 2 (aux)',
|
|
'power_station_id': 'panel_board_uuid_2_aux',
|
|
'power_station_quantity': 1,
|
|
'monitor_id': 'foo',
|
|
'ac_run_length': 0,
|
|
'inverter_quantity': 4,
|
|
'inverters': [
|
|
{
|
|
'model': InverterType.SMA.MODEL_20KW,
|
|
'strings_per_inverter': 6,
|
|
'sunshade': True,
|
|
'dc_switch': True,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': True,
|
|
'dc_switch': True,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 7,
|
|
'sunshade': False,
|
|
'dc_switch': True,
|
|
}
|
|
]
|
|
}
|
|
]
|
|
self.user_values.power_monitors.return_value = [{
|
|
'monitor_id': 'foo',
|
|
'power_source': ('Panel Board 2 (aux)', 'panel_board_uuid_2_aux')
|
|
}]
|
|
self.user_values.system_type.return_value = SystemType.dualTilt
|
|
self.user_values.module_type.return_value = ModuleType.Cell96
|
|
# 9 dc switches
|
|
expected_output = {
|
|
flat_washer: 76,
|
|
channel_nut: 20,
|
|
hex_nut_quarter_20: 36,
|
|
hex_nut_three_eighths_16: 102,
|
|
flat_washer_quarter_inch: 36,
|
|
hex_bolt_quarter_20: 36,
|
|
monitor_controller_480_v: 1,
|
|
stump: 84,
|
|
dc_switch_bracket: 9,
|
|
front_legs: 19,
|
|
back_legs: 19,
|
|
inverter_link: 38,
|
|
inverter_rail: 19,
|
|
sma_20kw_inverter: 3,
|
|
sunshade: 6,
|
|
hex_bolt_3_4: 64,
|
|
panel_board_4: 2,
|
|
panel_board_4_aux: 1,
|
|
panel_board_2: 1,
|
|
rubber_foot: 57,
|
|
harness_3_string_fm: 10,
|
|
harness_3_string_mf: 10,
|
|
harness_2_string_fm: 2,
|
|
harness_2_string_mf: 2,
|
|
harness_4_string_fm: 15,
|
|
harness_4_string_mf: 15,
|
|
harness_ac_inner: 8,
|
|
harness_ac_outer: 6,
|
|
sma_24kw_inverter: 9,
|
|
sma_12kw_inverter: 1,
|
|
sma_15kw_inverter: 1,
|
|
comm_cable: 11,
|
|
dc_switch_box: 9,
|
|
hex_bolt_1_2: 297,
|
|
whip_tray: 14,
|
|
mounting_back_plate: 19,
|
|
wire_clip_large: 2394,
|
|
cable_support: 270,
|
|
cable_support_lid: 270,
|
|
rear_skirt: -103,
|
|
ethernet_plug: 7.2,
|
|
monitor_power_plug: 1,
|
|
sunshade_bolt: 12,
|
|
sunshade_washer: 12,
|
|
}
|
|
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output)
|
|
|
|
def test_computes_ebom_with_aux_plugs_on_switchgear(self):
|
|
self.user_values.power_stations.return_value = [
|
|
{
|
|
'power_station_description': 'Panel Board 1',
|
|
'power_station_id': 'panel_board_uuid_1',
|
|
'power_station_quantity': 1,
|
|
'ac_run_length': 0,
|
|
'inverter_quantity': 2,
|
|
'inverters': [
|
|
{
|
|
'model': InverterType.SMA.MODEL_12KW,
|
|
'strings_per_inverter': 2,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_15KW,
|
|
'strings_per_inverter': 5,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
}
|
|
]
|
|
},
|
|
{
|
|
'power_station_description': 'Panel Board 2',
|
|
'power_station_id': 'panel_board_uuid_2',
|
|
'power_station_quantity': 3,
|
|
'ac_run_length': 0,
|
|
'inverter_quantity': 4,
|
|
'inverters': [
|
|
{
|
|
'model': InverterType.SMA.MODEL_20KW,
|
|
'strings_per_inverter': 6,
|
|
'sunshade': True,
|
|
'dc_switch': True,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': True,
|
|
'dc_switch': True,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 7,
|
|
'sunshade': False,
|
|
'dc_switch': True,
|
|
}
|
|
]
|
|
}
|
|
]
|
|
self.user_values.power_monitors.return_value = [{
|
|
'monitor_id': 'foo',
|
|
'power_source': ('Switch Gear/External', None)
|
|
}]
|
|
self.user_values.system_type.return_value = SystemType.dualTilt
|
|
self.user_values.module_type.return_value = ModuleType.Cell96
|
|
# 9 dc switches
|
|
expected_output = {
|
|
flat_washer: 76,
|
|
channel_nut: 20,
|
|
hex_nut_quarter_20: 36,
|
|
hex_nut_three_eighths_16: 102,
|
|
flat_washer_quarter_inch: 36,
|
|
hex_bolt_quarter_20: 36,
|
|
monitor_controller_480_v: 1,
|
|
stump: 84,
|
|
dc_switch_bracket: 9,
|
|
front_legs: 19,
|
|
back_legs: 19,
|
|
inverter_link: 38,
|
|
inverter_rail: 19,
|
|
sma_20kw_inverter: 3,
|
|
sunshade: 6,
|
|
hex_bolt_3_4: 64,
|
|
panel_board_4: 3,
|
|
panel_board_2: 1,
|
|
rubber_foot: 57,
|
|
harness_3_string_fm: 10,
|
|
harness_3_string_mf: 10,
|
|
harness_2_string_fm: 2,
|
|
harness_2_string_mf: 2,
|
|
harness_4_string_fm: 15,
|
|
harness_4_string_mf: 15,
|
|
harness_ac_inner: 8,
|
|
harness_ac_outer: 6,
|
|
sma_24kw_inverter: 9,
|
|
sma_12kw_inverter: 1,
|
|
sma_15kw_inverter: 1,
|
|
comm_cable: 10,
|
|
dc_switch_box: 9,
|
|
hex_bolt_1_2: 297,
|
|
whip_tray: 14,
|
|
mounting_back_plate: 19,
|
|
wire_clip_large: 2394,
|
|
cable_support: 270,
|
|
cable_support_lid: 270,
|
|
rear_skirt: -103,
|
|
ethernet_plug: 7.2,
|
|
monitor_power_plug: 1,
|
|
sunshade_bolt: 12,
|
|
sunshade_washer: 12,
|
|
}
|
|
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output)
|
|
|
|
def test_computes_ebom_with_aux_plugs_on_switchgear_on_pseries_dual_tilt(self):
|
|
self.user_values.power_stations.return_value = [
|
|
{
|
|
'power_station_description': 'Panel Board 1',
|
|
'power_station_id': 'panel_board_uuid_1',
|
|
'power_station_quantity': 1,
|
|
'ac_run_length': 0,
|
|
'inverter_quantity': 2,
|
|
'inverters': [
|
|
{
|
|
'model': InverterType.SMA.MODEL_12KW,
|
|
'strings_per_inverter': 2,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_15KW,
|
|
'strings_per_inverter': 5,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
}
|
|
]
|
|
},
|
|
{
|
|
'power_station_description': 'Panel Board 2',
|
|
'power_station_id': 'panel_board_uuid_2',
|
|
'power_station_quantity': 3,
|
|
'ac_run_length': 0,
|
|
'inverter_quantity': 4,
|
|
'inverters': [
|
|
{
|
|
'model': InverterType.SMA.MODEL_20KW,
|
|
'strings_per_inverter': 6,
|
|
'sunshade': True,
|
|
'dc_switch': True,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': True,
|
|
'dc_switch': True,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 7,
|
|
'sunshade': False,
|
|
'dc_switch': True,
|
|
}
|
|
]
|
|
}
|
|
]
|
|
self.user_values.power_monitors.return_value = [{
|
|
'monitor_id': 'foo',
|
|
'power_source': ('Switch Gear/External', None)
|
|
}]
|
|
self.user_values.system_type.return_value = SystemType.dualTilt
|
|
self.user_values.module_type.return_value = ModuleType.PSeries
|
|
# 9 dc switches
|
|
expected_output = {
|
|
flat_washer: 132,
|
|
channel_nut: 20,
|
|
hex_nut_quarter_20: 36,
|
|
hex_nut_three_eighths_16: 130,
|
|
flat_washer_quarter_inch: 36,
|
|
hex_bolt_quarter_20: 36,
|
|
monitor_controller_480_v: 1,
|
|
stump: 84,
|
|
dc_switch_bracket: 9,
|
|
front_legs: 19,
|
|
back_legs: 19,
|
|
inverter_link: 38,
|
|
inverter_rail: 19,
|
|
sma_20kw_inverter: 3,
|
|
sunshade: 6,
|
|
hex_bolt_3_4: 106,
|
|
panel_board_4: 3,
|
|
panel_board_2: 1,
|
|
rubber_foot: 57,
|
|
harness_3_string_fm: 10,
|
|
harness_3_string_mf: 10,
|
|
harness_2_string_fm: 2,
|
|
harness_2_string_mf: 2,
|
|
harness_4_string_fm: 15,
|
|
harness_4_string_mf: 15,
|
|
harness_ac_inner: 8,
|
|
harness_ac_outer: 6,
|
|
sma_24kw_inverter: 9,
|
|
sma_12kw_inverter: 1,
|
|
sma_15kw_inverter: 1,
|
|
comm_cable: 10,
|
|
dc_switch_box: 9,
|
|
hex_bolt_1_2: 297,
|
|
whip_tray: 14,
|
|
mounting_back_plate: 19,
|
|
wire_clip_large: 2394,
|
|
cable_support: 270,
|
|
cable_support_lid: 270,
|
|
rear_skirt: -103,
|
|
ethernet_plug: 7.2,
|
|
monitor_power_plug: 1,
|
|
fuseshade: 14,
|
|
screw_12_24x1_25: 28,
|
|
fuseshade_brace: 14,
|
|
sunshade_bolt: 12,
|
|
sunshade_washer: 12,
|
|
}
|
|
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output)
|
|
|
|
def test_computes_ebom_with_power_monitor_DELTA_brand(self):
|
|
self.user_values.inverter_brands.return_value = [{'inverter_brand_id':2}]
|
|
self.user_values.power_monitors.return_value = [{
|
|
'monitor_id': 'foo',
|
|
'power_source': ('Switch Gear/External', None)
|
|
}]
|
|
self.user_values.system_type.return_value = SystemType.singleTilt
|
|
self.user_values.module_type.return_value = ModuleType.Cell96
|
|
|
|
expected_output = {
|
|
monitor_power_plug: 1,
|
|
stump: 0,
|
|
cable_support: 0,
|
|
cable_support_lid: 0,
|
|
rear_skirt: 0,
|
|
monitor_controller_480_v:1,
|
|
}
|
|
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output)
|
|
|
|
def test_computes_ebom_with_power_monitor_SMA_brand(self):
|
|
self.user_values.inverter_brands.return_value = [{'inverter_brand_id':1}]
|
|
self.user_values.power_monitors.return_value = [{
|
|
'monitor_id': 'foo',
|
|
'power_source': ('Switch Gear/External', None)
|
|
}]
|
|
self.user_values.system_type.return_value = SystemType.singleTilt
|
|
self.user_values.module_type.return_value = ModuleType.Cell96
|
|
|
|
expected_output = {
|
|
monitor_power_plug: 1,
|
|
stump: 0,
|
|
cable_support: 0,
|
|
cable_support_lid: 0,
|
|
rear_skirt: 0,
|
|
monitor_controller_480_v:1,
|
|
flat_washer: 4,
|
|
channel_nut: 4,
|
|
hex_nut_three_eighths_16: 2,
|
|
front_legs: 1,
|
|
back_legs: 1,
|
|
inverter_link: 2,
|
|
inverter_rail: 1,
|
|
rubber_foot: 3,
|
|
hex_bolt_1_2: 9,
|
|
mounting_back_plate: 1,
|
|
}
|
|
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output)
|
|
|
|
def test_computes_ebom_with_aux_plugs_on_switchgear_on_pseries_single_tilt(self):
|
|
self.user_values.power_stations.return_value = [
|
|
{
|
|
'power_station_description': 'Panel Board 1',
|
|
'power_station_id': 'panel_board_uuid_1',
|
|
'power_station_quantity': 1,
|
|
'ac_run_length': 0,
|
|
'inverter_quantity': 2,
|
|
'inverters': [
|
|
{
|
|
'model': InverterType.SMA.MODEL_12KW,
|
|
'strings_per_inverter': 2,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_15KW,
|
|
'strings_per_inverter': 5,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
}
|
|
]
|
|
},
|
|
{
|
|
'power_station_description': 'Panel Board 2',
|
|
'power_station_id': 'panel_board_uuid_2',
|
|
'power_station_quantity': 3,
|
|
'ac_run_length': 0,
|
|
'inverter_quantity': 4,
|
|
'inverters': [
|
|
{
|
|
'model': InverterType.SMA.MODEL_20KW,
|
|
'strings_per_inverter': 6,
|
|
'sunshade': True,
|
|
'dc_switch': True,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': True,
|
|
'dc_switch': True,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 7,
|
|
'sunshade': False,
|
|
'dc_switch': True,
|
|
}
|
|
]
|
|
}
|
|
]
|
|
self.user_values.power_monitors.return_value = [{
|
|
'monitor_id': 'foo',
|
|
'power_source': ('Switch Gear/External', None)
|
|
}]
|
|
self.user_values.system_type.return_value = SystemType.singleTilt
|
|
self.user_values.module_type.return_value = ModuleType.PSeries
|
|
# 9 dc switches
|
|
expected_output = {
|
|
flat_washer: 132,
|
|
channel_nut: 20,
|
|
hex_nut_quarter_20: 36,
|
|
hex_nut_three_eighths_16: 130,
|
|
flat_washer_quarter_inch: 36,
|
|
hex_bolt_quarter_20: 36,
|
|
monitor_controller_480_v: 1,
|
|
stump: 84,
|
|
dc_switch_bracket: 9,
|
|
front_legs: 19,
|
|
back_legs: 19,
|
|
inverter_link: 24,
|
|
inverter_rail: 19,
|
|
inverter_link_long: 7,
|
|
inverter_link_short: 7,
|
|
sma_20kw_inverter: 3,
|
|
sunshade: 6,
|
|
hex_bolt_3_4: 106,
|
|
panel_board_4: 3,
|
|
panel_board_2: 1,
|
|
rubber_foot: 57,
|
|
harness_3_string_fm: 10,
|
|
harness_3_string_mf: 10,
|
|
harness_2_string_fm: 2,
|
|
harness_2_string_mf: 2,
|
|
harness_4_string_fm: 15,
|
|
harness_4_string_mf: 15,
|
|
harness_ac_inner: 8,
|
|
harness_ac_outer: 6,
|
|
sma_24kw_inverter: 9,
|
|
sma_12kw_inverter: 1,
|
|
sma_15kw_inverter: 1,
|
|
comm_cable: 10,
|
|
dc_switch_box: 9,
|
|
hex_bolt_1_2: 297,
|
|
whip_tray: 14,
|
|
mounting_back_plate: 19,
|
|
wire_clip_large: 2394,
|
|
cable_support: 694,
|
|
cable_support_lid: 694,
|
|
rear_skirt: -264,
|
|
ethernet_plug: 7.2,
|
|
monitor_power_plug: 1,
|
|
fuseshade: 14,
|
|
screw_12_24x1_25: 28,
|
|
fuseshade_brace: 14,
|
|
sunshade_bolt: 12,
|
|
sunshade_washer: 12,
|
|
}
|
|
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output)
|
|
|
|
def test_computes_monitor_type_with_aux_plugs(self):
|
|
self.user_values.power_stations.return_value = [
|
|
{
|
|
'power_station_description': 'Panel Board 1',
|
|
'power_station_id': 'panel_board_uuid_1',
|
|
'power_station_quantity': 1,
|
|
'ac_run_length': 0,
|
|
'inverter_quantity': 2,
|
|
'inverters': [
|
|
{
|
|
'model': InverterType.SMA.MODEL_12KW,
|
|
'strings_per_inverter': 2,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_15KW,
|
|
'strings_per_inverter': 5,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
}
|
|
]
|
|
},
|
|
{
|
|
'power_station_description': 'Panel Board 2',
|
|
'power_station_id': 'panel_board_uuid_2',
|
|
'power_station_quantity': 2,
|
|
'ac_run_length': 0,
|
|
'inverter_quantity': 4,
|
|
'inverters': [
|
|
{
|
|
'model': InverterType.SMA.MODEL_20KW,
|
|
'strings_per_inverter': 6,
|
|
'sunshade': True,
|
|
'dc_switch': True,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': True,
|
|
'dc_switch': True,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 7,
|
|
'sunshade': False,
|
|
'dc_switch': True,
|
|
}
|
|
]
|
|
},
|
|
{
|
|
'power_station_description': 'Panel Board 2 (aux)',
|
|
'power_station_id': 'panel_board_uuid_2_aux',
|
|
'power_station_quantity': 1,
|
|
'monitor_id': 'foo',
|
|
'ac_run_length': 0,
|
|
'inverter_quantity': 4,
|
|
'inverters': [
|
|
{
|
|
'model': InverterType.SMA.MODEL_20KW,
|
|
'strings_per_inverter': 6,
|
|
'sunshade': True,
|
|
'dc_switch': True,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': True,
|
|
'dc_switch': True,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 8,
|
|
'sunshade': False,
|
|
'dc_switch': False,
|
|
},
|
|
{
|
|
'model': InverterType.SMA.MODEL_24KW,
|
|
'strings_per_inverter': 7,
|
|
'sunshade': False,
|
|
'dc_switch': True,
|
|
}
|
|
]
|
|
}
|
|
]
|
|
self.user_values.power_monitors.return_value = [{
|
|
'monitor_id': 'foo',
|
|
'power_source': ('Panel Board 2 (aux)', 'panel_board_uuid_2_aux')
|
|
}]
|
|
|
|
self.user_values.system_type.return_value = SystemType.dualTilt
|
|
|
|
# 9 dc switches
|
|
expected_output_480 = {
|
|
flat_washer: 76,
|
|
channel_nut: 20,
|
|
hex_nut_quarter_20: 36,
|
|
hex_nut_three_eighths_16: 102,
|
|
flat_washer_quarter_inch: 36,
|
|
hex_bolt_quarter_20: 36,
|
|
monitor_controller_480_v: 1,
|
|
stump: 84,
|
|
dc_switch_bracket: 9,
|
|
front_legs: 19,
|
|
back_legs: 19,
|
|
inverter_link: 38,
|
|
inverter_rail: 19,
|
|
sma_20kw_inverter: 3,
|
|
sunshade: 6,
|
|
hex_bolt_3_4: 64,
|
|
panel_board_4: 2,
|
|
panel_board_4_aux: 1,
|
|
panel_board_2: 1,
|
|
rubber_foot: 57,
|
|
harness_3_string_fm: 10,
|
|
harness_3_string_mf: 10,
|
|
harness_2_string_fm: 2,
|
|
harness_2_string_mf: 2,
|
|
harness_4_string_fm: 15,
|
|
harness_4_string_mf: 15,
|
|
harness_ac_inner: 8,
|
|
harness_ac_outer: 6,
|
|
sma_24kw_inverter: 9,
|
|
sma_12kw_inverter: 1,
|
|
sma_15kw_inverter: 1,
|
|
comm_cable: 11,
|
|
dc_switch_box: 9,
|
|
hex_bolt_1_2: 297,
|
|
whip_tray: 14,
|
|
mounting_back_plate: 19,
|
|
wire_clip_large: 2394,
|
|
cable_support: 270,
|
|
cable_support_lid: 270,
|
|
rear_skirt: -103,
|
|
ethernet_plug: 7.2,
|
|
monitor_power_plug: 1,
|
|
sunshade_bolt: 12,
|
|
sunshade_washer: 12,
|
|
}
|
|
|
|
expected_output_240 = {
|
|
flat_washer: 72,
|
|
channel_nut: 16,
|
|
hex_nut_quarter_20: 36,
|
|
hex_nut_three_eighths_16: 100,
|
|
flat_washer_quarter_inch: 36,
|
|
hex_bolt_quarter_20: 36,
|
|
monitor_controller_240_v: 1,
|
|
stump: 84,
|
|
dc_switch_bracket: 9,
|
|
front_legs: 18,
|
|
back_legs: 18,
|
|
inverter_link: 36,
|
|
inverter_rail: 18,
|
|
sma_20kw_inverter: 3,
|
|
sunshade: 6,
|
|
hex_bolt_3_4: 64,
|
|
panel_board_4: 3,
|
|
panel_board_2: 1,
|
|
rubber_foot: 54,
|
|
harness_3_string_fm: 10,
|
|
harness_3_string_mf: 10,
|
|
harness_2_string_fm: 2,
|
|
harness_2_string_mf: 2,
|
|
harness_4_string_fm: 15,
|
|
harness_4_string_mf: 15,
|
|
harness_ac_inner: 8,
|
|
harness_ac_outer: 6,
|
|
sma_24kw_inverter: 9,
|
|
sma_12kw_inverter: 1,
|
|
sma_15kw_inverter: 1,
|
|
comm_cable: 10,
|
|
dc_switch_box: 9,
|
|
hex_bolt_1_2: 288,
|
|
whip_tray: 14,
|
|
mounting_back_plate: 18,
|
|
wire_clip_large: 2394,
|
|
cable_support: 270,
|
|
cable_support_lid: 270,
|
|
rear_skirt: -103,
|
|
ethernet_plug: 7.2,
|
|
sunshade_bolt: 12,
|
|
sunshade_washer: 12,
|
|
}
|
|
|
|
self.user_values.module_type.return_value = ModuleType.Cell96
|
|
|
|
self.subject = EbomCalculator(self.user_values, 171, 98, 306)
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output_480)
|
|
|
|
self.subject = EbomCalculator(self.user_values, 171, 98, 400)
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output_480)
|
|
|
|
self.subject = EbomCalculator(self.user_values, 171, 98, 304)
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output_240)
|
|
|
|
self.subject = EbomCalculator(self.user_values, 171, 98, 100)
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output_240)
|
|
|
|
self.user_values.module_type.return_value = ModuleType.Cell128
|
|
|
|
self.subject = EbomCalculator(self.user_values, 171, 98, 230)
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output_480)
|
|
|
|
self.subject = EbomCalculator(self.user_values, 171, 98, 400)
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output_480)
|
|
|
|
self.subject = EbomCalculator(self.user_values, 171, 98, 229)
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output_240)
|
|
|
|
self.subject = EbomCalculator(self.user_values, 171, 98, 100)
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output_240)
|
|
|
|
def test_computes_monitor_type_with_aux_plugs_on_switchgear(self):
|
|
self.user_values.power_stations.return_value = []
|
|
self.user_values.power_monitors.return_value = [{
|
|
'monitor_id': 'foo',
|
|
'power_source': ('Switch Gear/External', None)
|
|
}]
|
|
|
|
self.user_values.system_type.return_value = SystemType.dualTilt
|
|
|
|
# 9 dc switches
|
|
expected_output_480 = {
|
|
flat_washer: 4,
|
|
channel_nut: 4,
|
|
hex_nut_three_eighths_16: 2,
|
|
monitor_controller_480_v: 1,
|
|
stump: 0,
|
|
front_legs: 1,
|
|
back_legs: 1,
|
|
inverter_link: 2,
|
|
inverter_rail: 1,
|
|
rubber_foot: 3,
|
|
hex_bolt_1_2: 9,
|
|
mounting_back_plate: 1,
|
|
cable_support: 0,
|
|
cable_support_lid: 0,
|
|
rear_skirt: 0,
|
|
monitor_power_plug: 1,
|
|
}
|
|
|
|
expected_output_480_pseries = {
|
|
flat_washer: 4,
|
|
channel_nut: 4,
|
|
hex_nut_three_eighths_16: 2,
|
|
monitor_controller_480_v: 1,
|
|
stump: 0,
|
|
front_legs: 1,
|
|
back_legs: 1,
|
|
inverter_link: 2,
|
|
inverter_rail: 1,
|
|
rubber_foot: 3,
|
|
hex_bolt_1_2: 9,
|
|
mounting_back_plate: 1,
|
|
cable_support: 0,
|
|
cable_support_lid: 0,
|
|
rear_skirt: 0,
|
|
monitor_power_plug: 1,
|
|
}
|
|
|
|
expected_output_240 = {
|
|
monitor_controller_240_v: 1,
|
|
stump: 0,
|
|
cable_support: 0,
|
|
cable_support_lid: 0,
|
|
rear_skirt: 0
|
|
}
|
|
|
|
expected_output_240_pseries = {
|
|
stump: 0,
|
|
cable_support_lid: 0,
|
|
cable_support: 0,
|
|
rear_skirt: 0,
|
|
monitor_controller_240_v: 1,
|
|
}
|
|
|
|
self.user_values.module_type.return_value = ModuleType.Cell96
|
|
|
|
self.subject = EbomCalculator(self.user_values, 171, 98, 306)
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output_480)
|
|
|
|
self.subject = EbomCalculator(self.user_values, 171, 98, 304)
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output_240)
|
|
|
|
self.user_values.module_type.return_value = ModuleType.Cell128
|
|
|
|
self.subject = EbomCalculator(self.user_values, 171, 98, 230)
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output_480)
|
|
|
|
self.subject = EbomCalculator(self.user_values, 171, 98, 300)
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output_480)
|
|
|
|
self.subject = EbomCalculator(self.user_values, 171, 98, 229)
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output_240)
|
|
|
|
self.subject = EbomCalculator(self.user_values, 171, 98, 104)
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output_240)
|
|
|
|
self.user_values.module_type.return_value = ModuleType.PSeries
|
|
|
|
self.subject = EbomCalculator(self.user_values, 171, 98, 286)
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output_480_pseries)
|
|
|
|
self.subject = EbomCalculator(self.user_values, 171, 98, 300)
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output_480_pseries)
|
|
|
|
self.subject = EbomCalculator(self.user_values, 171, 98, 285)
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output_240_pseries)
|
|
|
|
self.subject = EbomCalculator(self.user_values, 171, 98, 104)
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output_240_pseries)
|
|
|
|
def test_computes_ebom_with_power_monitor_DELTA_brand(self):
|
|
self.user_values.inverter_brands.return_value = [{'inverter_brand_id':2}]
|
|
self.user_values.power_monitors.return_value = [{
|
|
'monitor_id': 'foo',
|
|
'power_source': ('Switch Gear/External', None)
|
|
}]
|
|
self.user_values.system_type.return_value = SystemType.singleTilt
|
|
self.user_values.module_type.return_value = ModuleType.Cell96
|
|
|
|
expected_output = {
|
|
monitor_power_plug: 1,
|
|
stump: 0,
|
|
cable_support: 0,
|
|
cable_support_lid: 0,
|
|
rear_skirt: 0,
|
|
monitor_controller_480_v: 1,
|
|
ethernet_plug: 2,
|
|
}
|
|
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output)
|
|
|
|
def test_computes_ebom_with_power_monitor_SMA_brand(self):
|
|
self.user_values.inverter_brands.return_value = [{'inverter_brand_id':1}]
|
|
self.user_values.power_monitors.return_value = [{
|
|
'monitor_id': 'foo',
|
|
'power_source': ('Switch Gear/External', None)
|
|
}]
|
|
self.user_values.system_type.return_value = SystemType.singleTilt
|
|
self.user_values.module_type.return_value = ModuleType.Cell96
|
|
|
|
expected_output = {
|
|
monitor_power_plug: 1,
|
|
stump: 0,
|
|
cable_support: 0,
|
|
cable_support_lid: 0,
|
|
rear_skirt: 0,
|
|
monitor_controller_480_v:1,
|
|
flat_washer: 4,
|
|
channel_nut: 4,
|
|
hex_nut_three_eighths_16: 2,
|
|
front_legs: 1,
|
|
back_legs: 1,
|
|
inverter_link: 2,
|
|
inverter_rail: 1,
|
|
rubber_foot: 3,
|
|
hex_bolt_1_2: 9,
|
|
mounting_back_plate: 1,
|
|
}
|
|
|
|
assert_dictionary_equal(self.subject.compute_ebom(), expected_output)
|
|
|
|
|
|
|
|
|