예제 #1
0
def test_exception_backend_worker(raises, monkeypatch):
    mocked_post = MockingFunction()
    monkeypatch.setattr(requests, 'post', mocked_post)

    def raising():
        raise raises

    worker_queue = queue.Queue()

    mocked_split_text = MockingFunction(raising, simple=True)
    monkeypatch.setattr(worker_queue, 'get', mocked_split_text)

    song_id = random.randint(1000, 10000)
    my_id = random.randint(0, 1000)
    my_host = str(random.randint(2, 1000)) + '/wowsers.html'

    worker_queue.put((web.PROCESS_SONG, '/filename/my_song.mp3', song_id))

    with pytest.raises(raises):
        web.backend_worker(worker_queue, my_host, my_id, '/output')

    assert mocked_post.called
    assert mocked_post.args[0][1]['json']['id'] == my_id
    if raises is MemoryError:
        assert mocked_post.args[0][0] == (my_host + '/ultra_died/', )
    else:
        assert mocked_post.args[0][0] == (my_host + '/died/', )
예제 #2
0
def text_nca_picker_feedback(nca_picker, monkeypatch, songs_dir):
    def my_get_userfeedback(feedback):
        assert feedback['old'] == feedback['good_old']
        assert feedback['new'] == feedback['good_new']
        assert feedback['old'].file_location != feedback['old'].file_location
        return feedback['number']

    mocked__optimize_weights = MockingFunction()
    mocked_get_userfeedback = MockingFunction(func=my_get_userfeedback)
    songs = []

    monkeypatch.setattr(nca_picker, 'get_userfeedback',
                        mocked_get_userfeedback)
    monkeypatch.setattr(nca_picker, '_optimize_weights',
                        mocked__optimize_weights)

    songs.append(nca_picker.get_next_song(None))
    songs.append(nca_picker.get_next_song(None))
    songs.append(nca_picker.get_next_song(None))

    # Here (4th time) the core will start sending feedback. However this uses a
    # non existing Seg-1 so it should not be used. See docs/timing.dt for more
    # information.
    songs.append(nca_picker.get_next_song(None))

    for i in range(10):
        songs.append(
            nca_picker.get_next_song({
                'good_old': songs[-5],
                'good_new': songs[-4],
                'number': i,
            }))

    assert mocked_get_userfeedback.called
    assert mocked__optimize_weights.called
예제 #3
0
def test_start_music(monkeypatch, app_client, empty):
    mocked_queue_empty = MockingFunction(lambda: empty, simple=True)
    monkeypatch.setattr(mp.queues.Queue, 'empty', mocked_queue_empty)
    mocked_queue_put = MockingFunction()
    monkeypatch.setattr(mp.queues.Queue, 'put', mocked_queue_put)

    try:
        response = app_client.post('/start/',
                                   data=json.dumps({}),
                                   content_type='application/json')
        other_res = []
        for _ in range(10):
            other_res.append(
                app_client.post('/start/',
                                data=json.dumps({}),
                                content_type='application/json'))
    except Exception as exp:
        raise exp
    finally:
        monkeypatch.undo()

    mocked_queue_empty.called

    assert response.status_code == 200
    assert json.loads(response.get_data(as_text=True))['ok'] == empty
    for res in other_res:
        assert res.status_code == (410 if empty else 200)
        assert not json.loads(res.get_data(as_text=True))['ok']

    if empty:
        assert mocked_queue_put.called
        assert mocked_queue_put.args[0][0] == ((web.START_LOOP, ), )
    else:
        assert not mocked_queue_put.called
예제 #4
0
def test_simple_picker_working_non_direct(monkeypatch, simple_picker):
    mock_random_choice = MockingFunction(func=random.choice)
    mock_is_file = MockingFunction(func=lambda i: i > 2, amount=True)
    monkeypatch.setattr(os.path, 'isfile', mock_is_file)
    monkeypatch.setattr(random, 'choice', mock_random_choice)
    simple_picker.get_next_song({})
    assert len(mock_is_file.args) == 3
    assert len(mock_random_choice.args) == 2
