Merge pull request #1082 from adamcik/feature/only-support-new-style-search-in-backends

core/backend: Stop supporting old search signatures
This commit is contained in:
Stein Magnus Jodal 2015-03-25 00:09:06 +01:00
commit d768a3b4f7
4 changed files with 45 additions and 62 deletions

View File

@ -242,25 +242,21 @@ class LibraryController(object):
The ``exact`` keyword argument, which replaces :meth:`find_exact`. The ``exact`` keyword argument, which replaces :meth:`find_exact`.
""" """
query = _normalize_query(query or kwargs) query = _normalize_query(query or kwargs)
futures = [] futures = {}
for backend, backend_uris in self._get_backends_to_uris(uris).items(): for backend, backend_uris in self._get_backends_to_uris(uris).items():
if hasattr(backend.library, 'find_exact'): futures[backend] = backend.library.search(
# Backends with find_exact probably don't have support for query=query, uris=backend_uris, exact=exact)
# search with the exact kwarg, so give them the legacy calls.
if exact:
futures.append(backend.library.find_exact(
query=query, uris=backend_uris))
else:
futures.append(backend.library.search(
query=query, uris=backend_uris))
else:
# Assume backends without find_exact are up to date. Worst case
# the exact gets swallowed by the **kwargs and things hopefully
# still work.
futures.append(backend.library.search(
query=query, uris=backend_uris, exact=exact))
return [result for result in pykka.get_all(futures) if result] results = []
for backend, future in futures.items():
try:
results.append(future.get())
except TypeError:
backend_name = backend.actor_ref.actor_class.__name__
logger.warning(
'%s does not implement library.search() with exact '
'support. Please upgrade it.', backend_name)
return [r for r in results if r]
def _normalize_query(query): def _normalize_query(query):

View File

@ -51,12 +51,7 @@ class LocalLibraryProvider(backend.LibraryProvider):
tracks = [tracks] tracks = [tracks]
return tracks return tracks
def find_exact(self, query=None, uris=None): def search(self, query=None, uris=None, exact=False):
if not self._library: if not self._library:
return None return None
return self._library.search(query=query, uris=uris, exact=True) return self._library.search(query=query, uris=uris, exact=exact)
def search(self, query=None, uris=None):
if not self._library:
return None
return self._library.search(query=query, uris=uris, exact=False)

View File

@ -361,42 +361,35 @@ class CoreLibraryTest(unittest.TestCase):
query={'any': ['foobar']}, uris=None, exact=True) query={'any': ['foobar']}, uris=None, exact=True)
class LegacyLibraryProvider(backend.LibraryProvider): class LegacyFindExactToSearchLibraryTest(unittest.TestCase):
def find_exact(self, query=None, uris=None): def setUp(self): # noqa: N802
pass self.backend = mock.Mock()
self.backend.actor_ref.actor_class.__name__ = 'DummyBackend'
self.backend.uri_schemes.get.return_value = ['dummy']
self.backend.library = mock.Mock(spec=backend.LibraryProvider)
self.core = core.Core(mixer=None, backends=[self.backend])
def test_core_find_exact_calls_backend_search_with_exact(self):
class LegacyCoreLibraryTest(unittest.TestCase): self.core.library.find_exact(query={'any': ['a']})
def test_backend_with_find_exact_gets_find_exact_call(self): self.backend.library.search.assert_called_once_with(
b1 = mock.Mock()
b1.uri_schemes.get.return_value = ['dummy1']
b1.library = mock.Mock(spec=LegacyLibraryProvider)
b2 = mock.Mock()
b2.uri_schemes.get.return_value = ['dummy2']
b2.library = mock.Mock(spec=backend.LibraryProvider)
c = core.Core(mixer=None, backends=[b1, b2])
c.library.find_exact(query={'any': ['a']})
b1.library.find_exact.assert_called_once_with(
query=dict(any=['a']), uris=None)
b2.library.search.assert_called_once_with(
query=dict(any=['a']), uris=None, exact=True) query=dict(any=['a']), uris=None, exact=True)
def test_backend_with_find_exact_gets_search_without_exact_arg(self): def test_core_find_exact_handles_legacy_backend(self):
b1 = mock.Mock() self.backend.library.search.return_value.get.side_effect = TypeError
b1.uri_schemes.get.return_value = ['dummy1'] self.core.library.find_exact(query={'any': ['a']})
b1.library = mock.Mock(spec=LegacyLibraryProvider) # We are just testing that this doesn't fail.
b2 = mock.Mock() def test_core_search_call_backend_search_with_exact(self):
b2.uri_schemes.get.return_value = ['dummy2'] self.core.library.search(query={'any': ['a']})
b2.library = mock.Mock(spec=backend.LibraryProvider) self.backend.library.search.assert_called_once_with(
c = core.Core(mixer=None, backends=[b1, b2])
c.library.search(query={'any': ['a']})
b1.library.search.assert_called_once_with(
query=dict(any=['a']), uris=None)
b2.library.search.assert_called_once_with(
query=dict(any=['a']), uris=None, exact=False) query=dict(any=['a']), uris=None, exact=False)
def test_core_search_with_exact_call_backend_search_with_exact(self):
self.core.library.search(query={'any': ['a']}, exact=True)
self.backend.library.search.assert_called_once_with(
query=dict(any=['a']), uris=None, exact=True)
def test_core_search_with_handles_legacy_backend(self):
self.backend.library.search.return_value.get.side_effect = TypeError
self.core.library.search(query={'any': ['a']}, exact=True)
# We are just testing that this doesn't fail.

View File

@ -46,16 +46,15 @@ class DummyLibraryProvider(backend.LibraryProvider):
def get_distinct(self, field, query=None): def get_distinct(self, field, query=None):
return self.dummy_get_distinct_result.get(field, set()) return self.dummy_get_distinct_result.get(field, set())
def find_exact(self, **query):
return self.dummy_find_exact_result
def lookup(self, uri): def lookup(self, uri):
return [t for t in self.dummy_library if uri == t.uri] return [t for t in self.dummy_library if uri == t.uri]
def refresh(self, uri=None): def refresh(self, uri=None):
pass pass
def search(self, **query): def search(self, query=None, uris=None, exact=False):
if exact: # TODO: remove uses of dummy_find_exact_result
return self.dummy_find_exact_result
return self.dummy_search_result return self.dummy_search_result