Add support for artist group request (experimental)

The purpose of this is mainly to support Hyperfine Remote for Android
This commit is contained in:
ejurgensen 2013-08-29 22:00:37 +02:00
parent 799fe9e684
commit 95fc525beb
6 changed files with 81 additions and 25 deletions

View File

@ -41,7 +41,7 @@ QUOTE : '\'';
LPAR : '('; LPAR : '(';
RPAR : ')'; RPAR : ')';
OPAND : '+'; OPAND : '+' | ' ';
OPOR : ','; OPOR : ',';
NEWLINE : '\r'? '\n'; NEWLINE : '\r'? '\n';

View File

@ -879,13 +879,13 @@ artwork_get_group(int id, int max_w, int max_h, int format, struct evbuffer *evb
files_art: files_art:
memset(&qp, 0, sizeof(struct query_params)); memset(&qp, 0, sizeof(struct query_params));
qp.type = Q_GROUPITEMS; qp.type = Q_GROUP_ITEMS;
qp.id = id; qp.id = id;
ret = db_query_start(&qp); ret = db_query_start(&qp);
if (ret < 0) if (ret < 0)
{ {
DPRINTF(E_LOG, L_ART, "Could not start Q_GROUPITEMS query\n"); DPRINTF(E_LOG, L_ART, "Could not start Q_GROUP_ITEMS query\n");
return -1; return -1;
} }
@ -899,7 +899,7 @@ artwork_get_group(int id, int max_w, int max_h, int format, struct evbuffer *evb
db_query_end(&qp); db_query_end(&qp);
if (ret < 0) if (ret < 0)
DPRINTF(E_LOG, L_ART, "Error fetching Q_GROUPITEMS results\n"); DPRINTF(E_LOG, L_ART, "Error fetching Q_GROUP_ITEMS results\n");
else if (got_art > 0) else if (got_art > 0)
return got_art; return got_art;

View File

@ -232,12 +232,13 @@ static const ssize_t dbpli_cols_map[] =
}; };
/* This list must be kept in sync with /* This list must be kept in sync with
* - the order of fields in the Q_GROUPS query * - the order of fields in the Q_GROUP_ALBUMS and Q_GROUP_ARTISTS query
* - the name of the fields in struct group_info * - the name of the fields in struct group_info
*/ */
static const ssize_t dbgri_cols_map[] = static const ssize_t dbgri_cols_map[] =
{ {
dbgri_offsetof(itemcount), dbgri_offsetof(itemcount),
dbgri_offsetof(groupalbumcount),
dbgri_offsetof(id), dbgri_offsetof(id),
dbgri_offsetof(persistentid), dbgri_offsetof(persistentid),
dbgri_offsetof(songalbumartist), dbgri_offsetof(songalbumartist),
@ -967,7 +968,7 @@ db_build_query_plitems(struct query_params *qp, char **q)
} }
static int static int
db_build_query_groups(struct query_params *qp, char **q) db_build_query_group_albums(struct query_params *qp, char **q)
{ {
char *query; char *query;
char *idx; char *idx;
@ -983,13 +984,13 @@ db_build_query_groups(struct query_params *qp, char **q)
return -1; return -1;
if (idx && qp->filter) if (idx && qp->filter)
query = sqlite3_mprintf("SELECT COUNT(*), g.id, g.persistentid, f.album_artist, g.name FROM files f, groups g WHERE f.songalbumid = g.persistentid AND g.type = %d AND f.disabled = 0 AND %s GROUP BY f.album, g.name %s;", G_ALBUMS, qp->filter, idx); query = sqlite3_mprintf("SELECT COUNT(*), 1, g.id, g.persistentid, f.album_artist, g.name FROM files f, groups g WHERE f.songalbumid = g.persistentid AND g.type = %d AND f.disabled = 0 AND %s GROUP BY f.album, g.name %s;", G_ALBUMS, qp->filter, idx);
else if (idx) else if (idx)
query = sqlite3_mprintf("SELECT COUNT(*), g.id, g.persistentid, f.album_artist, g.name FROM files f, groups g WHERE f.songalbumid = g.persistentid AND g.type = %d AND f.disabled = 0 GROUP BY f.album, g.name %s;", G_ALBUMS, idx); query = sqlite3_mprintf("SELECT COUNT(*), 1, g.id, g.persistentid, f.album_artist, g.name FROM files f, groups g WHERE f.songalbumid = g.persistentid AND g.type = %d AND f.disabled = 0 GROUP BY f.album, g.name %s;", G_ALBUMS, idx);
else if (qp->filter) else if (qp->filter)
query = sqlite3_mprintf("SELECT COUNT(*), g.id, g.persistentid, f.album_artist, g.name FROM files f, groups g WHERE f.songalbumid = g.persistentid AND g.type = %d AND f.disabled = 0 AND %s GROUP BY f.album, g.name;", G_ALBUMS, qp->filter); query = sqlite3_mprintf("SELECT COUNT(*), 1, g.id, g.persistentid, f.album_artist, g.name FROM files f, groups g WHERE f.songalbumid = g.persistentid AND g.type = %d AND f.disabled = 0 AND %s GROUP BY f.album, g.name;", G_ALBUMS, qp->filter);
else else
query = sqlite3_mprintf("SELECT COUNT(*), g.id, g.persistentid, f.album_artist, g.name FROM files f, groups g WHERE f.songalbumid = g.persistentid AND g.type = %d AND f.disabled = 0 GROUP BY f.album, g.name;", G_ALBUMS); query = sqlite3_mprintf("SELECT COUNT(*), 1, g.id, g.persistentid, f.album_artist, g.name FROM files f, groups g WHERE f.songalbumid = g.persistentid AND g.type = %d AND f.disabled = 0 GROUP BY f.album, g.name;", G_ALBUMS);
if (!query) if (!query)
{ {
@ -1003,7 +1004,43 @@ db_build_query_groups(struct query_params *qp, char **q)
} }
static int static int
db_build_query_groupitems(struct query_params *qp, char **q) db_build_query_group_artists(struct query_params *qp, char **q)
{
char *query;
char *idx;
int ret;
qp->results = db_get_count("SELECT COUNT(DISTINCT f.album_artist) FROM files f WHERE f.disabled = 0;");
if (qp->results < 0)
return -1;
/* Get index clause */
ret = db_build_query_index_clause(qp, &idx);
if (ret < 0)
return -1;
if (idx && qp->filter)
query = sqlite3_mprintf("SELECT COUNT(*), COUNT(DISTINCT f.album), 1, 1, f.album_artist, f.album_artist FROM files f WHERE f.disabled = 0 AND %s GROUP BY f.album_artist %s;", qp->filter, idx);
else if (idx)
query = sqlite3_mprintf("SELECT COUNT(*), COUNT(DISTINCT f.album), 1, 1, f.album_artist, f.album_artist FROM files f WHERE f.disabled = 0 GROUP BY f.album_artist %s;", idx);
else if (qp->filter)
query = sqlite3_mprintf("SELECT COUNT(*), COUNT(DISTINCT f.album), 1, 1, f.album_artist, f.album_artist FROM files f WHERE f.disabled = 0 AND %s GROUP BY f.album_artist;", qp->filter);
else
query = sqlite3_mprintf("SELECT COUNT(*), COUNT(DISTINCT f.album), 1, 1, f.album_artist, f.album_artist FROM files f WHERE f.disabled = 0 GROUP BY f.album_artist;");
if (!query)
{
DPRINTF(E_LOG, L_DB, "Out of memory for query string\n");
return -1;
}
*q = query;
return 0;
}
static int
db_build_query_group_items(struct query_params *qp, char **q)
{ {
char *query; char *query;
char *count; char *count;
@ -1189,12 +1226,16 @@ db_query_start(struct query_params *qp)
ret = db_build_query_plitems(qp, &query); ret = db_build_query_plitems(qp, &query);
break; break;
case Q_GROUPS: case Q_GROUP_ALBUMS:
ret = db_build_query_groups(qp, &query); ret = db_build_query_group_albums(qp, &query);
break; break;
case Q_GROUPITEMS: case Q_GROUP_ARTISTS:
ret = db_build_query_groupitems(qp, &query); ret = db_build_query_group_artists(qp, &query);
break;
case Q_GROUP_ITEMS:
ret = db_build_query_group_items(qp, &query);
break; break;
case Q_GROUP_DIRS: case Q_GROUP_DIRS:
@ -1269,7 +1310,7 @@ db_query_fetch_file(struct query_params *qp, struct db_media_file_info *dbmfi)
return -1; return -1;
} }
if ((qp->type != Q_ITEMS) && (qp->type != Q_PLITEMS) && (qp->type != Q_GROUPITEMS)) if ((qp->type != Q_ITEMS) && (qp->type != Q_PLITEMS) && (qp->type != Q_GROUP_ITEMS))
{ {
DPRINTF(E_LOG, L_DB, "Not an items, playlist or group items query!\n"); DPRINTF(E_LOG, L_DB, "Not an items, playlist or group items query!\n");
return -1; return -1;
@ -1405,7 +1446,7 @@ db_query_fetch_group(struct query_params *qp, struct db_group_info *dbgri)
return -1; return -1;
} }
if (qp->type != Q_GROUPS) if ((qp->type != Q_GROUP_ALBUMS) && (qp->type != Q_GROUP_ARTISTS))
{ {
DPRINTF(E_LOG, L_DB, "Not a groups query!\n"); DPRINTF(E_LOG, L_DB, "Not a groups query!\n");
return -1; return -1;

View File

@ -33,9 +33,10 @@ enum query_type {
Q_BROWSE_ALBUMS = Q_F_BROWSE | (1 << 4), Q_BROWSE_ALBUMS = Q_F_BROWSE | (1 << 4),
Q_BROWSE_GENRES = Q_F_BROWSE | (1 << 5), Q_BROWSE_GENRES = Q_F_BROWSE | (1 << 5),
Q_BROWSE_COMPOSERS = Q_F_BROWSE | (1 << 6), Q_BROWSE_COMPOSERS = Q_F_BROWSE | (1 << 6),
Q_GROUPS = (1 << 7), Q_GROUP_ALBUMS = (1 << 7),
Q_GROUPITEMS = (1 << 8), Q_GROUP_ARTISTS = (1 << 8),
Q_GROUP_DIRS = Q_F_BROWSE | (1 << 9), Q_GROUP_ITEMS = (1 << 9),
Q_GROUP_DIRS = Q_F_BROWSE | (1 << 10),
}; };
struct query_params { struct query_params {
@ -190,6 +191,7 @@ struct db_group_info {
char *persistentid; char *persistentid;
char *itemname; char *itemname;
char *itemcount; char *itemcount;
char *groupalbumcount;
char *songalbumartist; char *songalbumartist;
}; };

View File

@ -101,6 +101,7 @@ const struct dmap_field_map dfm_dmap_aeSP = { -1,
static const struct dmap_field_map dfm_dmap_aePS = { -1, -1, -1 }; static const struct dmap_field_map dfm_dmap_aePS = { -1, -1, -1 };
static const struct dmap_field_map dfm_dmap_ascd = { dbmfi_offsetof(codectype), -1, -1 }; static const struct dmap_field_map dfm_dmap_ascd = { dbmfi_offsetof(codectype), -1, -1 };
static const struct dmap_field_map dfm_dmap_ascs = { -1, -1, -1 }; static const struct dmap_field_map dfm_dmap_ascs = { -1, -1, -1 };
static const struct dmap_field_map dfm_dmap_agac = { -1, -1, dbgri_offsetof(groupalbumcount) };
static const struct dmap_field_map dfm_dmap_agrp = { dbmfi_offsetof(grouping), -1, -1 }; static const struct dmap_field_map dfm_dmap_agrp = { dbmfi_offsetof(grouping), -1, -1 };
static const struct dmap_field_map dfm_dmap_aeSV = { -1, -1, -1 }; static const struct dmap_field_map dfm_dmap_aeSV = { -1, -1, -1 };
static const struct dmap_field_map dfm_dmap_aePI = { -1, -1, -1 }; static const struct dmap_field_map dfm_dmap_aePI = { -1, -1, -1 };
@ -162,6 +163,7 @@ struct dmap_field;
"com.apple.itunes.smart-playlist", "aeSP", &dfm_dmap_aeSP, DMAP_TYPE_UBYTE "com.apple.itunes.smart-playlist", "aeSP", &dfm_dmap_aeSP, DMAP_TYPE_UBYTE
"com.apple.itunes.season-num", "aeSU", &dfm_dmap_aeSU, DMAP_TYPE_UINT "com.apple.itunes.season-num", "aeSU", &dfm_dmap_aeSU, DMAP_TYPE_UINT
"com.apple.itunes.music-sharing-version", "aeSV", &dfm_dmap_aeSV, DMAP_TYPE_UINT "com.apple.itunes.music-sharing-version", "aeSV", &dfm_dmap_aeSV, DMAP_TYPE_UINT
"daap.groupalbumcount", "agac", &dfm_dmap_agac, DMAP_TYPE_UINT
"daap.songgrouping", "agrp", &dfm_dmap_agrp, DMAP_TYPE_STRING "daap.songgrouping", "agrp", &dfm_dmap_agrp, DMAP_TYPE_STRING
"daap.databaseplaylists", "aply", &dfm_dmap_aply, DMAP_TYPE_LIST "daap.databaseplaylists", "aply", &dfm_dmap_aply, DMAP_TYPE_LIST
"daap.playlistrepeatmode", "aprm", &dfm_dmap_aprm, DMAP_TYPE_UBYTE "daap.playlistrepeatmode", "aprm", &dfm_dmap_aprm, DMAP_TYPE_UBYTE

View File

@ -1515,6 +1515,7 @@ daap_reply_groups(struct evhttp_request *req, struct evbuffer *evbuf, char **uri
struct sort_ctx *sctx; struct sort_ctx *sctx;
const char *param; const char *param;
char **strval; char **strval;
int group_type;
int nmeta; int nmeta;
int sort_headers; int sort_headers;
int ngrp; int ngrp;
@ -1527,8 +1528,17 @@ daap_reply_groups(struct evhttp_request *req, struct evbuffer *evbuf, char **uri
if (!s) if (!s)
return; return;
/* For now we only support album groups */ param = evhttp_find_header(query, "group-type");
if (strcmp(param, "artists") == 0)
{
tag = "agar";
group_type = Q_GROUP_ARTISTS;
}
else
{
tag = "agal"; tag = "agal";
group_type = Q_GROUP_ALBUMS;
}
ret = evbuffer_expand(evbuf, 61); ret = evbuffer_expand(evbuf, 61);
if (ret < 0) if (ret < 0)
@ -1595,7 +1605,7 @@ daap_reply_groups(struct evhttp_request *req, struct evbuffer *evbuf, char **uri
memset(&qp, 0, sizeof(struct query_params)); memset(&qp, 0, sizeof(struct query_params));
get_query_params(query, &sort_headers, &qp); get_query_params(query, &sort_headers, &qp);
qp.type = Q_GROUPS; qp.type = group_type;
sctx = NULL; sctx = NULL;
if (sort_headers) if (sort_headers)
@ -1669,7 +1679,8 @@ daap_reply_groups(struct evhttp_request *req, struct evbuffer *evbuf, char **uri
if ((ret == 0) && (val > 0)) if ((ret == 0) && (val > 0))
dmap_add_int(group, "mimc", val); dmap_add_int(group, "mimc", val);
/* Song album artist, always added (asaa) */ /* Song album artist (asaa), always added if group-type is albums */
if (group_type == Q_GROUP_ALBUMS)
dmap_add_string(group, "asaa", dbgri.songalbumartist); dmap_add_string(group, "asaa", dbgri.songalbumartist);
/* Item id (miid) */ /* Item id (miid) */