Pretty Code + Music property added in YouTube Video

This commit is contained in:
killer069 2022-01-03 15:59:32 +05:30
parent 433ec4976b
commit ffbe882037
9 changed files with 78 additions and 39 deletions

View File

@ -493,18 +493,18 @@ export class DeezerAlbum {
} }
/** /**
* Fetches all the tracks in the album and returns them * Fetches all the tracks in the album and returns them
* *
* ```ts * ```ts
* const album = await play.deezer('album url') * const album = await play.deezer('album url')
* *
* const tracks = await album.all_tracks() * const tracks = await album.all_tracks()
* ``` * ```
* @returns An array of {@link DeezerTrack} * @returns An array of {@link DeezerTrack}
*/ */
async all_tracks(): Promise<DeezerTrack[]> { async all_tracks(): Promise<DeezerTrack[]> {
await this.fetch() await this.fetch();
return this.tracks as DeezerTrack[] return this.tracks as DeezerTrack[];
} }
/** /**
* Converts instances of this class to JSON data * Converts instances of this class to JSON data
@ -763,18 +763,18 @@ export class DeezerPlaylist {
} }
/** /**
* Fetches all the tracks in the playlist and returns them * Fetches all the tracks in the playlist and returns them
* *
* ```ts * ```ts
* const playlist = await play.deezer('playlist url') * const playlist = await play.deezer('playlist url')
* *
* const tracks = await playlist.all_tracks() * const tracks = await playlist.all_tracks()
* ``` * ```
* @returns An array of {@link DeezerTrack} * @returns An array of {@link DeezerTrack}
*/ */
async all_tracks(): Promise<DeezerTrack[]> { async all_tracks(): Promise<DeezerTrack[]> {
await this.fetch() await this.fetch();
return this.tracks as DeezerTrack[] return this.tracks as DeezerTrack[];
} }
/** /**
* Converts instances of this class to JSON data * Converts instances of this class to JSON data

View File

@ -326,18 +326,18 @@ export class SoundCloudPlaylist {
} }
/** /**
* Fetches all the tracks in the playlist and returns them * Fetches all the tracks in the playlist and returns them
* *
* ```ts * ```ts
* const playlist = await play.soundcloud('playlist url') * const playlist = await play.soundcloud('playlist url')
* *
* const tracks = await playlist.all_tracks() * const tracks = await playlist.all_tracks()
* ``` * ```
* @returns An array of {@link SoundCloudTrack} * @returns An array of {@link SoundCloudTrack}
*/ */
async all_tracks(): Promise<SoundCloudTrack[]> { async all_tracks(): Promise<SoundCloudTrack[]> {
await this.fetch() await this.fetch();
return this.tracks as SoundCloudTrack[] return this.tracks as SoundCloudTrack[];
} }
/** /**
* Converts Class to JSON data * Converts Class to JSON data

View File

@ -325,22 +325,22 @@ export class SpotifyPlaylist {
} }
/** /**
* Fetches all the tracks in the playlist and returns them * Fetches all the tracks in the playlist and returns them
* *
* ```ts * ```ts
* const playlist = await play.spotify('playlist url') * const playlist = await play.spotify('playlist url')
* *
* const tracks = await playlist.all_tracks() * const tracks = await playlist.all_tracks()
* ``` * ```
* @returns An array of {@link SpotifyTrack} * @returns An array of {@link SpotifyTrack}
*/ */
async all_tracks() : Promise<SpotifyTrack[]>{ async all_tracks(): Promise<SpotifyTrack[]> {
await this.fetch() await this.fetch();
const tracks : SpotifyTrack[] = [] const tracks: SpotifyTrack[] = [];
for(const page of this.fetched_tracks.values()) tracks.push(...page); for (const page of this.fetched_tracks.values()) tracks.push(...page);
return tracks return tracks;
} }
/** /**
* Converts Class to JSON * Converts Class to JSON
@ -530,22 +530,22 @@ export class SpotifyAlbum {
} }
/** /**
* Fetches all the tracks in the album and returns them * Fetches all the tracks in the album and returns them
* *
* ```ts * ```ts
* const album = await play.spotify('album url') * const album = await play.spotify('album url')
* *
* const tracks = await album.all_tracks() * const tracks = await album.all_tracks()
* ``` * ```
* @returns An array of {@link SpotifyTrack} * @returns An array of {@link SpotifyTrack}
*/ */
async all_tracks() : Promise<SpotifyTrack[]>{ async all_tracks(): Promise<SpotifyTrack[]> {
await this.fetch() await this.fetch();
const tracks : SpotifyTrack[] = [] const tracks: SpotifyTrack[] = [];
for( const page of this.fetched_tracks.values() ) tracks.push(...page); for (const page of this.fetched_tracks.values()) tracks.push(...page);
return tracks return tracks;
} }
/** /**
* Converts Class to JSON * Converts Class to JSON

View File

@ -218,10 +218,10 @@ export class YouTubePlayList {
} }
/** /**
* Fetches all the videos in the playlist and returns them * Fetches all the videos in the playlist and returns them
* *
* ```ts * ```ts
* const playlist = await play.playlist_info('playlist url') * const playlist = await play.playlist_info('playlist url')
* *
* const videos = await playlist.all_videos() * const videos = await playlist.all_videos()
* ``` * ```
* @returns An array of {@link YouTubeVideo} objects * @returns An array of {@link YouTubeVideo} objects

View File

@ -1,6 +1,14 @@
import { YouTubeChannel } from './Channel'; import { YouTubeChannel } from './Channel';
import { YouTubeThumbnail } from './Thumbnail'; import { YouTubeThumbnail } from './Thumbnail';
interface VideoMusic {
song?: string;
artist?: string;
album?: string;
writers?: string;
license?: string;
}
interface VideoOptions { interface VideoOptions {
/** /**
* YouTube Video ID * YouTube Video ID
@ -66,6 +74,10 @@ interface VideoOptions {
* `true` if the video has been identified by the YouTube community as inappropriate or offensive to some audiences and viewer discretion is advised * `true` if the video has been identified by the YouTube community as inappropriate or offensive to some audiences and viewer discretion is advised
*/ */
discretionAdvised?: boolean; discretionAdvised?: boolean;
/**
* Gives info about music content in that video.
*/
music?: VideoMusic[];
} }
/** /**
* Class for YouTube Video url * Class for YouTube Video url
@ -135,6 +147,10 @@ export class YouTubeVideo {
* `true` if the video has been identified by the YouTube community as inappropriate or offensive to some audiences and viewer discretion is advised * `true` if the video has been identified by the YouTube community as inappropriate or offensive to some audiences and viewer discretion is advised
*/ */
discretionAdvised?: boolean; discretionAdvised?: boolean;
/**
* Gives info about music content in that video.
*/
music?: VideoMusic[];
/** /**
* Constructor for YouTube Video Class * Constructor for YouTube Video Class
* @param data JSON parsed data. * @param data JSON parsed data.
@ -161,7 +177,8 @@ export class YouTubeVideo {
this.live = !!data.live; this.live = !!data.live;
this.private = !!data.private; this.private = !!data.private;
this.tags = data.tags || []; this.tags = data.tags || [];
this.discretionAdvised = data.discretionAdvised === undefined ? undefined : data.discretionAdvised; this.discretionAdvised = data.discretionAdvised ?? undefined;
this.music = data.music || [];
} }
/** /**
* Converts class to title name of video. * Converts class to title name of video.
@ -190,7 +207,8 @@ export class YouTubeVideo {
likes: this.likes, likes: this.likes,
live: this.live, live: this.live,
private: this.private, private: this.private,
discretionAdvised: this.discretionAdvised discretionAdvised: this.discretionAdvised,
music: this.music
}; };
} }
} }

View File

@ -4,3 +4,4 @@ export { YouTube } from './search';
export { YouTubeVideo } from './classes/Video'; export { YouTubeVideo } from './classes/Video';
export { YouTubePlayList } from './classes/Playlist'; export { YouTubePlayList } from './classes/Playlist';
export { YouTubeChannel } from './classes/Channel'; export { YouTubeChannel } from './classes/Channel';
export { InfoData } from './utils/constants';

View File

@ -83,7 +83,7 @@ export async function stream_from_info(
else final.push(info.format[info.format.length - 1]); else final.push(info.format[info.format.length - 1]);
let type: StreamType = let type: StreamType =
final[0].codec === 'opus' && final[0].container === 'webm' ? StreamType.WebmOpus : StreamType.Arbitrary; final[0].codec === 'opus' && final[0].container === 'webm' ? StreamType.WebmOpus : StreamType.Arbitrary;
await request_stream(`https://${new URL(final[0].url).host}/generate_204`) await request_stream(`https://${new URL(final[0].url).host}/generate_204`);
if (options.seek) { if (options.seek) {
if (type === StreamType.WebmOpus) { if (type === StreamType.WebmOpus) {
if (options.seek >= info.video_details.durationInSec || options.seek <= 0) if (options.seek >= info.video_details.durationInSec || options.seek <= 0)

View File

@ -200,6 +200,25 @@ export async function video_basic_info(url: string, options: InfoOptions = {}):
} }
); );
const microformat = player_response.microformat.playerMicroformatRenderer; const microformat = player_response.microformat.playerMicroformatRenderer;
const musicInfo =
initial_response.contents.twoColumnWatchNextResults.results.results.contents?.[1]?.videoSecondaryInfoRenderer
?.metadataRowContainer?.metadataRowContainerRenderer?.rows;
const music: any[] = [];
if (musicInfo) {
let incompleteInfo: any = {};
musicInfo.forEach((x: any) => {
if (!x.metadataRowRenderer) return;
if (x.metadataRowRenderer.title.simpleText.toLowerCase() === 'song') {
music.push(incompleteInfo);
incompleteInfo = {};
incompleteInfo.song =
x.metadataRowRenderer.contents[0].simpleText ?? x.metadataRowRenderer.contents[0]?.runs?.[0]?.text;
} else
incompleteInfo[x.metadataRowRenderer.title.simpleText.toLowerCase()] =
x.metadataRowRenderer.contents[0].simpleText ?? x.metadataRowRenderer.contents[0]?.runs?.[0]?.text;
});
}
music.shift();
const video_details = new YouTubeVideo({ const video_details = new YouTubeVideo({
id: vid.videoId, id: vid.videoId,
title: vid.title, title: vid.title,
@ -228,7 +247,8 @@ export async function video_basic_info(url: string, options: InfoOptions = {}):
), ),
live: vid.isLiveContent, live: vid.isLiveContent,
private: vid.isPrivate, private: vid.isPrivate,
discretionAdvised discretionAdvised,
music
}); });
const format = player_response.streamingData.formats ?? []; const format = player_response.streamingData.formats ?? [];
format.push(...(player_response.streamingData.adaptiveFormats ?? [])); format.push(...(player_response.streamingData.adaptiveFormats ?? []));

View File

@ -9,7 +9,8 @@ import {
YouTubeStream, YouTubeStream,
YouTubeChannel, YouTubeChannel,
YouTubePlayList, YouTubePlayList,
YouTubeVideo YouTubeVideo,
InfoData
} from './YouTube'; } from './YouTube';
import { import {
spotify, spotify,
@ -73,7 +74,6 @@ import { existsSync, mkdirSync, writeFileSync } from 'node:fs';
import { stream as yt_stream, StreamOptions, stream_from_info as yt_stream_info } from './YouTube/stream'; import { stream as yt_stream, StreamOptions, stream_from_info as yt_stream_info } from './YouTube/stream';
import { yt_search } from './YouTube/search'; import { yt_search } from './YouTube/search';
import { EventEmitter } from 'stream'; import { EventEmitter } from 'stream';
import { InfoData } from './YouTube/utils/constants';
async function stream( async function stream(
url: string, url: string,
@ -477,7 +477,6 @@ export {
SpotifyAlbum, SpotifyAlbum,
SpotifyPlaylist, SpotifyPlaylist,
SpotifyTrack, SpotifyTrack,
YouTubeStream,
YouTubeChannel, YouTubeChannel,
YouTubePlayList, YouTubePlayList,
YouTubeVideo, YouTubeVideo,
@ -503,11 +502,12 @@ export {
validate, validate,
video_basic_info, video_basic_info,
video_info, video_info,
yt_validate yt_validate,
InfoData
}; };
// Export Types // Export Types
export { Deezer, YouTube, SoundCloud, Spotify }; export { Deezer, YouTube, SoundCloud, Spotify, YouTubeStream };
// Export Default // Export Default
export default { export default {