1 /****************************************************************************************
2 * Copyright (c) 2014 Leo Franchi <lfranchi@kde.org> *
3 * Copyright (c) 2014 Stefan Derkits <stefan@derkits.at> *
4 * *
5 * This program is free software; you can redistribute it and/or modify it under *
6 * the terms of the GNU General Public License as published by the Free Software *
7 * Foundation; either version 2 of the License, or (at your option) any later *
8 * version. *
9 * *
10 * This program is distributed in the hope that it will be useful, but WITHOUT ANY *
11 * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A *
12 * PARTICULAR PURPOSE. See the GNU General Public License for more details. *
13 * *
14 * You should have received a copy of the GNU General Public License along with *
15 * this program. If not, see <http://www.gnu.org/licenses/>. *
16 ****************************************************************************************/
17
18 #include "Genre.h"
19
20 #include "Genre_p.h"
21 #include "Parsing_p.h"
22
Genre()23 Echonest::Genre::Genre()
24 : d( new GenreData )
25 {
26 init();
27 }
28
29
Genre(const Echonest::Genre & other)30 Echonest::Genre::Genre( const Echonest::Genre& other )
31 : d( other.d )
32 {
33 init();
34 }
35
36
Genre(const QString & name)37 Echonest::Genre::Genre( const QString& name )
38 {
39 init();
40 setName( name );
41 }
42
operator =(const Echonest::Genre & genre)43 Echonest::Genre& Echonest::Genre::operator=( const Echonest::Genre& genre )
44 {
45 d = genre.d;
46 return *this;
47 }
48
49
~Genre()50 Echonest::Genre::~Genre()
51 {
52
53 }
54
init()55 void Echonest::Genre::init()
56 {
57 qRegisterMetaType<Echonest::Genre>("Echonest::Genre");
58 }
59
60
name() const61 QString Echonest::Genre::name() const
62 {
63 return d->name;
64 }
65
66
setName(const QString & name)67 void Echonest::Genre::setName( const QString& name )
68 {
69 d->name = name;
70 }
71
72
artists() const73 Echonest::Artists Echonest::Genre::artists() const
74 {
75 return d->artists;
76 }
77
78
setArtists(const Artists & artists)79 void Echonest::Genre::setArtists( const Artists& artists )
80 {
81 d->artists = artists;
82 }
83
84
wikipediaUrl() const85 QUrl Echonest::Genre::wikipediaUrl() const
86 {
87 return d->wikipedia_url;
88 }
89
90
setWikipediaUrl(const QUrl & url)91 void Echonest::Genre::setWikipediaUrl( const QUrl& url )
92 {
93 d->wikipedia_url = url;
94 }
95
96
description() const97 QString Echonest::Genre::description() const
98 {
99 return d->description;
100 }
101
102
setDescription(const QString & description)103 void Echonest::Genre::setDescription( const QString& description )
104 {
105 d->description = description;
106 }
107
108
fetchArtists(ArtistInformation information,int numResults,bool limit)109 QNetworkReply* Echonest::Genre::fetchArtists( ArtistInformation information, int numResults, bool limit )
110 {
111 QUrl url = setupQuery( "artists", numResults );
112 urlAddQueryItem( url, QLatin1String( "limit" ), QLatin1String( limit ? "true" : "false" ) );
113
114 Artist::addQueryInformation( url, information );
115
116 return Echonest::Config::instance()->nam()->get( QNetworkRequest( url ) );
117 }
118
119
fetchSimilar(GenreInformation information,int numResults,int start)120 QNetworkReply* Echonest::Genre::fetchSimilar( GenreInformation information, int numResults, int start )
121 {
122 QUrl url = setupQuery( "similar", numResults, start );
123 addQueryInformation( url, information );
124
125 return Echonest::Config::instance()->nam()->get( QNetworkRequest( url ) );
126 }
127
128
fetchProfile(const Echonest::Genres & genres,GenreInformation information)129 QNetworkReply* Echonest::Genre::fetchProfile( const Echonest::Genres& genres, GenreInformation information )
130 {
131 QUrl url = setupStaticQuery( "profile" );
132 addQueryInformation( url, information );
133
134 foreach( const Genre& g, genres )
135 urlAddQueryItem( url, QLatin1String( "name" ), QString::fromLatin1( Echonest::escapeSpacesAndPluses( g.name() ) ) );
136
137 return Echonest::Config::instance()->nam()->get( QNetworkRequest( url ) );
138 }
139
140
fetchList(GenreInformation information,int numResults)141 QNetworkReply* Echonest::Genre::fetchList( GenreInformation information, int numResults )
142 {
143 QUrl url = setupStaticQuery( "list", numResults );
144 addQueryInformation( url, information );
145
146 return Echonest::Config::instance()->nam()->get( QNetworkRequest( url ) );
147 }
148
149
fetchSearch(const QString & name,Echonest::GenreInformation information,int numResults,int start)150 QNetworkReply* Echonest::Genre::fetchSearch( const QString& name, Echonest::GenreInformation information, int numResults, int start )
151 {
152 QUrl url = setupStaticQuery( "search", numResults );
153 addQueryInformation( url, information );
154
155 urlAddQueryItem( url, QLatin1String( "name" ), QString::fromLatin1( Echonest::escapeSpacesAndPluses( name ) ) );
156
157 return Echonest::Config::instance()->nam()->get( QNetworkRequest( url ) );
158 }
159
160
parseArtists(QNetworkReply * reply)161 Echonest::Artists Echonest::Genre::parseArtists( QNetworkReply* reply ) throw( Echonest::ParseError )
162 {
163 return Artist::parseSearch( reply );
164 }
165
166
parseSimilar(QNetworkReply * reply)167 Echonest::Genres Echonest::Genre::parseSimilar( QNetworkReply* reply ) throw( Echonest::ParseError )
168 {
169 return parseList( reply );
170 }
171
172
parseProfile(QNetworkReply * reply)173 Echonest::Genres Echonest::Genre::parseProfile( QNetworkReply* reply ) throw( Echonest::ParseError )
174 {
175 return parseList( reply );
176 }
177
178
parseList(QNetworkReply * reply)179 Echonest::Genres Echonest::Genre::parseList( QNetworkReply* reply ) throw( Echonest::ParseError )
180 {
181 Echonest::Parser::checkForErrors( reply );
182
183 QXmlStreamReader xml( reply->readAll() );
184
185 Echonest::Parser::readStatus( xml );
186
187 Echonest::Genres genres = Echonest::Parser::parseGenres( xml );
188
189 reply->deleteLater();
190 return genres;
191 }
192
193
parseSearch(QNetworkReply * reply)194 Echonest::Genres Echonest::Genre::parseSearch( QNetworkReply* reply ) throw( Echonest::ParseError )
195 {
196 return parseList( reply );
197 }
198
199
setupStaticQuery(const QByteArray & methodName,int numResults,int start)200 QUrl Echonest::Genre::setupStaticQuery( const QByteArray& methodName, int numResults, int start )
201 {
202 QUrl url = Echonest::baseGetQuery( "genre", methodName );
203
204 if( numResults > 0 )
205 urlAddQueryItem( url, QLatin1String( "results" ), QString::number( numResults ) );
206 if( start >= 0 )
207 urlAddQueryItem( url, QLatin1String( "start" ), QString::number( start ) );
208
209 return url;
210 }
211
212
setupQuery(const QByteArray & methodName,int numResults,int start) const213 QUrl Echonest::Genre::setupQuery( const QByteArray& methodName, int numResults, int start) const
214 {
215 QUrl url = setupStaticQuery( methodName, numResults, start );
216 if( !d->name.isEmpty() ) {
217 urlAddQueryItem( url, QLatin1String( "name" ), QString::fromLatin1( Echonest::escapeSpacesAndPluses( d->name ) ) );
218 } else if ( methodName != "list" || methodName != "search" ) {
219 qWarning() << "Genre method" << methodName << "called on a genre object without name or id!";
220 return QUrl();
221 }
222 return url;
223 }
224
225
addQueryInformation(QUrl & url,Echonest::GenreInformation information)226 void Echonest::Genre::addQueryInformation( QUrl& url, Echonest::GenreInformation information )
227 {
228 if( information.flags().testFlag( Echonest::GenreInformation::Description ) )
229 urlAddQueryItem( url, QLatin1String( "bucket" ), QLatin1String( "description" ) );
230 if( information.flags().testFlag( Echonest::GenreInformation::Urls ) )
231 urlAddQueryItem( url, QLatin1String( "bucket" ), QLatin1String( "urls" ) );
232 }
233
234
operator <<(QDebug d,const Echonest::Genre & genre)235 QDebug Echonest::operator<<(QDebug d, const Echonest::Genre& genre)
236 {
237 return d.maybeSpace() << QString::fromLatin1( "Genre(%1)" ).arg( genre.name() );
238 }
239