From 18ebfad7c5833f24365e8316caf83ce0589ecedc Mon Sep 17 00:00:00 2001 From: Mathias Gawlista Date: Tue, 22 Jan 2013 16:04:15 +0100 Subject: [PATCH] Implements MusicBrainz::ReleaseGroup.search and .find_by_artist_and_title --- README.md | 3 + lib/musicbrainz.rb | 1 + .../bindings/release_group_search.rb | 20 +++++ lib/musicbrainz/models/release_group.rb | 17 ++++ spec/bindings/release_group_search_spec.rb | 17 ++++ spec/models/release_group_spec.rb | 79 +++++++++++++------ 6 files changed, 113 insertions(+), 24 deletions(-) create mode 100644 lib/musicbrainz/bindings/release_group_search.rb create mode 100644 spec/bindings/release_group_search_spec.rb diff --git a/README.md b/README.md index 95d65a3..25f502f 100644 --- a/README.md +++ b/README.md @@ -80,6 +80,9 @@ MusicBrainz::ReleaseGroup ```ruby # Class Methods MusicBrainz::ReleaseGroup.find(id) +MusicBrainz::ReleaseGroup.find_by_artist_and_title(artist_name, title, type: 'Album') +MusicBrainz::ReleaseGroup.search(artist_name, title) +MusicBrainz::ReleaseGroup.search(artist_name, title, type: 'Album') # Instance Methods @release_group.releases diff --git a/lib/musicbrainz.rb b/lib/musicbrainz.rb index a3a7c29..16390ec 100644 --- a/lib/musicbrainz.rb +++ b/lib/musicbrainz.rb @@ -24,6 +24,7 @@ require "musicbrainz/bindings/artist" require "musicbrainz/bindings/artist_search" require "musicbrainz/bindings/artist_release_groups" require "musicbrainz/bindings/release_group" +require "musicbrainz/bindings/release_group_search" require "musicbrainz/bindings/release_group_releases" require "musicbrainz/bindings/release" require "musicbrainz/bindings/release_tracks" diff --git a/lib/musicbrainz/bindings/release_group_search.rb b/lib/musicbrainz/bindings/release_group_search.rb new file mode 100644 index 0000000..7766dee --- /dev/null +++ b/lib/musicbrainz/bindings/release_group_search.rb @@ -0,0 +1,20 @@ +# encoding: UTF-8 +module MusicBrainz + module Bindings + module ReleaseGroupSearch + def parse(xml) + xml.xpath('./release-group-list/release-group').map do |xml| + { + id: (xml.attribute('id').value rescue nil), + mbid: (xml.attribute('id').value rescue nil), # Old shit + title: (xml.xpath('./title').text.gsub(/[`’]/, "'") rescue nil), + type: (xml.attribute('type').value rescue nil), + score: (xml.attribute('score').value.to_i rescue nil) + } rescue nil + end.delete_if{ |item| item.nil? } + end + + extend self + end + end +end diff --git a/lib/musicbrainz/models/release_group.rb b/lib/musicbrainz/models/release_group.rb index 42f35a1..ec8215e 100644 --- a/lib/musicbrainz/models/release_group.rb +++ b/lib/musicbrainz/models/release_group.rb @@ -23,6 +23,23 @@ module MusicBrainz create_model: :release_group }) end + + def search(artist_name, title, options = {}) + artist_name = CGI.escape(artist_name).gsub(/\!/, '\!') + title = CGI.escape(title).gsub(/\!/, '\!') + query = ["artist:\"#{artist_name}\"", "releasegroup:\"#{title}\""] + query << "type: #{options[:type]}" if options[:type] + + client.load( + :release_group, { query: query.join(' AND '), limit: 10 }, + { binding: :release_group_search } + ) + end + + def find_by_artist_and_title(artist_name, title, options = {}) + matches = search(artist_name, title, options) + matches.empty? ? nil : find(matches.first[:id]) + end end end end diff --git a/spec/bindings/release_group_search_spec.rb b/spec/bindings/release_group_search_spec.rb new file mode 100644 index 0000000..d1ff347 --- /dev/null +++ b/spec/bindings/release_group_search_spec.rb @@ -0,0 +1,17 @@ +# -*- encoding: utf-8 -*- + +require "spec_helper" + +describe MusicBrainz::Bindings::ReleaseGroupSearch do + describe '.parse' do + it "gets correct release group data" do + response = 'Empire' + described_class.parse(Nokogiri::XML.parse(response)).should == [ + { + id: '246bc928-2dc8-35ba-80ee-7a0079de1632', mbid: '246bc928-2dc8-35ba-80ee-7a0079de1632', + title: 'Empire', type: 'Single', score: 100 + } + ] + end + end +end \ No newline at end of file diff --git a/spec/models/release_group_spec.rb b/spec/models/release_group_spec.rb index c677093..d4ad0b8 100644 --- a/spec/models/release_group_spec.rb +++ b/spec/models/release_group_spec.rb @@ -3,32 +3,63 @@ require "spec_helper" describe MusicBrainz::ReleaseGroup do - it "gets no exception while loading release group info" do - lambda { - MusicBrainz::ReleaseGroup.find("6f33e0f0-cde2-38f9-9aee-2c60af8d1a61") - }.should_not raise_error(Exception) + describe '.find' do + it "gets no exception while loading release group info" do + lambda { + MusicBrainz::ReleaseGroup.find("6f33e0f0-cde2-38f9-9aee-2c60af8d1a61") + }.should_not raise_error(Exception) + end + + it "gets correct instance" do + release_group = MusicBrainz::ReleaseGroup.find("6f33e0f0-cde2-38f9-9aee-2c60af8d1a61") + release_group.should be_an_instance_of(MusicBrainz::ReleaseGroup) + end + + it "gets correct release group data" do + release_group = MusicBrainz::ReleaseGroup.find("6f33e0f0-cde2-38f9-9aee-2c60af8d1a61") + release_group.id.should == "6f33e0f0-cde2-38f9-9aee-2c60af8d1a61" + release_group.type.should == "Album" + release_group.title.should == "Empire" + release_group.first_release_date.should == Date.new(2006, 8, 28) + end end - - it "gets correct instance" do - release_group = MusicBrainz::ReleaseGroup.find("6f33e0f0-cde2-38f9-9aee-2c60af8d1a61") - release_group.should be_an_instance_of(MusicBrainz::ReleaseGroup) + + describe '.search' do + context 'without type filter' do + it "searches release group by artist name and title" do + matches = MusicBrainz::ReleaseGroup.search('Kasabian', 'Empire') + matches.length.should be > 0 + matches.first[:title].should == 'Empire' + matches.first[:type].should == 'Single' + end + end + + context 'with type filter' do + it "searches release group by artist name and title" do + matches = MusicBrainz::ReleaseGroup.search('Kasabian', 'Empire', type: 'Album') + matches.length.should be > 0 + matches.first[:title].should == 'Empire' + matches.first[:type].should == 'Album' + end + end end - - it "gets correct release group data" do - release_group = MusicBrainz::ReleaseGroup.find("6f33e0f0-cde2-38f9-9aee-2c60af8d1a61") - release_group.id.should == "6f33e0f0-cde2-38f9-9aee-2c60af8d1a61" - release_group.type.should == "Album" - release_group.title.should == "Empire" - release_group.first_release_date.should == Date.new(2006, 8, 28) + + describe '.find_by_artist_and_title' do + it "gets first release group by artist name and title" do + release_group = MusicBrainz::ReleaseGroup.find_by_artist_and_title('Kasabian', 'Empire') + release_group.id.should == '246bc928-2dc8-35ba-80ee-7a0079de1632' + end end - - it "gets correct release group's releases" do - releases = MusicBrainz::ReleaseGroup.find("6f33e0f0-cde2-38f9-9aee-2c60af8d1a61").releases - releases.length.should be >= 5 - releases.first.id.should == "2225dd4c-ae9a-403b-8ea0-9e05014c778f" - releases.first.status.should == "Official" - releases.first.title.should == "Empire" - releases.first.date.should == Date.new(2006, 8, 28) - releases.first.country.should == "GB" + + describe '#releases' do + it "gets correct release group's releases" do + releases = MusicBrainz::ReleaseGroup.find("6f33e0f0-cde2-38f9-9aee-2c60af8d1a61").releases + releases.length.should be >= 5 + releases.first.id.should == "2225dd4c-ae9a-403b-8ea0-9e05014c778f" + releases.first.status.should == "Official" + releases.first.title.should == "Empire" + releases.first.date.should == Date.new(2006, 8, 28) + releases.first.country.should == "GB" + end end end