Pregunta

I recently started using libspotify and were writing a simple hello world, based on the sample code of jukebox.h.

My code currently looks like this:

#include <stdio.h>
#include "libspotify/api.h"
#include "Key.h"
#include "Password.h"
#include <stdlib.h>
#include <pthread.h>
#include <time.h>

#define true 1
#define false 0

sp_session *g_session;
bool g_notify_do;
static pthread_mutex_t g_notify_mutex;
static pthread_cond_t g_notify_cond;

#define DEBUG 1

__stdcall static void debug(const char *format, ...) {
    if (!DEBUG)
        return;

    va_list argptr;
    va_start(argptr, format);
    vprintf(format, argptr);
    printf("\n");
}

void assertSpotify(sp_error error, char *details) {
    if (error != SP_ERROR_OK) {
        debug("Fatal error: %s", details);
        exit(1);
    }
}

__stdcall static void notify_main_thread(sp_session *sess) {
    pthread_mutex_lock(&g_notify_mutex);
    g_notify_do = 1;
    pthread_cond_signal(&g_notify_cond);
    pthread_mutex_unlock(&g_notify_mutex);
}

__stdcall static void logged_in(sp_session *sess, sp_error error) {
    assertSpotify(error, "Could not log in.");

    sp_playlistcontainer *pc = sp_session_playlistcontainer(sess);
    printf("Looking at %d playlists\n", sp_playlistcontainer_num_playlists(pc));
}

int main(void) {
    sp_error err;
    static sp_session_callbacks session_callbacks = {};
    static sp_session_config spconfig = {};
    int next_timeout = 0;

    printf("Starting up...\n");
    session_callbacks.notify_main_thread = &notify_main_thread;
    session_callbacks.logged_in = &logged_in;

    spconfig.api_version = SPOTIFY_API_VERSION;
    spconfig.cache_location = "tmp";
    spconfig.settings_location = "tmp";
    spconfig.application_key = g_appkey;
    spconfig.application_key_size = g_appkey_size;
    spconfig.user_agent = "Hello-World";
    spconfig.callbacks = &session_callbacks;

    pthread_mutex_init(&g_notify_mutex, NULL);
    pthread_cond_init(&g_notify_cond, NULL);

    err = sp_session_create(&spconfig, &g_session);
    assertSpotify(err, "Could not create Spotify Session.");
    debug("Session created.");

    err = sp_session_login(g_session, spotify_user, spotify_pw, 0, NULL); //Defined in Password.h
    assertSpotify(err, "Could not log in.");
    debug("Username: %s", sp_session_user_name(g_session));
    err = sp_session_set_connection_type(g_session, SP_CONNECTION_TYPE_WIRED );
    assertSpotify(err, "Could not set connection type.");
    pthread_mutex_lock(&g_notify_mutex);

    while (true) {
        if (next_timeout == 0) {
            while(!g_notify_do)
                pthread_cond_wait(&g_notify_cond, &g_notify_mutex);
        } else {
            time_t now = time(NULL);
            struct timespec ts;
            ts.tv_sec = now;
            ts.tv_sec = now / 1000000;
            ts.tv_sec += next_timeout / 1000;
            ts.tv_nsec += (next_timeout % 1000) * 1000000;
            pthread_cond_timedwait(&g_notify_cond, &g_notify_mutex, &ts);
        }

        g_notify_do = false;
        pthread_mutex_unlock(&g_notify_mutex);
        do {
            sp_session_process_events(g_session, &next_timeout);
        } while (next_timeout == 0);
        pthread_mutex_lock(&g_notify_mutex);
    }

    return 0;
}

The problem is, that sp_playlistcontainer_num_playlists returns 0, even if my account has about 10 Playlists.

My System: Windows 7 x64 with MinGW.

What am I doing wrong?

¿Fue útil?

Solución

Looking at the source of jukebox.c it seems like you should make sure that the playlist container is fully loaded before trying to query it for playlists. So if I understand it correctly you should add a callback for container_loaded.
I also think you should setup a callback so you will be notified when the user is logged in and when logged in you should try to get the playlist container. Something like this might help:

static sp_playlistcontainer_callbacks pc_callbacks = {
   NULL, /* playlist_added */
   NULL, /* playlist_removed */
   NULL, /* playlist_moved */
   &container_loaded,
};
static sp_session_callbacks session_callbacks = {
   &logged_in,
   &notify_main_thread,
   NULL, /* music_delivery */
   NULL, /* metadata_updated */
   NULL, /* play_token_lost */
   NULL, /* log_message */
   NULL  /* end_of_track */
};
static void container_loaded(sp_playlistcontainer *pc, void *userdata)
{
   // container is fully loaded now it should be safe to query the container
   int num_playlists = sp_playlistcontainer_num_playlists(pc);
}
static void logged_in(sp_session *sess, sp_error error)
{
    // get playlist when user is logged in
    sp_playlistcontainer *pc = sp_session_playlistcontainer(sess);

    // add callbacks
    sp_playlistcontainer_add_callbacks(
    pc,
    &pc_callbacks,
    NULL);
    /* rest of code */
}
Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top