예제 #5
0
def test_nca_picker_next_song(nca_picker, monkeypatch, songs_dir):
    real_rand = random.random

    def feedback_test(feedback):
        options = {
            "1453492_Regina_Original_Mix.wav": 0.8,
            "1665536_Hear_Me_Out_Original_Mix.wav": 0.3,
            "2064084_New_Day_Original_Mix.wav": 0.7,
            "2739576_Hunger_Original_Mix.wav": 0.1,
            "1313776_Slazenger_Joseph_Capriati_Remix.wav": 0.1,
            "1588390_Where_2D_Meets_3D_Chris_Liebing_Remix.wav": 0.1,
            "1928097_Egoist_Original_Mix.wav": 0.1,
            "22538_Panikattack_Original_Mix.wav": 0.1,
            "3030059_Neve___Me_Original_Mix.wav": 0.1,
        }
        needle = False
        if feedback['old'].find("Bubbler") > 0:
            needle = feedback['new']
        if feedback['new'].find("Bubbler") > 0:
            needle = feedback['old']
        if needle:
            for key, value in options.items():
                if key.find(needle) > 0:
                    return value

        return real_rand()

    mock_random = MockingFunction(func=lambda: 0.99999999999, simple=True)
    monkeypatch.setattr(random, 'random', mock_random)
    real_rand()
    assert not mock_random.called

    mock_feedback = MockingFunction(func=feedback_test)
    nca_picker.get_feedback = mock_feedback

    streak = 0

    next_song = nca_picker.get_next_song({})
    next_song2 = nca_picker.get_next_song({})
    assert isinstance(next_song2, dj_feet.song.Song)
    songs = [next_song.file_location]
    assert next_song.file_location == next_song2.file_location
    monkeypatch.undo()
    for _ in range(50):
        next_song2_new = nca_picker.get_next_song({}, force=streak > 3)
        if next_song2.file_location == next_song2_new.file_location:
            streak += 1
        else:
            streak = 0
        next_song2 = next_song2_new
        songs.append(next_song2.file_location)
        assert next_song2 is not None
        assert isinstance(next_song2, dj_feet.song.Song)
    if next_song == next_song2:
        pprint(nca_picker.song_distances)
    pprint(songs)
    assert mock_feedback.called
    assert len(songs) == 51
예제 #6
0
def test_get_class_instance(config, monkeypatch, basecls, cls, cls_args):
    mock_get_class = MockingFunction(lambda: cls, simple=True)
    mock_get_class_args = MockingFunction(lambda: cls_args, simple=True)
    monkeypatch.setattr(config, "get_class", mock_get_class)
    monkeypatch.setattr(config, "_get_class_args", mock_get_class_args)

    cls_instance = config._get_class_instance(basecls, cls.__name__)

    assert vars(cls_instance) == cls_args

    assert isinstance(cls_instance, cls)
    assert mock_get_class.called
    assert mock_get_class.args[0][0] == (basecls, cls.__name__)

    assert mock_get_class_args.called
    assert mock_get_class_args.args[0][0] == (cls, basecls.__name__)
예제 #7
0
def test_add_music(monkeypatch, app_client, throw, url, expected_code):
    def my_put():
        if throw:
            raise queue.Full('Err')
        else:
            return None

    mocked_queue_put = MockingFunction(my_put, simple=True)
    monkeypatch.setattr(mp.queues.Queue, 'put_nowait', mocked_queue_put)

    try:
        my_file_loc = str(random.random()) + 'location/'
        song_id = random.randint(10, 1000)
        res = app_client.post(url,
                              content_type='application/json',
                              data=json.dumps({
                                  'file_location': my_file_loc,
                                  'id': song_id,
                              }))

        assert mocked_queue_put.called
        assert mocked_queue_put.args[0][0][0] == (expected_code, my_file_loc,
                                                  song_id)

        assert json.loads(res.get_data(as_text=True))['ok'] != throw
        assert res.status_code == 200
    except Exception as exp:
        raise exp
    finally:
        monkeypatch.undo()
예제 #8
0
def test_my_flask_getters_and_setters(monkeypatch, func, my_flask):
    mock_setup = MockingFunction()
    monkeypatch.setattr(my_flask, 'setup', mock_setup)

    func(my_flask)

    assert mock_setup.called
