ripunzel/src/dissectLink.js

156 lines
3.8 KiB
JavaScript

'use strict';
const UrlPattern = require('url-pattern');
const hosts = [
{
method: 'self',
label: 'self',
pattern: new UrlPattern('http(s)\\://(www.)reddit.com/r/:subreddit/comments/:id/:uri/'),
},
{
method: 'redditImage',
label: 'reddit',
pattern: new UrlPattern('http(s)\\://i.redd.it/:id.:ext(?*)'),
},
{
method: 'redditImage',
label: 'reddit',
pattern: new UrlPattern('http(s)\\://i.reddituploads.com/:id(?*)'),
},
{
method: 'redditAlbum',
label: 'reddit',
pattern: new UrlPattern('http(s)\\://(www.)reddit.com/gallery/:id'),
},
{
method: 'redditVideo',
label: 'reddit',
pattern: new UrlPattern('http(s)\\://v.redd.it/:id(?*)'),
},
{
method: 'imgurImage',
label: 'imgur',
pattern: new UrlPattern('http(s)\\://(:subdomain.)imgur.com/(:id_d)(:id)(.:ext)(?*)'),
},
{
method: 'imgurAlbum',
label: 'imgur',
pattern: new UrlPattern('http(s)\\://(:subdomain.)imgur.com/:type/:id(#:focus)(?*)'),
},
{
method: 'vidbleImage',
label: 'vidble',
pattern: new UrlPattern('http(s)\\://(www.)vidble.com/(show/):id(.:ext)(?*)'),
},
{
method: 'vidbleVideo',
label: 'vidble',
pattern: new UrlPattern('http(s)\\://(www.)vidble.com/watch?v=:id(?*)'),
},
{
method: 'vidbleAlbum',
label: 'vidble',
pattern: new UrlPattern('http(s)\\://(www.)vidble.com/album/:id(?*)'),
},
{
method: 'gfycat',
label: 'gfycat',
pattern: new UrlPattern('http(s)\\://(:server.)gfycat.com/(gifs/detail/)(:id-mobile)(:id-size_restricted)(:id)(.:ext)(?*)'),
},
{
method: 'redgifs',
label: 'redgifs',
pattern: new UrlPattern('http(s)\\://(:subdomain.)redgifs.com(/watch)(/i)/(:id-mobile)(:id)(.:ext)(?*)'),
},
{
method: 'erome',
label: 'erome',
pattern: new UrlPattern('http(s)\\://(www.)erome.com/a/:id(?*)'),
},
{
method: 'eroshareAlbum',
label: 'eroshare',
pattern: new UrlPattern('http(s)\\://eroshare.com/:id(#)(:query)'),
},
{
method: 'eroshareItem',
label: 'eroshare',
pattern: new UrlPattern('http(s)\\://eroshare.com/i/:id(#)(:query)'),
},
];
const fallbacks = new Set([
'bbc',
'biqle',
'buzzfeed',
'chaturbate',
'dailymotion',
'eporner',
'instagram',
'keezmovies',
'liveleak',
'mixcloud',
'pornhd',
'pornhub',
'redtube',
'soundcloud',
'soundgasm',
'spankbang',
'spankwire',
'streamable',
'tiktok',
'tube8',
'tweakers',
'twitch',
'twitter',
'vimeo',
'xhamster',
'xnxx',
'youjizz',
'youporn',
'youtube',
]);
module.exports = function dissectLink(url) {
const hostMethod = hosts.reduce((acc, host) => {
if (acc) {
return acc;
}
// const match = host.pattern.match(url.replace(/(https?:\/\/)|(\/)+/g, '$1$2')); // remove double slashes
const { origin, pathname } = new URL(url);
const match = host.pattern.match(`${origin}${pathname}`); // remove double slashes
if (match) {
return Object.assign(match, {
url,
method: host.method,
label: host.label,
});
}
return null;
}, null);
if (hostMethod) {
return hostMethod;
}
const match = new UrlPattern('http(s)\\://(www.):hostname(*)').match(url);
if (match) {
const { hostname } = match;
if (hostname && fallbacks.has(hostname)) {
return {
url,
method: 'tube',
label: hostname,
};
}
}
return null;
};