Я подписан на ProgMetal subreddit, потому что нет ничего, что мне нравится больше, чем слышать, как виртуозно играет соло на 8-струнной гитаре, в то время как разные барабанщики, басисты, клавишники, виолончелисты и валторнисты чередуют такты 19/16 и 7/4. .
Большинство постов на /r/ProgMetal — это ссылки на треки на YouTube, которыми постер хочет поделиться с сообществом. Как и во всем Reddit, эти сообщения затем голосуются за или против других пользователей, в результате чего выбираются сообщения, которые можно упорядочить по «популярности».
Я вижу, что интересные треки из этого сабвуфера появляются часто, но часто в те моменты, когда нецелесообразно открывать YouTube; и к тому времени, когда я нахожусь в состоянии слушать, этот интересный трек уже давно забыт. Я понял, что мне бы очень хотелось, чтобы треки из этого саба были собраны в еженедельный плейлист, который я мог бы слушать на досуге. Итак, это то, что я намеревался сделать.
План состоял в том, чтобы создать приложение, которое вызывало бы API Reddit для получения первых n сообщений из заданного субреддита, отфильтровывало бы все, что не является просто рекомендацией трека, а затем использовало бы API Spotify для размещения эти песни в плейлисте.
Узел — Между погребённым и мной
Я решил написать это маленькое приложение с помощью Node, потому что считаю JavaScript хорошим языком для быстрого объединения вещей, а Node — хорошей средой выполнения для легкого запуска и быстрого выполнения итераций. Также я планировал позже развернуть это как Lambda, и я знал, что Node поддерживается.
mkdir reddlist cd reddlist npm init
Красный (дит) — King Crimson
Reddit имеет хорошо документированный веб-API, а для настройки ключей и т. д. вы можете следовать инструкциям здесь.
Я использовал npm-пакет reddit API-оболочки под названием snoowrap вместо того, чтобы самостоятельно отправлять http-запросы (хотя, оглядываясь назад, это не было огромным преимуществом).
npm install snoowrap
Я создал класс для инкапсуляции кода, связанного с Reddit.
Этот класс просто обертывает snoowrap и предоставляет метод для получения лучших сообщений из подписки. Затем он пытается отфильтровать их до только сообщений с песнями, убедившись, что они являются сообщениями в СМИ, а затем с помощью регулярного выражения попытается получить название группы и название песни. Эта последняя часть немного хрупкая, потому что, конечно, заголовок поста может быть любым, но многие сабвуферы, включая /r/ProgMetal, используют соглашение «название группы — название песни», так что это разумная ставка, которая уловит большинство вещей. .
Играй (список) со мной — Джефф Бек
Spotify также имеет хороший веб-API. Однако с точки зрения авторизации он, очевидно, в первую очередь предназначен для создания сторонних потоковых клиентов, а не для такой работы на стороне сервера, поэтому было немного сложнее выяснить, как именно получить правильный набор ключей доступа, секретов. и токены, чтобы иметь возможность совершать звонки, которые повлияют на мою личную учетную запись Spotify, например, редактировать список воспроизведения.
Однако в блоге Почтальона есть очень хороший путеводитель, который указал мне правильное направление. Ответ состоял в том, чтобы создать приложение на панели разработчика Spotify, чтобы получить идентификатор клиента и секрет клиента. Затем вручную вызовите конечную точку авторизации с помощью Postman, чтобы сгенерировать маркер доступа и маркер обновления. Подробнее о том, как это сделать, читайте в разделе этого поста под заголовком Настройка среды.
В данном случае оказалось проще делать HTTP-вызовы напрямую, чем использовать клиентскую библиотеку API. Я использовал axios для http-вызовов.
npm install axios
Поскольку токены доступа недолговечны, необходимо также периодически использовать токен обновления, чтобы получить новый. Этот процесс описан здесь. Я установил querystring в качестве помощника для выполнения необходимых вызовов application/x-www-form-urlencoded .
npm install querystring
Имея полный набор ключей и токенов, я создал еще один класс для инкапсуляции всего кода, связанного со Spotify.
Я решил проблему с токеном обновления, используя статический фабричный метод SpotifyApi.newApi, который заботится о создании нового токена доступа, а затем передает его в конструктор класса, поэтому каждый раз, когда вы создаете экземпляр класса, вы делаете это с новым токеном доступа. В языке, который позволял это, я мог бы сделать конструктор закрытым.
Затем у класса есть два других метода: один — searchSongUris — который берет объекты дорожки, возвращенные классом reddit, и пытается найти соответствующие URI Spotify для каждого из них, а другой — replacePlaylist — который заменяет содержимое существующего списка воспроизведения Spotify теми, которые URI.
Общая картина - Театр мечты
Нам нужен метод, чтобы склеить все это вместе.
keys.js, импортированный вверху, представляет собой (пропущенный git) файл, содержащий все мои идентификаторы, секреты, токены и т. д. Этот простой метод создает экземпляры классов Reddit и Spotify API и вызывает их методы по очереди, чтобы получить треки из Reddit и сохранить их. в плейлисте Spotify.
Наконец, нам просто нужна точка входа, которая импортирует и вызывает
createPlaylist("progmetal", "<playlist id>", 50)
Благодаря этому в index.js мы теперь можем запускать приложение из командной строки с помощью
node index.js
На прощание — Opeth
Полная версия находится в этом репозитории github. Там вы можете видеть, что я добавил несколько небольших дополнений, таких как возможность передавать параметры — сабреддит, плейлист и лимит — в качестве аргументов командной строки. Я также добавил функцию-обработчик и некоторую бессерверную конфигурацию, чтобы ее можно было развернуть как AWS Lambda и вызывать автоматически раз в неделю по расписанию.
Результирующий плейлист здесь, если вы хотите услышать музыку, которая вдохновила вас на эту, в основном, ненужную причину провести выходные за чтением документации по API.