예제 #9
0
def test_protocol_communicator_feedback(protocol_communicator, monkeypatch,
                                        data, _):
    class MyResponse:
        def json(self):
            return data

    mocked_post_request = MockingFunction(MyResponse, simple=True)
    monkeypatch.setattr(requests, 'post', mocked_post_request)

    remote = str(random.randint(0, 1000)) + '-remote'
    app_id = str(random.randint(1000, 2000)) + '-id'
    start = str(random.randint(2000, 3000)) + '-start'
    end = str(random.randint(3000, 4000)) + '-end'

    res = protocol_communicator.get_user_feedback(remote, app_id, start, end)

    assert res == data['feedback']
    assert mocked_post_request.called
    assert mocked_post_request.args == [((remote + '/get_feedback/', ), {
        'json': {
            'start': start,
            'end': end,
            'id': app_id
        }
    })]
예제 #10
0
def test_loop_excpetion(monkeypatch, mock_controller, mock_forcing_picker,
                        mock_exception_transitioner, mock_communicator, capsys,
                        patched_post):
    mock_sleep = MockingFunction(lambda: None, simple=True)
    monkeypatch.setattr(time, 'sleep', mock_sleep)
    core.loop(0, 'localhost', mock_controller, mock_forcing_picker,
              mock_exception_transitioner, mock_communicator)
    _, err = capsys.readouterr()
예제 #11
0
def test_app_test(monkeypatch):
    mocked_start = MockingFunction()
    monkeypatch.setattr(web, 'start', mocked_start)

    mocked_getenv = MockingFunction(lambda: 500, simple=True)
    monkeypatch.setattr(os, 'getenv', mocked_getenv)

    import dj_feet.wsgi as wsgi

    assert mocked_start.called
    assert mocked_getenv.called
    assert len(mocked_getenv.args) == 4

    for idx, var in enumerate([
            'SDAAS_ID', 'SDAAS_INPUT_DIR', 'SDAAS_OUTPUT_DIR',
            'SDAAS_REMOTE_URL'
    ]):
        assert var == mocked_getenv.args[idx][0][0]
예제 #12
0
def test_loop(monkeypatch, mock_controller, mock_picker, mock_transitioner,
              mock_communicator, capsys, patched_post):
    mock_sleep = MockingFunction(lambda: None, simple=True)
    monkeypatch.setattr(time, 'sleep', mock_sleep)
    now = round(time.time())
    my_id = random.randint(1, 10010101)
    my_addr = str(random.random()) + "/local"
    core.loop(my_id, my_addr, mock_controller, mock_picker, mock_transitioner,
              mock_communicator)
    _, err = capsys.readouterr()

    iterations = mock_controller.amount

    if err:
        assert mock_controller.waittime_amount < 0
    else:
        assert mock_controller.waittime_emitted == [
            x[0][0] for x in mock_sleep.args
        ]
    assert all([x[0][0] > 0 for x in mock_sleep.args])
    assert mock_controller.amount + 1 == mock_controller.called_amount

    assert mock_transitioner.merge_emitted == mock_transitioner.write_args

    if mock_controller.amount >= 5:
        assert mock_controller.amount == mock_communicator.called_amount + 4
    assert len(mock_communicator.emitted) == max(
        len(mock_picker.feedback) - 4, 0)
    assert mock_communicator.emitted == mock_picker.feedback[4:]
    assert mock_communicator.files == mock_picker.emitted

    assert (not mock_picker.feedback) or mock_picker.feedback[0] == {}

    if iterations > 4:
        correct_time = mock_transitioner.max_size * (
            iterations - 4) + mock_transitioner.merge_times[-4]
        assert mock_communicator.end_time == correct_time
        assert isinstance(mock_communicator.end_time, float)

    if iterations > 0:
        assert patched_post.called
        assert patched_post.args[0][0][0] == my_addr + '/controller_started/'
        assert patched_post.args[0][1]['json']['id'] == my_id
        assert patched_post.args[0][1]['json']['epoch'] == now

    i = 0
    for prev, new in mock_transitioner.merge_args:
        if i == 0:
            assert prev is None
        else:
            assert mock_picker.emitted[i - 1] == prev
        assert mock_picker.emitted[i] == new
        i += 1
