Конструктор плейлистов для Spotify

Статья о том, как Spotify Web API (SWA) и платформа Google Apps Script (GAS) позволили превратить библиотеку в гибкий конструктор плейлистов с бесплатным исполнением по расписанию.

Под конструктором плейлистов понимаем механизм сбора, фильтрации, сортировки и добавления треков.

Ссылки на исходный код и документацию в конце статьи.

Проблема

Наличие официального API породило для Spotify множество интересных инструментов. В нашем контексте рассмотрим Smarter Playlists. Графический интерфейс в виде графов, множество управляющих блоков делают его довольно дружелюбным для обычного пользователя.

Плотное использование сервиса выявило ряд недостатков: отсутствие истории прослушиваний, лимитированное добавление треков, ограниченное количество запусков по расписанию, некорректная работа с кириллицей. С течением времени сюда добавляется желание новых источников треков, более сложных алгоритмов фильтрации. Сервис перестал развиваться с точки зрения новых функций.

В связи с этим появилось желание альтернативы, устраняющей данные недостатки.

Решение

В результате была разработана библиотека для GAS на JavaScript – Goofy. Конструктором её делает возможность запуска на платформе в редакторе или по расписанию (триггерам) без стороннего ПО.

Естественно GAS накладывает свои ограничения, но другого порядка. Например, время исполнения не более 6 минут; количество запросов к внешним API не более 20 тысяч в день. С другой стороны, круг возможностей существенно расширился. Реализованы все функции Smarter Playlists, устранены его недостатки. Появились новые функции.

Алгоритм

Несколько простых примеров, которые можно реализовать с помощью Goofy

  • Объединение личных миксов с удалением ранее прослушанных треков

  • Выявление давно непрослушиваемых треков

  • Сбор новинок отслеживаемых исполнителей

  • Накопление треков обновляемого источника в плейлисте с удалением уже прослушанных

  • Рекомендации Last.fm любого пользователя, топ за период и прочее

Новые возможности

Особое внимание уделю истории прослушиваний. Частое прослушивание музыки без особо активных действий приводят стриминг платформы к повторам. Одни и те же треки приходят изо дня в день. Goofy позволяет удалить ранее прослушанные треки. Однако это сложнее, чем казалось на первых взгляд.

  • SWA дает возможность получить только 50 последних прослушанных треков. Появление 51-ого делает недоступным 1-й.

    GAS имеет выход к Google Drive. Библиотека создает повторяющийся триггер и опрашивает SWA на предмет новых прослушиваний. Если они есть, сохраняет в файл. Таким образом, появляется локальная полная история прослушиваний.

  • Есть другая проблема. Трек считается прослушанным только после 30 секунд. Причем зачастую недавние треки обновляются не сразу или вовсе теряются. Списываю это на “качество” SWA.

    Решение есть и здесь – использовать Last.fm. Реализовано два подхода. Во первых, можно просто запросить недавние прослушивания и удалять совпадения по названию трека. Во вторых, можно выполнить поиск трека в Spotify и сохранить его в файл на Google Drive. Тем самым получая историю прослушиваний от Last.fm готовую к работе со Spotify.

Кроме того, Last.fm API используется и для получения других источников. Например, рекомендации, треки соседей по музыкальным вкусам, любимые треки, топ за разный период.

Пример

Нужно выполнить установку (копирование в GAS) и настройку (выдача разрешений, ключи доступа). Все подробно есть в документации.

1) Простой пример: получить любимые треки, взять пять случайных и добавить в плейлист.

Далее графическими средствами GAS создаем триггер. В результате, например, раз в минуту плейлист будет обновляться пятью случайными треками.

function createHelloPlaylist() {
    let tracks = Source.getSavedTracks();
    Selector.keepRandom(tracks, 5);
    Playlist.saveWithReplace({
        name: 'Hello, playlist',
        tracks: tracks,
    });
}

2) Выявить любимые треки, которые не были прослушаны более чем месяц.

function templateSavedAndForgot(){
    let recentTracks = Source.getRecentTracks(2500);
    let savedTracks = Source.getSavedTracks(); 
    Filter.removeTracks(savedTracks, recentTracks);

    let startDate = new Date('2006-01-01');
    let endDate = Filter.getDateRel(30, 'endDay');
    Filter.rangeDateAbs(savedTracks, startDate, endDate);

    Selector.keepRandom(savedTracks, 20);    
    Order.sort(savedTracks, 'meta.added_at', 'asc');
    Playlist.saveWithReplace({
        name: 'Любимо и забыто',
        tracks: savedTracks,
        randomCover: 'update', // установить случайную обложку плейлиста
    });
}

3) Получить треки альбомов и синглов отслеживаемых исполнителей за неделю.

function createNewRelease() {
    const playlistId = 'abc';
    let tracks = Source.getArtistsTracks({
        artist: { 
          followed_include: true 
        },
        album: { 
          groups: 'album,single', 
          release_date: { sinceDays: 7, beforeDays: 0 } 
        },
    });
    Order.shuffle(tracks);

    Combiner.push(tracks, Source.getPlaylistTracks('name', playlistId));
    Filter.removeTracks(tracks, RecentTracks.get(3000));
    Filter.matchOriginalOnly(tracks);
    
    Playlist.saveWithReplace({
        id: playlistId,
        name: 'Новые релизы',
        tracks: tracks,
        randomCover: 'update',
    });
}

Ссылки

Документация писалась с ориентиром на пользователя, который не знаком с программированием. Чтобы дать возможность использовать Goofy через копипаст шаблонов и примеров.

Исходный код на GitHub, включая форум.

Let’s block ads! (Why?)

Read More

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *