feat: typescript support
This commit is contained in:
parent
7594ba06c6
commit
562f063dff
18
.eslintrc
Normal file
18
.eslintrc
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
{
|
||||||
|
"parser": "@typescript-eslint/parser",
|
||||||
|
"plugins": ["@typescript-eslint"],
|
||||||
|
"extends": ["eslint:recommended", "plugin:@typescript-eslint/recommended"],
|
||||||
|
"parserOptions": {
|
||||||
|
"ecmaVersion": 2020,
|
||||||
|
"project": ["tsconfig.json"]
|
||||||
|
},
|
||||||
|
"rules": {
|
||||||
|
"no-empty": [2, { "allowEmptyCatch": true }],
|
||||||
|
"no-inner-declarations": [0, "both"],
|
||||||
|
"@typescript-eslint/no-unused-vars": 2,
|
||||||
|
"@typescript-eslint/consistent-type-definitions": [2, "type"]
|
||||||
|
},
|
||||||
|
"env": {
|
||||||
|
"node": true
|
||||||
|
}
|
||||||
|
}
|
||||||
2
.gitignore
vendored
2
.gitignore
vendored
@ -1,3 +1,5 @@
|
|||||||
node_modules
|
node_modules
|
||||||
yarn-lock.json
|
yarn-lock.json
|
||||||
package-lock.json
|
package-lock.json
|
||||||
|
yarn.lock
|
||||||
|
lib
|
||||||
@ -2,3 +2,6 @@ node_modules
|
|||||||
yarn-lock.json
|
yarn-lock.json
|
||||||
package-lock.json
|
package-lock.json
|
||||||
.gitignore
|
.gitignore
|
||||||
|
tsconfig.json
|
||||||
|
.eslintrc
|
||||||
|
.prettierrc
|
||||||
16
.prettierrc
Normal file
16
.prettierrc
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
{
|
||||||
|
"arrowParens": "always",
|
||||||
|
"endOfLine": "auto",
|
||||||
|
"printWidth": 333,
|
||||||
|
"semi": false,
|
||||||
|
"tabWidth": 2,
|
||||||
|
"trailingComma": "none",
|
||||||
|
"overrides": [
|
||||||
|
{
|
||||||
|
"files": ["./src/types/*.ts"],
|
||||||
|
"options": {
|
||||||
|
"printWidth": 150
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
76
README.md
76
README.md
@ -23,7 +23,7 @@ yarn add @tobyg74/tiktok-api-dl
|
|||||||
|
|
||||||
### Tiktok Downloader
|
### Tiktok Downloader
|
||||||
|
|
||||||
```
|
```js
|
||||||
const { TiktokDL } = require("@tobyg74/tiktok-api-dl");
|
const { TiktokDL } = require("@tobyg74/tiktok-api-dl");
|
||||||
|
|
||||||
const tiktok_url = "https://vt.tiktok.com/ZS84BnrU9"
|
const tiktok_url = "https://vt.tiktok.com/ZS84BnrU9"
|
||||||
@ -36,7 +36,7 @@ TiktokDL(tiktok_url)
|
|||||||
|
|
||||||
### Tiktok Profile
|
### Tiktok Profile
|
||||||
|
|
||||||
```
|
```js
|
||||||
const { TiktokStalk } = require("@tobyg74/tiktok-api-dl");
|
const { TiktokStalk } = require("@tobyg74/tiktok-api-dl");
|
||||||
|
|
||||||
const username = "tobz2k19"
|
const username = "tobz2k19"
|
||||||
@ -51,50 +51,58 @@ TiktokStalk(username)
|
|||||||
|
|
||||||
### Tiktok Downloader
|
### Tiktok Downloader
|
||||||
|
|
||||||
```
|
```ts
|
||||||
{
|
{
|
||||||
status: "success",
|
status: "success" | "error"
|
||||||
result: {
|
message?: string
|
||||||
type: "video" // "image",
|
result?: {
|
||||||
id: ...,
|
type: "video" | "image"
|
||||||
create_time: ...,
|
id: string
|
||||||
description: ...,
|
create_time: number
|
||||||
|
description: string
|
||||||
author: {
|
author: {
|
||||||
...
|
username: string
|
||||||
},
|
nickname: string
|
||||||
|
signature: string
|
||||||
|
birthday: string
|
||||||
|
region: string
|
||||||
|
}
|
||||||
statistics: {
|
statistics: {
|
||||||
...
|
play_count: number
|
||||||
},
|
download_count: number
|
||||||
video // images: [
|
share_count: number
|
||||||
...
|
comment_count: number
|
||||||
],
|
like_count: number
|
||||||
music: [
|
favourite_count: number
|
||||||
...
|
}
|
||||||
]
|
video?: string[]
|
||||||
|
images?: string[]
|
||||||
|
music: string[]
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
### Tiktok Profile
|
### Tiktok Profile
|
||||||
|
|
||||||
```
|
```ts
|
||||||
{
|
{
|
||||||
status: "success",
|
status: "success" | "error"
|
||||||
result: {
|
message?: string
|
||||||
|
result?: {
|
||||||
users: {
|
users: {
|
||||||
username: ...,
|
username: string
|
||||||
nickname: ...,
|
nickname: string
|
||||||
avatar: ...,
|
avatar: string
|
||||||
signature: ...,
|
signature: string
|
||||||
verified: ...,
|
verified: boolean
|
||||||
region: ...
|
region: string
|
||||||
},
|
}
|
||||||
stats: {
|
stats: {
|
||||||
followerCount: ...,
|
followerCount: number
|
||||||
followingCount: ...,
|
followingCount: number
|
||||||
heartCount: ...,
|
heartCount: number
|
||||||
videoCount: ...,
|
videoCount: number
|
||||||
likeCount: ...
|
likeCount: number
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
3
index.js
3
index.js
@ -1,3 +0,0 @@
|
|||||||
const { TiktokDL, TiktokStalk } = require("./utils");
|
|
||||||
|
|
||||||
module.exports = { TiktokDL, TiktokStalk };
|
|
||||||
14
package.json
14
package.json
@ -1,10 +1,12 @@
|
|||||||
{
|
{
|
||||||
"name": "@tobyg74/tiktok-api-dl",
|
"name": "@tobyg74/tiktok-api-dl",
|
||||||
"version": "1.0.2-fix",
|
"version": "1.0.3",
|
||||||
"description": "Scrapper for download Video, Image, Music from Tiktok",
|
"description": "Scrapper for download Video, Image, Music from Tiktok",
|
||||||
"main": "index.js",
|
"main": "lib/index.js",
|
||||||
|
"types": "lib/index.d.ts",
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"test": "echo \"Error: no test specified\" && exit 1"
|
"test": "echo \"Error: no test specified\" && exit 1",
|
||||||
|
"build": "tsc"
|
||||||
},
|
},
|
||||||
"repository": {
|
"repository": {
|
||||||
"type": "git",
|
"type": "git",
|
||||||
@ -18,6 +20,7 @@
|
|||||||
"tiktok"
|
"tiktok"
|
||||||
],
|
],
|
||||||
"author": "Tobz",
|
"author": "Tobz",
|
||||||
|
"contributors": ["aqulzz"],
|
||||||
"license": "ISC",
|
"license": "ISC",
|
||||||
"bugs": {
|
"bugs": {
|
||||||
"url": "https://github.com/TobyG74/tiktok-api-dl/issues"
|
"url": "https://github.com/TobyG74/tiktok-api-dl/issues"
|
||||||
@ -26,5 +29,10 @@
|
|||||||
"dependencies": {
|
"dependencies": {
|
||||||
"axios": "^1.3.4",
|
"axios": "^1.3.4",
|
||||||
"cheerio": "^1.0.0-rc.12"
|
"cheerio": "^1.0.0-rc.12"
|
||||||
|
},
|
||||||
|
"devDependencies": {
|
||||||
|
"@types/cheerio": "^0.22.31",
|
||||||
|
"@types/node": "^18.15.11",
|
||||||
|
"typescript": "^5.0.3"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
1
src/index.ts
Normal file
1
src/index.ts
Normal file
@ -0,0 +1 @@
|
|||||||
|
export * from "./utils"
|
||||||
50
src/types/index.ts
Normal file
50
src/types/index.ts
Normal file
@ -0,0 +1,50 @@
|
|||||||
|
export type DLResult = {
|
||||||
|
status: "success" | "error"
|
||||||
|
message?: string
|
||||||
|
result?: {
|
||||||
|
type: "video" | "image"
|
||||||
|
id: string
|
||||||
|
create_time: number
|
||||||
|
description: string
|
||||||
|
author: {
|
||||||
|
username: string
|
||||||
|
nickname: string
|
||||||
|
signature: string
|
||||||
|
birthday: string
|
||||||
|
region: string
|
||||||
|
}
|
||||||
|
statistics: {
|
||||||
|
play_count: number
|
||||||
|
download_count: number
|
||||||
|
share_count: number
|
||||||
|
comment_count: number
|
||||||
|
like_count: number
|
||||||
|
favourite_count: number
|
||||||
|
}
|
||||||
|
video?: string[]
|
||||||
|
images?: string[]
|
||||||
|
music: string[]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export type StalkResult = {
|
||||||
|
status: "success" | "error"
|
||||||
|
message?: string
|
||||||
|
result?: {
|
||||||
|
users: {
|
||||||
|
username: string
|
||||||
|
nickname: string
|
||||||
|
avatar: string
|
||||||
|
signature: string
|
||||||
|
verified: boolean
|
||||||
|
region: string
|
||||||
|
}
|
||||||
|
stats: {
|
||||||
|
followerCount: number
|
||||||
|
followingCount: number
|
||||||
|
heartCount: number
|
||||||
|
videoCount: number
|
||||||
|
likeCount: number
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
130
src/utils/index.ts
Normal file
130
src/utils/index.ts
Normal file
@ -0,0 +1,130 @@
|
|||||||
|
import axios from "axios"
|
||||||
|
import { load } from "cheerio"
|
||||||
|
import { DLResult, StalkResult } from "../types"
|
||||||
|
|
||||||
|
const _tiktokurl: string = "https://www.tiktok.com"
|
||||||
|
const _tiktokapi = (id: string): string =>
|
||||||
|
`https://api16-va.tiktokv.com/aweme/v1/feed/?aweme_id=${id}&version_name=1.1.9&version_code=119&build_number=1.1.9&manifest_version_code=119&update_version_code=119&openudid=dlcrw3zg28ajm4ml&uuid=3703699664470627&_rticket=1677813932976&ts=1677813932&device_brand=Realme&device_type=RMX1821&device_platform=android&resolution=720*1370&dpi=320&os_version=11&os_api=30&carrier_region=US&sys_region=US%C2%AEion=US&app_name=TK%20Downloader&app_language=en&language=en&timezone_name=Western%20Indonesia%20Time&timezone_offset=25200&channel=googleplay&ac=wifi&mcc_mnc=&is_my_cn=0&aid=1180&ssmix=a&as=a1qwert123`
|
||||||
|
|
||||||
|
export const TiktokDL = (url: string): Promise<DLResult> =>
|
||||||
|
new Promise((resolve, reject) => {
|
||||||
|
url = url.replace("https://vm", "https://vt")
|
||||||
|
axios
|
||||||
|
.head(url)
|
||||||
|
.then(({ request }) => {
|
||||||
|
const { responseUrl } = request.res
|
||||||
|
let ID = responseUrl.match(/\d{17,21}/g)
|
||||||
|
if (ID === null)
|
||||||
|
return reject({
|
||||||
|
status: "error",
|
||||||
|
message: "Failed to fetch tiktok url. Make sure your tiktok url is correct!"
|
||||||
|
})
|
||||||
|
ID = ID[0]
|
||||||
|
axios
|
||||||
|
.get(_tiktokapi(ID))
|
||||||
|
.then(({ data }) => {
|
||||||
|
const content = data.aweme_list.filter((v) => v.aweme_id === ID)[0]
|
||||||
|
if (!content)
|
||||||
|
return resolve({
|
||||||
|
status: "error",
|
||||||
|
message: "Failed to find tiktok data. Make sure your tiktok url is correct!"
|
||||||
|
})
|
||||||
|
const statistics = {
|
||||||
|
play_count: content.statistics.play_count,
|
||||||
|
download_count: content.statistics.download_count,
|
||||||
|
share_count: content.statistics.share_count,
|
||||||
|
comment_count: content.statistics.comment_count,
|
||||||
|
like_count: content.statistics.digg_count,
|
||||||
|
favourite_count: content.statistics.collect_count
|
||||||
|
}
|
||||||
|
const author = {
|
||||||
|
username: content.author.unique_id,
|
||||||
|
nickname: content.author.nickname,
|
||||||
|
signature: content.author.signature,
|
||||||
|
birthday: content.author.birthday,
|
||||||
|
region: content.author.region
|
||||||
|
}
|
||||||
|
if (content.image_post_info) {
|
||||||
|
resolve({
|
||||||
|
status: "success",
|
||||||
|
result: {
|
||||||
|
type: "image",
|
||||||
|
id: content.aweme_id,
|
||||||
|
create_time: content.create_time,
|
||||||
|
description: content.desc,
|
||||||
|
author,
|
||||||
|
statistics,
|
||||||
|
images: content.image_post_info.images.map((v) => v.display_image.url_list[0]),
|
||||||
|
music: content.music.play_url.url_list
|
||||||
|
}
|
||||||
|
})
|
||||||
|
} else {
|
||||||
|
resolve({
|
||||||
|
status: "success",
|
||||||
|
result: {
|
||||||
|
type: "video",
|
||||||
|
id: content.aweme_id,
|
||||||
|
create_time: content.create_time,
|
||||||
|
description: content.desc,
|
||||||
|
author,
|
||||||
|
statistics,
|
||||||
|
video: content.video.play_addr.url_list,
|
||||||
|
music: content.music.play_url.url_list
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.catch(reject)
|
||||||
|
})
|
||||||
|
.catch(reject)
|
||||||
|
})
|
||||||
|
|
||||||
|
export const TiktokStalk = (username: string): Promise<StalkResult> =>
|
||||||
|
new Promise((resolve, reject) => {
|
||||||
|
axios
|
||||||
|
.get("https://pastebin.com/raw/ELJjcbZT")
|
||||||
|
.then(({ data: cookie }) => {
|
||||||
|
username = username.replace("@", "")
|
||||||
|
axios
|
||||||
|
.get(`${_tiktokurl}/@${username}`, {
|
||||||
|
headers: {
|
||||||
|
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/89.0.4389.114 Safari/537.36",
|
||||||
|
cookie: cookie
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.then(({ data }) => {
|
||||||
|
const $ = load(data)
|
||||||
|
const result = JSON.parse($("script#SIGI_STATE").text())
|
||||||
|
if (!result.UserModule) {
|
||||||
|
return resolve({
|
||||||
|
status: "error",
|
||||||
|
message: "User not found!"
|
||||||
|
})
|
||||||
|
}
|
||||||
|
const user = result.UserModule
|
||||||
|
const users = {
|
||||||
|
username: user.users[username].uniqueId,
|
||||||
|
nickname: user.users[username].nickname,
|
||||||
|
avatar: user.users[username].avatarLarger,
|
||||||
|
signature: user.users[username].signature,
|
||||||
|
verified: user.users[username].verified,
|
||||||
|
region: user.users[username].region
|
||||||
|
}
|
||||||
|
const stats = {
|
||||||
|
followerCount: user.stats[username].followerCount,
|
||||||
|
followingCount: user.stats[username].followingCount,
|
||||||
|
heartCount: user.stats[username].heartCount,
|
||||||
|
videoCount: user.stats[username].videoCount,
|
||||||
|
likeCount: user.stats[username].diggCount
|
||||||
|
}
|
||||||
|
resolve({
|
||||||
|
status: "success",
|
||||||
|
result: {
|
||||||
|
users,
|
||||||
|
stats
|
||||||
|
}
|
||||||
|
})
|
||||||
|
})
|
||||||
|
})
|
||||||
|
.catch((e) => resolve({ status: "error", message: e.message }))
|
||||||
|
})
|
||||||
22
tsconfig.json
Normal file
22
tsconfig.json
Normal file
@ -0,0 +1,22 @@
|
|||||||
|
{
|
||||||
|
"compilerOptions": {
|
||||||
|
"allowJs": false,
|
||||||
|
"checkJs": false,
|
||||||
|
"esModuleInterop": true,
|
||||||
|
"experimentalDecorators": true,
|
||||||
|
"forceConsistentCasingInFileNames": true,
|
||||||
|
"lib": ["ES2020", "ESNext.Array", "DOM"],
|
||||||
|
"module": "CommonJS",
|
||||||
|
"moduleResolution": "node",
|
||||||
|
"noImplicitThis": true,
|
||||||
|
"outDir": "lib",
|
||||||
|
"removeComments": true,
|
||||||
|
"resolveJsonModule": true,
|
||||||
|
"rootDir": "src",
|
||||||
|
"skipLibCheck": true,
|
||||||
|
"declaration": true,
|
||||||
|
"target": "ES2020"
|
||||||
|
},
|
||||||
|
"exclude": ["node_modules"],
|
||||||
|
"include": ["./src/**/*.ts"]
|
||||||
|
}
|
||||||
139
utils/index.js
139
utils/index.js
@ -1,139 +0,0 @@
|
|||||||
const Axios = require("axios");
|
|
||||||
const cheerio = require("cheerio");
|
|
||||||
|
|
||||||
const _tiktokurl = "https://www.tiktok.com";
|
|
||||||
const _tiktokapi = (id) =>
|
|
||||||
`https://api16-va.tiktokv.com/aweme/v1/feed/?aweme_id=${id}&version_name=1.1.9&version_code=119&build_number=1.1.9&manifest_version_code=119&update_version_code=119&openudid=dlcrw3zg28ajm4ml&uuid=3703699664470627&_rticket=1677813932976&ts=1677813932&device_brand=Realme&device_type=RMX1821&device_platform=android&resolution=720*1370&dpi=320&os_version=11&os_api=30&carrier_region=US&sys_region=US%C2%AEion=US&app_name=TK%20Downloader&app_language=en&language=en&timezone_name=Western%20Indonesia%20Time&timezone_offset=25200&channel=googleplay&ac=wifi&mcc_mnc=&is_my_cn=0&aid=1180&ssmix=a&as=a1qwert123`;
|
|
||||||
|
|
||||||
const TiktokDL = (url) => {
|
|
||||||
return new Promise((resolve, reject) => {
|
|
||||||
url = url.replace("https://vm", "https://vt");
|
|
||||||
Axios(url, {
|
|
||||||
method: "HEAD",
|
|
||||||
})
|
|
||||||
.then(({ request }) => {
|
|
||||||
const { responseUrl } = request.res;
|
|
||||||
let ID = responseUrl.match(/\d{17,21}/g);
|
|
||||||
if (ID === null)
|
|
||||||
return reject({
|
|
||||||
status: "error",
|
|
||||||
message:
|
|
||||||
"Failed to fetch tiktok url. Make sure your tiktok url is correct!",
|
|
||||||
});
|
|
||||||
ID = ID[0];
|
|
||||||
Axios(_tiktokapi(ID), {
|
|
||||||
method: "GET",
|
|
||||||
})
|
|
||||||
.then(({ data }) => {
|
|
||||||
const content = data.aweme_list.filter((v) => v.aweme_id === ID)[0];
|
|
||||||
if (!content)
|
|
||||||
return resolve({
|
|
||||||
status: "error",
|
|
||||||
message:
|
|
||||||
"Failed to find tiktok data. Make sure your tiktok url is correct!",
|
|
||||||
});
|
|
||||||
const statistics = {
|
|
||||||
play_count: content.statistics.play_count,
|
|
||||||
download_count: content.statistics.download_count,
|
|
||||||
share_count: content.statistics.share_count,
|
|
||||||
comment_count: content.statistics.comment_count,
|
|
||||||
like_count: content.statistics.digg_count,
|
|
||||||
favourite_count: content.statistics.collect_count,
|
|
||||||
};
|
|
||||||
const author = {
|
|
||||||
username: content.author.unique_id,
|
|
||||||
nickname: content.author.nickname,
|
|
||||||
signature: content.author.signature,
|
|
||||||
birthday: content.author.birthday,
|
|
||||||
region: content.author.region,
|
|
||||||
};
|
|
||||||
if (content.image_post_info) {
|
|
||||||
resolve({
|
|
||||||
status: "success",
|
|
||||||
result: {
|
|
||||||
type: "image",
|
|
||||||
id: content.aweme_id,
|
|
||||||
create_time: content.create_time,
|
|
||||||
description: content.desc,
|
|
||||||
author,
|
|
||||||
statistics,
|
|
||||||
images: content.image_post_info.images.map(
|
|
||||||
(v) => v.display_image.url_list[0]
|
|
||||||
),
|
|
||||||
music: content.music.play_url.url_list,
|
|
||||||
},
|
|
||||||
});
|
|
||||||
} else {
|
|
||||||
resolve({
|
|
||||||
status: "success",
|
|
||||||
result: {
|
|
||||||
type: "video",
|
|
||||||
id: content.aweme_id,
|
|
||||||
create_time: content.create_time,
|
|
||||||
description: content.desc,
|
|
||||||
author,
|
|
||||||
statistics,
|
|
||||||
video: content.video.play_addr.url_list,
|
|
||||||
music: content.music.play_url.url_list,
|
|
||||||
},
|
|
||||||
});
|
|
||||||
}
|
|
||||||
})
|
|
||||||
.catch(reject);
|
|
||||||
})
|
|
||||||
.catch(reject);
|
|
||||||
});
|
|
||||||
};
|
|
||||||
|
|
||||||
const TiktokStalk = (username) => {
|
|
||||||
return new Promise(async (resolve, reject) => {
|
|
||||||
const { data: cookie } = await Axios.get("https://pastebin.com/raw/ELJjcbZT");
|
|
||||||
username = username.replace("@", "");
|
|
||||||
Axios(`${_tiktokurl}/@${username}`, {
|
|
||||||
method: "GET",
|
|
||||||
headers: {
|
|
||||||
"user-agent":
|
|
||||||
"Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/89.0.4389.114 Safari/537.36",
|
|
||||||
cookie: cookie,
|
|
||||||
},
|
|
||||||
})
|
|
||||||
.then(({ data }) => {
|
|
||||||
const $ = cheerio.load(data);
|
|
||||||
const result = JSON.parse($("script#SIGI_STATE").text());
|
|
||||||
if (!result.UserModule) {
|
|
||||||
return resolve({
|
|
||||||
status: "error",
|
|
||||||
message: "User not found!",
|
|
||||||
});
|
|
||||||
}
|
|
||||||
const user = result.UserModule;
|
|
||||||
const users = {
|
|
||||||
username: user.users[username].uniqueId,
|
|
||||||
nickname: user.users[username].nickname,
|
|
||||||
avatar: user.users[username].avatarLarger,
|
|
||||||
signature: user.users[username].signature,
|
|
||||||
verified: user.users[username].verified,
|
|
||||||
region: user.users[username].region,
|
|
||||||
};
|
|
||||||
const stats = {
|
|
||||||
followerCount: user.stats[username].followerCount,
|
|
||||||
followingCount: user.stats[username].followingCount,
|
|
||||||
heartCount: user.stats[username].heartCount,
|
|
||||||
videoCount: user.stats[username].videoCount,
|
|
||||||
likeCount: user.stats[username].diggCount,
|
|
||||||
};
|
|
||||||
resolve({
|
|
||||||
status: "success",
|
|
||||||
result: {
|
|
||||||
users,
|
|
||||||
stats,
|
|
||||||
},
|
|
||||||
});
|
|
||||||
})
|
|
||||||
.catch((e) => {
|
|
||||||
resolve({ status: "error", message: e.message });
|
|
||||||
});
|
|
||||||
});
|
|
||||||
};
|
|
||||||
|
|
||||||
module.exports = { TiktokDL, TiktokStalk };
|
|
||||||
Loading…
x
Reference in New Issue
Block a user