예제 #13
0
def test_preserving_force(monkeypatch, nca_picker, _):
    amount = 0
    prev = None

    def call_and_add(amount, prev):
        new = nca_picker.get_next_song({})
        if prev is None or new.file_location != prev.file_location:
            return amount + 1, new
        return amount, new

    mock_get_feedback = MockingFunction(func=lambda: 1, simple=True)
    nca_picker.get_feedback = mock_get_feedback
    monkeypatch.setattr(nca_picker, '_optimize_weights',
                        lambda: mock_get_feedback({}))

    i = 0
    for _ in range(5):
        amount, prev = call_and_add(amount, prev)
        if i > 100:
            nca_picker.reset_songs()
            nca_picker.get_next_song({}, force=True)
            nca_picker.get_next_song({}, force=True)
            nca_picker.get_next_song({}, force=True)
        if i > 200:
            assert False
        i += 1
    assert not mock_get_feedback.called

    for _ in range(10):
        forced = nca_picker.get_next_song({}, force=True)
        assert forced.file_location != prev.file_location
        prev = forced

    assert not mock_get_feedback.called
    assert len(nca_picker.picked_songs) == 5

    i = 0
    while amount <= 5:
        amount, prev = call_and_add(amount, prev)
        if i > 100:
            nca_picker.reset_songs()
            nca_picker.get_next_song({}, force=True)
            nca_picker.get_next_song({}, force=True)
            nca_picker.get_next_song({}, force=True)
        if i > 200:
            assert False
        i += 1

    assert len(nca_picker.picked_songs) == 5
    if not mock_get_feedback.called:
        print(nca_picker.picked_songs)
    assert mock_get_feedback.called
예제 #14
0
def test_simple_picker_working_direct(monkeypatch, simple_picker,
                                      random_song_file, _):
    mock_random_choice = MockingFunction(func=lambda: random_song_file,
                                         simple=True)
    monkeypatch.setattr(random, 'choice', mock_random_choice)
    chosen_song = simple_picker.get_next_song({})
    assert isinstance(chosen_song, dj_feet.song.Song)
    assert chosen_song.file_location == random_song_file
    assert len(mock_random_choice.args) == 1
    assert len(mock_random_choice.args[0][0]) == 1
    assert len(mock_random_choice.args[0][1]) == 0
    assert isinstance(mock_random_choice.args[0][0][0], list)
    with pytest.raises(ValueError):
        simple_picker.get_next_song({})
예제 #15
0
def test_write_sample(inf_jukebox_transitioner, _, random_song_file,
                      monkeypatch):
    mocking_export = MockingFunction()

    class MyAudioSegment:
        def __init__(self, wav):
            assert wav.startswith('/tmp/')

        def export(self, *args, **kwargs):
            mocking_export(*args, **kwargs)

    mocking_librosa = MockingFunction(lambda x, sample, sr, norm: x)
    monkeypatch.setattr(librosa.output, 'write_wav', mocking_librosa)

    mocking_pydub = MockingFunction(MyAudioSegment)
    monkeypatch.setattr(pydub.AudioSegment, 'from_wav', mocking_pydub)

    time_series, sr = librosa.load(random_song_file)

    inf_jukebox_transitioner.write_sample(time_series)
    assert len(mocking_librosa.args) == 1
    assert len(mocking_export.args) == 1

    inf_jukebox_transitioner.write_sample(time_series)
    assert len(mocking_librosa.args) == 2
    assert len(mocking_export.args) == 2

    assert mocking_librosa.called
    a = mocking_librosa.args[0][0][1] == time_series
    assert hasattr(a, '__iter__') and a.all()
    assert mocking_librosa.args[0][1]['sr'] == sr

    assert mocking_pydub.called
    assert mocking_export.args[0][0][0] == os.path.join(
        inf_jukebox_transitioner.output_folder, "part0.mp3")
    assert mocking_export.args[1][0][0] == os.path.join(
        inf_jukebox_transitioner.output_folder, "part1.mp3")
예제 #16
0
def test_merge_sample(inf_jukebox_transitioner, random_song_files, monkeypatch,
                      same):
    mocking_append = MockingFunction(func=numpy.append)
    monkeypatch.setattr(numpy, 'append', mocking_append)
    song1 = Song(random_song_files[0])
    if same:
        song2 = song1
    else:
        song2 = Song(random_song_files[1])
    res, time_delta = inf_jukebox_transitioner.merge(song1, song2)
    assert (time_delta == inf_jukebox_transitioner.segment_size) == same
    assert mocking_append.called != same
    assert abs(
        librosa.core.get_duration(res, song1.sampling_rate) -
        inf_jukebox_transitioner.segment_size) < 0.0001
