tests migrated from nose to pytest

fixes #1

config.ini added to gitignore

rewording in readme, links to behringer/midas pages added.

kinds supported updated.

development dependencies updated in setup.py

kind maps in kinds module updated

kwarg port added (might revert this later)

pre-commit.ps1 added for use with git hook

mr18 tests badge added to readme
This commit is contained in:
onyx-and-iris 2022-05-01 03:46:44 +01:00
parent 8bad4d549a
commit 550b8c4240
12 changed files with 622 additions and 456 deletions

2
.gitignore vendored
View File

@ -1,3 +1,5 @@
config.ini
# Byte-compiled / optimized / DLL files
__pycache__/
*.py[cod]

0
CHANGELOG.md Normal file
View File

View File

@ -1,40 +1,49 @@
[![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://github.com/onyx-and-iris/xair-api-python/blob/dev/LICENSE)
[![Code style: black](https://img.shields.io/badge/code%20style-black-000000.svg)](https://github.com/psf/black)
![Tests Status](./tests/MR18.svg?dummy=8484744)
# Mair Remote
This package offers a python interface to the Midas MR18 digital rack mixer.
All testing was done using a Midas MR18 but I've been informed that the software for XR18 is identical.
Midas are not affiliated with/nor do they support this package in any way.
This package offers a python interface for the [Behringer XAir](https://www.behringer.com/series.html?category=R-BEHRINGER-XAIRSERIES), [Midas MR](https://www.midasconsoles.com/catalog.html?catalog=Category&category=C-MIDAS-MIXERS-DIGITALSTAGEBOXMIXERS) series of digital rack mixers. I only have access to an MR18 for testing so if there is an error in the kind maps feel free to raise an issue or PR.
## Prerequisites
- Python 3.9+
## Installation
```
git clone https://github.com/onyx-and-iris/mair-api-python
cd mair-api-python
git clone https://github.com/onyx-and-iris/xair-api-python
cd xair-api-python
```
Just the interface:
```
pip install .
```
With development dependencies:
```
pip install -e .['development']
```
## Usage
### Connection
An ini file named config.ini, placed into the current working directory of your code may be used to configure the mixers ip. It's contents should resemble:
```
[connection]
ip=<ip address>
```
Alternatively you may state it explicitly as an argument to mair.connect()
### Example 1
```python
import mair
@ -52,13 +61,16 @@ if __name__ == '__main__':
```
## API
Currently the following devices are support:
- `XR18`
- `MR18`
However, this interface can be expanded upon to support other devices.
- `XR16`
- `XR12`
### MAirRemote (higher level)
`mixer.lr`
A class representing Main LR channel
@ -95,42 +107,49 @@ An RTN tuple containing a class for each rtn channel
A class representing the main config settings
### `LR`
Contains the subclasses:
(`Config`, `Dyn`, `Insert`, `EQ`, `Mix`)
### `Strip`
Contains the subclasses:
(`Config`, `Preamp`, `Gate`, `Dyn`, `Insert`, `GEQ`, `EQ`, `Mix`, `Group`, `Automix`)
### `Bus`
Contains the subclasses:
(`Config`, `Dyn`, `Insert`, `EQ`, `Mix`, `Group`)
### `FXSend`
Contains the subclasses:
(`Config`, `Mix`, `Group`)
### `Aux`
Contains the subclasses:
(`Config`, `Preamp`, `EQ`, `Mix`, `Group`)
### `Rtn`
Contains the subclasses:
(`Config`, `Preamp`, `EQ`, `Mix`, `Group`)
### `Subclasses`
For each subclass the corresponding properties are available.
`Config`
- `name`: string
- `color`: int, from 0, 16
- `inputsource`: int
- `usbreturn`: int
`Preamp`
- `on`: bool
- `usbtrim`: float, from -18.0 to 18.0
- `usbinput`: bool
@ -139,6 +158,7 @@ For each subclass the corresponding properties are available.
- `highpassfilter`: int, from 20 to 400
`Gate`
- `on`: bool
- `mode`: str, one of ('gate', 'exp2', 'exp3', 'exp4', 'duck')
- `threshold`: float, from -80.0 to 0.0
@ -152,6 +172,7 @@ For each subclass the corresponding properties are available.
- `filterfreq`: float, from 20 to 20000
`Dyn`
- `on`: bool
- `mode`: str, one of ('comp', 'exp')
- `det`: str, one of ('peak', 'rms')
@ -171,11 +192,13 @@ For each subclass the corresponding properties are available.
- `filterfreq`: float, from 20 to 20000
`Insert`
- `on`: bool
- `sel`: int
`GEQ`
The following method names preceded by `slider_`
- `20`, `25`, `31_5`, `40`, `50`, `63`, `80`, `100`, `125`, `160`,
- `200`, `250`, `315`, `400`, `500`, `630`, `800`, `1k`, `1k25`, `1k6`, `2k`,
- `2k5`, `3k15`, `4k`, `5k`, `6k3`, `8k`, `10k`, `12k5`, `16k`, `20k`: float, from -15.0 to 15.0
@ -183,10 +206,12 @@ The following method names preceded by `slider_`
for example: `slider_20`, `slider_6k3` etc..
`EQ`
- `on`: bool
- `mode`: str, one of ('peq', 'geq', 'teq')
For the subclasses: `low`, `low2`, `lomid`, `himid`, `high2`, `high` the following properties are available:
- `type`: int, from 0 to 5
- `frequency`: float, from 20.0 to 20000.0
- `gain`: float, -15.0 to 15.0
@ -195,30 +220,35 @@ For the subclasses: `low`, `low2`, `lomid`, `himid`, `high2`, `high` the followi
for example: `eq.low2.type`
`Mix`
- `on`: bool
- `fader`: float, -inf, to 10.0
- `lr`: bool
`Group`
- `dca`: int, from 0 to 15
- `mute`: int, from 0 to 15
`Automix`
- `group`: int, from 0 to 2
- `weight`: float, from -12.0 to 12.0
### `DCA`
- `on`: bool
- `name`: str
- `color`: int, from 0 to 15
### `Config`
The following method names preceded by `chlink`
- `1_2`, `3_4`, `5_6`, `7_8`, `9_10`, `11_12`, `13_14`, `15_16`
The following method names preceded by `buslink`
- `1_2`, `3_4`, `5_6`
for example: `chlink1_2`, `buslink5_6` etc..
@ -231,6 +261,7 @@ for example: `chlink1_2`, `buslink5_6` etc..
- `mute_group`: bool
For the subclass `monitor` the following properties are available
- `level`: float, -inf to 10.0
- `source`: int, from 0 to 14
- `chmode` bool
@ -242,16 +273,17 @@ For the subclass `monitor` the following properties are available
for example: `config.monitor.chmode`
### `Tests`
First make sure you installed the [development dependencies](https://github.com/onyx-and-iris/mair-api-python#installation)
People plug expensive equipment into these mixers, the unit tests adjust parameter values such as gain sliders etc. My advice is
to unplug all equipment from the mixer before running these tests. No tests alter phantom power state.
Save your current settings to a snapshot first.
First make sure you installed the [development dependencies](https://github.com/onyx-and-iris/xair-api-python#installation)
To run the tests from tests directory:
WARNING: First save your settings and make sure your equipment is safe from damage.
Run tests at your own risk.
`nosetests --r test -v`.
`pytest -v`.
## License
@ -259,4 +291,4 @@ This project is licensed under the MIT License - see the [LICENSE](LICENSE) file
## Special Thanks
Peter Dikant for writing the base class
[Peter Dikant](https://github.com/peterdikant) for writing the base class

View File

@ -1,13 +1,17 @@
import mair
def main():
with mair.connect(kind_id, ip=ip) as mixer:
mixer.strip[8].config.name = 'sm7b'
mixer.strip[8].config.name = "sm7b"
mixer.strip[8].config.on = True
print(f'strip 09 ({mixer.strip[8].config.name}) has been set to {mixer.strip[8].config.on}')
print(
f"strip 09 ({mixer.strip[8].config.name}) has been set to {mixer.strip[8].config.on}"
)
if __name__ == '__main__':
kind_id = 'MR18'
ip = '<ip address>'
if __name__ == "__main__":
kind_id = "MR18"
ip = "mixer.local"
main()

View File

@ -1,9 +1,23 @@
from dataclasses import dataclass
"""
# osc slightly different, interface would need adjusting to support this mixer.
@dataclass
class X32KindMap:
id_: str = "X32"
num_dca: int = 8
num_strip: int = 32
num_bus: int = 16
num_fx: int = 8
num_rtn: int = 6
"""
@dataclass
class MR18KindMap:
id_: str = "MR18"
# note ch 17-18 defined as aux rtn
id_: str
num_dca: int = 4
num_strip: int = 16
num_bus: int = 6
@ -11,9 +25,36 @@ class MR18KindMap:
num_rtn: int = 4
@dataclass
class XR16KindMap:
id_: str
num_dca: int = 4
num_strip: int = 16
num_bus: int = 4
num_fx: int = 4
num_rtn: int = 4
@dataclass
class XR12KindMap:
id_: str
num_dca: int = 4
num_strip: int = 12
num_bus: int = 2
num_fx: int = 4
num_rtn: int = 4
_kinds = {
"XR18": MR18KindMap(),
"MR18": MR18KindMap(),
"XR18": MR18KindMap(id_="XR18"),
"MR18": MR18KindMap(id_="MR18"),
"XR16": XR16KindMap(id_="XR16"),
"XR12": XR12KindMap(id_="XR12"),
}
def get(kind_id):
return _kinds[kind_id]
all = list(kind for kind in _kinds.values())

View File

@ -54,7 +54,8 @@ class MAirRemote(abc.ABC):
dispatcher = Dispatcher()
dispatcher.set_default_handler(self.msg_handler)
self.xair_ip = kwargs["ip"] or self._ip_from_ini()
self.server = OSCClientServer((self.xair_ip, self.XAIR_PORT), dispatcher)
self.xair_port = kwargs["port"] or self.XAIR_PORT
self.server = OSCClientServer((self.xair_ip, self.xair_port), dispatcher)
def __enter__(self):
self.worker = threading.Thread(target=self.run_server)
@ -107,7 +108,7 @@ def _make_remote(kind: kinds.MR18KindMap) -> MAirRemote:
"""
def init(self, *args, **kwargs):
defaultkwargs = {"ip": None}
defaultkwargs = {"ip": None, "port": None}
kwargs = defaultkwargs | kwargs
MAirRemote.__init__(self, *args, **kwargs)
self.kind = kind

View File

@ -1,18 +1,10 @@
from setuptools import setup
setup(
name='mair_remote',
version='0.1',
description='MAIR Remote Python API',
packages=['mair'],
install_requires=[
'python-osc'
],
extras_require={
'development': [
'nose',
'randomize',
'parameterized'
]
}
name="mair_remote",
version="0.1",
description="MAIR Remote Python API",
packages=["mair"],
install_requires=["python-osc"],
extras_require={"development": ["pytest", "pytest-randomly", "genbadge[tests]"]},
)

1
tests/MR18.svg Normal file
View File

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="60" height="20" role="img" aria-label="tests: 67"><title>tests: 67</title><linearGradient id="s" x2="0" y2="100%"><stop offset="0" stop-color="#bbb" stop-opacity=".1"/><stop offset="1" stop-opacity=".1"/></linearGradient><clipPath id="r"><rect width="60" height="20" rx="3" fill="#fff"/></clipPath><g clip-path="url(#r)"><rect width="37" height="20" fill="#555"/><rect x="37" width="23" height="20" fill="#4c1"/><rect width="60" height="20" fill="url(#s)"/></g><g fill="#fff" text-anchor="middle" font-family="Verdana,Geneva,DejaVu Sans,sans-serif" text-rendering="geometricPrecision" font-size="110"><text aria-hidden="true" x="195" y="150" fill="#010101" fill-opacity=".3" transform="scale(.1)" textLength="270">tests</text><text x="195" y="140" transform="scale(.1)" fill="#fff" textLength="270">tests</text><text aria-hidden="true" x="475" y="150" fill="#010101" fill-opacity=".3" transform="scale(.1)" textLength="130">67</text><text x="475" y="140" transform="scale(.1)" fill="#fff" textLength="130">67</text></g></svg>

After

Width:  |  Height:  |  Size: 1.1 KiB

View File

@ -1,17 +1,39 @@
import mair
from mair import kinds
import threading
from dataclasses import dataclass
import sys
_kind = 'MR18'
kind_id = "MR18"
ip = "mixer.local"
mars = {kind.id_: mair.connect(_kind) for kind in kinds.all}
tests = mars[_kind]
tests = mair.connect(kind_id, ip=ip)
def setup_package():
tests.worker = threading.Thread(target = tests.run_server)
kind = kinds.get(kind_id)
@dataclass
class Data:
"""bounds data to map tests to a kind"""
name: str = kind.id_
dca: int = kind.num_dca - 1
strip: int = kind.num_strip - 1
bus: int = kind.num_bus - 1
fx: int = kind.num_fx - 1
rtn: int = kind.num_rtn - 1
data = Data()
def setup_module():
print(f"\nRunning tests for kind [{data.name}]\n", file=sys.stdout)
tests.worker = threading.Thread(target=tests.run_server)
tests.worker.daemon = True
tests.worker.start()
tests.validate_connection()
def teardown_package():
def teardown_module():
tests.server.shutdown()

31
tests/pre-commit.ps1 Normal file
View File

@ -0,0 +1,31 @@
Function RunTests {
$coverage = "./tests/pytest_coverage.log"
$run_tests = "pytest -v --capture=tee-sys --junitxml=./tests/.coverage.xml"
$match_pattern = "^=|^\s*$|^Running|^Using|^plugins|^collecting|^tests"
if ( Test-Path $coverage ) { Clear-Content $coverage }
ForEach ($line in $(Invoke-Expression $run_tests)) {
If ( $line -Match $match_pattern ) {
if ( $line -Match "^Running tests for kind \[(\w+)\]" ) { $kind = $Matches[1] }
$line | Tee-Object -FilePath $coverage -Append
}
}
Write-Output "$(Get-TimeStamp)" | Out-file $coverage -Append
Invoke-Expression "genbadge tests -t 90 -i ./tests/.coverage.xml -o ./tests/$kind.svg"
}
Function Get-TimeStamp {
return "[{0:MM/dd/yy} {0:HH:mm:ss}]" -f (Get-Date)
}
if ($MyInvocation.InvocationName -ne ".") {
Invoke-Expression ".\venv\Scripts\Activate.ps1"
RunTests
Invoke-Expression "deactivate"
}

View File

@ -1,332 +0,0 @@
from nose.tools import assert_equal, nottest
from parameterized import parameterized, parameterized_class
import unittest
from tests import tests
"""
Not every subclass is tested for every superclass to avoid redundancy.
LR: mix, config, insert, geq
Strip: mix, preamp, config, gate, automix
Bus: config, dyn, eq
FXSend: group
"""
""" LR TESTS """
#@nottest
class TestSetAndGetLRMixHigher(unittest.TestCase):
""" Mix """
def setUp(self):
self.target = getattr(tests, 'lr')
self.target = getattr(self.target, 'mix')
@parameterized.expand([
('on', True), ('on', False)
])
def test_it_sets_and_gets_lr_bool_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
self.assertTrue(isinstance(retval, bool))
assert_equal(retval, val)
@parameterized.expand([
('fader', -80.6), ('fader', -67.0)
])
def test_it_sets_and_gets_lr_float_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
assert_equal(retval, val)
#@nottest
class TestSetAndGetLRConfigHigher(unittest.TestCase):
""" Config """
def setUp(self):
self.target = getattr(tests, 'lr')
self.target = getattr(self.target, 'config')
@parameterized.expand([
('name', 'test0'), ('name', 'test1')
])
def test_it_sets_and_gets_lr_string_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
assert_equal(retval, val)
#@nottest
class TestSetAndGetLRInsertHigher(unittest.TestCase):
""" Insert """
def setUp(self):
self.target = getattr(tests, 'lr')
self.target = getattr(self.target, 'insert')
@parameterized.expand([
('on', True), ('on', False)
])
def test_it_sets_and_gets_lr_bool_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
self.assertTrue(isinstance(retval, bool))
assert_equal(retval, val)
@parameterized.expand([
('sel', 0), ('sel', 4)
])
def test_it_sets_and_gets_lr_int_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
assert_equal(retval, val)
#@nottest
class TestSetAndGetLRGEQHigher(unittest.TestCase):
""" GEQ """
def setUp(self):
self.target = getattr(tests, 'lr')
self.target = getattr(self.target, 'geq')
@parameterized.expand([
('slider_20', -13.5), ('slider_20', 5.5), ('slider_6k3', -8.5), ('slider_6k3', 8.5)
])
def test_it_sets_and_gets_lr_int_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
assert_equal(retval, val)
""" STRIP TESTS """
#@nottest
@parameterized_class([
{ 'i': 15 }
])
class TestSetAndGetStripMixHigher(unittest.TestCase):
""" Mix """
def setUp(self):
self.target = getattr(tests, 'strip')
self.target = getattr(self.target[self.i], 'mix')
@parameterized.expand([
('on', True), ('on', False), ('lr', True), ('lr', False)
])
def test_it_sets_and_gets_strip_bool_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
self.assertTrue(isinstance(retval, bool))
assert_equal(retval, val)
#@nottest
@parameterized_class([
{ 'i': 8 }
])
class TestSetAndGetStripPreampHigher(unittest.TestCase):
""" Preamp """
def setUp(self):
self.target = getattr(tests, 'strip')
self.target = getattr(self.target[self.i], 'preamp')
@parameterized.expand([
('highpasson', True), ('highpasson', False), ('usbinput', True), ('usbinput', False)
])
def test_it_sets_and_gets_strip_bool_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
self.assertTrue(isinstance(retval, bool))
assert_equal(retval, val)
@parameterized.expand([
('highpassfilter', 20), ('highpassfilter', 399)
])
def test_it_sets_and_gets_strip_int_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
assert_equal(retval, val)
@parameterized.expand([
('usbtrim', -16.5), ('usbtrim', 5.5)
])
def test_it_sets_and_gets_strip_float_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
assert_equal(retval, val)
#@nottest
@parameterized_class([
{ 'i': 3 }
])
class TestSetAndGetStripConfigHigher(unittest.TestCase):
""" Config """
def setUp(self):
self.target = getattr(tests, 'strip')
self.target = getattr(self.target[self.i], 'config')
@parameterized.expand([
('inputsource', 0), ('inputsource', 18), ('usbreturn', 3), ('usbreturn', 12)
])
def test_it_sets_and_gets_strip_int_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
assert_equal(retval, val)
@parameterized_class([
{ 'i': 12 }
])
class TestSetAndGetStripGateHigher(unittest.TestCase):
""" Gate """
def setUp(self):
self.target = getattr(tests, 'strip')
self.target = getattr(self.target[self.i], 'gate')
@parameterized.expand([
('on', True), ('on', False), ('invert', True), ('invert', False),
('filteron', True), ('filteron', False)
])
def test_it_sets_and_gets_strip_bool_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
self.assertTrue(isinstance(retval, bool))
assert_equal(retval, val)
@parameterized.expand([
('range', 11), ('range', 48), ('attack', 5), ('attack', 110),
('release', 360), ('release', 2505), ('filtertype', 0), ('filtertype', 8)
])
def test_it_sets_and_gets_strip_int_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
assert_equal(retval, val)
@parameterized.expand([
('mode', 'exp2'), ('mode', 'duck')
])
def test_it_sets_and_gets_strip_string_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
assert_equal(retval, val)
@parameterized.expand([
('threshold', -80.0), ('threshold', 0.0), ('hold', 355), ('hold', 63.2),
('filterfreq', 37.2), ('filterfreq', 12765)
])
def test_it_sets_and_gets_strip_float_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
assert_equal(retval, val)
#@nottest
@parameterized_class([
{ 'i': 6 }
])
class TestSetAndGetStripAutomixHigher(unittest.TestCase):
""" Automix """
def setUp(self):
self.target = getattr(tests, 'strip')
self.target = getattr(self.target[self.i], 'automix')
@parameterized.expand([
('group', 0), ('group', 2)
])
def test_it_sets_and_gets_fxsend_int_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
assert_equal(retval, val)
@parameterized.expand([
('weight', -10.5), ('weight', 3.5)
])
def test_it_sets_and_gets_fxsend_float_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
assert_equal(retval, val)
""" BUS TESTS """
#@nottest
@parameterized_class([
{ 'i': 1 }
])
class TestSetAndGetBusConfigHigher(unittest.TestCase):
""" Config """
def setUp(self):
self.target = getattr(tests, 'bus')
self.target = getattr(self.target[self.i], 'config')
@parameterized.expand([
('color', 0), ('color', 15)
])
def test_it_sets_and_gets_bus_bool_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
assert_equal(retval, val)
#@nottest
@parameterized_class([
{ 'i': 2 }
])
class TestSetAndGetBusDynHigher(unittest.TestCase):
""" Dyn """
def setUp(self):
self.target = getattr(tests, 'bus')
self.target = getattr(self.target[self.i], 'dyn')
@parameterized.expand([
('on', True), ('on', False)
])
def test_it_sets_and_gets_bus_bool_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
self.assertTrue(isinstance(retval, bool))
assert_equal(retval, val)
@parameterized.expand([
('mode', 'comp'), ('mode', 'exp'), ('env', 'lin'), ('env', 'log'),
('det', 'peak'), ('det', 'rms')
])
def test_it_sets_and_gets_bus_string_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
assert_equal(retval, val)
#@nottest
@parameterized_class([
{ 'i': 0 }
])
class TestSetAndGetBusEQHigher(unittest.TestCase):
""" EQ """
def setUp(self):
self.target = getattr(tests, 'bus')
self.target = getattr(self.target[self.i], 'eq')
@parameterized.expand([
('on', True), ('on', False)
])
def test_it_sets_and_gets_bus_bool_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
self.assertTrue(isinstance(retval, bool))
assert_equal(retval, val)
@parameterized.expand([
('mode', 'peq'), ('mode', 'geq'), ('mode', 'teq')
])
def test_it_sets_and_gets_bus_string_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
assert_equal(retval, val)
""" FXSEND TESTS """
#@nottest
@parameterized_class([
{ 'i': 1 }
])
class TestSetAndGetFXSendGroupHigher(unittest.TestCase):
""" Group """
def setUp(self):
self.target = getattr(tests, 'fxsend')
self.target = getattr(self.target[self.i], 'group')
@parameterized.expand([
('dca', 0), ('dca', 12), ('mute', 3), ('mute', 8)
])
def test_it_sets_and_gets_fxsend_int_params(self, param, val):
setattr(self.target, param, val)
retval = getattr(self.target, param)
assert_equal(retval, val)

372
tests/test_shared.py Normal file
View File

@ -0,0 +1,372 @@
import pytest
from tests import tests, data
"""
Not every subclass is tested for every superclass to avoid redundancy.
LR: mix, config, insert, geq
Strip: mix, preamp, config, gate, automix
Bus: config, dyn, eq
FXSend: group
"""
""" Main LR TESTS """
class TestSetAndGetLRMixHigher:
"""Mix"""
__test__ = True
def setup_class(self):
self.target = getattr(tests, "lr")
self.target = getattr(self.target, "mix")
@pytest.mark.parametrize(
"param,value",
[("on", True), ("on", False)],
)
def test_it_sets_and_gets_lr_bool_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
@pytest.mark.parametrize(
"param,value",
[("fader", -80.6), ("fader", -67.0)],
)
def test_it_sets_and_gets_lr_float_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
class TestSetAndGetLRConfigHigher:
"""Config"""
__test__ = True
def setup_class(self):
self.target = getattr(tests, "lr")
self.target = getattr(self.target, "config")
@pytest.mark.parametrize("param,value", [("name", "test0"), ("name", "test1")])
def test_it_sets_and_gets_lr_string_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
class TestSetAndGetLRInsertHigher:
"""Insert"""
__test__ = True
def setup_class(self):
self.target = getattr(tests, "lr")
self.target = getattr(self.target, "insert")
@pytest.mark.parametrize(
"param,value",
[("on", True), ("on", False)],
)
def test_it_sets_and_gets_lr_bool_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
@pytest.mark.parametrize(
"param,value",
[("sel", 0), ("sel", 4)],
)
def test_it_sets_and_gets_lr_int_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
class TestSetAndGetLRGEQHigher:
"""GEQ"""
__test__ = True
def setup_class(self):
self.target = getattr(tests, "lr")
self.target = getattr(self.target, "geq")
@pytest.mark.parametrize(
"param,value",
[
("slider_20", -13.5),
("slider_20", 5.5),
("slider_6k3", -8.5),
("slider_6k3", 8.5),
],
)
def test_it_sets_and_gets_lr_int_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
""" STRIP TESTS """
class TestSetAndGetStripMixHigher:
"""Mix"""
__test__ = True
def setup_class(self):
self.target = getattr(tests, "strip")
self.target = getattr(self.target[data.strip], "mix")
@pytest.mark.parametrize(
"param,value",
[("on", True), ("on", False), ("lr", True), ("lr", False)],
)
def test_it_sets_and_gets_strip_bool_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
class TestSetAndGetStripPreampHigher:
"""Preamp"""
__test__ = True
def setup_class(self):
self.target = getattr(tests, "strip")
self.target = getattr(self.target[data.strip], "preamp")
@pytest.mark.parametrize(
"param,value",
[
("highpasson", True),
("highpasson", False),
("usbinput", True),
("usbinput", False),
],
)
def test_it_sets_and_gets_strip_bool_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
@pytest.mark.parametrize(
"param,value",
[("highpassfilter", 20), ("highpassfilter", 399)],
)
def test_it_sets_and_gets_strip_int_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
@pytest.mark.parametrize(
"param,value",
[("usbtrim", -16.5), ("usbtrim", 5.5)],
)
def test_it_sets_and_gets_strip_float_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
class TestSetAndGetStripConfigHigher:
"""Config"""
__test__ = True
def setup_class(self):
self.target = getattr(tests, "strip")
self.target = getattr(self.target[data.strip], "config")
@pytest.mark.parametrize(
"param,value",
[("inputsource", 0), ("inputsource", 18), ("usbreturn", 3), ("usbreturn", 12)],
)
def test_it_sets_and_gets_strip_int_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
class TestSetAndGetStripGateHigher:
"""Gate"""
__test__ = True
def setup_class(self):
self.target = getattr(tests, "strip")
self.target = getattr(self.target[data.strip], "gate")
@pytest.mark.parametrize(
"param,value",
[
("on", True),
("on", False),
("invert", True),
("invert", False),
("filteron", True),
("filteron", False),
],
)
def test_it_sets_and_gets_strip_bool_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
@pytest.mark.parametrize(
"param,value",
[
("range", 11),
("range", 48),
("attack", 5),
("attack", 110),
("release", 360),
("release", 2505),
("filtertype", 0),
("filtertype", 8),
],
)
def test_it_sets_and_gets_strip_int_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
@pytest.mark.parametrize(
"param,value",
[("mode", "exp2"), ("mode", "duck")],
)
def test_it_sets_and_gets_strip_string_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
@pytest.mark.parametrize(
"param,value",
[
("threshold", -80.0),
("threshold", 0.0),
("hold", 355),
("hold", 63.2),
("filterfreq", 37.2),
("filterfreq", 12765),
],
)
def test_it_sets_and_gets_strip_float_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
class TestSetAndGetStripAutomixHigher:
"""Automix"""
__test__ = True
def setup_class(self):
self.target = getattr(tests, "strip")
self.target = getattr(self.target[data.strip], "automix")
@pytest.mark.parametrize(
"param,value",
[("group", 0), ("group", 2)],
)
def test_it_sets_and_gets_fxsend_int_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
@pytest.mark.parametrize(
"param,value",
[("weight", -10.5), ("weight", 3.5)],
)
def test_it_sets_and_gets_fxsend_float_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
""" BUS TESTS """
class TestSetAndGetBusConfigHigher:
"""Config"""
__test__ = True
def setup_class(self):
self.target = getattr(tests, "bus")
self.target = getattr(self.target[data.bus], "config")
@pytest.mark.parametrize(
"param,value",
[("color", 0), ("color", 15)],
)
def test_it_sets_and_gets_bus_bool_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
class TestSetAndGetBusDynHigher:
"""Dyn"""
__test__ = True
def setup_class(self):
self.target = getattr(tests, "bus")
self.target = getattr(self.target[data.bus], "dyn")
@pytest.mark.parametrize(
"param,value",
[("on", True), ("on", False)],
)
def test_it_sets_and_gets_bus_bool_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
@pytest.mark.parametrize(
"param,value",
[
("mode", "comp"),
("mode", "exp"),
("env", "lin"),
("env", "log"),
("det", "peak"),
("det", "rms"),
],
)
def test_it_sets_and_gets_bus_string_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
class TestSetAndGetBusDynHigher:
"""EQ"""
__test__ = True
def setup_class(self):
self.target = getattr(tests, "bus")
self.target = getattr(self.target[data.bus], "eq")
@pytest.mark.parametrize(
"param,value",
[("on", True), ("on", False)],
)
def test_it_sets_and_gets_bus_bool_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
@pytest.mark.parametrize(
"param,value",
[("mode", "peq"), ("mode", "geq"), ("mode", "teq")],
)
def test_it_sets_and_gets_bus_string_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value
""" FXSEND TESTS """
class TestSetAndGetFXSendGroupHigher:
"""Group"""
__test__ = True
def setup_class(self):
self.target = getattr(tests, "fxsend")
self.target = getattr(self.target[data.fx], "group")
@pytest.mark.parametrize(
"param,value",
[("dca", 0), ("dca", 12), ("mute", 3), ("mute", 8)],
)
def test_it_sets_and_gets_bus_bool_params(self, param, value):
setattr(self.target, param, value)
assert getattr(self.target, param) == value