diff --git a/src/core/Session.ts b/src/core/Session.ts index fe3cacfa..7c52a05e 100644 --- a/src/core/Session.ts +++ b/src/core/Session.ts @@ -56,6 +56,7 @@ export interface Context { export interface SessionOptions { lang?: string; + location?: string; account_index?: number; device_category?: DeviceCategory; client_type?: ClientType; @@ -112,6 +113,7 @@ export default class Session extends EventEmitterLike { static async create(options: SessionOptions = {}) { const { context, api_key, api_version, account_index } = await Session.getSessionData( options.lang, + options.location, options.account_index, options.device_category, options.client_type, @@ -123,6 +125,7 @@ export default class Session extends EventEmitterLike { static async getSessionData( lang = 'en-US', + location = '', account_index = 0, device_category: DeviceCategory = 'desktop', client_name: ClientType = ClientType.WEB, @@ -157,7 +160,7 @@ export default class Session extends EventEmitterLike { const context: Context = { client: { hl: device_info[0], - gl: device_info[2], + gl: location || device_info[2], remoteHost: device_info[3], screenDensityFloat: 1, screenHeightPoints: 720, diff --git a/src/parser/classes/CompactVideo.ts b/src/parser/classes/CompactVideo.ts index f1a17080..7946839c 100644 --- a/src/parser/classes/CompactVideo.ts +++ b/src/parser/classes/CompactVideo.ts @@ -4,6 +4,8 @@ import Author from './misc/Author'; import { timeToSeconds } from '../../utils/Utils'; import Thumbnail from './misc/Thumbnail'; import NavigationEndpoint from './NavigationEndpoint'; +import type Menu from './menus/Menu'; + import { YTNode } from '../helpers'; class CompactVideo extends YTNode { @@ -25,7 +27,7 @@ class CompactVideo extends YTNode { thumbnail_overlays; endpoint: NavigationEndpoint; - menu; + menu: Menu | null; constructor(data: any) { super(); @@ -43,9 +45,9 @@ class CompactVideo extends YTNode { seconds: timeToSeconds(new Text(data.lengthText).toString()) }; - this.thumbnail_overlays = Parser.parse(data.thumbnailOverlays); + this.thumbnail_overlays = Parser.parseArray(data.thumbnailOverlays); this.endpoint = new NavigationEndpoint(data.navigationEndpoint); - this.menu = Parser.parse(data.menu); + this.menu = Parser.parseItem(data.menu); } get best_thumbnail() { diff --git a/src/parser/classes/GridVideo.ts b/src/parser/classes/GridVideo.ts index 0c250f07..660e1ce4 100644 --- a/src/parser/classes/GridVideo.ts +++ b/src/parser/classes/GridVideo.ts @@ -3,6 +3,9 @@ import Text from './misc/Text'; import Thumbnail from './misc/Thumbnail'; import NavigationEndpoint from './NavigationEndpoint'; import Author from './misc/Author'; + +import type Menu from './menus/Menu'; + import { YTNode } from '../helpers'; class GridVideo extends YTNode { @@ -14,12 +17,12 @@ class GridVideo extends YTNode { thumbnail_overlays; rich_thumbnail; published: Text; - duration: Text | string; + duration: Text | null; author: Author; views: Text; short_view_count: Text; endpoint: NavigationEndpoint; - menu; + menu: Menu | null; constructor(data: any) { super(); @@ -27,15 +30,15 @@ class GridVideo extends YTNode { this.id = data.videoId; this.title = new Text(data.title); this.thumbnails = Thumbnail.fromResponse(data.thumbnail); - this.thumbnail_overlays = Parser.parse(data.thumbnailOverlays); + this.thumbnail_overlays = Parser.parseArray(data.thumbnailOverlays); this.rich_thumbnail = data.richThumbnail && Parser.parse(data.richThumbnail); this.published = new Text(data.publishedTimeText); - this.duration = data.lengthText ? new Text(data.lengthText) : length_alt?.text ? new Text(length_alt.text) : ''; + this.duration = data.lengthText ? new Text(data.lengthText) : length_alt?.text ? new Text(length_alt.text) : null; this.author = data.shortBylineText && new Author(data.shortBylineText, data.ownerBadges); this.views = new Text(data.viewCountText); this.short_view_count = new Text(data.shortViewCountText); this.endpoint = new NavigationEndpoint(data.navigationEndpoint); - this.menu = Parser.parse(data.menu); + this.menu = Parser.parseItem(data.menu); } } diff --git a/src/parser/classes/PlaylistPanelVideo.ts b/src/parser/classes/PlaylistPanelVideo.ts index b10429c6..08039519 100644 --- a/src/parser/classes/PlaylistPanelVideo.ts +++ b/src/parser/classes/PlaylistPanelVideo.ts @@ -76,8 +76,8 @@ class PlaylistPanelVideo extends YTNode { })); } - this.badges = Parser.parse(data.badges); - this.menu = Parser.parse(data.menu); + this.badges = Parser.parseArray(data.badges); + this.menu = Parser.parseItem(data.menu); this.set_video_id = data.playlistSetVideoId; } } diff --git a/src/parser/classes/PlaylistVideo.ts b/src/parser/classes/PlaylistVideo.ts index bf7636ed..7cbc4f34 100644 --- a/src/parser/classes/PlaylistVideo.ts +++ b/src/parser/classes/PlaylistVideo.ts @@ -3,6 +3,8 @@ import Parser from '../index'; import Thumbnail from './misc/Thumbnail'; import PlaylistAuthor from './misc/PlaylistAuthor'; import NavigationEndpoint from './NavigationEndpoint'; +import type Menu from './menus/Menu'; + import { YTNode } from '../helpers'; class PlaylistVideo extends YTNode { @@ -17,7 +19,7 @@ class PlaylistVideo extends YTNode { set_video_id: string | undefined; endpoint: NavigationEndpoint; is_playable: boolean; - menu; + menu: Menu | null; duration: { text: string; @@ -35,7 +37,7 @@ class PlaylistVideo extends YTNode { this.set_video_id = data?.setVideoId; this.endpoint = new NavigationEndpoint(data.navigationEndpoint); this.is_playable = data.isPlayable; - this.menu = Parser.parse(data.menu); + this.menu = Parser.parseItem(data.menu); this.duration = { text: new Text(data.lengthText).text, seconds: parseInt(data.lengthSeconds) diff --git a/src/utils/HTTPClient.ts b/src/utils/HTTPClient.ts index 467ee03c..e3f6d671 100644 --- a/src/utils/HTTPClient.ts +++ b/src/utils/HTTPClient.ts @@ -48,7 +48,7 @@ export default class HTTPClient { const request_headers = new Headers(headers); request_headers.set('Accept', '*/*'); - request_headers.set('Accept-Language', `en-${this.#session.context.client.gl || 'US'}`); + request_headers.set('Accept-Language', `${this.#session.context.client.hl}-${this.#session.context.client.gl}`); request_headers.set('x-goog-visitor-id', this.#session.context.client.visitorData || ''); request_headers.set('x-origin', request_url.origin); request_headers.set('x-youtube-client-version', this.#session.context.client.clientVersion || '');