예제 #17
0
def test_get_the_class_instance(config, monkeypatch, get_types_func, cls,
                                boolean):
    mock_get_class_instance = MockingFunction(cls, simple=True)
    monkeypatch.setattr(config, '_get_class_instance', mock_get_class_instance)
    func = "get_" + get_types_func.__name__.lower()
    if boolean:
        inst = getattr(config, func)(cls)
        assert mock_get_class_instance.called
        assert mock_get_class_instance.args[0][0] == (
            get_types_func,
            cls, )
    else:
        inst = getattr(config, func)()
        assert mock_get_class_instance.called
        assert mock_get_class_instance.args[0][0] == (
            get_types_func,
            None, )

    assert isinstance(inst, cls)
예제 #18
0
def test_protocol_communicator_iteration(protocol_communicator, monkeypatch,
                                         _):
    filename = str(random.randint(0, 1000)) + 'song_location'
    file_loc = '/tmp/#sdaas_only/' + filename + '.mp3'
    my_remote = str(random.randint(1000, 2000)) + 'remote'
    my_id = str(random.randint(1000, 2000)) + 'id'

    MySong = namedtuple('my_song', 'file_location')
    a_song = MySong(file_loc)
    mocked_post_request = MockingFunction()
    monkeypatch.setattr(requests, 'post', mocked_post_request)

    protocol_communicator.iteration(my_remote, my_id, a_song)

    assert mocked_post_request.called
    assert mocked_post_request.args == [((my_remote + '/iteration/', ), {
        'json': {
            'id': my_id,
            'filename_mixed': filename,
        }
    })]
예제 #19
0
def test_setup(monkeypatch):
    my_post_request = MockingFunction()
    monkeypatch.setattr(requests, 'post', my_post_request)
    my_id = random.randint(0, 100000)
    my_addr = str(random.randint(0, 100000)) + "-this-is-me-" + str(my_id)

    with web.app.app_context():
        web.start(str(my_id), "/in", "/out", my_addr)
        stop_worker(web.app.queue, web.app.worker)
        assert web.app.config['INPUT_DIR'] == '/in'
        assert web.app.config['OUTPUT_DIR'] == '/out'

    assert my_post_request.called
    assert len(my_post_request.args[0][0]) == 1
    assert my_post_request.args[0][0][0] == my_addr + '/im_alive/'

    data = my_post_request.args[0][1]['json']
    assert data['id'] == my_id
    assert 'MyPicker' in data['options']['Picker']
    assert 'param1' in data['options']['Picker']['MyPicker']['parts']
    assert data['options']['Picker']['MyPicker']['parts']['param1']['required']
예제 #20
0
def test_get_class(config, monkeypatch, expected, basecls, cls_name,
                   subclasses, boolean):
    mock_get_all_subclasses = MockingFunction(lambda: subclasses, simple=True)
    monkeypatch.setattr(helpers, 'get_all_subclasses', mock_get_all_subclasses)

    def get():
        if boolean:
            return config.get_class(basecls, cls_name)
        else:
            monkeypatch.setattr(config, "user_config",
                                {'main': {
                                    basecls.__name__: cls_name
                                }})
            return config.get_class(basecls, None)

    if isinstance(expected, type) and issubclass(expected, Exception):
        with pytest.raises(expected):
            get()
    else:
        assert expected == get()
        assert mock_get_all_subclasses.called
        assert mock_get_all_subclasses.args[0][0] == (basecls, )
예제 #21
0
def test_set_main_option(config, monkeypatch):
    class MyName():
        def __init__(self, num):
            self.__name__ = str(num)

    my_picker = str(random.randint(100000, 10000000))
    my_picker2 = str(random.randint(0, 100000 - 1))

    mocked_get_all_subclasses = MockingFunction(
        lambda: map(MyName, [0, my_picker2, my_picker]), simple=True)
    monkeypatch.setattr(helpers, 'get_all_subclasses',
                        mocked_get_all_subclasses)

    config.update_config_main_options({"Picker": my_picker})
    assert config.user_config['main']['Picker'] == my_picker

    config.update_config_main_options({"Picker": my_picker2})
    assert config.user_config['main']['Picker'] == my_picker2

    with pytest.raises(ValueError):
        config.update_config_main_options({"Picker": my_picker * 2})
    with pytest.raises(ValueError):
        config.update_config_main_options({"song_folder": my_picker})
예제 #22
0
def patched_post(monkeypatch):
    mocked_post = MockingFunction()
    monkeypatch.setattr(requests, 'post', mocked_post)
    yield mocked_post
