-
Notifications
You must be signed in to change notification settings - Fork 9
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Start expanding test coverage to windows submodule
- Loading branch information
Showing
2 changed files
with
149 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,77 @@ | ||
import re | ||
from collections import namedtuple | ||
from ..helpers import fake_edid | ||
|
||
FAKE_DISPLAYS = [ | ||
{'name': 'BNQ0123', 'uid': '10000', 'longname': 'BenQ 0123', 'laptop': False}, | ||
{'name': 'MSI4567', 'uid': '20000', 'longname': 'MSI 4567', 'laptop': False}, | ||
{'name': 'DEL8910', 'uid': '30000', 'longname': 'Dell 8910', 'laptop': False}, | ||
{'name': 'SEC544B', 'uid': '40000', 'longname': 'Hewlett-Packard 544B', 'laptop': True}, | ||
] | ||
|
||
def instance_name(fake: dict, wmi_style=False): | ||
name, uid, laptop = fake['name'], fake['uid'], fake['laptop'] | ||
mid = '4&dc911b1' if laptop else '5&24bdd39e' | ||
if wmi_style: | ||
return rf'DISPLAY\{name}\{mid}&0&UID{uid}_0' | ||
return rf'\\?\DISPLAY#{name}#{mid}&0&UID{uid}#{{e6f07b5f-ee97-4a90-b076-33f57bf4eaa7}}' | ||
|
||
|
||
class FakeMSMonitor: | ||
def __init__(self, fake: dict): | ||
self.InstanceName = instance_name(fake, True) | ||
self.__fake = fake | ||
|
||
def WmiGetMonitorRawEEdidV1Block(self, _index: int): | ||
if self.__fake['laptop']: | ||
raise Exception('<obscure WMI error> no edid on laptop displays') | ||
edid = fake_edid(self.__fake['name'][:3], self.__fake['longname'], 'serialnum') | ||
# split into 2 char chunks and turn into hex nums | ||
return [tuple(int(i, 16) for i in re.findall(r'..', edid)), 1] | ||
|
||
|
||
class FakeWmiMonitorBrightnessMethods: | ||
def __init__(self, fake: dict): | ||
self.InstanceName = instance_name(fake, True) | ||
self.__fake = fake | ||
|
||
def WmiSetBrightness(self, value: int, timeout: int): | ||
return 0 | ||
|
||
|
||
class FakeWMI: | ||
def WmiMonitorBrightness(self): | ||
wmb = namedtuple('FakeWmiMonitorBrightness', ('InstanceName', 'CurrentBrightness')) | ||
monitors = [] | ||
for fake in FAKE_DISPLAYS: | ||
if fake['laptop']: | ||
monitors.append(wmb(instance_name(fake, True), 100)) | ||
return monitors | ||
|
||
def WmiMonitorDescriptorMethods(self): | ||
for fake in FAKE_DISPLAYS: | ||
yield FakeMSMonitor(fake) | ||
|
||
def WmiMonitorBrightnessMethods(self): | ||
monitors = [] | ||
for fake in FAKE_DISPLAYS: | ||
if fake['laptop']: | ||
monitors.append(FakeWmiMonitorBrightnessMethods(fake)) | ||
return monitors | ||
|
||
|
||
class FakePyDISPLAY_DEVICE: | ||
DeviceID: str | ||
|
||
def __init__(self, fake: dict): | ||
self.__fake = fake | ||
self.DeviceID = instance_name(fake) | ||
|
||
|
||
def mock_wmi_init(): | ||
return FakeWMI() | ||
|
||
|
||
def mock_enum_display_devices(): | ||
for fake in FAKE_DISPLAYS: | ||
yield FakePyDISPLAY_DEVICE(fake) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,72 @@ | ||
from dataclasses import dataclass | ||
import screen_brightness_control as sbc | ||
from typing import Type | ||
from unittest.mock import Mock | ||
import pytest | ||
from pytest_mock import MockerFixture | ||
from unittest.mock import call | ||
|
||
from .helpers import BrightnessMethodTest | ||
from screen_brightness_control.helpers import BrightnessMethod | ||
from .mocks.windows_mock import mock_enum_display_devices, mock_wmi_init | ||
|
||
@pytest.fixture | ||
def patch_global_get_display_info(mocker: MockerFixture): | ||
'''Mock everything needed to get `sbc.windows.get_display_info` to run''' | ||
mocker.patch.object(sbc.windows, 'enum_display_devices', mock_enum_display_devices) | ||
mocker.patch.object(sbc.windows, '_wmi_init', mock_wmi_init) | ||
|
||
|
||
class TestWMI(BrightnessMethodTest): | ||
@pytest.fixture | ||
def patch_get_display_info(self, patch_global_get_display_info): | ||
'''Mock everything needed to get `WMI.get_display_info` to run''' | ||
pass | ||
|
||
@pytest.fixture | ||
def patch_get_brightness(self, mocker: MockerFixture, patch_get_display_info): | ||
pass | ||
|
||
@pytest.fixture | ||
def patch_set_brightness(self, mocker: MockerFixture, patch_get_display_info): | ||
pass | ||
|
||
@pytest.fixture | ||
def method(self) -> Type[BrightnessMethod]: | ||
return sbc.windows.WMI | ||
|
||
class TestGetBrightness(BrightnessMethodTest.TestGetBrightness): | ||
class TestDisplayKwarg(BrightnessMethodTest.TestGetBrightness.TestDisplayKwarg): | ||
# skip these because WMI doesn't really make display specific calls when getting brightness | ||
# and perf is negligible anyway | ||
@pytest.mark.skip('skip TestGetBrightness.TestDisplayKwarg perf tests for WMI') | ||
def test_with(self): | ||
pass | ||
|
||
@pytest.mark.skip('skip TestGetBrightness.TestDisplayKwarg perf tests for WMI') | ||
def test_without(self): | ||
pass | ||
|
||
class TestSetBrightness(BrightnessMethodTest.TestSetBrightness): | ||
class TestDisplayKwarg(BrightnessMethodTest.TestSetBrightness.TestDisplayKwarg): | ||
def test_with(self, mocker: MockerFixture, freeze_display_info, method): | ||
wmi = sbc.windows._wmi_init() | ||
mocker.patch.object(sbc.windows, '_wmi_init', Mock(return_value=wmi, spec=True)) | ||
brightness_method = wmi.WmiMonitorBrightnessMethods()[0] | ||
mocker.patch.object(wmi,'WmiMonitorBrightnessMethods', lambda: [brightness_method] * 3) | ||
spy = mocker.spy(brightness_method, 'WmiSetBrightness') | ||
for index, display in enumerate(freeze_display_info): | ||
method.set_brightness(100, display=index) | ||
spy.assert_called_once_with(100, 0) | ||
spy.reset_mock() | ||
|
||
def test_without(self, mocker: MockerFixture, freeze_display_info, method): | ||
wmi = sbc.windows._wmi_init() | ||
mocker.patch.object(sbc.windows, '_wmi_init', Mock(return_value=wmi, spec=True)) | ||
brightness_method = wmi.WmiMonitorBrightnessMethods()[0] | ||
mocker.patch.object(wmi,'WmiMonitorBrightnessMethods', lambda: [brightness_method] * 3) | ||
spy = mocker.spy(brightness_method, 'WmiSetBrightness') | ||
|
||
method.set_brightness(100) | ||
spy.assert_has_calls([call(100, 0)] * 3) | ||
spy.reset_mock() |