Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add browse_collections method #274

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
34 changes: 34 additions & 0 deletions examples/browse.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
#!/usr/bin/env python
"""
Browse entities on musicbrainz
"""
import json
import sys
from argparse import ArgumentParser

import musicbrainzngs

musicbrainzngs.set_useragent(
"python-musicbrainzngs-example",
"0.1",
"https://github.com/alastair/python-musicbrainzngs/",
)

if __name__ == '__main__':
parser = ArgumentParser()
parser.add_argument(
"entity_type",
choices=["collection"],
help="The type of entity we're trying to get"
)
parser.add_argument("linked_entity_type", help="The entity type it's linked to")
parser.add_argument("mbid", help="The ID of the linked entity")
args = parser.parse_args()

result = {}
if args.entity_type == "collection":
result = musicbrainzngs.browse_collections(args.linked_entity_type, args.mbid)
else:
print("Invalid entity type passed", file=sys.stderr)
exit(1)
print(json.dumps(result, indent=2))
32 changes: 28 additions & 4 deletions musicbrainzngs/musicbrainz.py
Original file line number Diff line number Diff line change
Expand Up @@ -83,6 +83,7 @@
}
VALID_BROWSE_INCLUDES = {
'artist': ["aliases"] + TAG_INCLUDES + RATING_INCLUDES + RELATION_INCLUDES,
'collection': [],
'event': ["aliases"] + TAG_INCLUDES + RATING_INCLUDES + RELATION_INCLUDES,
'label': ["aliases"] + TAG_INCLUDES + RATING_INCLUDES + RELATION_INCLUDES,
'recording': ["artist-credits", "isrcs"] + TAG_INCLUDES + RATING_INCLUDES + RELATION_INCLUDES,
Expand All @@ -94,6 +95,11 @@
'work': ["aliases", "annotation"] + TAG_INCLUDES + RATING_INCLUDES + RELATION_INCLUDES,
}

VALID_BROWSE_LINK_ENTITIES = {
'collection': ["area", "artist", "editor", "event", "label", "place", "recording", "release", "release-group",
"work"]
}

#: These can be used to filter whenever releases are includes or browsed
VALID_RELEASE_TYPES = [
"nat",
Expand Down Expand Up @@ -284,6 +290,10 @@ def _docstring_browse(entity):
includes = list(VALID_BROWSE_INCLUDES.get(entity, []))
return _docstring_impl("includes", includes)

def _docstring_browse_links(entity):
includes = list(VALID_BROWSE_LINK_ENTITIES.get(entity, []))
return _docstring_impl("link_entities", includes)

def _docstring_search(entity):
search_fields = list(VALID_SEARCH_FIELDS.get(entity, []))
return _docstring_impl("fields", search_fields)
Expand Down Expand Up @@ -710,7 +720,7 @@ def _get_auth_type(entity, id, includes):
return AUTH_NO


def _do_mb_query(entity, id, includes=[], params={}):
def _do_mb_query(entity, id, includes=[], params={}, auth_type=None):
"""Make a single GET call to the MusicBrainz XML API. `entity` is a
string indicated the type of object to be retrieved. The id may be
empty, in which case the query is a search. `includes` is a list
Expand All @@ -722,7 +732,7 @@ def _do_mb_query(entity, id, includes=[], params={}):
if not isinstance(includes, list):
includes = [includes]
_check_includes(entity, includes)
auth_required = _get_auth_type(entity, id, includes)
auth_required = auth_type or _get_auth_type(entity, id, includes)
args = dict(params)
if len(includes) > 0:
inc = " ".join(includes)
Expand Down Expand Up @@ -1064,7 +1074,7 @@ def get_works_by_iswc(iswc, includes=[]):
return _do_mb_query("iswc", iswc, includes)


def _browse_impl(entity, includes, limit, offset, params, release_status=[], release_type=[]):
def _browse_impl(entity, includes, limit, offset, params, release_status=[], release_type=[], auth_type=None):
includes = includes if isinstance(includes, list) else [includes]
valid_includes = VALID_BROWSE_INCLUDES[entity]
_check_includes_impl(includes, valid_includes)
Expand All @@ -1078,7 +1088,7 @@ def _browse_impl(entity, includes, limit, offset, params, release_status=[], rel
if offset: p["offset"] = offset
filterp = _check_filter_and_make_params(entity, includes, release_status, release_type)
p.update(filterp)
return _do_mb_query(entity, "", includes, p)
return _do_mb_query(entity, "", includes, p, auth_type=auth_type)

# Browse methods
# Browse include are a subset of regular get includes, so we check them here
Expand All @@ -1096,6 +1106,20 @@ def browse_artists(recording=None, release=None, release_group=None,
"work": work}
return _browse_impl("artist", includes, limit, offset, params)

@_docstring_browse_links("collection")
def browse_collections(entity_type, entity_mbid, includes=None, limit=None, offset=None):
"""Get all collections linked to a given entity.
You need to give one MusicBrainz ID.

*Available entity_types*: {link_entities}"""
includes = includes or []
valid_linked_entities = VALID_BROWSE_LINK_ENTITIES["collection"]
if entity_type not in valid_linked_entities:
raise ValueError("Not a valid linked entity type", valid_linked_entities)

params = dict([(entity_type, entity_mbid)])
return _browse_impl("collection", includes, limit, offset, params, auth_type=AUTH_IFSET)

@_docstring_browse("event")
def browse_events(area=None, artist=None, place=None,
includes=[], limit=None, offset=None):
Expand Down
7 changes: 7 additions & 0 deletions test/test_browse.py
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,13 @@ def test_browse_artist(self):
musicbrainzngs.browse_artists(work=work)
self.assertEqual("https://musicbrainz.org/ws/2/artist/?work=deb27b88-cf41-4f7c-b3aa-bc3268bc3c02", self.opener.get_url())

def test_browse_collection(self):
musicbrainzngs.browse_collections("release", "5fa83c79-ef7d-42ad-8a09-30a1d4c35f63")
self.assertEqual("https://musicbrainz.org/ws/2/collection/?release=5fa83c79-ef7d-42ad-8a09-30a1d4c35f63", self.opener.get_url())

with self.assertRaises(ValueError):
musicbrainzngs.browse_collections("I don't exist", "just whatever")

def test_browse_event(self):
area = "f03d09b3-39dc-4083-afd6-159e3f0d462f"
musicbrainzngs.browse_events(area=area)
Expand Down