Merge pull request #151 from absidue/deezer-share-improvements
Improve Deezer share link handling
This commit is contained in:
commit
9dd6cb6560
@ -18,7 +18,7 @@ console.log(data.type); // Console logs the type of data that you got.
|
|||||||
|
|
||||||
_This checks that given url is Deezer url or not._
|
_This checks that given url is Deezer url or not._
|
||||||
|
|
||||||
**Returns :** `track` | `album` | `playlist` | `search` | `share` | `false`
|
**Returns :** `track` | `album` | `playlist` | `search` | `false`
|
||||||
|
|
||||||
```js
|
```js
|
||||||
let check = dz_validate(url)
|
let check = dz_validate(url)
|
||||||
@ -27,8 +27,6 @@ if(!check) // Invalid Deezer URL
|
|||||||
|
|
||||||
if(check === 'track') // Deezer Track URL
|
if(check === 'track') // Deezer Track URL
|
||||||
|
|
||||||
if(check === 'share') // Deezer Share URL
|
|
||||||
|
|
||||||
if(check === "search") // Given term is a search query. Search it somewhere.
|
if(check === "search") // Given term is a search query. Search it somewhere.
|
||||||
```
|
```
|
||||||
|
|
||||||
@ -54,18 +52,6 @@ const results = await dz_search(query, {
|
|||||||
}); // Returns an array with one track, using exact matching
|
}); // Returns an array with one track, using exact matching
|
||||||
```
|
```
|
||||||
|
|
||||||
## Resolving a share URL
|
|
||||||
|
|
||||||
### dz_resolve_share_url(url: `string`)
|
|
||||||
|
|
||||||
_Resolves a Deezer share link (deezer.page.link) returning the deezer.com URL._
|
|
||||||
|
|
||||||
**Returns :** `string` the resolved URL. Warning the returned URL might not be a track, album or playlist URL.
|
|
||||||
|
|
||||||
```js
|
|
||||||
const resolvedURL = await dz_resolve_share_url(url);
|
|
||||||
```
|
|
||||||
|
|
||||||
## Classes [ Returned by `deezer(url)` function ]
|
## Classes [ Returned by `deezer(url)` function ]
|
||||||
|
|
||||||
### DeezerTrack
|
### DeezerTrack
|
||||||
|
|||||||
@ -12,7 +12,7 @@ For source specific commands :-
|
|||||||
|
|
||||||
_This checks all type of urls that are supported by play-dl._
|
_This checks all type of urls that are supported by play-dl._
|
||||||
|
|
||||||
**Returns :** `so_playlist` | `so_track` | `sp_track` | `sp_album` | `sp_playlist` | `dz_track` | `dz_playlist` | `dz_album` | `dz_share` | `yt_video` | `yt_playlist` | `search` | `false`
|
**Returns :** `so_playlist` | `so_track` | `sp_track` | `sp_album` | `sp_playlist` | `dz_track` | `dz_playlist` | `dz_album` | `yt_video` | `yt_playlist` | `search` | `false`
|
||||||
|
|
||||||
`so` = **SoundCloud**
|
`so` = **SoundCloud**
|
||||||
|
|
||||||
|
|||||||
@ -3,8 +3,9 @@ import { request, request_resolve_redirect } from '../Request';
|
|||||||
import { DeezerAlbum, DeezerPlaylist, DeezerTrack } from './classes';
|
import { DeezerAlbum, DeezerPlaylist, DeezerTrack } from './classes';
|
||||||
|
|
||||||
interface TypeData {
|
interface TypeData {
|
||||||
type: 'track' | 'playlist' | 'album' | 'search' | 'share' | false;
|
type: 'track' | 'playlist' | 'album' | 'search' | false;
|
||||||
id?: string;
|
id?: string;
|
||||||
|
error?: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
interface DeezerSearchOptions {
|
interface DeezerSearchOptions {
|
||||||
@ -13,7 +14,7 @@ interface DeezerSearchOptions {
|
|||||||
fuzzy?: boolean;
|
fuzzy?: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
function internalValidate(url: string): TypeData {
|
async function internalValidate(url: string): Promise<TypeData> {
|
||||||
let urlObj;
|
let urlObj;
|
||||||
try {
|
try {
|
||||||
// will throw a TypeError if the input is not a valid URL so we need to catch it
|
// will throw a TypeError if the input is not a valid URL so we need to catch it
|
||||||
@ -68,7 +69,13 @@ function internalValidate(url: string): TypeData {
|
|||||||
}
|
}
|
||||||
case 'deezer.page.link': {
|
case 'deezer.page.link': {
|
||||||
if (path.length === 2 && path[1].match(/^[A-Za-z0-9]+$/)) {
|
if (path.length === 2 && path[1].match(/^[A-Za-z0-9]+$/)) {
|
||||||
return { type: 'share' };
|
const resolved = await request_resolve_redirect(url).catch((err) => err);
|
||||||
|
|
||||||
|
if (resolved instanceof Error) {
|
||||||
|
return { type: false, error: resolved.message };
|
||||||
|
}
|
||||||
|
|
||||||
|
return await internalValidate(resolved);
|
||||||
} else {
|
} else {
|
||||||
return { type: false };
|
return { type: false };
|
||||||
}
|
}
|
||||||
@ -90,16 +97,13 @@ export type Deezer = DeezerTrack | DeezerPlaylist | DeezerAlbum;
|
|||||||
* object depending on the provided URL.
|
* object depending on the provided URL.
|
||||||
*/
|
*/
|
||||||
export async function deezer(url: string): Promise<Deezer> {
|
export async function deezer(url: string): Promise<Deezer> {
|
||||||
const typeData = internalValidate(url);
|
const typeData = await internalValidate(url);
|
||||||
|
|
||||||
if (!typeData.type || typeData.type === 'search')
|
if (typeData.error) {
|
||||||
|
throw new Error(`This is not a Deezer track, playlist or album URL:\n${typeData.error}`);
|
||||||
|
} else if (!typeData.type || typeData.type === 'search')
|
||||||
throw new Error('This is not a Deezer track, playlist or album URL');
|
throw new Error('This is not a Deezer track, playlist or album URL');
|
||||||
|
|
||||||
if (typeData.type === 'share') {
|
|
||||||
const resolvedURL = await internalResolve(url);
|
|
||||||
return await deezer(resolvedURL);
|
|
||||||
}
|
|
||||||
|
|
||||||
const response = await request(`https://api.deezer.com/${typeData.type}/${typeData.id}`).catch((err: Error) => err);
|
const response = await request(`https://api.deezer.com/${typeData.type}/${typeData.id}`).catch((err: Error) => err);
|
||||||
|
|
||||||
if (response instanceof Error) throw response;
|
if (response instanceof Error) throw response;
|
||||||
@ -123,11 +127,12 @@ export async function deezer(url: string): Promise<Deezer> {
|
|||||||
/**
|
/**
|
||||||
* Validates a Deezer URL
|
* Validates a Deezer URL
|
||||||
* @param url The URL to validate
|
* @param url The URL to validate
|
||||||
* @returns The type of the URL either 'track', 'playlist', 'album', 'search', 'share' or false.
|
* @returns The type of the URL either 'track', 'playlist', 'album', 'search' or false.
|
||||||
* false means that the provided URL was a wrongly formatted or unsupported Deezer URL.
|
* false means that the provided URL was a wrongly formatted or unsupported Deezer URL.
|
||||||
*/
|
*/
|
||||||
export function dz_validate(url: string): 'track' | 'playlist' | 'album' | 'search' | 'share' | false {
|
export async function dz_validate(url: string): Promise<'track' | 'playlist' | 'album' | 'search' | false> {
|
||||||
return internalValidate(url).type;
|
const typeData = await internalValidate(url);
|
||||||
|
return typeData.type;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -183,30 +188,3 @@ export async function dz_search(query: string, options: DeezerSearchOptions): Pr
|
|||||||
|
|
||||||
return results;
|
return results;
|
||||||
}
|
}
|
||||||
|
|
||||||
async function internalResolve(url: string): Promise<string> {
|
|
||||||
const resolved = await request_resolve_redirect(url);
|
|
||||||
const urlObj = new URL(resolved);
|
|
||||||
urlObj.search = ''; // remove tracking parameters, not needed and also make that URL unnecessarily longer
|
|
||||||
return urlObj.toString();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Resolves a Deezer share link (deezer.page.link) to the equivalent Deezer link.
|
|
||||||
*
|
|
||||||
* The {@link deezer} function automatically does this if {@link dz_validate} returns 'share'.
|
|
||||||
*
|
|
||||||
* @param url The Deezer share link (deezer.page.link) to resolve
|
|
||||||
* @returns The resolved URL.
|
|
||||||
*/
|
|
||||||
export async function dz_resolve_share_url(url: string): Promise<string> {
|
|
||||||
const typeData = internalValidate(url);
|
|
||||||
|
|
||||||
if (typeData.type === 'share') {
|
|
||||||
return await internalResolve(url);
|
|
||||||
} else if (typeData.type === 'track' || typeData.type === 'playlist' || typeData.type === 'album') {
|
|
||||||
return url;
|
|
||||||
} else {
|
|
||||||
throw new Error('This is not a valid Deezer URL');
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|||||||
@ -127,11 +127,19 @@ export function request_resolve_redirect(url: string): Promise<string> {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const statusCode = Number(res.statusCode);
|
const statusCode = Number(res.statusCode);
|
||||||
if (statusCode >= 300 && statusCode < 400) {
|
if (statusCode < 300) {
|
||||||
const resolved = await request_resolve_redirect(res.headers.location as string);
|
resolve(url);
|
||||||
|
} else if (statusCode < 400) {
|
||||||
|
const resolved = await request_resolve_redirect(res.headers.location as string).catch((err) => err);
|
||||||
|
|
||||||
|
if (res instanceof Error) {
|
||||||
|
reject(res);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
resolve(resolved);
|
resolve(resolved);
|
||||||
} else {
|
} else {
|
||||||
resolve(url);
|
reject(new Error(`${res.statusCode}: ${res.statusMessage}, ${url}`));
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|||||||
@ -10,7 +10,7 @@ export {
|
|||||||
} from './YouTube';
|
} from './YouTube';
|
||||||
export { spotify, sp_validate, refreshToken, is_expired, Spotify } from './Spotify';
|
export { spotify, sp_validate, refreshToken, is_expired, Spotify } from './Spotify';
|
||||||
export { soundcloud, so_validate, SoundCloud, SoundCloudStream, getFreeClientID } from './SoundCloud';
|
export { soundcloud, so_validate, SoundCloud, SoundCloudStream, getFreeClientID } from './SoundCloud';
|
||||||
export { deezer, dz_validate, dz_search, dz_resolve_share_url, Deezer } from './Deezer';
|
export { deezer, dz_validate, dz_search, Deezer } from './Deezer';
|
||||||
export { setToken } from './token';
|
export { setToken } from './token';
|
||||||
|
|
||||||
enum AudioPlayerStatus {
|
enum AudioPlayerStatus {
|
||||||
@ -123,7 +123,6 @@ export async function validate(
|
|||||||
| 'dz_track'
|
| 'dz_track'
|
||||||
| 'dz_playlist'
|
| 'dz_playlist'
|
||||||
| 'dz_album'
|
| 'dz_album'
|
||||||
| 'dz_share'
|
|
||||||
| 'yt_video'
|
| 'yt_video'
|
||||||
| 'yt_playlist'
|
| 'yt_playlist'
|
||||||
| 'search'
|
| 'search'
|
||||||
@ -138,8 +137,8 @@ export async function validate(
|
|||||||
check = await so_validate(url);
|
check = await so_validate(url);
|
||||||
return check !== false ? (('so_' + check) as 'so_playlist' | 'so_track') : false;
|
return check !== false ? (('so_' + check) as 'so_playlist' | 'so_track') : false;
|
||||||
} else if (url.indexOf('deezer') !== -1) {
|
} else if (url.indexOf('deezer') !== -1) {
|
||||||
check = dz_validate(url);
|
check = await dz_validate(url);
|
||||||
return check !== false ? (('dz_' + check) as 'dz_track' | 'dz_playlist' | 'dz_album' | 'dz_share') : false;
|
return check !== false ? (('dz_' + check) as 'dz_track' | 'dz_playlist' | 'dz_album') : false;
|
||||||
} else {
|
} else {
|
||||||
check = yt_validate(url);
|
check = yt_validate(url);
|
||||||
return check !== false ? (('yt_' + check) as 'yt_video' | 'yt_playlist') : false;
|
return check !== false ? (('yt_' + check) as 'yt_video' | 'yt_playlist') : false;
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user