emmental/tests/tracklist/test_sorter.py

300 lines
12 KiB
Python

# Copyright 2022 (c) Anna Schumaker.
"""Tests our Playlist Sorter."""
import emmental.tracklist.sorter
import unittest
from gi.repository import GObject
from gi.repository import Gio
class TestSortConstants(unittest.TestCase):
"""Test case for Sort Order constants."""
def test_flags(self):
"""Test flags passed to the sort_order property."""
self.assertEqual(emmental.tracklist.sorter.SORT_ORDER_FLAGS,
GObject.ParamFlags.READWRITE |
GObject.ParamFlags.EXPLICIT_NOTIFY)
def test_sort_fields(self):
"""Test the sort fields definition dictionary."""
self.assertDictEqual(emmental.tracklist.sorter.SORT_FIELDS,
{"Album": ["album"], "Artist": ["artist"],
"Album Artist": ["albumartist"],
"Filepath": ["filepath"], "Length": ["length"],
"Last Played Date": ["lastplayed"],
"Last Started Date": ["laststarted"],
"Play Count": ["playcount"],
"Release Date": ["release"],
"Title": ["title"],
"Track Number": ["mediumno", "number"]})
def test_reverse_lookup(self):
"""Test the sort field reverse lookup dictionary."""
self.assertDictEqual(emmental.tracklist.sorter.REVERSE_LOOKUP,
{"album": "Album", "artist": "Artist",
"albumartist": "Album Artist",
"filepath": "Filepath", "length": "Length",
"lastplayed": "Last Played Date",
"laststarted": "Last Started Date",
"playcount": "Play Count",
"release": "Release Date", "title": "Title",
"mediumno": "Track Number",
"number": "Track Number"})
class TestSortField(unittest.TestCase):
"""Test case for our SortField object."""
def setUp(self):
"""Set up common variables."""
self.model = Gio.ListStore()
self.field = emmental.tracklist.sorter.SortField(self.model, "Album")
def test_init(self):
"""Test that the Sort Field is initialized correctly."""
self.assertIsInstance(self.field, GObject.GObject)
self.assertEqual(self.field.name, "Album")
self.assertEqual(self.field.model, self.model)
self.assertFalse(self.field.enabled)
self.assertFalse(self.field.reversed)
with self.assertRaises(KeyError):
emmental.tracklist.sorter.SortField(self.model, "Invalid Field")
def test_str(self):
"""Test converting a Sort Field to a string."""
for (field, cols) in emmental.tracklist.sorter.SORT_FIELDS.items():
expected = ", ".join(cols)
reversed = ", ".join([f"{c} DESC" for c in cols])
with self.subTest(field=field, expected=(expected, reversed)):
self.field.name = field
self.field.reversed = False
self.assertEqual(str(self.field), expected)
self.field.reversed = True
self.assertEqual(str(self.field), reversed)
def test_disable(self):
"""Test disabling a Sort Field."""
self.model.disable = unittest.mock.Mock()
self.field.disable()
self.model.disable.assert_called_with(self.field)
def test_enable(self):
"""Test enabling a Sort Field."""
self.model.enable = unittest.mock.Mock()
self.field.enable()
self.model.enable.assert_called_with(self.field)
def test_move_down(self):
"""Test moving a Sort Field down."""
self.model.move_down = unittest.mock.Mock()
self.field.move_down()
self.model.move_down.assert_called_with(self.field)
def test_move_up(self):
"""Test moving a Sort Field up."""
self.model.move_up = unittest.mock.Mock()
self.field.move_up()
self.model.move_up.assert_called_with(self.field)
def test_reverse(self):
"""Test reversing a Sort Field."""
self.model.reverse = unittest.mock.Mock()
self.field.reverse()
self.model.reverse.assert_called_with(self.field)
class TestSortOrderModel(unittest.TestCase):
"""Test case for our Sort Order Model."""
def setUp(self):
"""Set up common variables."""
self.sort_fields = emmental.tracklist.sorter.SORT_FIELDS
self.model = emmental.tracklist.sorter.SortOrderModel()
def test_init(self):
"""Test that the model is initialized properly."""
self.assertIsInstance(self.model, Gio.ListStore)
self.assertEqual(self.model.n_enabled, 0)
self.assertEqual(self.model.get_item_type(),
emmental.tracklist.sorter.SortField.__gtype__)
self.assertEqual(self.model.sort_order, "")
for i, name in enumerate(self.sort_fields.keys()):
with self.subTest(i=i, name=name):
self.assertIsInstance(self.model[i],
emmental.tracklist.sorter.SortField)
self.assertEqual(self.model[i].name, name)
def test_index(self):
"""Test the Sort Order Model index() function."""
for i, name in enumerate(emmental.tracklist.sorter.SORT_FIELDS.keys()):
with self.subTest(i=i, name=name):
self.assertEqual(self.model.index(self.model[i]), i)
field2 = emmental.tracklist.sorter.SortField(self.model, "Album")
self.assertIsNone(self.model.index(field2))
def test_lookup(self):
"""Test looping up sort fields by name."""
for name in emmental.tracklist.sorter.SORT_FIELDS.keys():
with self.subTest(name=name):
self.assertEqual(self.model.lookup(name).name, name)
self.assertIsNone(self.model.lookup("Invalid Name"))
def test_disable(self):
"""Test disabling a sort field."""
(field_0 := self.model[0]).enable()
(field_1 := self.model[1]).enable()
(field_2 := self.model[2]).enable()
field_2.reversed = True
self.assertTrue(self.model.disable(field_2))
self.assertFalse(field_2.enabled)
self.assertFalse(field_2.reversed)
self.assertEqual(self.model.n_enabled, 2)
self.assertEqual(self.model.index(field_2), 2)
self.assertEqual(self.model.sort_order,
f"{str(field_0)}, {str(field_1)}")
self.assertFalse(self.model.disable(field_2))
self.assertEqual(self.model.n_enabled, 2)
self.assertTrue(self.model.disable(field_0))
self.assertFalse(field_0.enabled)
self.assertEqual(self.model.n_enabled, 1)
self.assertEqual(self.model.index(field_0), 1)
self.assertEqual(self.model.sort_order, str(field_1))
def test_enable(self):
"""Test enabling a sort field."""
field_0 = self.model[0]
self.assertTrue(self.model.enable(field_0))
self.assertTrue(field_0.enabled)
self.assertEqual(self.model.n_enabled, 1)
self.assertEqual(self.model.index(field_0), 0)
self.assertEqual(self.model.sort_order, str(field_0))
self.assertFalse(self.model.enable(field_0))
self.assertEqual(self.model.n_enabled, 1)
field_3 = self.model[3]
self.assertTrue(self.model.enable(field_3))
self.assertTrue(field_3.enabled)
self.assertEqual(self.model.n_enabled, 2)
self.assertEqual(self.model.index(field_3), 1)
self.assertEqual(self.model.sort_order,
f"{str(field_0)}, {str(field_3)}")
def test_move_down(self):
"""Test moving a sort field down in the list."""
(field_0 := self.model[0]).enable()
(field_1 := self.model[1]).enable()
for res in [True, False]:
with self.subTest(res=res):
self.assertEqual(self.model.move_down(field_0), res)
self.assertEqual(self.model[0], field_1)
self.assertEqual(self.model[1], field_0)
self.assertEqual(self.model.sort_order,
f"{str(field_1)}, {str(field_0)}")
def test_move_up(self):
"""Test moving a sort field down in the list."""
(field_0 := self.model[0]).enable()
(field_1 := self.model[1]).enable()
for res in [True, False]:
with self.subTest(res=res):
self.assertEqual(self.model.move_up(field_1), res)
self.assertEqual(self.model[0], field_1)
self.assertEqual(self.model[1], field_0)
self.assertEqual(self.model.sort_order,
f"{str(field_1)}, {str(field_0)}")
def test_reverse(self):
"""Test reversing a sort field."""
(field_0 := self.model[0]).enable()
self.model.reverse(field_0)
self.assertTrue(field_0.reversed)
self.assertEqual(self.model.sort_order, str(field_0))
self.model.reverse(field_0)
self.assertFalse(field_0.reversed)
self.assertEqual(self.model.sort_order, str(field_0))
def test_set_sort_order_artist(self):
"""Test setting the Sort Order property to "artist"."""
self.model.set_sort_order("artist")
self.assertEqual(self.model.n_enabled, 1)
self.assertEqual(self.model.sort_order, "artist")
self.assertEqual(self.model[0].name, "Artist")
self.assertTrue(self.model[0].enabled)
self.assertFalse(self.model[0].reversed)
self.assertFalse(self.model[1].enabled)
def test_set_sort_order_album_title(self):
"""Test setting the Sort Order property to "album DESC, title"."""
self.model[1].enable()
self.model[1].reverse()
self.model.set_sort_order("album DESC, title")
self.assertEqual(self.model.n_enabled, 2)
self.assertEqual(self.model.sort_order, "album DESC, title")
self.assertEqual(self.model[0].name, "Album")
self.assertTrue(self.model[0].enabled)
self.assertTrue(self.model[0].reversed)
self.assertEqual(self.model[1].name, "Title")
self.assertTrue(self.model[1].enabled)
self.assertFalse(self.model[1].reversed)
self.assertFalse(self.model[2].enabled)
self.assertFalse(self.model[2].reversed)
def test_set_sort_order_trackno_playcount(self):
"""Test setting the Sort Order property to "album DESC, title"."""
self.model.set_sort_order("mediumno, number, playcount")
self.assertEqual(self.model.n_enabled, 2)
self.assertEqual(self.model.sort_order, "mediumno, number, playcount")
self.assertEqual(self.model[0].name, "Track Number")
self.assertTrue(self.model[0].enabled)
self.assertFalse(self.model[0].reversed)
self.assertEqual(self.model[1].name, "Play Count")
self.assertTrue(self.model[1].enabled)
self.assertFalse(self.model[1].reversed)
self.assertFalse(self.model[2].enabled)
self.assertFalse(self.model[2].reversed)
def test_set_sort_order_user(self):
"""Test setting the Sort Order property to "user"."""
self.model[0].enable()
self.model.set_sort_order("user")
self.assertEqual(self.model.n_enabled, 0)
self.assertEqual(self.model.sort_order, "user")
self.assertFalse(self.model[0].enabled)
def test_set_sort_order_same(self):
"""Test setting the Sort Order property to the same value."""
self.model.set_sort_order("user")
notify = unittest.mock.Mock()
self.model.connect("notify::sort-order", notify)
self.model.set_sort_order("user")
notify.assert_not_called()
def test_set_sort_order_none(self):
"""Test setting the Sort Order property to 'None'."""
notify = unittest.mock.Mock()
self.model.connect("notify::sort-order", notify)
self.model.set_sort_order(None)
notify.assert_not_called()