예제 #23
0
def test_backend_worker(monkeypatch):
    class MyAudioSegement():
        def __init__(self):
            self.args = []
            self.called = False

        def export(self, filename, format):
            self.args.append((filename, format))
            self.called = True

    class MyPicker(pickers.Picker):
        called = False
        args = []

        def __init__(self, other, rest=101, a=True):
            pass

        @staticmethod
        def process_song_file(song_file, rest):
            MyPicker.args.append((song_file, rest))
            MyPicker.called = True

    mocked_get_controller = MockingFunction(lambda: 'Controller')
    mocked_get_picker = MockingFunction(lambda: 'Picker')
    mocked_get_transitioner = MockingFunction(lambda: 'Transitioner')
    mocked_get_communicator = MockingFunction(lambda: 'Communicator')
    monkeypatch.setattr(config.Config, 'get_controller', mocked_get_controller)
    monkeypatch.setattr(config.Config, 'get_picker', mocked_get_picker)
    monkeypatch.setattr(config.Config, 'get_transitioner',
                        mocked_get_transitioner)
    monkeypatch.setattr(config.Config, 'get_communicator',
                        mocked_get_communicator)

    mocked_loop = MockingFunction()
    monkeypatch.setattr(core, 'loop', mocked_loop)
    my_segment = MyAudioSegement()
    mocked_from_mp3 = MockingFunction(lambda: my_segment, simple=True)
    monkeypatch.setattr(pydub.AudioSegment, 'from_mp3', mocked_from_mp3)
    # This also patches .export as this is done in MyAudioSegement

    mocked_get_class = MockingFunction(lambda: MyPicker, simple=True)
    monkeypatch.setattr(config.Config, 'get_class', mocked_get_class)

    mocked_post = MockingFunction()
    monkeypatch.setattr(requests, 'post', mocked_post)

    mocked_config_mupdate = MockingFunction()
    mocked_config_cupdate = MockingFunction()
    monkeypatch.setattr(config.Config, 'update_config_class_options',
                        mocked_config_cupdate)
    monkeypatch.setattr(config.Config, 'update_config_main_options',
                        mocked_config_mupdate)

    mocked_remove = MockingFunction()
    monkeypatch.setattr(os, 'remove', mocked_remove)

    worker_queue = queue.Queue()

    start_loop_arg = random.random()
    my_host = str(random.random()) + 'loc'
    my_id = random.randint(0, 1000)
    song_id = random.randint(1000, 10000)

    worker_queue.put((web.PROCESS_SONG, '/filename/my_song.mp3', song_id))
    worker_queue.put((web.START_LOOP, start_loop_arg))
    worker_queue.put((web.OPTIONS, {
        'Picker': {
            'name': 'MyPicker',
            'options': {
                'a': None
            }
        }
    }))
    worker_queue.put((web.DELETE_SONG, '/remove/this.mp3', song_id))
    worker_queue.put((web.STOP, ))

    web.backend_worker(worker_queue, my_host, my_id, '/output')

    assert mocked_loop.called
    assert mocked_loop.args[0][0] == (my_id, my_host, 'Controller', 'Picker',
                                      'Transitioner', 'Communicator')
    assert mocked_from_mp3.called

    assert my_segment.called
    assert my_segment.args[0][0].startswith('/tmp/')
    assert my_segment.args[0][0].endswith('/my_song.wav')
    assert my_segment.args[0][1] == 'wav'

    assert mocked_config_cupdate.called
    assert mocked_config_mupdate.called
    assert mocked_config_cupdate.args[0][0] == ('Picker', 'MyPicker', {
        'a': None
    })
    assert mocked_config_mupdate.args[0][0] == ({'Picker': 'MyPicker'}, )

    assert mocked_post.called
    assert mocked_post.args[0][0][0] == my_host + '/music_processed/'
    assert mocked_post.args[0][1]['json']['id'] == song_id

    assert mocked_post.args[1][0][0] == my_host + '/music_deleted/'
    assert mocked_post.args[1][1]['json']['id'] == song_id
    assert mocked_remove.called
    assert mocked_remove.args[0][0][0].endswith('this.wav')
    assert mocked_remove.args[0][0][0].startswith('/tmp/')

    assert mocked_get_class.called
    assert MyPicker.called
    assert MyPicker.args == [(my_segment.args[0][0], 101)]