Quellcode durchsuchen

Added (untested) queueSong.add function.

KrisVos130 vor 8 Jahren
Ursprung
Commit
1ecc92e85e

+ 157 - 0
backend/logic/actions/queueSongs.js

@@ -0,0 +1,157 @@
+'use strict';
+
+const db = require('../db');
+const utils = require('../utils');
+const async = require('async');
+
+module.exports = {
+
+	index: (session, cb) => {
+		//TODO Require admin/login
+		db.models.song.find({}, (err, songs) => {
+			if (err) throw err;
+			cb(songs);
+		});
+	},
+
+	update: (session, id, song, cb) => {
+		//TODO Require admin/login
+		db.models.song.findOneAndUpdate({ id: id }, song, { upsert: true }, (err, updatedSong) => {
+			if (err) throw err;
+			cb(updatedSong);
+		});
+	},
+
+	remove: (session, id, cb) => {
+		//TODO Require admin/login
+		db.models.song.find({ id: song.id }).remove().exec();
+	},
+
+	add: (session, id, cb) => {
+		//TODO Require login
+		//TODO Check if id is valid
+		//TODO Check if id is duplicate
+		// if (!session.logged_in) return cb({ status: 'failure', message: 'You must be logged in to add a song' });
+
+		let requestedAt = Date.now();
+
+		async.waterfall([
+			// Get YouTube data from id
+			(next) => {
+				const youtubeParams = [
+					'part=snippet,contentDetails,statistics,status',
+					`id=${encodeURIComponent(id)}`,
+					`key=${config.get('apis.youtube.key')}`
+				].join('&');
+
+				request(`https://www.googleapis.com/youtube/v3/videos?${youtubeParams}`, (err, res, body) => {
+
+					if (err) {
+						console.error(err);
+						return next('Failed to find song from YouTube');
+					}
+
+					body = JSON.parse(body);
+
+					//TODO Clean up duration converter
+					let dur = body.items[0].contentDetails.duration;
+					dur = dur.replace("PT", "");
+					let durInSec = 0;
+					dur = dur.replace(/([\d]*)H/, function(v, v2) {
+						v2 = Number(v2);
+						durInSec = (v2 * 60 * 60)
+						return "";
+					});
+					dur = dur.replace(/([\d]*)M/, function(v, v2) {
+						v2 = Number(v2);
+						durInSec = (v2 * 60)
+						return "";
+					});
+					dur = dur.replace(/([\d]*)S/, function(v, v2) {
+						v2 = Number(v2);
+						durInSec += v2;
+						return "";
+					});
+
+					let newSong = {
+						id: body.items[0].id,
+						title: body.items[0].snippet.title,
+						artists: [],
+						genres: [],
+						duration: durInSec,
+						skipDuration: 0,
+						thumbnail: '',
+						requestedBy: '',
+						requestedAt: requestedAt
+					};
+
+					next(null, newSong);
+				});
+			},
+			(newSong, next) => {
+				const spotifyParams = [
+					`q=${encodeURIComponent(newSong.title)}`,
+					`type=track`
+				].join('&');
+
+				request(`https://api.spotify.com/v1/search?${spotifyParams}`, (err, res, body) => {
+
+					if (err) {
+						console.error(err);
+						return next('Failed to find song from Spotify');
+					}
+
+					body = JSON.parse(body);
+
+					durationArtistLoop:
+					for (let i in body) {
+						let items = body[i].items;
+						for (let j in items) {
+							let item = items[j];
+							let hasArtist = false;
+							for (let k = 0; k < item.artists.length; k++) {
+								let artist = item.artists[k];
+								if (newSong.title.indexOf(artist.name) !== -1) {
+									hasArtist = true;
+								}
+							}
+							if (hasArtist && newSong.title.indexOf(item.name) !== -1) {
+								newSong.duration = item.duration_ms / 1000;
+								newSong.artists = item.map(function (artist) {
+									return artist.name;
+								});
+								newSong.title = item.name;
+								break durationArtistLoop;
+							}
+						}
+					}
+
+					next(null, newSong);
+				});
+			},
+			(newSong, next) => {
+				const song = new db.models.song(newSong);
+
+				song.save(err => {
+
+					if (err) {
+						console.error(err);
+						return next('Failed to add song to database.');
+					}
+
+					//stations.getStation(station).playlist.push(newSong);
+
+					next(null);
+				});
+			}
+		],
+		(err) => {
+			if (err) {
+				return cb({ status: 'failure', message: err });
+			}
+
+			return cb({ status: 'success', message: 'Successfully added that song to the queue.' });
+		});
+	}
+
+};

