mirror of
https://github.com/maotoumao/MusicFreePlugins.git
synced 2026-09-03 06:34:15 +08:00
update
This commit is contained in:
2
dist/_plugins/plugins.json
vendored
2
dist/_plugins/plugins.json
vendored
@@ -1 +1 @@
|
||||
{"desc":"此链接为 MusicFree 插件,插件开发及使用方式参考 https://musicfree.upup.fun","plugins":[{"name":"bilibili","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/bilibili/index.js","version":"0.1.15"},{"name":"Audiomack","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/audiomack/index.js","version":"0.0.2"},{"name":"歌词千寻","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/geciqianxun/index.js","version":"0.0.0"},{"name":"歌词网","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/geciwang/index.js","version":"0.0.0"},{"name":"快手","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/kuaishou/index.js","version":"0.0.1"},{"name":"Navidrome","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/navidrome/index.js","version":"0.0.0"},{"name":"猫耳FM","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/maoerfm/index.js","version":"0.1.4"},{"name":"suno","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/suno/index.js","version":"0.0.0"},{"name":"udio","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/udio/index.js","version":"0.0.0"},{"name":"音悦台","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/yinyuetai/index.js","version":"0.0.1"},{"name":"WebDAV","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/webdav/index.js","version":"0.0.2"},{"name":"Youtube","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/youtube/index.js","version":"0.0.1"}]}
|
||||
{"desc":"此链接为 MusicFree 插件,插件开发及使用方式参考 https://musicfree.upup.fun","plugins":[{"name":"Audiomack","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/audiomack/index.js","version":"0.0.2"},{"name":"歌词千寻","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/geciqianxun/index.js","version":"0.0.0"},{"name":"bilibili","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/bilibili/index.js","version":"0.2.0"},{"name":"歌词网","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/geciwang/index.js","version":"0.0.0"},{"name":"suno","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/suno/index.js","version":"0.0.0"},{"name":"猫耳FM","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/maoerfm/index.js","version":"0.1.4"},{"name":"快手","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/kuaishou/index.js","version":"0.0.1"},{"name":"udio","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/udio/index.js","version":"0.0.0"},{"name":"Navidrome","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/navidrome/index.js","version":"0.0.0"},{"name":"WebDAV","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/webdav/index.js","version":"0.0.2"},{"name":"Youtube","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/youtube/index.js","version":"0.0.1"},{"name":"音悦台","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/yinyuetai/index.js","version":"0.0.1"}]}
|
||||
952
dist/audiomack/index.js
vendored
952
dist/audiomack/index.js
vendored
@@ -1,476 +1,476 @@
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
const cheerio_1 = require("cheerio");
|
||||
const CryptoJS = require("crypto-js");
|
||||
const dayjs = require("dayjs");
|
||||
const pageSize = 20;
|
||||
const headers = {
|
||||
"user-agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/119.0.0.0 Safari/537.36",
|
||||
};
|
||||
function nonce(e = 10) {
|
||||
let n = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789", r = "";
|
||||
for (let i = 0; i < e; i++)
|
||||
r += n.charAt(Math.floor(Math.random() * n.length));
|
||||
return r;
|
||||
}
|
||||
function getNormalizedParams(parameters) {
|
||||
const sortedKeys = [];
|
||||
const normalizedParameters = [];
|
||||
for (let e in parameters) {
|
||||
sortedKeys.push(_encode(e));
|
||||
}
|
||||
sortedKeys.sort();
|
||||
for (let idx = 0; idx < sortedKeys.length; idx++) {
|
||||
const e = sortedKeys[idx];
|
||||
var n, r, i = _decode(e), a = parameters[i];
|
||||
for (a.sort(), n = 0; n < a.length; n++)
|
||||
(r = _encode(a[n])), normalizedParameters.push(e + "=" + r);
|
||||
}
|
||||
return normalizedParameters.join("&");
|
||||
}
|
||||
function _encode(e) {
|
||||
return e
|
||||
? encodeURIComponent(e)
|
||||
.replace(/[!'()]/g, escape)
|
||||
.replace(/\*/g, "%2A")
|
||||
: "";
|
||||
}
|
||||
function _decode(e) {
|
||||
return e ? decodeURIComponent(e) : "";
|
||||
}
|
||||
function u(e) {
|
||||
(this._parameters = {}), this._loadParameters(e || {});
|
||||
}
|
||||
u.prototype = {
|
||||
_loadParameters: function (e) {
|
||||
e instanceof Array
|
||||
? this._loadParametersFromArray(e)
|
||||
: "object" == typeof e && this._loadParametersFromObject(e);
|
||||
},
|
||||
_loadParametersFromArray: function (e) {
|
||||
var n;
|
||||
for (n = 0; n < e.length; n++)
|
||||
this._loadParametersFromObject(e[n]);
|
||||
},
|
||||
_loadParametersFromObject: function (e) {
|
||||
var n;
|
||||
for (n in e)
|
||||
if (e.hasOwnProperty(n)) {
|
||||
var r = this._getStringFromParameter(e[n]);
|
||||
this._loadParameterValue(n, r);
|
||||
}
|
||||
},
|
||||
_loadParameterValue: function (e, n) {
|
||||
var r;
|
||||
if (n instanceof Array) {
|
||||
for (r = 0; r < n.length; r++) {
|
||||
var i = this._getStringFromParameter(n[r]);
|
||||
this._addParameter(e, i);
|
||||
}
|
||||
0 == n.length && this._addParameter(e, "");
|
||||
}
|
||||
else
|
||||
this._addParameter(e, n);
|
||||
},
|
||||
_getStringFromParameter: function (e) {
|
||||
var n = e || "";
|
||||
try {
|
||||
("number" == typeof e || "boolean" == typeof e) && (n = e.toString());
|
||||
}
|
||||
catch (e) { }
|
||||
return n;
|
||||
},
|
||||
_addParameter: function (e, n) {
|
||||
this._parameters[e] || (this._parameters[e] = []),
|
||||
this._parameters[e].push(n);
|
||||
},
|
||||
get: function () {
|
||||
return this._parameters;
|
||||
},
|
||||
};
|
||||
function getSignature(method, urlPath, params, secret = "f3ac5b086f3eab260520d8e3049561e6") {
|
||||
urlPath = urlPath.split("?")[0];
|
||||
urlPath = urlPath.startsWith("http")
|
||||
? urlPath
|
||||
: "https://api.audiomack.com/v1" + urlPath;
|
||||
const r = new u(params).get();
|
||||
const httpMethod = method.toUpperCase();
|
||||
const normdParams = getNormalizedParams(r);
|
||||
const l = _encode(httpMethod) + "&" + _encode(urlPath) + "&" + _encode(normdParams);
|
||||
const hash = CryptoJS.HmacSHA1(l, secret + "&").toString(CryptoJS.enc.Base64);
|
||||
return hash;
|
||||
}
|
||||
function formatMusicItem(raw) {
|
||||
return {
|
||||
id: raw.id,
|
||||
artwork: raw.image || raw.image_base,
|
||||
duration: +raw.duration,
|
||||
title: raw.title,
|
||||
artist: raw.artist,
|
||||
album: raw.album,
|
||||
url_slug: raw.url_slug,
|
||||
};
|
||||
}
|
||||
function formatAlbumItem(raw) {
|
||||
var _a, _b;
|
||||
return {
|
||||
artist: raw.artist,
|
||||
artwork: raw.image || raw.image_base,
|
||||
id: raw.id,
|
||||
date: dayjs.unix(+raw.released).format("YYYY-MM-DD"),
|
||||
title: raw.title,
|
||||
_musicList: (_b = (_a = raw === null || raw === void 0 ? void 0 : raw.tracks) === null || _a === void 0 ? void 0 : _a.map) === null || _b === void 0 ? void 0 : _b.call(_a, (it) => ({
|
||||
id: it.song_id || it.id,
|
||||
artwork: raw.image || raw.image_base,
|
||||
duration: +it.duration,
|
||||
title: it.title,
|
||||
artist: it.artist,
|
||||
album: raw.title,
|
||||
})),
|
||||
};
|
||||
}
|
||||
function formatMusicSheetItem(raw) {
|
||||
var _a, _b, _c, _d, _e, _f;
|
||||
return {
|
||||
worksNum: raw.track_count,
|
||||
id: raw.id,
|
||||
title: raw.title,
|
||||
artist: (_a = raw.artist) === null || _a === void 0 ? void 0 : _a.name,
|
||||
artwork: raw.image || raw.image_base,
|
||||
artistItem: {
|
||||
id: (_b = raw.artist) === null || _b === void 0 ? void 0 : _b.id,
|
||||
avatar: ((_c = raw.artist) === null || _c === void 0 ? void 0 : _c.image) || ((_d = raw.artist) === null || _d === void 0 ? void 0 : _d.image_base),
|
||||
name: (_e = raw.artist) === null || _e === void 0 ? void 0 : _e.name,
|
||||
url_slug: (_f = raw.artist) === null || _f === void 0 ? void 0 : _f.url_slug,
|
||||
},
|
||||
createAt: dayjs.unix(+raw.created).format("YYYY-MM-DD"),
|
||||
url_slug: raw.url_slug,
|
||||
};
|
||||
}
|
||||
async function searchBase(query, page, show) {
|
||||
const params = {
|
||||
limit: pageSize,
|
||||
oauth_consumer_key: "audiomack-js",
|
||||
oauth_nonce: nonce(32),
|
||||
oauth_signature_method: "HMAC-SHA1",
|
||||
oauth_timestamp: Math.round(Date.now() / 1e3),
|
||||
oauth_version: "1.0",
|
||||
page: page,
|
||||
q: query,
|
||||
show: show,
|
||||
sort: "popular",
|
||||
};
|
||||
const oauth_signature = getSignature("GET", "/search", params);
|
||||
const results = (await axios_1.default.get("https://api.audiomack.com/v1/search", {
|
||||
headers,
|
||||
params: Object.assign(Object.assign({}, params), { oauth_signature }),
|
||||
})).data.results;
|
||||
return results;
|
||||
}
|
||||
async function searchMusic(query, page) {
|
||||
const results = await searchBase(query, page, "songs");
|
||||
return {
|
||||
isEnd: results.length < pageSize,
|
||||
data: results.map(formatMusicItem),
|
||||
};
|
||||
}
|
||||
async function searchAlbum(query, page) {
|
||||
const results = await searchBase(query, page, "albums");
|
||||
return {
|
||||
isEnd: results.length < pageSize,
|
||||
data: results.map(formatAlbumItem),
|
||||
};
|
||||
}
|
||||
async function searchMusicSheet(query, page) {
|
||||
const results = await searchBase(query, page, "playlists");
|
||||
return {
|
||||
isEnd: results.length < pageSize,
|
||||
data: results.map(formatMusicSheetItem),
|
||||
};
|
||||
}
|
||||
async function searchArtist(query, page) {
|
||||
const results = await searchBase(query, page, "artists");
|
||||
return {
|
||||
isEnd: results.length < pageSize,
|
||||
data: results.map((raw) => ({
|
||||
name: raw.name,
|
||||
id: raw.id,
|
||||
avatar: raw.image || raw.image_base,
|
||||
url_slug: raw.url_slug,
|
||||
})),
|
||||
};
|
||||
}
|
||||
let dataUrlBase;
|
||||
async function getDataUrlBase() {
|
||||
if (dataUrlBase) {
|
||||
return dataUrlBase;
|
||||
}
|
||||
const rawHtml = (await axios_1.default.get("https://audiomack.com/")).data;
|
||||
const $ = (0, cheerio_1.load)(rawHtml);
|
||||
const script = $("script#__NEXT_DATA__").text();
|
||||
const jsonObj = JSON.parse(script);
|
||||
if (jsonObj.buildId) {
|
||||
dataUrlBase = `https://audiomack.com/_next/data/${jsonObj.buildId}`;
|
||||
}
|
||||
return dataUrlBase;
|
||||
}
|
||||
async function getArtistWorks(artistItem, page, type) {
|
||||
if (type === "music") {
|
||||
const params = {
|
||||
artist_id: artistItem.id,
|
||||
limit: pageSize,
|
||||
oauth_consumer_key: "audiomack-js",
|
||||
oauth_nonce: nonce(32),
|
||||
oauth_signature_method: "HMAC-SHA1",
|
||||
oauth_timestamp: Math.round(Date.now() / 1e3),
|
||||
oauth_version: "1.0",
|
||||
page: page,
|
||||
sort: "rank",
|
||||
type: "songs",
|
||||
};
|
||||
const oauth_signature = getSignature("GET", "/search_artist_content", params);
|
||||
const results = (await axios_1.default.get("https://api.audiomack.com/v1/search_artist_content", {
|
||||
headers,
|
||||
params: Object.assign(Object.assign({}, params), { oauth_signature }),
|
||||
})).data.results;
|
||||
return {
|
||||
isEnd: results.length < pageSize,
|
||||
data: results.map(formatMusicItem),
|
||||
};
|
||||
}
|
||||
else if (type === "album") {
|
||||
const params = {
|
||||
artist_id: artistItem.id,
|
||||
limit: pageSize,
|
||||
oauth_consumer_key: "audiomack-js",
|
||||
oauth_nonce: nonce(32),
|
||||
oauth_signature_method: "HMAC-SHA1",
|
||||
oauth_timestamp: Math.round(Date.now() / 1e3),
|
||||
oauth_version: "1.0",
|
||||
page: page,
|
||||
sort: "rank",
|
||||
type: "albums",
|
||||
};
|
||||
const oauth_signature = getSignature("GET", "/search_artist_content", params);
|
||||
const results = (await axios_1.default.get("https://api.audiomack.com/v1/search_artist_content", {
|
||||
headers,
|
||||
params: Object.assign(Object.assign({}, params), { oauth_signature }),
|
||||
})).data.results;
|
||||
return {
|
||||
isEnd: results.length < pageSize,
|
||||
data: results.map(formatAlbumItem),
|
||||
};
|
||||
}
|
||||
}
|
||||
async function getMusicSheetInfo(sheet, page) {
|
||||
const _dataUrlBase = await getDataUrlBase();
|
||||
const res = (await axios_1.default.get(`${_dataUrlBase}/${sheet.artistItem.url_slug}/playlist/${sheet.url_slug}.json`, {
|
||||
params: {
|
||||
page_slug: sheet.artistItem.url_slug,
|
||||
playlist_slug: sheet.url_slug,
|
||||
},
|
||||
headers: Object.assign({}, headers),
|
||||
})).data;
|
||||
const musicPage = res.pageProps.initialState.musicPage;
|
||||
const targetKey = Object.keys(musicPage).find((it) => it.startsWith("musicMusicPage"));
|
||||
const tracks = musicPage[targetKey].results.tracks;
|
||||
return {
|
||||
isEnd: true,
|
||||
musicList: tracks.map(formatMusicItem),
|
||||
};
|
||||
}
|
||||
async function getMediaSource(musicItem, quality) {
|
||||
if (quality !== "standard") {
|
||||
return;
|
||||
}
|
||||
const params = {
|
||||
environment: "desktop-web",
|
||||
hq: true,
|
||||
oauth_consumer_key: "audiomack-js",
|
||||
oauth_nonce: nonce(32),
|
||||
oauth_signature_method: "HMAC-SHA1",
|
||||
oauth_timestamp: Math.round(Date.now() / 1e3),
|
||||
oauth_version: "1.0",
|
||||
section: "/search",
|
||||
};
|
||||
const oauth_signature = getSignature("GET", `/music/play/${musicItem.id}`, params);
|
||||
const res = (await axios_1.default.get(`https://api.audiomack.com/v1/music/play/${musicItem.id}`, {
|
||||
headers: Object.assign(Object.assign({}, headers), { origin: "https://audiomack.com" }),
|
||||
params: Object.assign(Object.assign({}, params), { oauth_signature }),
|
||||
})).data;
|
||||
return {
|
||||
url: res.signedUrl,
|
||||
};
|
||||
}
|
||||
async function getAlbumInfo(albumItem) {
|
||||
return {
|
||||
musicList: albumItem._musicList.map((it) => (Object.assign({}, it))),
|
||||
};
|
||||
}
|
||||
async function getRecommendSheetTags() {
|
||||
const rawHtml = (await axios_1.default.get("https://audiomack.com/playlists")).data;
|
||||
const $ = (0, cheerio_1.load)(rawHtml);
|
||||
const script = $("script#__NEXT_DATA__").text();
|
||||
const jsonObj = JSON.parse(script);
|
||||
return {
|
||||
data: [
|
||||
{
|
||||
data: jsonObj.props.pageProps.categories,
|
||||
},
|
||||
],
|
||||
};
|
||||
}
|
||||
async function getRecommendSheetsByTag(tag, page) {
|
||||
if (!tag.id) {
|
||||
tag = { id: "34", title: "What's New", url_slug: "whats-new" };
|
||||
}
|
||||
const params = {
|
||||
featured: "yes",
|
||||
limit: pageSize,
|
||||
oauth_consumer_key: "audiomack-js",
|
||||
oauth_nonce: nonce(32),
|
||||
oauth_signature_method: "HMAC-SHA1",
|
||||
oauth_timestamp: Math.round(Date.now() / 1e3),
|
||||
oauth_version: "1.0",
|
||||
page: page,
|
||||
slug: tag.url_slug,
|
||||
};
|
||||
const oauth_signature = getSignature("GET", "/playlist/categories", params);
|
||||
const results = (await axios_1.default.get("https://api.audiomack.com/v1/playlist/categories", {
|
||||
headers,
|
||||
params: Object.assign(Object.assign({}, params), { oauth_signature }),
|
||||
})).data.results.playlists;
|
||||
return {
|
||||
isEnd: results.length < pageSize,
|
||||
data: results.map(formatMusicSheetItem),
|
||||
};
|
||||
}
|
||||
async function getTopLists() {
|
||||
const genres = [
|
||||
{
|
||||
title: "All Genres",
|
||||
url_slug: null,
|
||||
},
|
||||
{
|
||||
title: "Afrosounds",
|
||||
url_slug: "afrobeats",
|
||||
},
|
||||
{
|
||||
title: "Hip-Hop/Rap",
|
||||
url_slug: "rap",
|
||||
},
|
||||
{
|
||||
title: "Latin",
|
||||
url_slug: "latin",
|
||||
},
|
||||
{
|
||||
title: "Caribbean",
|
||||
url_slug: "caribbean",
|
||||
},
|
||||
{
|
||||
title: "Pop",
|
||||
url_slug: "pop",
|
||||
},
|
||||
{
|
||||
title: "R&B",
|
||||
url_slug: "rb",
|
||||
},
|
||||
{
|
||||
title: "Gospel",
|
||||
url_slug: "gospel",
|
||||
},
|
||||
{
|
||||
title: "Electronic",
|
||||
url_slug: "electronic",
|
||||
},
|
||||
{
|
||||
title: "Rock",
|
||||
url_slug: "rock",
|
||||
},
|
||||
{
|
||||
title: "Punjabi",
|
||||
url_slug: "punjabi",
|
||||
},
|
||||
{
|
||||
title: "Country",
|
||||
url_slug: "country",
|
||||
},
|
||||
{
|
||||
title: "Instrumental",
|
||||
url_slug: "instrumental",
|
||||
},
|
||||
{
|
||||
title: "Podcast",
|
||||
url_slug: "podcast",
|
||||
},
|
||||
];
|
||||
return [
|
||||
{
|
||||
title: "Trending Songs",
|
||||
data: genres.map((it) => {
|
||||
var _a;
|
||||
return (Object.assign(Object.assign({}, it), { type: "trending", id: (_a = it.url_slug) !== null && _a !== void 0 ? _a : it.title }));
|
||||
}),
|
||||
},
|
||||
{
|
||||
title: "Recently Added Music",
|
||||
data: genres.map((it) => {
|
||||
var _a;
|
||||
return (Object.assign(Object.assign({}, it), { type: "recent", id: (_a = it.url_slug) !== null && _a !== void 0 ? _a : it.title }));
|
||||
}),
|
||||
},
|
||||
];
|
||||
}
|
||||
async function getTopListDetail(topListItem, page = 1) {
|
||||
const type = topListItem.type;
|
||||
const partialUrl = `/music/${topListItem.url_slug ? `${topListItem.url_slug}/` : ""}${type}/page/${page}`;
|
||||
const url = `https://api.audiomack.com/v1${partialUrl}`;
|
||||
const params = {
|
||||
oauth_consumer_key: "audiomack-js",
|
||||
oauth_nonce: nonce(32),
|
||||
oauth_signature_method: "HMAC-SHA1",
|
||||
oauth_timestamp: Math.round(Date.now() / 1e3),
|
||||
oauth_version: "1.0",
|
||||
type: "song",
|
||||
};
|
||||
const oauth_signature = getSignature("GET", partialUrl, params);
|
||||
const results = (await axios_1.default.get(url, {
|
||||
headers,
|
||||
params: Object.assign(Object.assign({}, params), { oauth_signature }),
|
||||
})).data.results;
|
||||
return {
|
||||
musicList: results.map(formatMusicItem),
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "Audiomack",
|
||||
version: "0.0.2",
|
||||
author: '猫头猫',
|
||||
primaryKey: ["id", "url_slug"],
|
||||
srcUrl: "https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/audiomack/index.js",
|
||||
cacheControl: "no-cache",
|
||||
supportedSearchType: ['music', 'album', 'sheet', 'artist'],
|
||||
async search(query, page, type) {
|
||||
if (type === "music") {
|
||||
return await searchMusic(query, page);
|
||||
}
|
||||
else if (type === "album") {
|
||||
return await searchAlbum(query, page);
|
||||
}
|
||||
else if (type === "sheet") {
|
||||
return await searchMusicSheet(query, page);
|
||||
}
|
||||
else if (type === "artist") {
|
||||
return await searchArtist(query, page);
|
||||
}
|
||||
},
|
||||
getMediaSource,
|
||||
getAlbumInfo,
|
||||
getMusicSheetInfo,
|
||||
getArtistWorks,
|
||||
getRecommendSheetTags,
|
||||
getRecommendSheetsByTag,
|
||||
getTopLists,
|
||||
getTopListDetail,
|
||||
};
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
const cheerio_1 = require("cheerio");
|
||||
const CryptoJS = require("crypto-js");
|
||||
const dayjs = require("dayjs");
|
||||
const pageSize = 20;
|
||||
const headers = {
|
||||
"user-agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/119.0.0.0 Safari/537.36",
|
||||
};
|
||||
function nonce(e = 10) {
|
||||
let n = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789", r = "";
|
||||
for (let i = 0; i < e; i++)
|
||||
r += n.charAt(Math.floor(Math.random() * n.length));
|
||||
return r;
|
||||
}
|
||||
function getNormalizedParams(parameters) {
|
||||
const sortedKeys = [];
|
||||
const normalizedParameters = [];
|
||||
for (let e in parameters) {
|
||||
sortedKeys.push(_encode(e));
|
||||
}
|
||||
sortedKeys.sort();
|
||||
for (let idx = 0; idx < sortedKeys.length; idx++) {
|
||||
const e = sortedKeys[idx];
|
||||
var n, r, i = _decode(e), a = parameters[i];
|
||||
for (a.sort(), n = 0; n < a.length; n++)
|
||||
(r = _encode(a[n])), normalizedParameters.push(e + "=" + r);
|
||||
}
|
||||
return normalizedParameters.join("&");
|
||||
}
|
||||
function _encode(e) {
|
||||
return e
|
||||
? encodeURIComponent(e)
|
||||
.replace(/[!'()]/g, escape)
|
||||
.replace(/\*/g, "%2A")
|
||||
: "";
|
||||
}
|
||||
function _decode(e) {
|
||||
return e ? decodeURIComponent(e) : "";
|
||||
}
|
||||
function u(e) {
|
||||
(this._parameters = {}), this._loadParameters(e || {});
|
||||
}
|
||||
u.prototype = {
|
||||
_loadParameters: function (e) {
|
||||
e instanceof Array
|
||||
? this._loadParametersFromArray(e)
|
||||
: "object" == typeof e && this._loadParametersFromObject(e);
|
||||
},
|
||||
_loadParametersFromArray: function (e) {
|
||||
var n;
|
||||
for (n = 0; n < e.length; n++)
|
||||
this._loadParametersFromObject(e[n]);
|
||||
},
|
||||
_loadParametersFromObject: function (e) {
|
||||
var n;
|
||||
for (n in e)
|
||||
if (e.hasOwnProperty(n)) {
|
||||
var r = this._getStringFromParameter(e[n]);
|
||||
this._loadParameterValue(n, r);
|
||||
}
|
||||
},
|
||||
_loadParameterValue: function (e, n) {
|
||||
var r;
|
||||
if (n instanceof Array) {
|
||||
for (r = 0; r < n.length; r++) {
|
||||
var i = this._getStringFromParameter(n[r]);
|
||||
this._addParameter(e, i);
|
||||
}
|
||||
0 == n.length && this._addParameter(e, "");
|
||||
}
|
||||
else
|
||||
this._addParameter(e, n);
|
||||
},
|
||||
_getStringFromParameter: function (e) {
|
||||
var n = e || "";
|
||||
try {
|
||||
("number" == typeof e || "boolean" == typeof e) && (n = e.toString());
|
||||
}
|
||||
catch (e) { }
|
||||
return n;
|
||||
},
|
||||
_addParameter: function (e, n) {
|
||||
this._parameters[e] || (this._parameters[e] = []),
|
||||
this._parameters[e].push(n);
|
||||
},
|
||||
get: function () {
|
||||
return this._parameters;
|
||||
},
|
||||
};
|
||||
function getSignature(method, urlPath, params, secret = "f3ac5b086f3eab260520d8e3049561e6") {
|
||||
urlPath = urlPath.split("?")[0];
|
||||
urlPath = urlPath.startsWith("http")
|
||||
? urlPath
|
||||
: "https://api.audiomack.com/v1" + urlPath;
|
||||
const r = new u(params).get();
|
||||
const httpMethod = method.toUpperCase();
|
||||
const normdParams = getNormalizedParams(r);
|
||||
const l = _encode(httpMethod) + "&" + _encode(urlPath) + "&" + _encode(normdParams);
|
||||
const hash = CryptoJS.HmacSHA1(l, secret + "&").toString(CryptoJS.enc.Base64);
|
||||
return hash;
|
||||
}
|
||||
function formatMusicItem(raw) {
|
||||
return {
|
||||
id: raw.id,
|
||||
artwork: raw.image || raw.image_base,
|
||||
duration: +raw.duration,
|
||||
title: raw.title,
|
||||
artist: raw.artist,
|
||||
album: raw.album,
|
||||
url_slug: raw.url_slug,
|
||||
};
|
||||
}
|
||||
function formatAlbumItem(raw) {
|
||||
var _a, _b;
|
||||
return {
|
||||
artist: raw.artist,
|
||||
artwork: raw.image || raw.image_base,
|
||||
id: raw.id,
|
||||
date: dayjs.unix(+raw.released).format("YYYY-MM-DD"),
|
||||
title: raw.title,
|
||||
_musicList: (_b = (_a = raw === null || raw === void 0 ? void 0 : raw.tracks) === null || _a === void 0 ? void 0 : _a.map) === null || _b === void 0 ? void 0 : _b.call(_a, (it) => ({
|
||||
id: it.song_id || it.id,
|
||||
artwork: raw.image || raw.image_base,
|
||||
duration: +it.duration,
|
||||
title: it.title,
|
||||
artist: it.artist,
|
||||
album: raw.title,
|
||||
})),
|
||||
};
|
||||
}
|
||||
function formatMusicSheetItem(raw) {
|
||||
var _a, _b, _c, _d, _e, _f;
|
||||
return {
|
||||
worksNum: raw.track_count,
|
||||
id: raw.id,
|
||||
title: raw.title,
|
||||
artist: (_a = raw.artist) === null || _a === void 0 ? void 0 : _a.name,
|
||||
artwork: raw.image || raw.image_base,
|
||||
artistItem: {
|
||||
id: (_b = raw.artist) === null || _b === void 0 ? void 0 : _b.id,
|
||||
avatar: ((_c = raw.artist) === null || _c === void 0 ? void 0 : _c.image) || ((_d = raw.artist) === null || _d === void 0 ? void 0 : _d.image_base),
|
||||
name: (_e = raw.artist) === null || _e === void 0 ? void 0 : _e.name,
|
||||
url_slug: (_f = raw.artist) === null || _f === void 0 ? void 0 : _f.url_slug,
|
||||
},
|
||||
createAt: dayjs.unix(+raw.created).format("YYYY-MM-DD"),
|
||||
url_slug: raw.url_slug,
|
||||
};
|
||||
}
|
||||
async function searchBase(query, page, show) {
|
||||
const params = {
|
||||
limit: pageSize,
|
||||
oauth_consumer_key: "audiomack-js",
|
||||
oauth_nonce: nonce(32),
|
||||
oauth_signature_method: "HMAC-SHA1",
|
||||
oauth_timestamp: Math.round(Date.now() / 1e3),
|
||||
oauth_version: "1.0",
|
||||
page: page,
|
||||
q: query,
|
||||
show: show,
|
||||
sort: "popular",
|
||||
};
|
||||
const oauth_signature = getSignature("GET", "/search", params);
|
||||
const results = (await axios_1.default.get("https://api.audiomack.com/v1/search", {
|
||||
headers,
|
||||
params: Object.assign(Object.assign({}, params), { oauth_signature }),
|
||||
})).data.results;
|
||||
return results;
|
||||
}
|
||||
async function searchMusic(query, page) {
|
||||
const results = await searchBase(query, page, "songs");
|
||||
return {
|
||||
isEnd: results.length < pageSize,
|
||||
data: results.map(formatMusicItem),
|
||||
};
|
||||
}
|
||||
async function searchAlbum(query, page) {
|
||||
const results = await searchBase(query, page, "albums");
|
||||
return {
|
||||
isEnd: results.length < pageSize,
|
||||
data: results.map(formatAlbumItem),
|
||||
};
|
||||
}
|
||||
async function searchMusicSheet(query, page) {
|
||||
const results = await searchBase(query, page, "playlists");
|
||||
return {
|
||||
isEnd: results.length < pageSize,
|
||||
data: results.map(formatMusicSheetItem),
|
||||
};
|
||||
}
|
||||
async function searchArtist(query, page) {
|
||||
const results = await searchBase(query, page, "artists");
|
||||
return {
|
||||
isEnd: results.length < pageSize,
|
||||
data: results.map((raw) => ({
|
||||
name: raw.name,
|
||||
id: raw.id,
|
||||
avatar: raw.image || raw.image_base,
|
||||
url_slug: raw.url_slug,
|
||||
})),
|
||||
};
|
||||
}
|
||||
let dataUrlBase;
|
||||
async function getDataUrlBase() {
|
||||
if (dataUrlBase) {
|
||||
return dataUrlBase;
|
||||
}
|
||||
const rawHtml = (await axios_1.default.get("https://audiomack.com/")).data;
|
||||
const $ = (0, cheerio_1.load)(rawHtml);
|
||||
const script = $("script#__NEXT_DATA__").text();
|
||||
const jsonObj = JSON.parse(script);
|
||||
if (jsonObj.buildId) {
|
||||
dataUrlBase = `https://audiomack.com/_next/data/${jsonObj.buildId}`;
|
||||
}
|
||||
return dataUrlBase;
|
||||
}
|
||||
async function getArtistWorks(artistItem, page, type) {
|
||||
if (type === "music") {
|
||||
const params = {
|
||||
artist_id: artistItem.id,
|
||||
limit: pageSize,
|
||||
oauth_consumer_key: "audiomack-js",
|
||||
oauth_nonce: nonce(32),
|
||||
oauth_signature_method: "HMAC-SHA1",
|
||||
oauth_timestamp: Math.round(Date.now() / 1e3),
|
||||
oauth_version: "1.0",
|
||||
page: page,
|
||||
sort: "rank",
|
||||
type: "songs",
|
||||
};
|
||||
const oauth_signature = getSignature("GET", "/search_artist_content", params);
|
||||
const results = (await axios_1.default.get("https://api.audiomack.com/v1/search_artist_content", {
|
||||
headers,
|
||||
params: Object.assign(Object.assign({}, params), { oauth_signature }),
|
||||
})).data.results;
|
||||
return {
|
||||
isEnd: results.length < pageSize,
|
||||
data: results.map(formatMusicItem),
|
||||
};
|
||||
}
|
||||
else if (type === "album") {
|
||||
const params = {
|
||||
artist_id: artistItem.id,
|
||||
limit: pageSize,
|
||||
oauth_consumer_key: "audiomack-js",
|
||||
oauth_nonce: nonce(32),
|
||||
oauth_signature_method: "HMAC-SHA1",
|
||||
oauth_timestamp: Math.round(Date.now() / 1e3),
|
||||
oauth_version: "1.0",
|
||||
page: page,
|
||||
sort: "rank",
|
||||
type: "albums",
|
||||
};
|
||||
const oauth_signature = getSignature("GET", "/search_artist_content", params);
|
||||
const results = (await axios_1.default.get("https://api.audiomack.com/v1/search_artist_content", {
|
||||
headers,
|
||||
params: Object.assign(Object.assign({}, params), { oauth_signature }),
|
||||
})).data.results;
|
||||
return {
|
||||
isEnd: results.length < pageSize,
|
||||
data: results.map(formatAlbumItem),
|
||||
};
|
||||
}
|
||||
}
|
||||
async function getMusicSheetInfo(sheet, page) {
|
||||
const _dataUrlBase = await getDataUrlBase();
|
||||
const res = (await axios_1.default.get(`${_dataUrlBase}/${sheet.artistItem.url_slug}/playlist/${sheet.url_slug}.json`, {
|
||||
params: {
|
||||
page_slug: sheet.artistItem.url_slug,
|
||||
playlist_slug: sheet.url_slug,
|
||||
},
|
||||
headers: Object.assign({}, headers),
|
||||
})).data;
|
||||
const musicPage = res.pageProps.initialState.musicPage;
|
||||
const targetKey = Object.keys(musicPage).find((it) => it.startsWith("musicMusicPage"));
|
||||
const tracks = musicPage[targetKey].results.tracks;
|
||||
return {
|
||||
isEnd: true,
|
||||
musicList: tracks.map(formatMusicItem),
|
||||
};
|
||||
}
|
||||
async function getMediaSource(musicItem, quality) {
|
||||
if (quality !== "standard") {
|
||||
return;
|
||||
}
|
||||
const params = {
|
||||
environment: "desktop-web",
|
||||
hq: true,
|
||||
oauth_consumer_key: "audiomack-js",
|
||||
oauth_nonce: nonce(32),
|
||||
oauth_signature_method: "HMAC-SHA1",
|
||||
oauth_timestamp: Math.round(Date.now() / 1e3),
|
||||
oauth_version: "1.0",
|
||||
section: "/search",
|
||||
};
|
||||
const oauth_signature = getSignature("GET", `/music/play/${musicItem.id}`, params);
|
||||
const res = (await axios_1.default.get(`https://api.audiomack.com/v1/music/play/${musicItem.id}`, {
|
||||
headers: Object.assign(Object.assign({}, headers), { origin: "https://audiomack.com" }),
|
||||
params: Object.assign(Object.assign({}, params), { oauth_signature }),
|
||||
})).data;
|
||||
return {
|
||||
url: res.signedUrl,
|
||||
};
|
||||
}
|
||||
async function getAlbumInfo(albumItem) {
|
||||
return {
|
||||
musicList: albumItem._musicList.map((it) => (Object.assign({}, it))),
|
||||
};
|
||||
}
|
||||
async function getRecommendSheetTags() {
|
||||
const rawHtml = (await axios_1.default.get("https://audiomack.com/playlists")).data;
|
||||
const $ = (0, cheerio_1.load)(rawHtml);
|
||||
const script = $("script#__NEXT_DATA__").text();
|
||||
const jsonObj = JSON.parse(script);
|
||||
return {
|
||||
data: [
|
||||
{
|
||||
data: jsonObj.props.pageProps.categories,
|
||||
},
|
||||
],
|
||||
};
|
||||
}
|
||||
async function getRecommendSheetsByTag(tag, page) {
|
||||
if (!tag.id) {
|
||||
tag = { id: "34", title: "What's New", url_slug: "whats-new" };
|
||||
}
|
||||
const params = {
|
||||
featured: "yes",
|
||||
limit: pageSize,
|
||||
oauth_consumer_key: "audiomack-js",
|
||||
oauth_nonce: nonce(32),
|
||||
oauth_signature_method: "HMAC-SHA1",
|
||||
oauth_timestamp: Math.round(Date.now() / 1e3),
|
||||
oauth_version: "1.0",
|
||||
page: page,
|
||||
slug: tag.url_slug,
|
||||
};
|
||||
const oauth_signature = getSignature("GET", "/playlist/categories", params);
|
||||
const results = (await axios_1.default.get("https://api.audiomack.com/v1/playlist/categories", {
|
||||
headers,
|
||||
params: Object.assign(Object.assign({}, params), { oauth_signature }),
|
||||
})).data.results.playlists;
|
||||
return {
|
||||
isEnd: results.length < pageSize,
|
||||
data: results.map(formatMusicSheetItem),
|
||||
};
|
||||
}
|
||||
async function getTopLists() {
|
||||
const genres = [
|
||||
{
|
||||
title: "All Genres",
|
||||
url_slug: null,
|
||||
},
|
||||
{
|
||||
title: "Afrosounds",
|
||||
url_slug: "afrobeats",
|
||||
},
|
||||
{
|
||||
title: "Hip-Hop/Rap",
|
||||
url_slug: "rap",
|
||||
},
|
||||
{
|
||||
title: "Latin",
|
||||
url_slug: "latin",
|
||||
},
|
||||
{
|
||||
title: "Caribbean",
|
||||
url_slug: "caribbean",
|
||||
},
|
||||
{
|
||||
title: "Pop",
|
||||
url_slug: "pop",
|
||||
},
|
||||
{
|
||||
title: "R&B",
|
||||
url_slug: "rb",
|
||||
},
|
||||
{
|
||||
title: "Gospel",
|
||||
url_slug: "gospel",
|
||||
},
|
||||
{
|
||||
title: "Electronic",
|
||||
url_slug: "electronic",
|
||||
},
|
||||
{
|
||||
title: "Rock",
|
||||
url_slug: "rock",
|
||||
},
|
||||
{
|
||||
title: "Punjabi",
|
||||
url_slug: "punjabi",
|
||||
},
|
||||
{
|
||||
title: "Country",
|
||||
url_slug: "country",
|
||||
},
|
||||
{
|
||||
title: "Instrumental",
|
||||
url_slug: "instrumental",
|
||||
},
|
||||
{
|
||||
title: "Podcast",
|
||||
url_slug: "podcast",
|
||||
},
|
||||
];
|
||||
return [
|
||||
{
|
||||
title: "Trending Songs",
|
||||
data: genres.map((it) => {
|
||||
var _a;
|
||||
return (Object.assign(Object.assign({}, it), { type: "trending", id: (_a = it.url_slug) !== null && _a !== void 0 ? _a : it.title }));
|
||||
}),
|
||||
},
|
||||
{
|
||||
title: "Recently Added Music",
|
||||
data: genres.map((it) => {
|
||||
var _a;
|
||||
return (Object.assign(Object.assign({}, it), { type: "recent", id: (_a = it.url_slug) !== null && _a !== void 0 ? _a : it.title }));
|
||||
}),
|
||||
},
|
||||
];
|
||||
}
|
||||
async function getTopListDetail(topListItem, page = 1) {
|
||||
const type = topListItem.type;
|
||||
const partialUrl = `/music/${topListItem.url_slug ? `${topListItem.url_slug}/` : ""}${type}/page/${page}`;
|
||||
const url = `https://api.audiomack.com/v1${partialUrl}`;
|
||||
const params = {
|
||||
oauth_consumer_key: "audiomack-js",
|
||||
oauth_nonce: nonce(32),
|
||||
oauth_signature_method: "HMAC-SHA1",
|
||||
oauth_timestamp: Math.round(Date.now() / 1e3),
|
||||
oauth_version: "1.0",
|
||||
type: "song",
|
||||
};
|
||||
const oauth_signature = getSignature("GET", partialUrl, params);
|
||||
const results = (await axios_1.default.get(url, {
|
||||
headers,
|
||||
params: Object.assign(Object.assign({}, params), { oauth_signature }),
|
||||
})).data.results;
|
||||
return {
|
||||
musicList: results.map(formatMusicItem),
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "Audiomack",
|
||||
version: "0.0.2",
|
||||
author: '猫头猫',
|
||||
primaryKey: ["id", "url_slug"],
|
||||
srcUrl: "https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/audiomack/index.js",
|
||||
cacheControl: "no-cache",
|
||||
supportedSearchType: ['music', 'album', 'sheet', 'artist'],
|
||||
async search(query, page, type) {
|
||||
if (type === "music") {
|
||||
return await searchMusic(query, page);
|
||||
}
|
||||
else if (type === "album") {
|
||||
return await searchAlbum(query, page);
|
||||
}
|
||||
else if (type === "sheet") {
|
||||
return await searchMusicSheet(query, page);
|
||||
}
|
||||
else if (type === "artist") {
|
||||
return await searchArtist(query, page);
|
||||
}
|
||||
},
|
||||
getMediaSource,
|
||||
getAlbumInfo,
|
||||
getMusicSheetInfo,
|
||||
getArtistWorks,
|
||||
getRecommendSheetTags,
|
||||
getRecommendSheetsByTag,
|
||||
getTopLists,
|
||||
getTopListDetail,
|
||||
};
|
||||
|
||||
1000
dist/bilibili/index.js
vendored
1000
dist/bilibili/index.js
vendored
File diff suppressed because it is too large
Load Diff
98
dist/geciqianxun/index.js
vendored
98
dist/geciqianxun/index.js
vendored
@@ -1,49 +1,49 @@
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
const cheerio_1 = require("cheerio");
|
||||
async function search(query, page, type) {
|
||||
if (type !== 'lyric') {
|
||||
return;
|
||||
}
|
||||
const result = (await axios_1.default.get('https://so.lrcgc.com/', {
|
||||
params: {
|
||||
q: query,
|
||||
}
|
||||
})).data;
|
||||
const $ = (0, cheerio_1.load)(result);
|
||||
const results = $('.resultWrap').children();
|
||||
const data = [];
|
||||
if (results.first().prop('tagName') === 'DL') {
|
||||
const title = results.first().find('dt > a');
|
||||
const desc = results.first().find('dd > small');
|
||||
const descText = desc.text().replace(/[\s|\n]/g, '').split(/[歌手:|专辑:]/).filter(it => it.trim() !== '');
|
||||
data.push({
|
||||
title: title.text(),
|
||||
id: title.attr('href'),
|
||||
artist: descText === null || descText === void 0 ? void 0 : descText[0],
|
||||
album: descText === null || descText === void 0 ? void 0 : descText[1]
|
||||
});
|
||||
}
|
||||
return {
|
||||
isEnd: true,
|
||||
data
|
||||
};
|
||||
}
|
||||
async function getLyric(musicItem) {
|
||||
const res = (await axios_1.default.get(musicItem.id)).data;
|
||||
const $ = (0, cheerio_1.load)(res);
|
||||
const rawLrc = $('p#J_lyric').text().replace(/\n/g, '');
|
||||
return {
|
||||
rawLrc: rawLrc,
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "歌词千寻",
|
||||
version: "0.0.0",
|
||||
srcUrl: 'https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/geciqianxun/index.js',
|
||||
cacheControl: "no-store",
|
||||
supportedSearchType: ['lyric'],
|
||||
search,
|
||||
getLyric
|
||||
};
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
const cheerio_1 = require("cheerio");
|
||||
async function search(query, page, type) {
|
||||
if (type !== 'lyric') {
|
||||
return;
|
||||
}
|
||||
const result = (await axios_1.default.get('https://so.lrcgc.com/', {
|
||||
params: {
|
||||
q: query,
|
||||
}
|
||||
})).data;
|
||||
const $ = (0, cheerio_1.load)(result);
|
||||
const results = $('.resultWrap').children();
|
||||
const data = [];
|
||||
if (results.first().prop('tagName') === 'DL') {
|
||||
const title = results.first().find('dt > a');
|
||||
const desc = results.first().find('dd > small');
|
||||
const descText = desc.text().replace(/[\s|\n]/g, '').split(/[歌手:|专辑:]/).filter(it => it.trim() !== '');
|
||||
data.push({
|
||||
title: title.text(),
|
||||
id: title.attr('href'),
|
||||
artist: descText === null || descText === void 0 ? void 0 : descText[0],
|
||||
album: descText === null || descText === void 0 ? void 0 : descText[1]
|
||||
});
|
||||
}
|
||||
return {
|
||||
isEnd: true,
|
||||
data
|
||||
};
|
||||
}
|
||||
async function getLyric(musicItem) {
|
||||
const res = (await axios_1.default.get(musicItem.id)).data;
|
||||
const $ = (0, cheerio_1.load)(res);
|
||||
const rawLrc = $('p#J_lyric').text().replace(/\n/g, '');
|
||||
return {
|
||||
rawLrc: rawLrc,
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "歌词千寻",
|
||||
version: "0.0.0",
|
||||
srcUrl: 'https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/geciqianxun/index.js',
|
||||
cacheControl: "no-store",
|
||||
supportedSearchType: ['lyric'],
|
||||
search,
|
||||
getLyric
|
||||
};
|
||||
|
||||
104
dist/geciwang/index.js
vendored
104
dist/geciwang/index.js
vendored
@@ -1,52 +1,52 @@
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
const cheerio_1 = require("cheerio");
|
||||
async function search(query, page, type) {
|
||||
if (type !== 'lyric') {
|
||||
return;
|
||||
}
|
||||
const result = (await axios_1.default.get('https://zh.followlyrics.com/search', {
|
||||
params: {
|
||||
name: query,
|
||||
type: 'song'
|
||||
}
|
||||
})).data;
|
||||
const $ = (0, cheerio_1.load)(result);
|
||||
const results = $('.table.table-striped > tbody');
|
||||
const items = results.children('tr');
|
||||
const data = items.map((index, el) => {
|
||||
const tds = $(el).children();
|
||||
const title = $(tds.get(0)).text().trim();
|
||||
const artist = $(tds.get(1)).text().trim();
|
||||
const album = $(tds.get(2)).text().trim();
|
||||
const id = $(tds.get(3)).children('a').attr('href');
|
||||
return {
|
||||
title,
|
||||
artist,
|
||||
album,
|
||||
id
|
||||
};
|
||||
}).toArray();
|
||||
return {
|
||||
isEnd: true,
|
||||
data
|
||||
};
|
||||
}
|
||||
async function getLyric(musicItem) {
|
||||
const res = (await axios_1.default.get(musicItem.id)).data;
|
||||
const $ = (0, cheerio_1.load)(res);
|
||||
const rawLrc = $('div#lyrics').text().replace(/\n/g, '');
|
||||
return {
|
||||
rawLrc: rawLrc,
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "歌词网",
|
||||
version: "0.0.0",
|
||||
srcUrl: 'https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/geciwang/index.js',
|
||||
cacheControl: "no-store",
|
||||
supportedSearchType: ['lyric'],
|
||||
search,
|
||||
getLyric
|
||||
};
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
const cheerio_1 = require("cheerio");
|
||||
async function search(query, page, type) {
|
||||
if (type !== 'lyric') {
|
||||
return;
|
||||
}
|
||||
const result = (await axios_1.default.get('https://zh.followlyrics.com/search', {
|
||||
params: {
|
||||
name: query,
|
||||
type: 'song'
|
||||
}
|
||||
})).data;
|
||||
const $ = (0, cheerio_1.load)(result);
|
||||
const results = $('.table.table-striped > tbody');
|
||||
const items = results.children('tr');
|
||||
const data = items.map((index, el) => {
|
||||
const tds = $(el).children();
|
||||
const title = $(tds.get(0)).text().trim();
|
||||
const artist = $(tds.get(1)).text().trim();
|
||||
const album = $(tds.get(2)).text().trim();
|
||||
const id = $(tds.get(3)).children('a').attr('href');
|
||||
return {
|
||||
title,
|
||||
artist,
|
||||
album,
|
||||
id
|
||||
};
|
||||
}).toArray();
|
||||
return {
|
||||
isEnd: true,
|
||||
data
|
||||
};
|
||||
}
|
||||
async function getLyric(musicItem) {
|
||||
const res = (await axios_1.default.get(musicItem.id)).data;
|
||||
const $ = (0, cheerio_1.load)(res);
|
||||
const rawLrc = $('div#lyrics').text().replace(/\n/g, '');
|
||||
return {
|
||||
rawLrc: rawLrc,
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "歌词网",
|
||||
version: "0.0.0",
|
||||
srcUrl: 'https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/geciwang/index.js',
|
||||
cacheControl: "no-store",
|
||||
supportedSearchType: ['lyric'],
|
||||
search,
|
||||
getLyric
|
||||
};
|
||||
|
||||
324
dist/kuaishou/index.js
vendored
324
dist/kuaishou/index.js
vendored
@@ -1,162 +1,162 @@
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
const pageSize = 20;
|
||||
function formatMusicItem(it) {
|
||||
return {
|
||||
id: it.photo.id,
|
||||
title: it.photo.caption,
|
||||
artist: it.author.name,
|
||||
artwork: it.photo.coverUrl || it.photo.photoUrl,
|
||||
manifest: it.photo.manifest
|
||||
};
|
||||
}
|
||||
async function searchMusic(query, page) {
|
||||
var _a, _b;
|
||||
const body = {
|
||||
query: `fragment photoContent on PhotoEntity {
|
||||
__typename
|
||||
id
|
||||
duration
|
||||
caption
|
||||
originCaption
|
||||
likeCount
|
||||
viewCount
|
||||
commentCount
|
||||
realLikeCount
|
||||
coverUrl
|
||||
photoUrl
|
||||
photoH265Url
|
||||
manifest
|
||||
manifestH265
|
||||
videoResource
|
||||
coverUrls {
|
||||
url
|
||||
__typename
|
||||
}
|
||||
timestamp
|
||||
expTag
|
||||
animatedCoverUrl
|
||||
distance
|
||||
videoRatio
|
||||
liked
|
||||
stereoType
|
||||
profileUserTopPhoto
|
||||
musicBlocked
|
||||
}
|
||||
|
||||
fragment recoPhotoFragment on recoPhotoEntity {
|
||||
__typename
|
||||
id
|
||||
duration
|
||||
caption
|
||||
originCaption
|
||||
likeCount
|
||||
viewCount
|
||||
commentCount
|
||||
realLikeCount
|
||||
coverUrl
|
||||
photoUrl
|
||||
photoH265Url
|
||||
manifest
|
||||
manifestH265
|
||||
videoResource
|
||||
coverUrls {
|
||||
url
|
||||
__typename
|
||||
}
|
||||
timestamp
|
||||
expTag
|
||||
animatedCoverUrl
|
||||
distance
|
||||
videoRatio
|
||||
liked
|
||||
stereoType
|
||||
profileUserTopPhoto
|
||||
musicBlocked
|
||||
}
|
||||
|
||||
fragment feedContent on Feed {
|
||||
type
|
||||
author {
|
||||
id
|
||||
name
|
||||
headerUrl
|
||||
following
|
||||
headerUrls {
|
||||
url
|
||||
__typename
|
||||
}
|
||||
__typename
|
||||
}
|
||||
photo {
|
||||
...photoContent
|
||||
...recoPhotoFragment
|
||||
__typename
|
||||
}
|
||||
canAddComment
|
||||
llsid
|
||||
status
|
||||
currentPcursor
|
||||
tags {
|
||||
type
|
||||
name
|
||||
__typename
|
||||
}
|
||||
__typename
|
||||
}
|
||||
|
||||
query visionSearchPhoto($keyword: String, $pcursor: String, $searchSessionId: String, $page: String, $webPageArea: String) {
|
||||
visionSearchPhoto(keyword: $keyword, pcursor: $pcursor, searchSessionId: $searchSessionId, page: $page, webPageArea: $webPageArea) {
|
||||
result
|
||||
llsid
|
||||
webPageArea
|
||||
feeds {
|
||||
...feedContent
|
||||
__typename
|
||||
}
|
||||
searchSessionId
|
||||
pcursor
|
||||
aladdinBanner {
|
||||
imgUrl
|
||||
link
|
||||
__typename
|
||||
}
|
||||
__typename
|
||||
}
|
||||
}`,
|
||||
variables: {
|
||||
keyword: query,
|
||||
page: "search",
|
||||
pcursor: `${page - 1}`,
|
||||
},
|
||||
};
|
||||
const result = (await axios_1.default.post("https://www.kuaishou.com/graphql", body)).data.data.visionSearchPhoto;
|
||||
return {
|
||||
isEnd: !(result === null || result === void 0 ? void 0 : result.pcursor) || (result === null || result === void 0 ? void 0 : result.pcursor) === 'no_more',
|
||||
data: (_b = (_a = result === null || result === void 0 ? void 0 : result.feeds) === null || _a === void 0 ? void 0 : _a.map) === null || _b === void 0 ? void 0 : _b.call(_a, formatMusicItem)
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "快手",
|
||||
version: "0.0.1",
|
||||
author: '猫头猫',
|
||||
srcUrl: "https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/kuaishou/index.js",
|
||||
cacheControl: "no-cache",
|
||||
supportedSearchType: ["music"],
|
||||
async search(query, page, type) {
|
||||
if (type === "music") {
|
||||
return await searchMusic(query, page);
|
||||
}
|
||||
},
|
||||
async getMediaSource(musicItem, quality) {
|
||||
if (!musicItem.manifest) {
|
||||
return;
|
||||
}
|
||||
const adaptationSet = musicItem.manifest.adaptationSet;
|
||||
const representation = adaptationSet[0].representation;
|
||||
return {
|
||||
url: representation[0].url
|
||||
};
|
||||
},
|
||||
};
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
const pageSize = 20;
|
||||
function formatMusicItem(it) {
|
||||
return {
|
||||
id: it.photo.id,
|
||||
title: it.photo.caption,
|
||||
artist: it.author.name,
|
||||
artwork: it.photo.coverUrl || it.photo.photoUrl,
|
||||
manifest: it.photo.manifest
|
||||
};
|
||||
}
|
||||
async function searchMusic(query, page) {
|
||||
var _a, _b;
|
||||
const body = {
|
||||
query: `fragment photoContent on PhotoEntity {
|
||||
__typename
|
||||
id
|
||||
duration
|
||||
caption
|
||||
originCaption
|
||||
likeCount
|
||||
viewCount
|
||||
commentCount
|
||||
realLikeCount
|
||||
coverUrl
|
||||
photoUrl
|
||||
photoH265Url
|
||||
manifest
|
||||
manifestH265
|
||||
videoResource
|
||||
coverUrls {
|
||||
url
|
||||
__typename
|
||||
}
|
||||
timestamp
|
||||
expTag
|
||||
animatedCoverUrl
|
||||
distance
|
||||
videoRatio
|
||||
liked
|
||||
stereoType
|
||||
profileUserTopPhoto
|
||||
musicBlocked
|
||||
}
|
||||
|
||||
fragment recoPhotoFragment on recoPhotoEntity {
|
||||
__typename
|
||||
id
|
||||
duration
|
||||
caption
|
||||
originCaption
|
||||
likeCount
|
||||
viewCount
|
||||
commentCount
|
||||
realLikeCount
|
||||
coverUrl
|
||||
photoUrl
|
||||
photoH265Url
|
||||
manifest
|
||||
manifestH265
|
||||
videoResource
|
||||
coverUrls {
|
||||
url
|
||||
__typename
|
||||
}
|
||||
timestamp
|
||||
expTag
|
||||
animatedCoverUrl
|
||||
distance
|
||||
videoRatio
|
||||
liked
|
||||
stereoType
|
||||
profileUserTopPhoto
|
||||
musicBlocked
|
||||
}
|
||||
|
||||
fragment feedContent on Feed {
|
||||
type
|
||||
author {
|
||||
id
|
||||
name
|
||||
headerUrl
|
||||
following
|
||||
headerUrls {
|
||||
url
|
||||
__typename
|
||||
}
|
||||
__typename
|
||||
}
|
||||
photo {
|
||||
...photoContent
|
||||
...recoPhotoFragment
|
||||
__typename
|
||||
}
|
||||
canAddComment
|
||||
llsid
|
||||
status
|
||||
currentPcursor
|
||||
tags {
|
||||
type
|
||||
name
|
||||
__typename
|
||||
}
|
||||
__typename
|
||||
}
|
||||
|
||||
query visionSearchPhoto($keyword: String, $pcursor: String, $searchSessionId: String, $page: String, $webPageArea: String) {
|
||||
visionSearchPhoto(keyword: $keyword, pcursor: $pcursor, searchSessionId: $searchSessionId, page: $page, webPageArea: $webPageArea) {
|
||||
result
|
||||
llsid
|
||||
webPageArea
|
||||
feeds {
|
||||
...feedContent
|
||||
__typename
|
||||
}
|
||||
searchSessionId
|
||||
pcursor
|
||||
aladdinBanner {
|
||||
imgUrl
|
||||
link
|
||||
__typename
|
||||
}
|
||||
__typename
|
||||
}
|
||||
}`,
|
||||
variables: {
|
||||
keyword: query,
|
||||
page: "search",
|
||||
pcursor: `${page - 1}`,
|
||||
},
|
||||
};
|
||||
const result = (await axios_1.default.post("https://www.kuaishou.com/graphql", body)).data.data.visionSearchPhoto;
|
||||
return {
|
||||
isEnd: !(result === null || result === void 0 ? void 0 : result.pcursor) || (result === null || result === void 0 ? void 0 : result.pcursor) === 'no_more',
|
||||
data: (_b = (_a = result === null || result === void 0 ? void 0 : result.feeds) === null || _a === void 0 ? void 0 : _a.map) === null || _b === void 0 ? void 0 : _b.call(_a, formatMusicItem)
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "快手",
|
||||
version: "0.0.1",
|
||||
author: '猫头猫',
|
||||
srcUrl: "https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/kuaishou/index.js",
|
||||
cacheControl: "no-cache",
|
||||
supportedSearchType: ["music"],
|
||||
async search(query, page, type) {
|
||||
if (type === "music") {
|
||||
return await searchMusic(query, page);
|
||||
}
|
||||
},
|
||||
async getMediaSource(musicItem, quality) {
|
||||
if (!musicItem.manifest) {
|
||||
return;
|
||||
}
|
||||
const adaptationSet = musicItem.manifest.adaptationSet;
|
||||
const representation = adaptationSet[0].representation;
|
||||
return {
|
||||
url: representation[0].url
|
||||
};
|
||||
},
|
||||
};
|
||||
|
||||
398
dist/maoerfm/index.js
vendored
398
dist/maoerfm/index.js
vendored
@@ -1,199 +1,199 @@
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
const pageSize = 30;
|
||||
function validMusicFilter(_) {
|
||||
return `${_.pay_type}` === "0";
|
||||
}
|
||||
function formatMusicItem(_) {
|
||||
var _a;
|
||||
return {
|
||||
id: _.id,
|
||||
artwork: _.front_cover,
|
||||
title: _.soundstr,
|
||||
artist: _.username,
|
||||
user_id: _.user_id,
|
||||
duration: +((_a = _.duration) !== null && _a !== void 0 ? _a : 0),
|
||||
};
|
||||
}
|
||||
function formatAlbumItem(_) {
|
||||
return {
|
||||
id: _.id,
|
||||
artist: _.author,
|
||||
title: _.name,
|
||||
artwork: _.cover,
|
||||
description: _.abstract,
|
||||
};
|
||||
}
|
||||
const searchHeaders = {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36 Edg/109.0.1518.61",
|
||||
accept: "application/json",
|
||||
"accept-encoding": "gzip, deflate, br",
|
||||
referer: "https://www.missevan.com/sound/search",
|
||||
};
|
||||
async function searchMusic(query, page) {
|
||||
const res = (await axios_1.default.get("https://www.missevan.com/sound/getsearch", {
|
||||
params: {
|
||||
s: query,
|
||||
p: page,
|
||||
type: 3,
|
||||
page_size: pageSize,
|
||||
},
|
||||
headers: searchHeaders,
|
||||
})).data.info;
|
||||
return {
|
||||
isEnd: res.pagination.p >= res.pagination.maxpage,
|
||||
data: res.Datas.filter(validMusicFilter).map(formatMusicItem),
|
||||
};
|
||||
}
|
||||
async function searchAlbum(query, page) {
|
||||
const res = (await axios_1.default.get("https://www.missevan.com/dramaapi/search", {
|
||||
headers: searchHeaders,
|
||||
params: {
|
||||
s: query,
|
||||
page,
|
||||
},
|
||||
})).data.info;
|
||||
return {
|
||||
isEnd: res.pagination.p >= res.pagination.maxpage,
|
||||
data: res.Datas.filter(validMusicFilter).map(formatAlbumItem),
|
||||
};
|
||||
}
|
||||
async function getAlbumInfo(albumItem) {
|
||||
const res = (await axios_1.default.get("https://www.missevan.com/dramaapi/getdrama", {
|
||||
headers: {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36 Edg/109.0.1518.61",
|
||||
accept: "application/json",
|
||||
"accept-encoding": "gzip, deflate, br",
|
||||
referer: `https://www.missevan.com/mdrama/${albumItem.id}`,
|
||||
},
|
||||
params: {
|
||||
drama_id: albumItem.id,
|
||||
},
|
||||
})).data;
|
||||
return {
|
||||
musicList: res.info.episodes.episode
|
||||
.filter(validMusicFilter)
|
||||
.map(_ => {
|
||||
const r = formatMusicItem(_);
|
||||
r.artwork = albumItem.artwork;
|
||||
return r;
|
||||
}),
|
||||
};
|
||||
}
|
||||
async function getMediaSource(musicItem, quality) {
|
||||
if (quality === "high" || quality === "super") {
|
||||
return;
|
||||
}
|
||||
const res = (await axios_1.default.get("https://www.missevan.com/sound/getsound", {
|
||||
headers: {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36 Edg/109.0.1518.61",
|
||||
accept: "application/json",
|
||||
"accept-encoding": "gzip, deflate, br",
|
||||
referer: `https://www.missevan.com/sound/player?id=${musicItem.id}`,
|
||||
},
|
||||
params: {
|
||||
soundid: musicItem.id,
|
||||
},
|
||||
})).data.info;
|
||||
if (quality === "low") {
|
||||
return {
|
||||
url: res.sound.soundurl_128,
|
||||
};
|
||||
}
|
||||
else {
|
||||
return {
|
||||
url: res.sound.soundurl,
|
||||
};
|
||||
}
|
||||
}
|
||||
async function getRecommendSheetTags() {
|
||||
const res = (await axios_1.default.get(`https://www.missevan.com/malbum/recommand`, {
|
||||
headers: {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36 Edg/109.0.1518.61",
|
||||
accept: "application/json",
|
||||
"accept-encoding": "gzip, deflate, br",
|
||||
referer: `https://www.missevan.com`,
|
||||
}
|
||||
})).data.info;
|
||||
const data = Object.entries(res !== null && res !== void 0 ? res : {}).map(group => ({
|
||||
title: group[0],
|
||||
data: group[1].map(_ => ({
|
||||
id: _[0],
|
||||
title: _[1]
|
||||
}))
|
||||
}));
|
||||
return {
|
||||
data,
|
||||
};
|
||||
}
|
||||
async function getRecommendSheetsByTag(tag, page) {
|
||||
const res = (await axios_1.default.get(`https://www.missevan.com/explore/tagalbum`, {
|
||||
headers: {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36 Edg/109.0.1518.61",
|
||||
accept: "application/json",
|
||||
"accept-encoding": "gzip, deflate, br",
|
||||
referer: `https://m.missevan.com`,
|
||||
},
|
||||
params: {
|
||||
order: 0,
|
||||
tid: (tag === null || tag === void 0 ? void 0 : tag.id) || 0,
|
||||
p: page
|
||||
}
|
||||
})).data;
|
||||
return {
|
||||
isEnd: res.page >= res.maxpage,
|
||||
data: res.albums.map(sheet => ({
|
||||
id: sheet.id,
|
||||
title: sheet.title,
|
||||
artwork: sheet.front_cover,
|
||||
artist: sheet.username,
|
||||
createUserId: sheet.user_id
|
||||
}))
|
||||
};
|
||||
}
|
||||
async function getMusicSheetInfo(sheet, page) {
|
||||
const res = (await axios_1.default.get(`https://www.missevan.com/sound/soundalllist`, {
|
||||
headers: {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36 Edg/109.0.1518.61",
|
||||
accept: "application/json",
|
||||
"accept-encoding": "gzip, deflate, br",
|
||||
referer: `https://m.missevan.com`,
|
||||
},
|
||||
params: {
|
||||
albumid: sheet.id
|
||||
}
|
||||
})).data.info;
|
||||
return {
|
||||
isEnd: true,
|
||||
musicList: res.sounds.filter(validMusicFilter).map(item => ({
|
||||
id: item.id,
|
||||
title: item.soundstr,
|
||||
artwork: item.front_cover,
|
||||
url: item.soundurl,
|
||||
artist: item.username,
|
||||
}))
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "猫耳FM",
|
||||
author: '猫头猫',
|
||||
version: "0.1.4",
|
||||
appVersion: ">0.1.0-alpha.0",
|
||||
srcUrl: "https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/maoerfm/index.js",
|
||||
cacheControl: "no-cache",
|
||||
supportedSearchType: ["music", "album",],
|
||||
async search(query, page, type) {
|
||||
if (type === "music") {
|
||||
return await searchMusic(query, page);
|
||||
}
|
||||
if (type === "album") {
|
||||
return await searchAlbum(query, page);
|
||||
}
|
||||
},
|
||||
getMediaSource,
|
||||
getAlbumInfo,
|
||||
getRecommendSheetTags,
|
||||
getRecommendSheetsByTag,
|
||||
getMusicSheetInfo
|
||||
};
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
const pageSize = 30;
|
||||
function validMusicFilter(_) {
|
||||
return `${_.pay_type}` === "0";
|
||||
}
|
||||
function formatMusicItem(_) {
|
||||
var _a;
|
||||
return {
|
||||
id: _.id,
|
||||
artwork: _.front_cover,
|
||||
title: _.soundstr,
|
||||
artist: _.username,
|
||||
user_id: _.user_id,
|
||||
duration: +((_a = _.duration) !== null && _a !== void 0 ? _a : 0),
|
||||
};
|
||||
}
|
||||
function formatAlbumItem(_) {
|
||||
return {
|
||||
id: _.id,
|
||||
artist: _.author,
|
||||
title: _.name,
|
||||
artwork: _.cover,
|
||||
description: _.abstract,
|
||||
};
|
||||
}
|
||||
const searchHeaders = {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36 Edg/109.0.1518.61",
|
||||
accept: "application/json",
|
||||
"accept-encoding": "gzip, deflate, br",
|
||||
referer: "https://www.missevan.com/sound/search",
|
||||
};
|
||||
async function searchMusic(query, page) {
|
||||
const res = (await axios_1.default.get("https://www.missevan.com/sound/getsearch", {
|
||||
params: {
|
||||
s: query,
|
||||
p: page,
|
||||
type: 3,
|
||||
page_size: pageSize,
|
||||
},
|
||||
headers: searchHeaders,
|
||||
})).data.info;
|
||||
return {
|
||||
isEnd: res.pagination.p >= res.pagination.maxpage,
|
||||
data: res.Datas.filter(validMusicFilter).map(formatMusicItem),
|
||||
};
|
||||
}
|
||||
async function searchAlbum(query, page) {
|
||||
const res = (await axios_1.default.get("https://www.missevan.com/dramaapi/search", {
|
||||
headers: searchHeaders,
|
||||
params: {
|
||||
s: query,
|
||||
page,
|
||||
},
|
||||
})).data.info;
|
||||
return {
|
||||
isEnd: res.pagination.p >= res.pagination.maxpage,
|
||||
data: res.Datas.filter(validMusicFilter).map(formatAlbumItem),
|
||||
};
|
||||
}
|
||||
async function getAlbumInfo(albumItem) {
|
||||
const res = (await axios_1.default.get("https://www.missevan.com/dramaapi/getdrama", {
|
||||
headers: {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36 Edg/109.0.1518.61",
|
||||
accept: "application/json",
|
||||
"accept-encoding": "gzip, deflate, br",
|
||||
referer: `https://www.missevan.com/mdrama/${albumItem.id}`,
|
||||
},
|
||||
params: {
|
||||
drama_id: albumItem.id,
|
||||
},
|
||||
})).data;
|
||||
return {
|
||||
musicList: res.info.episodes.episode
|
||||
.filter(validMusicFilter)
|
||||
.map(_ => {
|
||||
const r = formatMusicItem(_);
|
||||
r.artwork = albumItem.artwork;
|
||||
return r;
|
||||
}),
|
||||
};
|
||||
}
|
||||
async function getMediaSource(musicItem, quality) {
|
||||
if (quality === "high" || quality === "super") {
|
||||
return;
|
||||
}
|
||||
const res = (await axios_1.default.get("https://www.missevan.com/sound/getsound", {
|
||||
headers: {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36 Edg/109.0.1518.61",
|
||||
accept: "application/json",
|
||||
"accept-encoding": "gzip, deflate, br",
|
||||
referer: `https://www.missevan.com/sound/player?id=${musicItem.id}`,
|
||||
},
|
||||
params: {
|
||||
soundid: musicItem.id,
|
||||
},
|
||||
})).data.info;
|
||||
if (quality === "low") {
|
||||
return {
|
||||
url: res.sound.soundurl_128,
|
||||
};
|
||||
}
|
||||
else {
|
||||
return {
|
||||
url: res.sound.soundurl,
|
||||
};
|
||||
}
|
||||
}
|
||||
async function getRecommendSheetTags() {
|
||||
const res = (await axios_1.default.get(`https://www.missevan.com/malbum/recommand`, {
|
||||
headers: {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36 Edg/109.0.1518.61",
|
||||
accept: "application/json",
|
||||
"accept-encoding": "gzip, deflate, br",
|
||||
referer: `https://www.missevan.com`,
|
||||
}
|
||||
})).data.info;
|
||||
const data = Object.entries(res !== null && res !== void 0 ? res : {}).map(group => ({
|
||||
title: group[0],
|
||||
data: group[1].map(_ => ({
|
||||
id: _[0],
|
||||
title: _[1]
|
||||
}))
|
||||
}));
|
||||
return {
|
||||
data,
|
||||
};
|
||||
}
|
||||
async function getRecommendSheetsByTag(tag, page) {
|
||||
const res = (await axios_1.default.get(`https://www.missevan.com/explore/tagalbum`, {
|
||||
headers: {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36 Edg/109.0.1518.61",
|
||||
accept: "application/json",
|
||||
"accept-encoding": "gzip, deflate, br",
|
||||
referer: `https://m.missevan.com`,
|
||||
},
|
||||
params: {
|
||||
order: 0,
|
||||
tid: (tag === null || tag === void 0 ? void 0 : tag.id) || 0,
|
||||
p: page
|
||||
}
|
||||
})).data;
|
||||
return {
|
||||
isEnd: res.page >= res.maxpage,
|
||||
data: res.albums.map(sheet => ({
|
||||
id: sheet.id,
|
||||
title: sheet.title,
|
||||
artwork: sheet.front_cover,
|
||||
artist: sheet.username,
|
||||
createUserId: sheet.user_id
|
||||
}))
|
||||
};
|
||||
}
|
||||
async function getMusicSheetInfo(sheet, page) {
|
||||
const res = (await axios_1.default.get(`https://www.missevan.com/sound/soundalllist`, {
|
||||
headers: {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36 Edg/109.0.1518.61",
|
||||
accept: "application/json",
|
||||
"accept-encoding": "gzip, deflate, br",
|
||||
referer: `https://m.missevan.com`,
|
||||
},
|
||||
params: {
|
||||
albumid: sheet.id
|
||||
}
|
||||
})).data.info;
|
||||
return {
|
||||
isEnd: true,
|
||||
musicList: res.sounds.filter(validMusicFilter).map(item => ({
|
||||
id: item.id,
|
||||
title: item.soundstr,
|
||||
artwork: item.front_cover,
|
||||
url: item.soundurl,
|
||||
artist: item.username,
|
||||
}))
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "猫耳FM",
|
||||
author: '猫头猫',
|
||||
version: "0.1.4",
|
||||
appVersion: ">0.1.0-alpha.0",
|
||||
srcUrl: "https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/maoerfm/index.js",
|
||||
cacheControl: "no-cache",
|
||||
supportedSearchType: ["music", "album",],
|
||||
async search(query, page, type) {
|
||||
if (type === "music") {
|
||||
return await searchMusic(query, page);
|
||||
}
|
||||
if (type === "album") {
|
||||
return await searchAlbum(query, page);
|
||||
}
|
||||
},
|
||||
getMediaSource,
|
||||
getAlbumInfo,
|
||||
getRecommendSheetTags,
|
||||
getRecommendSheetsByTag,
|
||||
getMusicSheetInfo
|
||||
};
|
||||
|
||||
274
dist/navidrome/index.js
vendored
274
dist/navidrome/index.js
vendored
@@ -1,137 +1,137 @@
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
const CryptoJs = require("crypto-js");
|
||||
const pageSize = 25;
|
||||
async function httpGet(urlPath, params) {
|
||||
var _a;
|
||||
const userVariables = (_a = env === null || env === void 0 ? void 0 : env.getUserVariables()) !== null && _a !== void 0 ? _a : {};
|
||||
let { url, username, password } = userVariables;
|
||||
console.log(userVariables);
|
||||
if (!(url && username && password)) {
|
||||
return null;
|
||||
}
|
||||
if (!url.startsWith("http://") && !url.startsWith("https://")) {
|
||||
url = `http://${url}`;
|
||||
}
|
||||
const salt = Math.random().toString(16).slice(2);
|
||||
const preParams = {
|
||||
u: username,
|
||||
s: salt,
|
||||
t: CryptoJs.MD5(`${password}${salt}`).toString(CryptoJs.enc.Hex),
|
||||
c: "MusicFree",
|
||||
v: "1.14.1",
|
||||
f: "json",
|
||||
};
|
||||
return (await axios_1.default.get(`${url}/rest/${urlPath}`, {
|
||||
params: Object.assign(Object.assign({}, preParams), params),
|
||||
})).data;
|
||||
}
|
||||
function formatMusicItem(it) {
|
||||
return Object.assign(Object.assign({}, it), { artwork: it.coverArt });
|
||||
}
|
||||
function formatAlbumItem(it) {
|
||||
return Object.assign(Object.assign({}, it), { artwork: it.coverArt });
|
||||
}
|
||||
function formatArtistItem(it) {
|
||||
return Object.assign(Object.assign({}, it), { avatar: it.artistImageUrl });
|
||||
}
|
||||
async function searchMusic(query, page) {
|
||||
const data = await httpGet('search2', {
|
||||
query,
|
||||
songCount: pageSize,
|
||||
songOffset: (page - 1) * pageSize
|
||||
});
|
||||
const songs = data['subsonic-response'].searchResult2.song;
|
||||
return {
|
||||
isEnd: songs.length < pageSize,
|
||||
data: songs.map(formatMusicItem)
|
||||
};
|
||||
}
|
||||
async function searchAlbum(query, page) {
|
||||
const data = await httpGet('search2', {
|
||||
query,
|
||||
albumCount: pageSize,
|
||||
albumOffset: (page - 1) * pageSize
|
||||
});
|
||||
const songs = data['subsonic-response'].searchResult2.album;
|
||||
return {
|
||||
isEnd: songs.length < pageSize,
|
||||
data: songs.map(formatAlbumItem)
|
||||
};
|
||||
}
|
||||
async function searchArtist(query, page) {
|
||||
const data = await httpGet('search2', {
|
||||
query,
|
||||
songCount: pageSize,
|
||||
songOffset: (page - 1) * pageSize
|
||||
});
|
||||
const songs = data['subsonic-response'].searchResult2.song;
|
||||
return {
|
||||
isEnd: songs.length < pageSize,
|
||||
data: songs.map(formatMusicItem)
|
||||
};
|
||||
}
|
||||
async function getAlbumInfo(albumItem) {
|
||||
const data = await httpGet('getAlbum', {
|
||||
id: albumItem.id
|
||||
});
|
||||
return {
|
||||
isEnd: true,
|
||||
data: data['subsonic-response'].album.song.map(formatMusicItem)
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "Navidrome",
|
||||
version: "0.0.0",
|
||||
author: '猫头猫',
|
||||
appVersion: ">0.1.0-alpha.0",
|
||||
srcUrl: "https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/navidrome/index.js",
|
||||
cacheControl: "no-cache",
|
||||
userVariables: [
|
||||
{
|
||||
key: "url",
|
||||
name: "服务器地址",
|
||||
},
|
||||
{
|
||||
key: "username",
|
||||
name: "用户名",
|
||||
},
|
||||
{
|
||||
key: "password",
|
||||
name: "密码",
|
||||
},
|
||||
],
|
||||
supportedSearchType: ["music", "album"],
|
||||
async search(query, page, type) {
|
||||
if (type === "music") {
|
||||
return await searchMusic(query, page);
|
||||
}
|
||||
if (type === "album") {
|
||||
return await searchAlbum(query, page);
|
||||
}
|
||||
},
|
||||
async getMediaSource(musicItem) {
|
||||
var _a;
|
||||
const userVariables = (_a = env === null || env === void 0 ? void 0 : env.getUserVariables()) !== null && _a !== void 0 ? _a : {};
|
||||
let { url, username, password } = userVariables;
|
||||
if (!(url && username && password)) {
|
||||
return null;
|
||||
}
|
||||
if (!url.startsWith("http://") && !url.startsWith("https://")) {
|
||||
url = `http://${url}`;
|
||||
}
|
||||
const salt = Math.random().toString(16).slice(2);
|
||||
const urlObj = new URL(`${url}/rest/stream`);
|
||||
urlObj.searchParams.append('u', username);
|
||||
urlObj.searchParams.append('s', salt);
|
||||
urlObj.searchParams.append('t', CryptoJs.MD5(`${password}${salt}`).toString(CryptoJs.enc.Hex));
|
||||
urlObj.searchParams.append('c', 'MusicFree');
|
||||
urlObj.searchParams.append('v', '1.14.1');
|
||||
urlObj.searchParams.append('f', 'json');
|
||||
urlObj.searchParams.append('id', musicItem.id);
|
||||
return {
|
||||
url: urlObj.toString()
|
||||
};
|
||||
}
|
||||
};
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
const CryptoJs = require("crypto-js");
|
||||
const pageSize = 25;
|
||||
async function httpGet(urlPath, params) {
|
||||
var _a;
|
||||
const userVariables = (_a = env === null || env === void 0 ? void 0 : env.getUserVariables()) !== null && _a !== void 0 ? _a : {};
|
||||
let { url, username, password } = userVariables;
|
||||
console.log(userVariables);
|
||||
if (!(url && username && password)) {
|
||||
return null;
|
||||
}
|
||||
if (!url.startsWith("http://") && !url.startsWith("https://")) {
|
||||
url = `http://${url}`;
|
||||
}
|
||||
const salt = Math.random().toString(16).slice(2);
|
||||
const preParams = {
|
||||
u: username,
|
||||
s: salt,
|
||||
t: CryptoJs.MD5(`${password}${salt}`).toString(CryptoJs.enc.Hex),
|
||||
c: "MusicFree",
|
||||
v: "1.14.1",
|
||||
f: "json",
|
||||
};
|
||||
return (await axios_1.default.get(`${url}/rest/${urlPath}`, {
|
||||
params: Object.assign(Object.assign({}, preParams), params),
|
||||
})).data;
|
||||
}
|
||||
function formatMusicItem(it) {
|
||||
return Object.assign(Object.assign({}, it), { artwork: it.coverArt });
|
||||
}
|
||||
function formatAlbumItem(it) {
|
||||
return Object.assign(Object.assign({}, it), { artwork: it.coverArt });
|
||||
}
|
||||
function formatArtistItem(it) {
|
||||
return Object.assign(Object.assign({}, it), { avatar: it.artistImageUrl });
|
||||
}
|
||||
async function searchMusic(query, page) {
|
||||
const data = await httpGet('search2', {
|
||||
query,
|
||||
songCount: pageSize,
|
||||
songOffset: (page - 1) * pageSize
|
||||
});
|
||||
const songs = data['subsonic-response'].searchResult2.song;
|
||||
return {
|
||||
isEnd: songs.length < pageSize,
|
||||
data: songs.map(formatMusicItem)
|
||||
};
|
||||
}
|
||||
async function searchAlbum(query, page) {
|
||||
const data = await httpGet('search2', {
|
||||
query,
|
||||
albumCount: pageSize,
|
||||
albumOffset: (page - 1) * pageSize
|
||||
});
|
||||
const songs = data['subsonic-response'].searchResult2.album;
|
||||
return {
|
||||
isEnd: songs.length < pageSize,
|
||||
data: songs.map(formatAlbumItem)
|
||||
};
|
||||
}
|
||||
async function searchArtist(query, page) {
|
||||
const data = await httpGet('search2', {
|
||||
query,
|
||||
songCount: pageSize,
|
||||
songOffset: (page - 1) * pageSize
|
||||
});
|
||||
const songs = data['subsonic-response'].searchResult2.song;
|
||||
return {
|
||||
isEnd: songs.length < pageSize,
|
||||
data: songs.map(formatMusicItem)
|
||||
};
|
||||
}
|
||||
async function getAlbumInfo(albumItem) {
|
||||
const data = await httpGet('getAlbum', {
|
||||
id: albumItem.id
|
||||
});
|
||||
return {
|
||||
isEnd: true,
|
||||
data: data['subsonic-response'].album.song.map(formatMusicItem)
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "Navidrome",
|
||||
version: "0.0.0",
|
||||
author: '猫头猫',
|
||||
appVersion: ">0.1.0-alpha.0",
|
||||
srcUrl: "https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/navidrome/index.js",
|
||||
cacheControl: "no-cache",
|
||||
userVariables: [
|
||||
{
|
||||
key: "url",
|
||||
name: "服务器地址",
|
||||
},
|
||||
{
|
||||
key: "username",
|
||||
name: "用户名",
|
||||
},
|
||||
{
|
||||
key: "password",
|
||||
name: "密码",
|
||||
},
|
||||
],
|
||||
supportedSearchType: ["music", "album"],
|
||||
async search(query, page, type) {
|
||||
if (type === "music") {
|
||||
return await searchMusic(query, page);
|
||||
}
|
||||
if (type === "album") {
|
||||
return await searchAlbum(query, page);
|
||||
}
|
||||
},
|
||||
async getMediaSource(musicItem) {
|
||||
var _a;
|
||||
const userVariables = (_a = env === null || env === void 0 ? void 0 : env.getUserVariables()) !== null && _a !== void 0 ? _a : {};
|
||||
let { url, username, password } = userVariables;
|
||||
if (!(url && username && password)) {
|
||||
return null;
|
||||
}
|
||||
if (!url.startsWith("http://") && !url.startsWith("https://")) {
|
||||
url = `http://${url}`;
|
||||
}
|
||||
const salt = Math.random().toString(16).slice(2);
|
||||
const urlObj = new URL(`${url}/rest/stream`);
|
||||
urlObj.searchParams.append('u', username);
|
||||
urlObj.searchParams.append('s', salt);
|
||||
urlObj.searchParams.append('t', CryptoJs.MD5(`${password}${salt}`).toString(CryptoJs.enc.Hex));
|
||||
urlObj.searchParams.append('c', 'MusicFree');
|
||||
urlObj.searchParams.append('v', '1.14.1');
|
||||
urlObj.searchParams.append('f', 'json');
|
||||
urlObj.searchParams.append('id', musicItem.id);
|
||||
return {
|
||||
url: urlObj.toString()
|
||||
};
|
||||
}
|
||||
};
|
||||
|
||||
188
dist/suno/index.js
vendored
188
dist/suno/index.js
vendored
@@ -1,94 +1,94 @@
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
const headers = {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36 Edg/109.0.1518.61",
|
||||
host: "studio-api.suno.ai"
|
||||
};
|
||||
async function getTopLists() {
|
||||
return [
|
||||
{
|
||||
title: "趋势榜",
|
||||
data: [
|
||||
{
|
||||
id: "1190bf92-10dc-4ce5-968a-7a377f37f984",
|
||||
title: "趋势榜 - 最近一天",
|
||||
},
|
||||
{
|
||||
id: "08a079b2-a63b-4f9c-9f29-de3c1864ddef",
|
||||
title: "趋势榜 - 最近一周",
|
||||
},
|
||||
{
|
||||
id: "845539aa-2a39-4cf5-b4ae-16d3fe159a77",
|
||||
title: "趋势榜 - 最近一月",
|
||||
},
|
||||
{
|
||||
id: "6943c7ee-cbc5-4f72-bc4e-f3371a8be9d5",
|
||||
title: "趋势榜 - 全部时间",
|
||||
},
|
||||
],
|
||||
},
|
||||
{
|
||||
title: "最新榜",
|
||||
data: [
|
||||
{
|
||||
id: "cc14084a-2622-4c4b-8258-1f6b4b4f54b3",
|
||||
title: "最新榜",
|
||||
},
|
||||
],
|
||||
},
|
||||
{
|
||||
title: "其他类别",
|
||||
data: [
|
||||
{
|
||||
id: "1ac7823f-8faf-474f-b14c-e4f7c7bb373f",
|
||||
title: "动物开会",
|
||||
},
|
||||
{
|
||||
id: '6713d315-3541-460d-8788-162cce241336',
|
||||
title: 'Lo-Fi'
|
||||
}
|
||||
],
|
||||
},
|
||||
];
|
||||
}
|
||||
async function getTopListDetail(topListItem) {
|
||||
const result = (await axios_1.default.get(`https://studio-api.suno.ai/api/playlist/${topListItem.id}/?page=0`, {
|
||||
headers
|
||||
})).data;
|
||||
return {
|
||||
isEnd: true,
|
||||
musicList: result.playlist_clips.map(it => {
|
||||
var _a, _b;
|
||||
const clip = it.clip;
|
||||
return {
|
||||
id: clip.id,
|
||||
url: clip.audio_url,
|
||||
artwork: clip.image_large_url || clip.image_url,
|
||||
duration: (_a = clip.metadata) === null || _a === void 0 ? void 0 : _a.duration,
|
||||
title: clip.title,
|
||||
artist: clip.display_name,
|
||||
userId: clip.user_id,
|
||||
rawLrc: (_b = clip.metadata) === null || _b === void 0 ? void 0 : _b.prompt
|
||||
};
|
||||
})
|
||||
};
|
||||
}
|
||||
async function getLyric(musicItem) {
|
||||
return {
|
||||
rawLrc: musicItem.rawLrc
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "suno",
|
||||
version: "0.0.0",
|
||||
srcUrl: "https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/suno/index.js",
|
||||
cacheControl: "no-cache",
|
||||
getTopLists,
|
||||
getTopListDetail,
|
||||
getLyric
|
||||
};
|
||||
getTopListDetail({
|
||||
id: "1ac7823f-8faf-474f-b14c-e4f7c7bb373f",
|
||||
title: "最新榜",
|
||||
}).then(e => console.log(e.musicList[0]));
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
const headers = {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36 Edg/109.0.1518.61",
|
||||
host: "studio-api.suno.ai"
|
||||
};
|
||||
async function getTopLists() {
|
||||
return [
|
||||
{
|
||||
title: "趋势榜",
|
||||
data: [
|
||||
{
|
||||
id: "1190bf92-10dc-4ce5-968a-7a377f37f984",
|
||||
title: "趋势榜 - 最近一天",
|
||||
},
|
||||
{
|
||||
id: "08a079b2-a63b-4f9c-9f29-de3c1864ddef",
|
||||
title: "趋势榜 - 最近一周",
|
||||
},
|
||||
{
|
||||
id: "845539aa-2a39-4cf5-b4ae-16d3fe159a77",
|
||||
title: "趋势榜 - 最近一月",
|
||||
},
|
||||
{
|
||||
id: "6943c7ee-cbc5-4f72-bc4e-f3371a8be9d5",
|
||||
title: "趋势榜 - 全部时间",
|
||||
},
|
||||
],
|
||||
},
|
||||
{
|
||||
title: "最新榜",
|
||||
data: [
|
||||
{
|
||||
id: "cc14084a-2622-4c4b-8258-1f6b4b4f54b3",
|
||||
title: "最新榜",
|
||||
},
|
||||
],
|
||||
},
|
||||
{
|
||||
title: "其他类别",
|
||||
data: [
|
||||
{
|
||||
id: "1ac7823f-8faf-474f-b14c-e4f7c7bb373f",
|
||||
title: "动物开会",
|
||||
},
|
||||
{
|
||||
id: '6713d315-3541-460d-8788-162cce241336',
|
||||
title: 'Lo-Fi'
|
||||
}
|
||||
],
|
||||
},
|
||||
];
|
||||
}
|
||||
async function getTopListDetail(topListItem) {
|
||||
const result = (await axios_1.default.get(`https://studio-api.suno.ai/api/playlist/${topListItem.id}/?page=0`, {
|
||||
headers
|
||||
})).data;
|
||||
return {
|
||||
isEnd: true,
|
||||
musicList: result.playlist_clips.map(it => {
|
||||
var _a, _b;
|
||||
const clip = it.clip;
|
||||
return {
|
||||
id: clip.id,
|
||||
url: clip.audio_url,
|
||||
artwork: clip.image_large_url || clip.image_url,
|
||||
duration: (_a = clip.metadata) === null || _a === void 0 ? void 0 : _a.duration,
|
||||
title: clip.title,
|
||||
artist: clip.display_name,
|
||||
userId: clip.user_id,
|
||||
rawLrc: (_b = clip.metadata) === null || _b === void 0 ? void 0 : _b.prompt
|
||||
};
|
||||
})
|
||||
};
|
||||
}
|
||||
async function getLyric(musicItem) {
|
||||
return {
|
||||
rawLrc: musicItem.rawLrc
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "suno",
|
||||
version: "0.0.0",
|
||||
srcUrl: "https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/suno/index.js",
|
||||
cacheControl: "no-cache",
|
||||
getTopLists,
|
||||
getTopListDetail,
|
||||
getLyric
|
||||
};
|
||||
getTopListDetail({
|
||||
id: "1ac7823f-8faf-474f-b14c-e4f7c7bb373f",
|
||||
title: "最新榜",
|
||||
}).then(e => console.log(e.musicList[0]));
|
||||
|
||||
316
dist/udio/index.js
vendored
316
dist/udio/index.js
vendored
@@ -1,158 +1,158 @@
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
const headers = {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36 Edg/109.0.1518.61",
|
||||
};
|
||||
function formatMusicItem(it) {
|
||||
return {
|
||||
id: it.id,
|
||||
artist: it.artist,
|
||||
title: it.title,
|
||||
createdAt: it.created_at,
|
||||
artwork: it.image_path,
|
||||
url: it.song_path,
|
||||
duration: it.duration,
|
||||
mv: it.video_path,
|
||||
rawLrc: it.lyrics,
|
||||
};
|
||||
}
|
||||
async function searchMusic(query, page) {
|
||||
const pageSize = 30;
|
||||
const data = `{"searchQuery":{"sort":"plays","searchTerm":"${query}"},"pageParam":${page - 1},"pageSize":${pageSize},"trendingId":"93de406e-bdc1-40a6-befd-90637a362158"}`;
|
||||
const config = {
|
||||
method: "post",
|
||||
url: "https://www.udio.com/api/songs/search",
|
||||
headers: {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/106.0.0.0 Safari/537.36 Edg/106.0.0.0",
|
||||
host: "www.udio.com",
|
||||
},
|
||||
data: data,
|
||||
};
|
||||
const result = (await (0, axios_1.default)(config)).data.data;
|
||||
return {
|
||||
isEnd: result.length < pageSize,
|
||||
data: result.map(formatMusicItem),
|
||||
};
|
||||
}
|
||||
async function search(query, page, type) {
|
||||
if (type === "music") {
|
||||
return await searchMusic(query, page);
|
||||
}
|
||||
}
|
||||
async function getMediaSource(musicItem, quality) {
|
||||
if (quality !== "standard") {
|
||||
return;
|
||||
}
|
||||
return musicItem.url;
|
||||
}
|
||||
async function getTopLists() {
|
||||
return [
|
||||
{
|
||||
title: "趋势榜",
|
||||
data: [
|
||||
{
|
||||
id: "today",
|
||||
maxAgeInHours: 24,
|
||||
type: "search",
|
||||
title: "趋势榜 - 最近一天",
|
||||
},
|
||||
{
|
||||
id: "1week",
|
||||
maxAgeInHours: 168,
|
||||
type: "search",
|
||||
title: "趋势榜 - 最近一周",
|
||||
},
|
||||
{
|
||||
id: "1month",
|
||||
maxAgeInHours: 720,
|
||||
type: "search",
|
||||
title: "趋势榜 - 最近一月",
|
||||
},
|
||||
{
|
||||
id: "alltime",
|
||||
type: "search",
|
||||
title: "趋势榜 - 全部时间",
|
||||
},
|
||||
],
|
||||
},
|
||||
{
|
||||
title: "流派榜单",
|
||||
data: [
|
||||
{
|
||||
id: "89f0089f-1bfe-4713-8070-5830a6161afb",
|
||||
type: "playlist",
|
||||
title: "爵士",
|
||||
},
|
||||
{
|
||||
id: "935deb12-dc32-4005-a1fe-3c00c284ca52",
|
||||
type: "playlist",
|
||||
title: "乡村",
|
||||
},
|
||||
{
|
||||
id: "6028ad08-68cb-406d-aa35-a4917b6467d6",
|
||||
type: "playlist",
|
||||
title: "流行",
|
||||
},
|
||||
{
|
||||
id: "d033aa6e-655e-45d0-8138-dc9a0dc6b3a6",
|
||||
type: "playlist",
|
||||
title: "摇滚",
|
||||
},
|
||||
],
|
||||
},
|
||||
];
|
||||
}
|
||||
async function getTopListDetail(topListItem) {
|
||||
if (topListItem.type === "playlist") {
|
||||
const res = (await axios_1.default.get(`https://www.udio.com/api/playlists?id=${topListItem.id}`, {
|
||||
headers,
|
||||
})).data;
|
||||
const songList = res.playlists[0].song_list.join(",");
|
||||
const songs = (await axios_1.default.get(`https://www.udio.com/api/songs?songIds=${songList}`, {
|
||||
headers,
|
||||
})).data.songs;
|
||||
return {
|
||||
isEnd: true,
|
||||
musicList: songs.map(formatMusicItem),
|
||||
};
|
||||
}
|
||||
else if (topListItem.type === "search") {
|
||||
const pageSize = 30;
|
||||
const data = `{"searchQuery":{"sort":"plays","searchTerm":""${topListItem.maxAgeInHours
|
||||
? `,"maxAgeInHours": ${topListItem.maxAgeInHours}`
|
||||
: ""}},"pageParam":0,"pageSize":${pageSize}}`;
|
||||
const config = {
|
||||
method: "post",
|
||||
url: "https://www.udio.com/api/songs/search",
|
||||
headers: {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/106.0.0.0 Safari/537.36 Edg/106.0.0.0",
|
||||
host: "www.udio.com",
|
||||
},
|
||||
data: data,
|
||||
};
|
||||
const songs = (await (0, axios_1.default)(config)).data.data;
|
||||
return {
|
||||
isEnd: true,
|
||||
musicList: songs.map(formatMusicItem),
|
||||
};
|
||||
}
|
||||
}
|
||||
async function getLyric(musicItem) {
|
||||
return {
|
||||
rawLrc: musicItem.rawLrc
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "udio",
|
||||
author: "猫头猫",
|
||||
version: "0.0.0",
|
||||
supportedSearchType: ["music"],
|
||||
srcUrl: "https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/udio/index.js",
|
||||
cacheControl: "no-cache",
|
||||
search,
|
||||
getMediaSource,
|
||||
getTopListDetail,
|
||||
getTopLists,
|
||||
getLyric
|
||||
};
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
const headers = {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/109.0.0.0 Safari/537.36 Edg/109.0.1518.61",
|
||||
};
|
||||
function formatMusicItem(it) {
|
||||
return {
|
||||
id: it.id,
|
||||
artist: it.artist,
|
||||
title: it.title,
|
||||
createdAt: it.created_at,
|
||||
artwork: it.image_path,
|
||||
url: it.song_path,
|
||||
duration: it.duration,
|
||||
mv: it.video_path,
|
||||
rawLrc: it.lyrics,
|
||||
};
|
||||
}
|
||||
async function searchMusic(query, page) {
|
||||
const pageSize = 30;
|
||||
const data = `{"searchQuery":{"sort":"plays","searchTerm":"${query}"},"pageParam":${page - 1},"pageSize":${pageSize},"trendingId":"93de406e-bdc1-40a6-befd-90637a362158"}`;
|
||||
const config = {
|
||||
method: "post",
|
||||
url: "https://www.udio.com/api/songs/search",
|
||||
headers: {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/106.0.0.0 Safari/537.36 Edg/106.0.0.0",
|
||||
host: "www.udio.com",
|
||||
},
|
||||
data: data,
|
||||
};
|
||||
const result = (await (0, axios_1.default)(config)).data.data;
|
||||
return {
|
||||
isEnd: result.length < pageSize,
|
||||
data: result.map(formatMusicItem),
|
||||
};
|
||||
}
|
||||
async function search(query, page, type) {
|
||||
if (type === "music") {
|
||||
return await searchMusic(query, page);
|
||||
}
|
||||
}
|
||||
async function getMediaSource(musicItem, quality) {
|
||||
if (quality !== "standard") {
|
||||
return;
|
||||
}
|
||||
return musicItem.url;
|
||||
}
|
||||
async function getTopLists() {
|
||||
return [
|
||||
{
|
||||
title: "趋势榜",
|
||||
data: [
|
||||
{
|
||||
id: "today",
|
||||
maxAgeInHours: 24,
|
||||
type: "search",
|
||||
title: "趋势榜 - 最近一天",
|
||||
},
|
||||
{
|
||||
id: "1week",
|
||||
maxAgeInHours: 168,
|
||||
type: "search",
|
||||
title: "趋势榜 - 最近一周",
|
||||
},
|
||||
{
|
||||
id: "1month",
|
||||
maxAgeInHours: 720,
|
||||
type: "search",
|
||||
title: "趋势榜 - 最近一月",
|
||||
},
|
||||
{
|
||||
id: "alltime",
|
||||
type: "search",
|
||||
title: "趋势榜 - 全部时间",
|
||||
},
|
||||
],
|
||||
},
|
||||
{
|
||||
title: "流派榜单",
|
||||
data: [
|
||||
{
|
||||
id: "89f0089f-1bfe-4713-8070-5830a6161afb",
|
||||
type: "playlist",
|
||||
title: "爵士",
|
||||
},
|
||||
{
|
||||
id: "935deb12-dc32-4005-a1fe-3c00c284ca52",
|
||||
type: "playlist",
|
||||
title: "乡村",
|
||||
},
|
||||
{
|
||||
id: "6028ad08-68cb-406d-aa35-a4917b6467d6",
|
||||
type: "playlist",
|
||||
title: "流行",
|
||||
},
|
||||
{
|
||||
id: "d033aa6e-655e-45d0-8138-dc9a0dc6b3a6",
|
||||
type: "playlist",
|
||||
title: "摇滚",
|
||||
},
|
||||
],
|
||||
},
|
||||
];
|
||||
}
|
||||
async function getTopListDetail(topListItem) {
|
||||
if (topListItem.type === "playlist") {
|
||||
const res = (await axios_1.default.get(`https://www.udio.com/api/playlists?id=${topListItem.id}`, {
|
||||
headers,
|
||||
})).data;
|
||||
const songList = res.playlists[0].song_list.join(",");
|
||||
const songs = (await axios_1.default.get(`https://www.udio.com/api/songs?songIds=${songList}`, {
|
||||
headers,
|
||||
})).data.songs;
|
||||
return {
|
||||
isEnd: true,
|
||||
musicList: songs.map(formatMusicItem),
|
||||
};
|
||||
}
|
||||
else if (topListItem.type === "search") {
|
||||
const pageSize = 30;
|
||||
const data = `{"searchQuery":{"sort":"plays","searchTerm":""${topListItem.maxAgeInHours
|
||||
? `,"maxAgeInHours": ${topListItem.maxAgeInHours}`
|
||||
: ""}},"pageParam":0,"pageSize":${pageSize}}`;
|
||||
const config = {
|
||||
method: "post",
|
||||
url: "https://www.udio.com/api/songs/search",
|
||||
headers: {
|
||||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/106.0.0.0 Safari/537.36 Edg/106.0.0.0",
|
||||
host: "www.udio.com",
|
||||
},
|
||||
data: data,
|
||||
};
|
||||
const songs = (await (0, axios_1.default)(config)).data.data;
|
||||
return {
|
||||
isEnd: true,
|
||||
musicList: songs.map(formatMusicItem),
|
||||
};
|
||||
}
|
||||
}
|
||||
async function getLyric(musicItem) {
|
||||
return {
|
||||
rawLrc: musicItem.rawLrc
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "udio",
|
||||
author: "猫头猫",
|
||||
version: "0.0.0",
|
||||
supportedSearchType: ["music"],
|
||||
srcUrl: "https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/udio/index.js",
|
||||
cacheControl: "no-cache",
|
||||
search,
|
||||
getMediaSource,
|
||||
getTopListDetail,
|
||||
getTopLists,
|
||||
getLyric
|
||||
};
|
||||
|
||||
240
dist/webdav/index.js
vendored
240
dist/webdav/index.js
vendored
@@ -1,120 +1,120 @@
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const webdav_1 = require("webdav");
|
||||
let cachedData = {};
|
||||
function getClient() {
|
||||
var _a, _b, _c;
|
||||
const { url, username, password, searchPath } = (_b = (_a = env === null || env === void 0 ? void 0 : env.getUserVariables) === null || _a === void 0 ? void 0 : _a.call(env)) !== null && _b !== void 0 ? _b : {};
|
||||
if (!(url && username && password)) {
|
||||
return null;
|
||||
}
|
||||
if (!(cachedData.url === url &&
|
||||
cachedData.username === username &&
|
||||
cachedData.password === password &&
|
||||
cachedData.searchPath === searchPath)) {
|
||||
cachedData.url = url;
|
||||
cachedData.username = username;
|
||||
cachedData.password = password;
|
||||
cachedData.searchPath = searchPath;
|
||||
cachedData.searchPathList = (_c = searchPath === null || searchPath === void 0 ? void 0 : searchPath.split) === null || _c === void 0 ? void 0 : _c.call(searchPath, ",");
|
||||
cachedData.cacheFileList = null;
|
||||
}
|
||||
return (0, webdav_1.createClient)(url, {
|
||||
authType: webdav_1.AuthType.Password,
|
||||
username,
|
||||
password,
|
||||
});
|
||||
}
|
||||
async function searchMusic(query) {
|
||||
var _a, _b;
|
||||
const client = getClient();
|
||||
if (!cachedData.cacheFileList) {
|
||||
const searchPathList = ((_a = cachedData.searchPathList) === null || _a === void 0 ? void 0 : _a.length)
|
||||
? cachedData.searchPathList
|
||||
: ["/"];
|
||||
let result = [];
|
||||
for (let search of searchPathList) {
|
||||
try {
|
||||
const fileItems = (await client.getDirectoryContents(search)).filter((it) => it.type === "file" && it.mime.startsWith("audio"));
|
||||
result = [...result, ...fileItems];
|
||||
}
|
||||
catch (_c) { }
|
||||
}
|
||||
cachedData.cacheFileList = result;
|
||||
}
|
||||
return {
|
||||
isEnd: true,
|
||||
data: ((_b = cachedData.cacheFileList) !== null && _b !== void 0 ? _b : [])
|
||||
.filter((it) => it.basename.includes(query))
|
||||
.map((it) => ({
|
||||
title: it.basename,
|
||||
id: it.filename,
|
||||
artist: "未知作者",
|
||||
album: "未知专辑",
|
||||
})),
|
||||
};
|
||||
}
|
||||
async function getTopLists() {
|
||||
getClient();
|
||||
const data = {
|
||||
title: "全部歌曲",
|
||||
data: (cachedData.searchPathList || []).map((it) => ({
|
||||
title: it,
|
||||
id: it,
|
||||
})),
|
||||
};
|
||||
return [data];
|
||||
}
|
||||
async function getTopListDetail(topListItem) {
|
||||
const client = getClient();
|
||||
const fileItems = (await client.getDirectoryContents(topListItem.id)).filter((it) => it.type === "file" && it.mime.startsWith("audio"));
|
||||
return {
|
||||
musicList: fileItems.map((it) => ({
|
||||
title: it.basename,
|
||||
id: it.filename,
|
||||
artist: "未知作者",
|
||||
album: "未知专辑",
|
||||
})),
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "WebDAV",
|
||||
author: "猫头猫",
|
||||
description: "使用此插件前先配置用户变量",
|
||||
userVariables: [
|
||||
{
|
||||
key: "url",
|
||||
name: "WebDAV地址",
|
||||
},
|
||||
{
|
||||
key: "username",
|
||||
name: "用户名",
|
||||
},
|
||||
{
|
||||
key: "password",
|
||||
name: "密码",
|
||||
type: "password",
|
||||
},
|
||||
{
|
||||
key: "searchPath",
|
||||
name: "存放歌曲的路径",
|
||||
},
|
||||
],
|
||||
version: "0.0.2",
|
||||
supportedSearchType: ["music"],
|
||||
srcUrl: "https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/webdav/index.js",
|
||||
cacheControl: "no-cache",
|
||||
search(query, page, type) {
|
||||
if (type === "music") {
|
||||
return searchMusic(query);
|
||||
}
|
||||
},
|
||||
getTopLists,
|
||||
getTopListDetail,
|
||||
getMediaSource(musicItem) {
|
||||
const client = getClient();
|
||||
return {
|
||||
url: client.getFileDownloadLink(musicItem.id),
|
||||
};
|
||||
},
|
||||
};
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const webdav_1 = require("webdav");
|
||||
let cachedData = {};
|
||||
function getClient() {
|
||||
var _a, _b, _c;
|
||||
const { url, username, password, searchPath } = (_b = (_a = env === null || env === void 0 ? void 0 : env.getUserVariables) === null || _a === void 0 ? void 0 : _a.call(env)) !== null && _b !== void 0 ? _b : {};
|
||||
if (!(url && username && password)) {
|
||||
return null;
|
||||
}
|
||||
if (!(cachedData.url === url &&
|
||||
cachedData.username === username &&
|
||||
cachedData.password === password &&
|
||||
cachedData.searchPath === searchPath)) {
|
||||
cachedData.url = url;
|
||||
cachedData.username = username;
|
||||
cachedData.password = password;
|
||||
cachedData.searchPath = searchPath;
|
||||
cachedData.searchPathList = (_c = searchPath === null || searchPath === void 0 ? void 0 : searchPath.split) === null || _c === void 0 ? void 0 : _c.call(searchPath, ",");
|
||||
cachedData.cacheFileList = null;
|
||||
}
|
||||
return (0, webdav_1.createClient)(url, {
|
||||
authType: webdav_1.AuthType.Password,
|
||||
username,
|
||||
password,
|
||||
});
|
||||
}
|
||||
async function searchMusic(query) {
|
||||
var _a, _b;
|
||||
const client = getClient();
|
||||
if (!cachedData.cacheFileList) {
|
||||
const searchPathList = ((_a = cachedData.searchPathList) === null || _a === void 0 ? void 0 : _a.length)
|
||||
? cachedData.searchPathList
|
||||
: ["/"];
|
||||
let result = [];
|
||||
for (let search of searchPathList) {
|
||||
try {
|
||||
const fileItems = (await client.getDirectoryContents(search)).filter((it) => it.type === "file" && it.mime.startsWith("audio"));
|
||||
result = [...result, ...fileItems];
|
||||
}
|
||||
catch (_c) { }
|
||||
}
|
||||
cachedData.cacheFileList = result;
|
||||
}
|
||||
return {
|
||||
isEnd: true,
|
||||
data: ((_b = cachedData.cacheFileList) !== null && _b !== void 0 ? _b : [])
|
||||
.filter((it) => it.basename.includes(query))
|
||||
.map((it) => ({
|
||||
title: it.basename,
|
||||
id: it.filename,
|
||||
artist: "未知作者",
|
||||
album: "未知专辑",
|
||||
})),
|
||||
};
|
||||
}
|
||||
async function getTopLists() {
|
||||
getClient();
|
||||
const data = {
|
||||
title: "全部歌曲",
|
||||
data: (cachedData.searchPathList || []).map((it) => ({
|
||||
title: it,
|
||||
id: it,
|
||||
})),
|
||||
};
|
||||
return [data];
|
||||
}
|
||||
async function getTopListDetail(topListItem) {
|
||||
const client = getClient();
|
||||
const fileItems = (await client.getDirectoryContents(topListItem.id)).filter((it) => it.type === "file" && it.mime.startsWith("audio"));
|
||||
return {
|
||||
musicList: fileItems.map((it) => ({
|
||||
title: it.basename,
|
||||
id: it.filename,
|
||||
artist: "未知作者",
|
||||
album: "未知专辑",
|
||||
})),
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "WebDAV",
|
||||
author: "猫头猫",
|
||||
description: "使用此插件前先配置用户变量",
|
||||
userVariables: [
|
||||
{
|
||||
key: "url",
|
||||
name: "WebDAV地址",
|
||||
},
|
||||
{
|
||||
key: "username",
|
||||
name: "用户名",
|
||||
},
|
||||
{
|
||||
key: "password",
|
||||
name: "密码",
|
||||
type: "password",
|
||||
},
|
||||
{
|
||||
key: "searchPath",
|
||||
name: "存放歌曲的路径",
|
||||
},
|
||||
],
|
||||
version: "0.0.2",
|
||||
supportedSearchType: ["music"],
|
||||
srcUrl: "https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/webdav/index.js",
|
||||
cacheControl: "no-cache",
|
||||
search(query, page, type) {
|
||||
if (type === "music") {
|
||||
return searchMusic(query);
|
||||
}
|
||||
},
|
||||
getTopLists,
|
||||
getTopListDetail,
|
||||
getMediaSource(musicItem) {
|
||||
const client = getClient();
|
||||
return {
|
||||
url: client.getFileDownloadLink(musicItem.id),
|
||||
};
|
||||
},
|
||||
};
|
||||
|
||||
192
dist/yinyuetai/index.js
vendored
192
dist/yinyuetai/index.js
vendored
@@ -1,96 +1,96 @@
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
const pageNum = 20;
|
||||
function formatMusicItem(item) {
|
||||
var _a, _b, _c, _d;
|
||||
return {
|
||||
id: item.id,
|
||||
title: item.title,
|
||||
artist: (item === null || item === void 0 ? void 0 : item.allArtistNames) ||
|
||||
((_b = (_a = item.artists) === null || _a === void 0 ? void 0 : _a.map) === null || _b === void 0 ? void 0 : _b.call(_a, (s) => s.name).join(", ")) ||
|
||||
((_c = item.user) === null || _c === void 0 ? void 0 : _c.niceName),
|
||||
artwork: item === null || item === void 0 ? void 0 : item.headImg,
|
||||
urls: (_d = item === null || item === void 0 ? void 0 : item.fullClip) === null || _d === void 0 ? void 0 : _d.urls,
|
||||
};
|
||||
}
|
||||
function formatArtistItem(item) {
|
||||
return {
|
||||
id: item.id,
|
||||
name: item.name,
|
||||
avatar: item.headImg,
|
||||
};
|
||||
}
|
||||
let lastQuery;
|
||||
let lastMusicId;
|
||||
async function searchMusic(query, page) {
|
||||
if (query !== lastQuery || page === 1) {
|
||||
lastMusicId = 0;
|
||||
}
|
||||
lastQuery = query;
|
||||
let data = JSON.stringify({
|
||||
searchType: "MV",
|
||||
key: query,
|
||||
sinceId: lastMusicId,
|
||||
size: pageNum,
|
||||
requestTagRows: [
|
||||
{
|
||||
key: "sortType",
|
||||
chosenTags: ["HOTTEST"],
|
||||
},
|
||||
{
|
||||
key: "source",
|
||||
chosenTags: ["-1"],
|
||||
},
|
||||
{
|
||||
key: "duration",
|
||||
chosenTags: ["-1"],
|
||||
},
|
||||
],
|
||||
});
|
||||
let config = {
|
||||
method: "post",
|
||||
maxBodyLength: Infinity,
|
||||
url: "https://search-api.yinyuetai.com/search/get_search_result.json",
|
||||
headers: {
|
||||
referrer: "https://www.yinyuetai.com/",
|
||||
accept: "application/json",
|
||||
"content-type": "application/json",
|
||||
wua: "YYT/1.0.0 (WEB;web;11;zh-CN;kADiV2jNJFy2ryvuyB5Ne)",
|
||||
},
|
||||
data: data,
|
||||
};
|
||||
const response = (await axios_1.default.request(config)).data.data;
|
||||
lastMusicId = response[response.length - 1].id;
|
||||
return {
|
||||
isEnd: pageNum > response.length,
|
||||
data: response.map(formatMusicItem),
|
||||
};
|
||||
}
|
||||
async function search(query, page, type) {
|
||||
if (type === "music") {
|
||||
return await searchMusic(query, page);
|
||||
}
|
||||
}
|
||||
async function getMediaSource(musicItem, quality) {
|
||||
let url;
|
||||
if (quality === "standard") {
|
||||
url = musicItem.urls.find((it) => it.streamType === 5).url;
|
||||
}
|
||||
else if (quality === "high") {
|
||||
url = musicItem.urls.find((it) => it.streamType === 1).url;
|
||||
}
|
||||
return {
|
||||
url,
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "音悦台",
|
||||
author: '猫头猫',
|
||||
version: "0.0.1",
|
||||
supportedSearchType: ["music"],
|
||||
srcUrl: "https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/yinyuetai/index.js",
|
||||
cacheControl: "no-cache",
|
||||
search,
|
||||
getMediaSource,
|
||||
};
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
const pageNum = 20;
|
||||
function formatMusicItem(item) {
|
||||
var _a, _b, _c, _d;
|
||||
return {
|
||||
id: item.id,
|
||||
title: item.title,
|
||||
artist: (item === null || item === void 0 ? void 0 : item.allArtistNames) ||
|
||||
((_b = (_a = item.artists) === null || _a === void 0 ? void 0 : _a.map) === null || _b === void 0 ? void 0 : _b.call(_a, (s) => s.name).join(", ")) ||
|
||||
((_c = item.user) === null || _c === void 0 ? void 0 : _c.niceName),
|
||||
artwork: item === null || item === void 0 ? void 0 : item.headImg,
|
||||
urls: (_d = item === null || item === void 0 ? void 0 : item.fullClip) === null || _d === void 0 ? void 0 : _d.urls,
|
||||
};
|
||||
}
|
||||
function formatArtistItem(item) {
|
||||
return {
|
||||
id: item.id,
|
||||
name: item.name,
|
||||
avatar: item.headImg,
|
||||
};
|
||||
}
|
||||
let lastQuery;
|
||||
let lastMusicId;
|
||||
async function searchMusic(query, page) {
|
||||
if (query !== lastQuery || page === 1) {
|
||||
lastMusicId = 0;
|
||||
}
|
||||
lastQuery = query;
|
||||
let data = JSON.stringify({
|
||||
searchType: "MV",
|
||||
key: query,
|
||||
sinceId: lastMusicId,
|
||||
size: pageNum,
|
||||
requestTagRows: [
|
||||
{
|
||||
key: "sortType",
|
||||
chosenTags: ["HOTTEST"],
|
||||
},
|
||||
{
|
||||
key: "source",
|
||||
chosenTags: ["-1"],
|
||||
},
|
||||
{
|
||||
key: "duration",
|
||||
chosenTags: ["-1"],
|
||||
},
|
||||
],
|
||||
});
|
||||
let config = {
|
||||
method: "post",
|
||||
maxBodyLength: Infinity,
|
||||
url: "https://search-api.yinyuetai.com/search/get_search_result.json",
|
||||
headers: {
|
||||
referrer: "https://www.yinyuetai.com/",
|
||||
accept: "application/json",
|
||||
"content-type": "application/json",
|
||||
wua: "YYT/1.0.0 (WEB;web;11;zh-CN;kADiV2jNJFy2ryvuyB5Ne)",
|
||||
},
|
||||
data: data,
|
||||
};
|
||||
const response = (await axios_1.default.request(config)).data.data;
|
||||
lastMusicId = response[response.length - 1].id;
|
||||
return {
|
||||
isEnd: pageNum > response.length,
|
||||
data: response.map(formatMusicItem),
|
||||
};
|
||||
}
|
||||
async function search(query, page, type) {
|
||||
if (type === "music") {
|
||||
return await searchMusic(query, page);
|
||||
}
|
||||
}
|
||||
async function getMediaSource(musicItem, quality) {
|
||||
let url;
|
||||
if (quality === "standard") {
|
||||
url = musicItem.urls.find((it) => it.streamType === 5).url;
|
||||
}
|
||||
else if (quality === "high") {
|
||||
url = musicItem.urls.find((it) => it.streamType === 1).url;
|
||||
}
|
||||
return {
|
||||
url,
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "音悦台",
|
||||
author: '猫头猫',
|
||||
version: "0.0.1",
|
||||
supportedSearchType: ["music"],
|
||||
srcUrl: "https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/yinyuetai/index.js",
|
||||
cacheControl: "no-cache",
|
||||
search,
|
||||
getMediaSource,
|
||||
};
|
||||
|
||||
392
dist/youtube/index.js
vendored
392
dist/youtube/index.js
vendored
@@ -1,196 +1,196 @@
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
function formatMusicItem(item) {
|
||||
var _a, _b, _c, _d, _e, _f, _g;
|
||||
return {
|
||||
id: item.videoId,
|
||||
title: (_b = (_a = item.title.runs) === null || _a === void 0 ? void 0 : _a[0]) === null || _b === void 0 ? void 0 : _b.text,
|
||||
artist: (_d = (_c = item.ownerText.runs) === null || _c === void 0 ? void 0 : _c[0]) === null || _d === void 0 ? void 0 : _d.text,
|
||||
artwork: (_g = (_f = (_e = item === null || item === void 0 ? void 0 : item.thumbnail) === null || _e === void 0 ? void 0 : _e.thumbnails) === null || _f === void 0 ? void 0 : _f[0]) === null || _g === void 0 ? void 0 : _g.url,
|
||||
};
|
||||
}
|
||||
let lastQuery;
|
||||
let musicContinToken;
|
||||
async function searchMusic(query, page) {
|
||||
if (query !== lastQuery || page === 1) {
|
||||
musicContinToken = undefined;
|
||||
}
|
||||
lastQuery = query;
|
||||
let data = JSON.stringify({
|
||||
context: {
|
||||
client: {
|
||||
hl: "zh-CN",
|
||||
gl: "US",
|
||||
deviceMake: "",
|
||||
deviceModel: "",
|
||||
userAgent: "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/119.0.0.0 Safari/537.36 Edg/119.0.0.0,gzip(gfe)",
|
||||
clientName: "WEB",
|
||||
clientVersion: "2.20231121.08.00",
|
||||
osName: "Windows",
|
||||
osVersion: "10.0",
|
||||
platform: "DESKTOP",
|
||||
userInterfaceTheme: "USER_INTERFACE_THEME_LIGHT",
|
||||
browserName: "Edge Chromium",
|
||||
browserVersion: "119.0.0.0",
|
||||
acceptHeader: "text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.7",
|
||||
screenWidthPoints: 1358,
|
||||
screenHeightPoints: 1012,
|
||||
screenPixelDensity: 1,
|
||||
screenDensityFloat: 1.2395833730697632,
|
||||
utcOffsetMinutes: 480,
|
||||
memoryTotalKbytes: "8000000",
|
||||
mainAppWebInfo: {
|
||||
pwaInstallabilityStatus: "PWA_INSTALLABILITY_STATUS_UNKNOWN",
|
||||
webDisplayMode: "WEB_DISPLAY_MODE_BROWSER",
|
||||
isWebNativeShareAvailable: true,
|
||||
},
|
||||
timeZone: "Asia/Shanghai",
|
||||
},
|
||||
user: {
|
||||
lockedSafetyMode: false,
|
||||
},
|
||||
request: {
|
||||
useSsl: true,
|
||||
internalExperimentFlags: [],
|
||||
},
|
||||
},
|
||||
query: musicContinToken ? undefined : query,
|
||||
continuation: musicContinToken || undefined,
|
||||
});
|
||||
var config = {
|
||||
method: "post",
|
||||
url: "https://www.youtube.com/youtubei/v1/search?prettyPrint=false",
|
||||
headers: {
|
||||
"Content-Type": "text/plain",
|
||||
},
|
||||
data: data,
|
||||
};
|
||||
const response = (await (0, axios_1.default)(config)).data;
|
||||
const contents = response.contents.twoColumnSearchResultsRenderer.primaryContents
|
||||
.sectionListRenderer.contents;
|
||||
const isEndItem = contents.find((it) => {
|
||||
var _a, _b, _c;
|
||||
return ((_c = (_b = (_a = it.continuationItemRenderer) === null || _a === void 0 ? void 0 : _a.continuationEndpoint) === null || _b === void 0 ? void 0 : _b.continuationCommand) === null || _c === void 0 ? void 0 : _c.request) === "CONTINUATION_REQUEST_TYPE_SEARCH";
|
||||
});
|
||||
if (isEndItem) {
|
||||
musicContinToken =
|
||||
isEndItem.continuationItemRenderer.continuationEndpoint
|
||||
.continuationCommand.token;
|
||||
}
|
||||
const musicData = contents.find((it) => it.itemSectionRenderer)
|
||||
.itemSectionRenderer.contents;
|
||||
let resultMusicData = [];
|
||||
for (let i = 0; i < musicData.length; ++i) {
|
||||
if (musicData[i].videoRenderer) {
|
||||
resultMusicData.push(formatMusicItem(musicData[i].videoRenderer));
|
||||
}
|
||||
}
|
||||
return {
|
||||
isEnd: !isEndItem,
|
||||
data: resultMusicData,
|
||||
};
|
||||
}
|
||||
async function search(query, page, type) {
|
||||
if (type === "music") {
|
||||
return await searchMusic(query, page);
|
||||
}
|
||||
}
|
||||
let cacheMediaSource = {
|
||||
id: null,
|
||||
urls: {},
|
||||
};
|
||||
function getQuality(label) {
|
||||
if (label === "small") {
|
||||
return "standard";
|
||||
}
|
||||
else if (label === "tiny") {
|
||||
return "low";
|
||||
}
|
||||
else if (label === "medium") {
|
||||
return "high";
|
||||
}
|
||||
else if (label === "large") {
|
||||
return "super";
|
||||
}
|
||||
else {
|
||||
return "standard";
|
||||
}
|
||||
}
|
||||
async function getMediaSource(musicItem, quality) {
|
||||
var _a, _b;
|
||||
if (musicItem.id === cacheMediaSource.id) {
|
||||
return {
|
||||
url: cacheMediaSource.urls[quality],
|
||||
};
|
||||
}
|
||||
cacheMediaSource = {
|
||||
id: null,
|
||||
urls: {},
|
||||
};
|
||||
const data = {
|
||||
context: {
|
||||
client: {
|
||||
screenWidthPoints: 689,
|
||||
screenHeightPoints: 963,
|
||||
screenPixelDensity: 1,
|
||||
utcOffsetMinutes: 120,
|
||||
hl: "en",
|
||||
gl: "GB",
|
||||
remoteHost: "1.1.1.1",
|
||||
deviceMake: "",
|
||||
deviceModel: "",
|
||||
userAgent: "com.google.android.apps.youtube.music/6.14.50 (Linux; U; Android 13; GB) gzip",
|
||||
clientName: "ANDROID_MUSIC",
|
||||
clientVersion: "6.14.50",
|
||||
osName: "Android",
|
||||
osVersion: "13",
|
||||
originalUrl: "https://www.youtube.com/tv?is_account_switch=1&hrld=1&fltor=1",
|
||||
theme: "CLASSIC",
|
||||
platform: "MOBILE",
|
||||
clientFormFactor: "UNKNOWN_FORM_FACTOR",
|
||||
webpSupport: false,
|
||||
timeZone: "Europe/Amsterdam",
|
||||
acceptHeader: "text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,*/*;q=0.8",
|
||||
},
|
||||
user: { enableSafetyMode: false },
|
||||
request: {
|
||||
internalExperimentFlags: [],
|
||||
consistencyTokenJars: [],
|
||||
},
|
||||
},
|
||||
contentCheckOk: true,
|
||||
racyCheckOk: true,
|
||||
video_id: musicItem.id,
|
||||
};
|
||||
var config = {
|
||||
method: "post",
|
||||
url: "https://www.youtube.com/youtubei/v1/player?prettyPrint=false",
|
||||
headers: {
|
||||
"Content-Type": "application/json",
|
||||
},
|
||||
data: JSON.stringify(data),
|
||||
};
|
||||
const result = (await (0, axios_1.default)(config)).data;
|
||||
const formats = (_a = result.streamingData.formats) !== null && _a !== void 0 ? _a : [];
|
||||
const adaptiveFormats = (_b = result.streamingData.adaptiveFormats) !== null && _b !== void 0 ? _b : [];
|
||||
[...formats, ...adaptiveFormats].forEach((it) => {
|
||||
const q = getQuality(it.quality);
|
||||
if (q && it.url && !cacheMediaSource.urls[q]) {
|
||||
cacheMediaSource.urls[q] = it.url;
|
||||
}
|
||||
});
|
||||
return {
|
||||
url: cacheMediaSource.urls[quality],
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "Youtube",
|
||||
author: '猫头猫',
|
||||
version: "0.0.1",
|
||||
supportedSearchType: ["music"],
|
||||
srcUrl: "https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/youtube/index.js",
|
||||
cacheControl: "no-cache",
|
||||
search,
|
||||
getMediaSource,
|
||||
};
|
||||
"use strict";
|
||||
Object.defineProperty(exports, "__esModule", { value: true });
|
||||
const axios_1 = require("axios");
|
||||
function formatMusicItem(item) {
|
||||
var _a, _b, _c, _d, _e, _f, _g;
|
||||
return {
|
||||
id: item.videoId,
|
||||
title: (_b = (_a = item.title.runs) === null || _a === void 0 ? void 0 : _a[0]) === null || _b === void 0 ? void 0 : _b.text,
|
||||
artist: (_d = (_c = item.ownerText.runs) === null || _c === void 0 ? void 0 : _c[0]) === null || _d === void 0 ? void 0 : _d.text,
|
||||
artwork: (_g = (_f = (_e = item === null || item === void 0 ? void 0 : item.thumbnail) === null || _e === void 0 ? void 0 : _e.thumbnails) === null || _f === void 0 ? void 0 : _f[0]) === null || _g === void 0 ? void 0 : _g.url,
|
||||
};
|
||||
}
|
||||
let lastQuery;
|
||||
let musicContinToken;
|
||||
async function searchMusic(query, page) {
|
||||
if (query !== lastQuery || page === 1) {
|
||||
musicContinToken = undefined;
|
||||
}
|
||||
lastQuery = query;
|
||||
let data = JSON.stringify({
|
||||
context: {
|
||||
client: {
|
||||
hl: "zh-CN",
|
||||
gl: "US",
|
||||
deviceMake: "",
|
||||
deviceModel: "",
|
||||
userAgent: "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/119.0.0.0 Safari/537.36 Edg/119.0.0.0,gzip(gfe)",
|
||||
clientName: "WEB",
|
||||
clientVersion: "2.20231121.08.00",
|
||||
osName: "Windows",
|
||||
osVersion: "10.0",
|
||||
platform: "DESKTOP",
|
||||
userInterfaceTheme: "USER_INTERFACE_THEME_LIGHT",
|
||||
browserName: "Edge Chromium",
|
||||
browserVersion: "119.0.0.0",
|
||||
acceptHeader: "text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.7",
|
||||
screenWidthPoints: 1358,
|
||||
screenHeightPoints: 1012,
|
||||
screenPixelDensity: 1,
|
||||
screenDensityFloat: 1.2395833730697632,
|
||||
utcOffsetMinutes: 480,
|
||||
memoryTotalKbytes: "8000000",
|
||||
mainAppWebInfo: {
|
||||
pwaInstallabilityStatus: "PWA_INSTALLABILITY_STATUS_UNKNOWN",
|
||||
webDisplayMode: "WEB_DISPLAY_MODE_BROWSER",
|
||||
isWebNativeShareAvailable: true,
|
||||
},
|
||||
timeZone: "Asia/Shanghai",
|
||||
},
|
||||
user: {
|
||||
lockedSafetyMode: false,
|
||||
},
|
||||
request: {
|
||||
useSsl: true,
|
||||
internalExperimentFlags: [],
|
||||
},
|
||||
},
|
||||
query: musicContinToken ? undefined : query,
|
||||
continuation: musicContinToken || undefined,
|
||||
});
|
||||
var config = {
|
||||
method: "post",
|
||||
url: "https://www.youtube.com/youtubei/v1/search?prettyPrint=false",
|
||||
headers: {
|
||||
"Content-Type": "text/plain",
|
||||
},
|
||||
data: data,
|
||||
};
|
||||
const response = (await (0, axios_1.default)(config)).data;
|
||||
const contents = response.contents.twoColumnSearchResultsRenderer.primaryContents
|
||||
.sectionListRenderer.contents;
|
||||
const isEndItem = contents.find((it) => {
|
||||
var _a, _b, _c;
|
||||
return ((_c = (_b = (_a = it.continuationItemRenderer) === null || _a === void 0 ? void 0 : _a.continuationEndpoint) === null || _b === void 0 ? void 0 : _b.continuationCommand) === null || _c === void 0 ? void 0 : _c.request) === "CONTINUATION_REQUEST_TYPE_SEARCH";
|
||||
});
|
||||
if (isEndItem) {
|
||||
musicContinToken =
|
||||
isEndItem.continuationItemRenderer.continuationEndpoint
|
||||
.continuationCommand.token;
|
||||
}
|
||||
const musicData = contents.find((it) => it.itemSectionRenderer)
|
||||
.itemSectionRenderer.contents;
|
||||
let resultMusicData = [];
|
||||
for (let i = 0; i < musicData.length; ++i) {
|
||||
if (musicData[i].videoRenderer) {
|
||||
resultMusicData.push(formatMusicItem(musicData[i].videoRenderer));
|
||||
}
|
||||
}
|
||||
return {
|
||||
isEnd: !isEndItem,
|
||||
data: resultMusicData,
|
||||
};
|
||||
}
|
||||
async function search(query, page, type) {
|
||||
if (type === "music") {
|
||||
return await searchMusic(query, page);
|
||||
}
|
||||
}
|
||||
let cacheMediaSource = {
|
||||
id: null,
|
||||
urls: {},
|
||||
};
|
||||
function getQuality(label) {
|
||||
if (label === "small") {
|
||||
return "standard";
|
||||
}
|
||||
else if (label === "tiny") {
|
||||
return "low";
|
||||
}
|
||||
else if (label === "medium") {
|
||||
return "high";
|
||||
}
|
||||
else if (label === "large") {
|
||||
return "super";
|
||||
}
|
||||
else {
|
||||
return "standard";
|
||||
}
|
||||
}
|
||||
async function getMediaSource(musicItem, quality) {
|
||||
var _a, _b;
|
||||
if (musicItem.id === cacheMediaSource.id) {
|
||||
return {
|
||||
url: cacheMediaSource.urls[quality],
|
||||
};
|
||||
}
|
||||
cacheMediaSource = {
|
||||
id: null,
|
||||
urls: {},
|
||||
};
|
||||
const data = {
|
||||
context: {
|
||||
client: {
|
||||
screenWidthPoints: 689,
|
||||
screenHeightPoints: 963,
|
||||
screenPixelDensity: 1,
|
||||
utcOffsetMinutes: 120,
|
||||
hl: "en",
|
||||
gl: "GB",
|
||||
remoteHost: "1.1.1.1",
|
||||
deviceMake: "",
|
||||
deviceModel: "",
|
||||
userAgent: "com.google.android.apps.youtube.music/6.14.50 (Linux; U; Android 13; GB) gzip",
|
||||
clientName: "ANDROID_MUSIC",
|
||||
clientVersion: "6.14.50",
|
||||
osName: "Android",
|
||||
osVersion: "13",
|
||||
originalUrl: "https://www.youtube.com/tv?is_account_switch=1&hrld=1&fltor=1",
|
||||
theme: "CLASSIC",
|
||||
platform: "MOBILE",
|
||||
clientFormFactor: "UNKNOWN_FORM_FACTOR",
|
||||
webpSupport: false,
|
||||
timeZone: "Europe/Amsterdam",
|
||||
acceptHeader: "text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,*/*;q=0.8",
|
||||
},
|
||||
user: { enableSafetyMode: false },
|
||||
request: {
|
||||
internalExperimentFlags: [],
|
||||
consistencyTokenJars: [],
|
||||
},
|
||||
},
|
||||
contentCheckOk: true,
|
||||
racyCheckOk: true,
|
||||
video_id: musicItem.id,
|
||||
};
|
||||
var config = {
|
||||
method: "post",
|
||||
url: "https://www.youtube.com/youtubei/v1/player?prettyPrint=false",
|
||||
headers: {
|
||||
"Content-Type": "application/json",
|
||||
},
|
||||
data: JSON.stringify(data),
|
||||
};
|
||||
const result = (await (0, axios_1.default)(config)).data;
|
||||
const formats = (_a = result.streamingData.formats) !== null && _a !== void 0 ? _a : [];
|
||||
const adaptiveFormats = (_b = result.streamingData.adaptiveFormats) !== null && _b !== void 0 ? _b : [];
|
||||
[...formats, ...adaptiveFormats].forEach((it) => {
|
||||
const q = getQuality(it.quality);
|
||||
if (q && it.url && !cacheMediaSource.urls[q]) {
|
||||
cacheMediaSource.urls[q] = it.url;
|
||||
}
|
||||
});
|
||||
return {
|
||||
url: cacheMediaSource.urls[quality],
|
||||
};
|
||||
}
|
||||
module.exports = {
|
||||
platform: "Youtube",
|
||||
author: '猫头猫',
|
||||
version: "0.0.1",
|
||||
supportedSearchType: ["music"],
|
||||
srcUrl: "https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/youtube/index.js",
|
||||
cacheControl: "no-cache",
|
||||
search,
|
||||
getMediaSource,
|
||||
};
|
||||
|
||||
@@ -1 +1 @@
|
||||
{"desc":"此链接为 MusicFree 插件,插件开发及使用方式参考 https://musicfree.upup.fun","plugins":[{"name":"bilibili","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/bilibili/index.js","version":"0.1.15"},{"name":"Audiomack","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/audiomack/index.js","version":"0.0.2"},{"name":"歌词千寻","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/geciqianxun/index.js","version":"0.0.0"},{"name":"歌词网","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/geciwang/index.js","version":"0.0.0"},{"name":"快手","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/kuaishou/index.js","version":"0.0.1"},{"name":"Navidrome","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/navidrome/index.js","version":"0.0.0"},{"name":"猫耳FM","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/maoerfm/index.js","version":"0.1.4"},{"name":"suno","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/suno/index.js","version":"0.0.0"},{"name":"udio","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/udio/index.js","version":"0.0.0"},{"name":"音悦台","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/yinyuetai/index.js","version":"0.0.1"},{"name":"WebDAV","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/webdav/index.js","version":"0.0.2"},{"name":"Youtube","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/youtube/index.js","version":"0.0.1"}]}
|
||||
{"desc":"此链接为 MusicFree 插件,插件开发及使用方式参考 https://musicfree.upup.fun","plugins":[{"name":"Audiomack","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/audiomack/index.js","version":"0.0.2"},{"name":"歌词千寻","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/geciqianxun/index.js","version":"0.0.0"},{"name":"bilibili","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/bilibili/index.js","version":"0.2.0"},{"name":"歌词网","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/geciwang/index.js","version":"0.0.0"},{"name":"suno","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/suno/index.js","version":"0.0.0"},{"name":"猫耳FM","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/maoerfm/index.js","version":"0.1.4"},{"name":"快手","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/kuaishou/index.js","version":"0.0.1"},{"name":"udio","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/udio/index.js","version":"0.0.0"},{"name":"Navidrome","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/navidrome/index.js","version":"0.0.0"},{"name":"WebDAV","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/webdav/index.js","version":"0.0.2"},{"name":"Youtube","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/youtube/index.js","version":"0.0.1"},{"name":"音悦台","url":"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/yinyuetai/index.js","version":"0.0.1"}]}
|
||||
@@ -521,10 +521,54 @@ async function importMusicSheet(urlLike: string) {
|
||||
}));
|
||||
}
|
||||
|
||||
function formatComment(item) {
|
||||
return {
|
||||
id: item.rpid,
|
||||
// 用户名
|
||||
nickName: item.member?.uname,
|
||||
// 头像
|
||||
avatar: item.member?.avatar,
|
||||
// 评论内容
|
||||
comment: item.content?.message,
|
||||
// 点赞数
|
||||
like: item.like,
|
||||
// 评论时间
|
||||
createAt: item.ctime * 1000,
|
||||
// 地址
|
||||
location: item.reply_control?.location?.startsWith("IP属地:") ? item.reply_control.location.slice(5): undefined
|
||||
}
|
||||
}
|
||||
|
||||
async function getMusicComments(musicItem) {
|
||||
const res = (await (axios.get("https://api.bilibili.com/x/v2/reply", {
|
||||
params: {
|
||||
type: 1,
|
||||
oid: musicItem.aid,
|
||||
mode: 3,
|
||||
plat: 1
|
||||
}
|
||||
}))).data;
|
||||
|
||||
const data = res.data.replies;
|
||||
|
||||
const comments = [];
|
||||
for (let i = 0; i < data.length; ++i) {
|
||||
comments[i] = formatComment(data[i]);
|
||||
if (data[i].replies?.length) {
|
||||
comments[i].replies = data[i]?.replies.map(formatComment);
|
||||
}
|
||||
}
|
||||
|
||||
return {
|
||||
isEnd: true,
|
||||
data: comments
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
platform: "bilibili",
|
||||
appVersion: ">=0.0",
|
||||
version: "0.1.15",
|
||||
version: "0.2.0",
|
||||
author: "猫头猫",
|
||||
cacheControl: "no-cache",
|
||||
srcUrl:
|
||||
@@ -579,6 +623,7 @@ module.exports = {
|
||||
getTopLists,
|
||||
getTopListDetail,
|
||||
importMusicSheet,
|
||||
getMusicComments
|
||||
};
|
||||
|
||||
// searchAlbum('周杰伦', 2)
|
||||
@@ -595,7 +640,7 @@ module.exports = {
|
||||
// }
|
||||
// }
|
||||
|
||||
// getMediaSource( {
|
||||
// getMediaComment( {
|
||||
// id: 'BV1r7411p7R4',
|
||||
// aid: 86670567,
|
||||
// bvid: 'BV1r7411p7R4',
|
||||
@@ -610,7 +655,7 @@ module.exports = {
|
||||
// '重新修复伪4K,修复仅为提升观感',
|
||||
// duration: 242,
|
||||
// date: '2020-02-04'
|
||||
// }, 'standard').then(console.log)
|
||||
// }).then(console.log)
|
||||
|
||||
// getArtistWorks({
|
||||
// name: '不想睡觉猫头猫',
|
||||
|
||||
@@ -1,169 +1,182 @@
|
||||
import axios from "axios";
|
||||
|
||||
const pageSize = 20;
|
||||
|
||||
function formatMusicItem(it){
|
||||
return {
|
||||
id: it.photo.id,
|
||||
title: it.photo.caption,
|
||||
artist: it.author.name,
|
||||
artwork: it.photo.coverUrl || it.photo.photoUrl,
|
||||
manifest: it.photo.manifest
|
||||
}
|
||||
}
|
||||
|
||||
async function searchMusic(query, page) {
|
||||
const body = {
|
||||
query: `fragment photoContent on PhotoEntity {
|
||||
__typename
|
||||
id
|
||||
duration
|
||||
caption
|
||||
originCaption
|
||||
likeCount
|
||||
viewCount
|
||||
commentCount
|
||||
realLikeCount
|
||||
coverUrl
|
||||
photoUrl
|
||||
photoH265Url
|
||||
manifest
|
||||
manifestH265
|
||||
videoResource
|
||||
coverUrls {
|
||||
url
|
||||
__typename
|
||||
}
|
||||
timestamp
|
||||
expTag
|
||||
animatedCoverUrl
|
||||
distance
|
||||
videoRatio
|
||||
liked
|
||||
stereoType
|
||||
profileUserTopPhoto
|
||||
musicBlocked
|
||||
}
|
||||
|
||||
fragment recoPhotoFragment on recoPhotoEntity {
|
||||
__typename
|
||||
id
|
||||
duration
|
||||
caption
|
||||
originCaption
|
||||
likeCount
|
||||
viewCount
|
||||
commentCount
|
||||
realLikeCount
|
||||
coverUrl
|
||||
photoUrl
|
||||
photoH265Url
|
||||
manifest
|
||||
manifestH265
|
||||
videoResource
|
||||
coverUrls {
|
||||
url
|
||||
__typename
|
||||
}
|
||||
timestamp
|
||||
expTag
|
||||
animatedCoverUrl
|
||||
distance
|
||||
videoRatio
|
||||
liked
|
||||
stereoType
|
||||
profileUserTopPhoto
|
||||
musicBlocked
|
||||
}
|
||||
|
||||
fragment feedContent on Feed {
|
||||
type
|
||||
author {
|
||||
id
|
||||
name
|
||||
headerUrl
|
||||
following
|
||||
headerUrls {
|
||||
url
|
||||
__typename
|
||||
}
|
||||
__typename
|
||||
}
|
||||
photo {
|
||||
...photoContent
|
||||
...recoPhotoFragment
|
||||
__typename
|
||||
}
|
||||
canAddComment
|
||||
llsid
|
||||
status
|
||||
currentPcursor
|
||||
tags {
|
||||
type
|
||||
name
|
||||
__typename
|
||||
}
|
||||
__typename
|
||||
}
|
||||
|
||||
query visionSearchPhoto($keyword: String, $pcursor: String, $searchSessionId: String, $page: String, $webPageArea: String) {
|
||||
visionSearchPhoto(keyword: $keyword, pcursor: $pcursor, searchSessionId: $searchSessionId, page: $page, webPageArea: $webPageArea) {
|
||||
result
|
||||
llsid
|
||||
webPageArea
|
||||
feeds {
|
||||
...feedContent
|
||||
__typename
|
||||
}
|
||||
searchSessionId
|
||||
pcursor
|
||||
aladdinBanner {
|
||||
imgUrl
|
||||
link
|
||||
__typename
|
||||
}
|
||||
__typename
|
||||
}
|
||||
}`,
|
||||
variables: {
|
||||
keyword: query,
|
||||
page: "search",
|
||||
pcursor: `${page - 1}`,
|
||||
},
|
||||
};
|
||||
const result = (await axios.post("https://www.kuaishou.com/graphql", body)).data.data.visionSearchPhoto;
|
||||
return {
|
||||
isEnd: !result?.pcursor || result?.pcursor === 'no_more',
|
||||
data: result?.feeds?.map?.(formatMusicItem)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
module.exports = {
|
||||
platform: "快手",
|
||||
version: "0.0.1",
|
||||
author: '猫头猫',
|
||||
srcUrl:
|
||||
"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/kuaishou/index.js",
|
||||
cacheControl: "no-cache",
|
||||
supportedSearchType: ["music"],
|
||||
async search(query, page, type) {
|
||||
if (type === "music") {
|
||||
return await searchMusic(query, page);
|
||||
}
|
||||
},
|
||||
async getMediaSource(musicItem, quality: IMusic.IQualityKey) {
|
||||
if(!musicItem.manifest) {
|
||||
return;
|
||||
}
|
||||
const adaptationSet = musicItem.manifest.adaptationSet;
|
||||
const representation = adaptationSet[0].representation;
|
||||
return {
|
||||
url: representation[0].url
|
||||
};
|
||||
|
||||
},
|
||||
};
|
||||
|
||||
|
||||
// searchMusic('夜曲', 1).then(e => console.log(e.data[1].manifest.adaptationSet[0].representation));
|
||||
import axios from "axios";
|
||||
|
||||
const pageSize = 20;
|
||||
|
||||
function formatMusicItem(it){
|
||||
return {
|
||||
id: it.photo.id,
|
||||
title: it.photo.caption,
|
||||
artist: it.author.name,
|
||||
artwork: it.photo.coverUrl || it.photo.photoUrl,
|
||||
manifest: it.photo.manifest
|
||||
}
|
||||
}
|
||||
|
||||
async function searchMusic(query, page) {
|
||||
const body = {
|
||||
query: `fragment photoContent on PhotoEntity {
|
||||
__typename
|
||||
id
|
||||
duration
|
||||
caption
|
||||
originCaption
|
||||
likeCount
|
||||
viewCount
|
||||
commentCount
|
||||
realLikeCount
|
||||
coverUrl
|
||||
photoUrl
|
||||
photoH265Url
|
||||
manifest
|
||||
manifestH265
|
||||
videoResource
|
||||
coverUrls {
|
||||
url
|
||||
__typename
|
||||
}
|
||||
timestamp
|
||||
expTag
|
||||
animatedCoverUrl
|
||||
distance
|
||||
videoRatio
|
||||
liked
|
||||
stereoType
|
||||
profileUserTopPhoto
|
||||
musicBlocked
|
||||
riskTagContent
|
||||
riskTagUrl
|
||||
}
|
||||
|
||||
fragment recoPhotoFragment on recoPhotoEntity {
|
||||
__typename
|
||||
id
|
||||
duration
|
||||
caption
|
||||
originCaption
|
||||
likeCount
|
||||
viewCount
|
||||
commentCount
|
||||
realLikeCount
|
||||
coverUrl
|
||||
photoUrl
|
||||
photoH265Url
|
||||
manifest
|
||||
manifestH265
|
||||
videoResource
|
||||
coverUrls {
|
||||
url
|
||||
__typename
|
||||
}
|
||||
timestamp
|
||||
expTag
|
||||
animatedCoverUrl
|
||||
distance
|
||||
videoRatio
|
||||
liked
|
||||
stereoType
|
||||
profileUserTopPhoto
|
||||
musicBlocked
|
||||
riskTagContent
|
||||
riskTagUrl
|
||||
}
|
||||
|
||||
fragment feedContent on Feed {
|
||||
type
|
||||
author {
|
||||
id
|
||||
name
|
||||
headerUrl
|
||||
following
|
||||
headerUrls {
|
||||
url
|
||||
__typename
|
||||
}
|
||||
__typename
|
||||
}
|
||||
photo {
|
||||
...photoContent
|
||||
...recoPhotoFragment
|
||||
__typename
|
||||
}
|
||||
canAddComment
|
||||
llsid
|
||||
status
|
||||
currentPcursor
|
||||
tags {
|
||||
type
|
||||
name
|
||||
__typename
|
||||
}
|
||||
__typename
|
||||
}
|
||||
|
||||
query visionSearchPhoto($keyword: String, $pcursor: String, $searchSessionId: String, $page: String, $webPageArea: String) {
|
||||
visionSearchPhoto(keyword: $keyword, pcursor: $pcursor, searchSessionId: $searchSessionId, page: $page, webPageArea: $webPageArea) {
|
||||
result
|
||||
llsid
|
||||
webPageArea
|
||||
feeds {
|
||||
...feedContent
|
||||
__typename
|
||||
}
|
||||
searchSessionId
|
||||
pcursor
|
||||
aladdinBanner {
|
||||
imgUrl
|
||||
link
|
||||
__typename
|
||||
}
|
||||
__typename
|
||||
}
|
||||
}`,
|
||||
variables: {
|
||||
keyword: query,
|
||||
page: "search",
|
||||
pcursor: `${page - 1}`,
|
||||
},
|
||||
};
|
||||
const result = (await axios.post("https://www.kuaishou.com/graphql", body, {
|
||||
headers: {
|
||||
'user-agent': "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/128.0.0.0 Safari/537.36",
|
||||
host: 'www.kuaishou.com',
|
||||
origin: 'https://www.kuaishou.com',
|
||||
referer: `https://www.kuaishou.com/search/video?searchKey=${encodeURIComponent((query))}`,
|
||||
|
||||
|
||||
}
|
||||
})).data.data.visionSearchPhoto;
|
||||
return {
|
||||
isEnd: !result?.pcursor || result?.pcursor === 'no_more',
|
||||
data: result?.feeds?.map?.(formatMusicItem)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
module.exports = {
|
||||
platform: "快手",
|
||||
version: "0.0.2",
|
||||
author: '猫头猫',
|
||||
srcUrl:
|
||||
"https://gitee.com/maotoumao/MusicFreePlugins/raw/v0.1/dist/kuaishou/index.js",
|
||||
cacheControl: "no-cache",
|
||||
supportedSearchType: ["music"],
|
||||
async search(query, page, type) {
|
||||
if (type === "music") {
|
||||
return await searchMusic(query, page);
|
||||
}
|
||||
},
|
||||
async getMediaSource(musicItem, quality) {
|
||||
if(!musicItem.manifest) {
|
||||
return;
|
||||
}
|
||||
const adaptationSet = musicItem.manifest.adaptationSet;
|
||||
const representation = adaptationSet[0].representation;
|
||||
return {
|
||||
url: representation[0].url
|
||||
};
|
||||
|
||||
},
|
||||
};
|
||||
|
||||
|
||||
// searchMusic('夜曲', 1).then(e => console.log(e.data[1].manifest.adaptationSet[0].representation));
|
||||
|
||||
17
test/geciqianxun.ts
Normal file
17
test/geciqianxun.ts
Normal file
@@ -0,0 +1,17 @@
|
||||
const plugin = require('../plugins/geciqianxun');
|
||||
|
||||
|
||||
async function run() {
|
||||
// 测试搜索歌词
|
||||
const searchResult = await plugin.search('七里香', 1, 'lyric');
|
||||
console.log(searchResult);
|
||||
|
||||
if (searchResult.data.length > 0) {
|
||||
const musicItem = searchResult.data[0];
|
||||
const lyricResult = await plugin.getLyric(musicItem);
|
||||
console.log(lyricResult);
|
||||
}
|
||||
}
|
||||
|
||||
run();
|
||||
|
||||
17
test/geciwang.ts
Normal file
17
test/geciwang.ts
Normal file
@@ -0,0 +1,17 @@
|
||||
const plugin = require('../plugins/geciwang');
|
||||
|
||||
|
||||
async function run() {
|
||||
// 测试搜索歌词
|
||||
const searchResult = await plugin.search('七里香', 1, 'lyric');
|
||||
console.log(searchResult);
|
||||
|
||||
if (searchResult.data.length > 0) {
|
||||
const musicItem = searchResult.data[0];
|
||||
const lyricResult = await plugin.getLyric(musicItem);
|
||||
console.log(lyricResult);
|
||||
}
|
||||
}
|
||||
|
||||
run();
|
||||
|
||||
18
test/kuaishou.ts
Normal file
18
test/kuaishou.ts
Normal file
@@ -0,0 +1,18 @@
|
||||
const plugin = require('../plugins/kuaishou');
|
||||
|
||||
|
||||
async function run() {
|
||||
// 搜索歌曲
|
||||
const res = await plugin.search('七里香', 1,'music');
|
||||
|
||||
console.log(res);
|
||||
|
||||
if (res.data.length > 0) {
|
||||
const musicItem = res.data[0];
|
||||
const sourceResult = await plugin.getMediaSource(musicItem, 'standard');
|
||||
console.log(sourceResult);
|
||||
}
|
||||
}
|
||||
|
||||
run();
|
||||
|
||||
@@ -1,17 +1,17 @@
|
||||
{
|
||||
"compilerOptions": {
|
||||
"noImplicitAny": false,
|
||||
"noEmitOnError": true,
|
||||
"removeComments": true,
|
||||
"allowJs": true,
|
||||
"sourceMap": false,
|
||||
"module": "CommonJS",
|
||||
"target": "ES2017",
|
||||
"outDir": "dist",
|
||||
"baseUrl": "./",
|
||||
},
|
||||
"include": [
|
||||
"./types/*",
|
||||
"./plugins/*/index.ts"
|
||||
]
|
||||
}
|
||||
{
|
||||
"compilerOptions": {
|
||||
"noImplicitAny": false,
|
||||
"noEmitOnError": true,
|
||||
"removeComments": true,
|
||||
"allowJs": true,
|
||||
"sourceMap": false,
|
||||
"module": "CommonJS",
|
||||
"target": "ES2017",
|
||||
"outDir": "dist",
|
||||
"baseUrl": "./",
|
||||
},
|
||||
"include": [
|
||||
"./types/*",
|
||||
"./plugins/*/index.ts"
|
||||
]
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user