Skip to content

Spirc task not working in spawn task? #1515

@GChalony

Description

@GChalony

I'm using librespot as a library for a player I've developping (which reads NFC tags and plays the corresponding music). This works fine, but I tried to refactor the code so that I can control the playback with buttons on the box. I moved the logic to a tokio task, and nothing happens anymore. The player is not playing any music, nor pausing / skipping to the next song.

To make it clearer, here is the code that works

fn main() {
    let mut reader = nfc_reader::Pn532Nfc::new().expect("Couldn't setup PN532");
    let mut music_player = MusicImpl::new().await.expect("Couldn't create music player");

    loop {
        info!("Waiting for tag");
        let tag = reader.read().await.expect("Couldn't read tag");

        info!("Reading music {tag}");
        music_player.play(&tag);

        info!("Waiting for removal");
        reader.wait_for_removal().await;

        info!("Pausing music");
        music_player.pause();
    }
}

And here is what I have tried:

fn main() {
    let mut reader = nfc_reader::Pn532Nfc::new().expect("Couldn't setup PN532");
    let mut music_player = MusicImpl::new().await.expect("Couldn't create music player");

    // Spawn music player task
    let (button_tx, mut button_rx) = mpsc::channel();
    
    tokio::spawn(async move {
        info!("Created music player");

        music_player.play("spotify:album:6Xvc1TfpVEhDeHhmTQEtp0").expect("Couldn't play");    // This works, the album starts playing

        while let Ok(request) = button_rx.recv() {
            info!("Received music request {request:?}");                    // Requests are correctly received
            match request {
                MusicRequest::Next => music_player.next(),
                MusicRequest::Previous => music_player.prev(),
                MusicRequest::PlayPause => music_player.play_pause(),
                MusicRequest::Pause => music_player.pause(),
                MusicRequest::PlayUri(uri) => music_player.play(&uri).expect("Couldn't play")      // But this doesn't seem to do anything
            }
        }
    });


    loop {
        info!("Waiting for tag");
        let tag = reader.read().await.expect("Couldn't read tag");

        info!("Reading music {tag}");
        button_tx.send(MusicRequest::PlayUri(tag));
        
        info!("Waiting for removal");
        reader.wait_for_removal().await;

        info!("Pausing music");
        button_tx.send(MusicRequest::Pause);
    }
}

In the background, the music_player is just delegating to a Spirc instance (calling load, next, play_pause). The spirc is created in MusicPlayer::new(), and the spirc_task is spawn there too. I'm really confused, but I'm thinking that the spirc might not be working in this context ? Do you have any idea ?

Thanks a lot !

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions