Building a Youtube music recommender
By: Luis Meazzini
Tags: Machine Learning, Artificial Inteligence, Music, Data Science, YouTube

Building a Youtube music recommender

From scratch to deploy: recommending youtube music videos to you

Overview

On this article, I`ll comment some details of a simple solution I built to recommend Youtube music videos to myself. You can check out the deployed solution on Heroku at Youtube Music Recommender. I know, it is not beautiful. Maybe one day I will develop my front-end skills.

Then, the main idea here is to go from scratch to deployment. Mainly, this process will include all these steps:

Scrapping video data from Youtube pages; Extracting the video information from each page; Preprocess data from each video into a single dataset; Manually label some of samples, active learning the rest; Extract features from the dataset; Train a Random Forest and a LightGBM model and ensemble them; Build a simple app to serve the model through Heroku.

Also, if you want to check out the code, I will be citing which script is used on each step.

Lets begin!

Scrapping video data from Youtube pages

First of all, we need data! To get some data, I scrapped youtube pages by querying on Youtube search. Since I am looking for music to recommend to myself, I used six queries:

‘Folk rock’, ‘Classical guitar’, ‘Acoustic rock’, ‘Orchestral rock’, ‘Cello songs’ and ‘Brazillian rock’

Then, I saved the first 100 pages of each query. This is done in “search_data_collection.py” script.

Extracting the video information from each page

Now we have data from Youtube search pages, we need to extract information from the videos present on those pages. To do so, I made a parser with BeautifulSoup.

This parser just saves the link, title and query used for each video on the 600 pages. Also, since there is a possibily of videos been duplicated, I dropped the duplicates. This is done in “search_data_parsing.py” script.

Preprocess data from each video into a single dataset

From the parsed data, we are able to web scrap each video. There is much information here, most of the features we can get are from this step. Since this is a simple solution and I did not spent a lot of time engenieering features I used just a few of the possibilities.

There are 2277 videos totally, then this script takes a quite longe time to run, ~2h. The script name is “video_data_processing.py”

Manually label some of samples possibly with active learning

The most tedious and boring part of this work. I had to get labels. So, I opened the raw_data file generated by the previous step on sheets and added a “y” column and manually filled 1000 rows with 0 or 1.

With the labelled data, it is possible to train a Random Forest model and the features extracted on the next step and use this model to identify which samples are the hardest to classify (~0.5 output), then I manually labelled 200 of the samples identified by active learning.

The active learning helps a lot to mitigate the labelling cost. However, the labelling time I was expecting to spend was less then I imagined, so I ended manually labelling everything.

Extract features from the video data

Now, each row of our dataset is a video with its data, like title, number of views, author, description, video height, video width and other information. From these fields, I made feature engineering to extract some features that can be helpful to later.

This way, I extracted the number of views, view per day, video resolution and made a Bag of Words (BoW) with the title string. Surely, there are much more features that could be extracted, especially from video description and video tags. However, I left a more deep feature engineering to future works.

Train a Random Forest and a LightGBM model and ensamble them

With the extracted features and the labels, we can split the dataset in train and validation. I chose not to make a test set, leaving the ultimate validation to production data.

First I trained a LightGBM model optimizing its parameters with a bayesian optimization along with some data pre-processing parameters (like n_gram range for BoW). Then, the Random Forest model was trained with the same pre-processing parameters found on bayesian search. For more details, you can check the implementation. I looked for an ensemble of these two models giving a weight to each model.

To measure how well the model is performing, I chose not to use precision, recall and F1-Score. Since the problem involves a recommendation, the final output should be a ranking of the most relevant recommendations (output closer to 1). Then I used the average_precision_score, roc_auc and log_loss to better evaluate the model.

Also, I made a Learning Curve Analysis (LCA) to check if the data used was enough to have a consistent prediction. The ROC curve and the LCA can be seen on the figures below. The feature extraction and the modelling is on “final_model.py”