Skip to content

Commit

Permalink
Hitokoto-api v1.1.0
Browse files Browse the repository at this point in the history
  • Loading branch information
a632079 committed Feb 21, 2018
1 parent 5d2f8f8 commit 1b3c964
Show file tree
Hide file tree
Showing 4 changed files with 120 additions and 100 deletions.
5 changes: 3 additions & 2 deletions package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "Hitokoto-api",
"version": "1.0.1",
"name": "hitokoto",
"version": "1.1.0",
"description": "Fast & Powerful Hitokoto API Framework.",
"main": "core.js",
"engines": {
Expand Down Expand Up @@ -56,6 +56,7 @@
"nconf": "^0.10.0",
"nodemailer": "^4.4.2",
"passthrough-counter": "^1.0.0",
"pify": "^3.0.0",
"redis": "^2.8.0",
"sequelize": "^4.32.2",
"simple-netease-cloud-music": "git+https://github.com/a632079/simple-netease-cloud-music.git",
Expand Down
9 changes: 9 additions & 0 deletions shrinkwrap.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ dependencies:
nconf: 0.10.0
nodemailer: 4.4.2
passthrough-counter: 1.0.0
pify: 3.0.0
redis: 2.8.0
sequelize: 4.33.4
simple-netease-cloud-music: github.com/a632079/simple-netease-cloud-music/6138128704a2e59766311f884da60e627e9e720c
Expand Down Expand Up @@ -1990,6 +1991,13 @@ packages:
resolution:
integrity: sha1-7RQaasBDqEnqWISY59yosVMw6Qw=
tarball: 'http://registry.npm.taobao.org/pify/download/pify-2.3.0.tgz'
/pify/3.0.0:
dev: false
engines:
node: '>=4'
resolution:
integrity: sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=
tarball: 'http://registry.npm.taobao.org/pify/download/pify-3.0.0.tgz'
/pinkie-promise/2.0.1:
dependencies:
pinkie: 2.0.4
Expand Down Expand Up @@ -2729,6 +2737,7 @@ specifiers:
nodemailer: ^4.4.2
nyc: ^11.4.1
passthrough-counter: ^1.0.0
pify: ^3.0.0
redis: ^2.8.0
sequelize: ^4.32.2
simple-netease-cloud-music: 'git+https://github.com/a632079/simple-netease-cloud-music.git'
Expand Down
202 changes: 104 additions & 98 deletions src/controllers/netease.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
// Import Packages
const NeteaseMusic = require('simple-netease-cloud-music')
const async = require('async')
const pify = require('pify')
const cache = require('../cache')
const nm = new NeteaseMusic()

Expand All @@ -17,17 +19,19 @@ controllers.summary = async (ctx, next) => {
// Without Check song whether is blocked
const ret = await quickSummary(id, ctx)
if (ret) {
const data = ret.data
data.ids = ret.ids
const data = ctx.query && ctx.query.common ? handleResult(ret, true) : handleResult(ret)
data.code = 200
data.message = 'ok'
ctx.body = data
} else {
Response400(ctx)
}
} else {
const ret = await silentSummary(id, ctx)
if (ret) {
const data = ret.data
data.ids = ret.ids
const data = ctx.query && ctx.query.common ? handleResult(ret, true) : handleResult(ret)
data.code = 200
data.message = 'ok'
ctx.body = data
} else {
Response400(ctx)
Expand Down Expand Up @@ -55,6 +59,7 @@ controllers.search = async (ctx, next) => {
cache.set('nm:search:' + ctx.params.id, ret, 60 * 60 * 2) // Cache 2 Hour
}
ctx.body = ret || {
code: 400,
message: 'API 在请求时出现了问题,再试一下看看?',
feedback: '访问 /status 获得详细信息',
now: new Date().toString()
Expand All @@ -71,6 +76,7 @@ controllers.playlist = async (ctx, next) => {
cache.set('nm:playlist:' + ctx.params.id, ret, 60 * 60 * 2) // Cache 2 Hour
}
ctx.body = ret || {
code: 400,
message: 'API 在请求时出现了问题,再试一下看看?',
feedback: '访问 /status 获得详细信息',
now: new Date().toString()
Expand All @@ -81,6 +87,7 @@ controllers.playlist = async (ctx, next) => {
controllers.picture = async (ctx, next) => {
const ret = ctx.params.height ? await nm.picture(ctx.params.id, ctx.params.height) : await nm.picture(ctx.params.id)
ctx.body = ret || {
code: 400,
message: 'API 在请求时出现了问题,再试一下看看?',
feedback: '访问 /status 获得详细信息',
now: new Date().toString()
Expand All @@ -97,6 +104,7 @@ controllers.artist = async (ctx, next) => {
cache.set('nm:artist:' + ctx.params.id, ret, 60 * 60 * 2) // Cache 2 Hour
}
ctx.body = ret || {
code: 400,
message: 'API 在请求时出现了问题,再试一下看看?',
feedback: '访问 /status 获得详细信息',
now: new Date().toString()
Expand All @@ -113,6 +121,7 @@ controllers.album = async (ctx, next) => {
cache.set('nm:album:' + ctx.params.id, ret, 60 * 60 * 2) // Cache 2 Hour
}
ctx.body = ret || {
code: 400,
message: 'API 在请求时出现了问题,再试一下看看?',
feedback: '访问 /status 获得详细信息',
now: new Date().toString()
Expand All @@ -129,6 +138,7 @@ controllers.lyric = async (ctx, next) => {
cache.set('nm:lyric:' + ctx.params.id, ret, 60 * 60 * 2) // Cache 2 Hour
}
ctx.body = ret || {
code: 400,
message: 'API 在请求时出现了问题,再试一下看看?',
feedback: '访问 /status 获得详细信息',
now: new Date().toString()
Expand All @@ -139,6 +149,7 @@ controllers.lyric = async (ctx, next) => {
controllers.url = async (ctx, next) => {
const ret = await nm.url(ctx.params.id)
ctx.body = ret || {
code: 400,
message: 'API 在请求时出现了问题,再试一下看看?',
feedback: '访问 /status 获得详细信息',
now: new Date().toString()
Expand All @@ -155,6 +166,7 @@ controllers.detail = async (ctx, next) => {
cache.set('nm:detail:' + ctx.params.id, ret, 60 * 60 * 2)
}
ctx.body = ret || {
code: 400,
message: 'API 在请求时出现了问题,再试一下看看?',
feedback: '访问 /status 获得详细信息',
now: new Date().toString()
Expand All @@ -166,6 +178,7 @@ const Response400 = (ctx, code = 0) => {
case 1:
ctx.status = 400
ctx.body = {
code: 400,
message: 'id 数超出限制,最多为 20 个',
feedback: '访问 /status 获得详细信息',
ts: Date.now()
Expand All @@ -175,6 +188,7 @@ const Response400 = (ctx, code = 0) => {
default:
ctx.status = 400
ctx.body = {
code: 400,
message: '请求错误,乐曲不存在或者版权受限',
feedback: '访问 /status 获得详细信息',
ts: Date.now()
Expand All @@ -188,60 +202,22 @@ const silentSummary = async (id, ctx) => {
const URLs = await nm.url(id)
if (URLs && URLs.data && URLs.data.length > 0) {
const ids = []
const data = {}
for (let _ of URLs.data) {
if (_.code !== 404 && _.url) {
ids.push(_.id)
data[_.id] = {}
data[_.id].url = 'https://api.a632079.me/nm/redirect/music/' + _.id

// Get Music Detail
let detail
if (await cache.get('nm:detail:' + _.id)) {
detail = await cache.get('nm:detail:' + _.id)
} else {
detail = await nm.song(_.id.toString())
cache.set('nm:detail:' + _.id, detail, 60 * 60 * 24 * 7) // Cache 7 D
}
data[_.id].name = detail.songs[0].name
data[_.id].artists = []
for (let artist of detail.songs[0].ar) {
data[_.id].artists.push(artist.name)
}
data[_.id].album = {}
data[_.id].album.id = detail.songs[0].al.id
data[_.id].album.name = detail.songs[0].al.name

let album
if (await cache.get('nm:album:' + detail.songs[0].al.id)) {
album = await cache.get('nm:album:' + detail.songs[0].al.id)
} else {
album = await nm.album(detail.songs[0].al.id.toString())
cache.set('nm:album:' + detail.songs[0].al.id, album, 60 * 60 * 24 * 7) // Cache 7 D
}
data[_.id].album.picture = (await nm.picture(album.songs[0].al.pic_str)).url

// Get Lyric
if (ctx.query && ctx.query.lyric) {
let lyric
if (await cache.get('nm:lyric:' + _.id)) {
lyric = await cache.get('nm:lyric:' + _.id)
} else {
lyric = await nm.lyric(_.id.toString())
cache.set('nm:lyric:' + _.id, lyric, 60 * 60 * 24 * 7) // Cache 7 D
}

data[_.id].lyric = {}
data[_.id].lyric.base = (lyric.lrc && lyric.lrc.lyric) ? lyric.lrc.lyric : '[00:00.00] 纯音乐,敬请聆听。\n'
data[_.id].lyric.translate = (lyric.tlyric && lyric.tlyric.lyric) ? lyric.tlyric.lyric : null
}
}
}
if (ids.length > 0) {
const ret = {}
ret.ids = ids
ret.data = data
return ret
const result = await pify(async).mapLimit(ids, 5, async id => {
if (ctx.query && ctx.query.lyric) {
const ret = await Promise.all([handleSummary(id, true), getLyric(id, true)])
return ret
} else {
const ret = await Promise.all([handleSummary(id, true)])
return ret
}
})
return result
} else {
return false
}
Expand All @@ -252,60 +228,90 @@ const silentSummary = async (id, ctx) => {

const quickSummary = async (ID, ctx) => {
const ids = ID.split(',')
const data = {}
for (let id of ids) {
data[id] = {}
data[id].url = 'https://api.a632079.me/nm/redirect/music/' + id

// Get Music Detail
let detail
if (await cache.get('nm:detail:' + id)) {
detail = await cache.get('nm:detail:' + id)
const result = await pify(async).mapLimit(ids, 5, async id => {
if (ctx.query && ctx.query.lyric) {
return Promise.all([handleSummary(id), getLyric(id)])
} else {
detail = await nm.song(id.toString())
cache.set('nm:detail:' + id, detail, 60 * 60 * 2) // Cache 2 Hour
}
data[id].name = detail.songs[0].name
data[id].artists = []
for (let artist of detail.songs[0].ar) {
data[id].artists.push(artist.name)
return Promise.all([handleSummary(id)])
}
data[id].album = {}
data[id].album.id = detail.songs[0].al.id
data[id].album.name = detail.songs[0].al.name
})
return result
}

let album
if (await cache.get('nm:album:' + detail.songs[0].al.id)) {
album = await cache.get('nm:album:' + detail.songs[0].al.id)
} else {
album = await nm.album(detail.songs[0].al.id.toString())
cache.set('nm:album:' + detail.songs[0].al.id, album, 60 * 60 * 2) // Cache 2 Hour
}
data[id].album.picture = (await nm.picture(album.songs[0].al.pic_str)).url
const handleSummary = async (id, check = false) => {
const cacheTime = check ? 60 * 60 * 24 * 7 : 60 * 60 * 2
const data = {}
data.id = id
data.url = 'https://api.a632079.me/nm/redirect/music/' + id

// Get Lyric
if (ctx.query && ctx.query.lyric) {
let lyric
if (await cache.get('nm:lyric:' + id)) {
lyric = await cache.get('nm:lyric:' + id)
} else {
lyric = await nm.lyric(id.toString())
cache.set('nm:lyric:' + id, lyric, 60 * 60 * 2) // Cache 2 Hour
}
// Get Music Detail
let detail
if (await cache.get('nm:detail:' + id)) {
detail = await cache.get('nm:detail:' + id)
} else {
detail = await nm.song(id.toString())
cache.set('nm:detail:' + id, detail, cacheTime)
}
data.name = detail.songs[0].name
data.artists = []
for (let artist of detail.songs[0].ar) {
data.artists.push(artist.name)
}
data.album = {}
data.album.id = detail.songs[0].al.id
data.album.name = detail.songs[0].al.name

data[id].lyric = {}
data[id].lyric.base = (lyric.lrc && lyric.lrc.lyric) ? lyric.lrc.lyric : '[00:00.00] 纯音乐,敬请聆听。\n'
data[id].lyric.translate = (lyric.tlyric && lyric.tlyric.lyric) ? lyric.tlyric.lyric : null
}
let album
if (await cache.get('nm:album:' + detail.songs[0].al.id)) {
album = await cache.get('nm:album:' + detail.songs[0].al.id)
} else {
album = await nm.album(detail.songs[0].al.id.toString())
cache.set('nm:album:' + detail.songs[0].al.id, album, cacheTime) // Cache 2 Hour
}
data.album.picture = (await nm.picture(album.songs[0].al.pic_str)).url
return data
}

if (ids.length > 0) {
const ret = {}
ret.ids = ids
ret.data = data
return ret
const getLyric = async (id, check = false) => {
const cacheTime = check ? 60 * 60 * 24 * 7 : 60 * 60 * 2
// Get Lyric
let lyric
if (await cache.get('nm:lyric:' + id)) {
lyric = await cache.get('nm:lyric:' + id)
} else {
return false
lyric = await nm.lyric(id.toString())
cache.set('nm:lyric:' + id, lyric, cacheTime)
}
const data = {}
data.id = id
data.lyric = {}
data.lyric.base = (lyric.lrc && lyric.lrc.lyric) ? lyric.lrc.lyric : '[00:00.00] 纯音乐,敬请聆听。\n'
data.lyric.translate = (lyric.tlyric && lyric.tlyric.lyric) ? lyric.tlyric.lyric : null
return data
}

const handleResult = (result, common = false) => {
const data = {}
const ids = []
for (let _ of result) {
const id = _[0].id
ids.push(id)
if (common) {
data.songs = []
const song = {}
for (let $ of _) {
Object.assign(song, $)
}
data.songs.push(song)
} else {
data[id] = {}
for (let $ of _) {
Object.assign(data[id], $)
}
}
}
data.ids = ids
return data
}

module.exports = controllers
4 changes: 4 additions & 0 deletions yarn.lock
Original file line number Diff line number Diff line change
Expand Up @@ -2021,6 +2021,10 @@ pify@^2.0.0:
version "2.3.0"
resolved "http://registry.npm.taobao.org/pify/download/pify-2.3.0.tgz#ed141a6ac043a849ea588498e7dca8b15330e90c"

pify@^3.0.0:
version "3.0.0"
resolved "http://registry.npm.taobao.org/pify/download/pify-3.0.0.tgz#e5a4acd2c101fdf3d9a4d07f0dbc4db49dd28176"

pinkie-promise@^2.0.0:
version "2.0.1"
resolved "http://registry.npm.taobao.org/pinkie-promise/download/pinkie-promise-2.0.1.tgz#2135d6dfa7a358c069ac9b178776288228450ffa"
Expand Down

0 comments on commit 1b3c964

Please sign in to comment.