diff --git a/lib/url-utils.js b/lib/url-utils.js index 95726b88..c60789df 100644 --- a/lib/url-utils.js +++ b/lib/url-utils.js @@ -22,13 +22,13 @@ const validQueryDomains = new Set([ 'music.youtube.com', 'gaming.youtube.com', ]); -const validPathDomains = /^https?:\/\/(youtu\.be\/|(www\.)?youtube.com\/(embed|v|shorts)\/)/; +const validPathDomains = /^https?:\/\/(youtu\.be\/|(www\.)?youtube\.com\/(embed|v|shorts)\/)/; exports.getURLVideoID = link => { const parsed = new URL(link); let id = parsed.searchParams.get('v'); if (validPathDomains.test(link) && !id) { const paths = parsed.pathname.split('/'); - id = paths[paths.length - 1]; + id = parsed.host === 'youtu.be' ? paths[1] : paths[2]; } else if (parsed.hostname && !validQueryDomains.has(parsed.hostname)) { throw Error('Not a YouTube domain'); } diff --git a/test/url-utils-test.js b/test/url-utils-test.js index 6b9fac28..de4a96e3 100644 --- a/test/url-utils-test.js +++ b/test/url-utils-test.js @@ -19,6 +19,8 @@ describe('getURLVideoID()', () => { assert.strictEqual(id, 'RAW_VIDEOID'); id = getVideoID('http://youtube.com/shorts/RAW_VIDEOID'); assert.strictEqual(id, 'RAW_VIDEOID'); + id = getVideoID('http://youtube.com/v/RAW_VIDEOID/FakeVideoID'); + assert.strictEqual(id, 'RAW_VIDEOID'); id = getVideoID('https://music.youtube.com/watch?v=RAW_VIDEOID&list=RDAMVMmtLgabce8KQ'); assert.strictEqual(id, 'RAW_VIDEOID'); id = getVideoID('https://gaming.youtube.com/watch?v=RAW_VIDEOID'); @@ -59,6 +61,8 @@ describe('getVideoID()', () => { assert.strictEqual(id, 'RAW_VIDEOID'); id = getVideoID('http://youtube.com/shorts/RAW_VIDEOID'); assert.strictEqual(id, 'RAW_VIDEOID'); + id = getVideoID('http://youtube.com/v/RAW_VIDEOID/FakeVideoID'); + assert.strictEqual(id, 'RAW_VIDEOID'); id = getVideoID('_LENGTH_11_'); assert.strictEqual(id, '_LENGTH_11_'); assert.throws(() => {