+ 47 - 4
backend/logic/actions/songs.js

@@ -11,15 +11,58 @@ module.exports = {
 		});
 	},
 
-	update: (session, song, cb) => {
-		db.models.song.findOneAndUpdate({ id: song.id }, song, { upsert: true }, (err, updatedSong) => {
+	update: (session, id, song, cb) => {
+		//TODO Require admin/login
+		db.models.song.findOneAndUpdate({ id: id }, song, { upsert: true }, (err, updatedSong) => {
 			if (err) throw err;
 			cb(updatedSong);
 		});
 	},
 
-	remove: (session, song, cb) => {
-		db.models.song.find({ id: song.id }).remove().exec();
+	remove: (session, id, cb) => {
+		//TODO Require admin/login
+		db.models.song.find({ id: id }).remove().exec();
+	},
+
+	add: (session, id, cb) => {
+		//TODO Require admin/login
+		// if (!session.logged_in) return cb({ status: 'failure', message: 'You must be logged in to add a song' });
+
+		const params = [
+			'part=snippet,contentDetails,statistics,status',
+			`id=${encodeURIComponent(id)}`,
+			`key=${config.get('apis.youtube.key')}`
+		].join('&');
+
+		request(`https://www.googleapis.com/youtube/v3/videos?${params}`, (err, res, body) => {
+
+			if (err) {
+				console.error(err);
+				return cb({ status: 'error', message: 'Failed to find song from youtube' });
+			}
+
+			body = JSON.parse(body);
+
+			const newSong = new db.models.song({
+				id: body.items[0].id,
+				title: body.items[0].snippet.title,
+				duration: utils.convertTime(body.items[0].contentDetails.duration),
+				thumbnail: body.items[0].snippet.thumbnails.high.url
+			});
+
+			// save the song to the database
+			newSong.save(err => {
+
+				if (err) {
+					console.error(err);
+					return cb({ status: 'error', message: 'Failed to save song from youtube to the database' });
+				}
+
+				// stations.getStation(station).playlist.push(newSong);
+
+				// cb({ status: 'success', data: stations.getStation(station.playlist) });
+			});
+		});
 	}
 
 };

+ 2 - 0
backend/logic/db/index.js

@@ -18,12 +18,14 @@ let lib = {
 
 			lib.schemas = {
 				song: new mongoose.Schema(require(`./schemas/song`)),
+				queueSong: new mongoose.Schema(require(`./schemas/queueSong`)),
 				station: new mongoose.Schema(require(`./schemas/station`)),
 				user: new mongoose.Schema(require(`./schemas/user`))
 			};
 
 			lib.models = {
 				song: mongoose.model('song', lib.schemas.song),
+				queueSong: mongoose.model('queueSong', lib.schemas.queueSong),
 				station: mongoose.model('station', lib.schemas.station),
 				user: mongoose.model('user', lib.schemas.user)
 			};

+ 11 - 0
backend/logic/db/schemas/queueSong.js

@@ -0,0 +1,11 @@
+module.exports = {
+	id: { type: String, unique: true, required: true },
+	title: { type: String, required: true },
+	artists: [{ type: String }],
+	genres: [{ type: String }],
+	duration: { type: Number, required: true },
+	skipDuration: { type: Number, required: true },
+	thumbnail: { type: String, required: true },
+	requestedBy: { type: String, required: true },
+	requestedAt: { type: Date, required: true }
+};