feat: add open review deny log and max denies restriction (#510)

* feat: add open review log channel and embed

* chore: do not include submit page

* chore: mention instead of date

* feat: add max denies error

* typo: 더 이상

Co-authored-by: Junseo Park <wonderlandpark@outlook.kr>

* feat: add exceptions to deny count

* fix: invalid embed used

Co-authored-by: Junseo Park <wonderlandpark@outlook.kr>

* fix: invalid guild

Co-authored-by: Junseo Park <wonderlandpark@outlook.kr>

* fix: invalid position

Co-authored-by: Junseo Park <wonderlandpark@outlook.kr>

* fix: proper reason check position

Co-authored-by: Junseo Park <wonderlandpark@outlook.kr>

* feat: sepcific error message

* refactor: change reason embed format

* fix: knex andWhereNot method to whereNotIn method

Co-authored-by: Junseo Park <wonderlandpark@outlook.kr>
This commit is contained in:
Eunwoo Choi 2022-08-15 21:22:55 +09:00 committed by GitHub
parent ca55dc8597
commit 516f72ad08
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 29 additions and 15 deletions

View File

@ -76,6 +76,12 @@ const Bots = RequestHandler()
message: '디스코드 서버에 참가해주세요.',
errors: ['봇 신청하시기 위해서는 공식 디스코드 서버에 참가해주셔야합니다.'],
})
else if (result === 5)
return ResponseWrapper(res, {
code: 403,
message: '더 이상 해당 봇에 대한 심사 요청을 하실 수 없습니다.',
errors: ['해당 봇은 심사에서 3회 이상 거부되었습니다. 더 이상의 심사를 요청하실 수 없습니다.', '이의 제기를 원하시는 경우 디스코드 서버를 통해 문의해주세요.'],
})
get.botSubmits.clear(user)
await discordLog('BOT/SUBMIT', user, new MessageEmbed().setDescription(`[${result.id}/${result.date}](${KoreanbotsEndPoints.URL.submittedBot(result.id, result.date)})`), {
@ -154,7 +160,7 @@ const Bots = RequestHandler()
)
return ResponseWrapper(res, { code: 200 })
}
})
interface GetApiRequest extends NextApiRequest {

View File

@ -5,7 +5,7 @@ import tracer from 'dd-trace'
import RequestHandler from '@utils/RequestHandler'
import ResponseWrapper from '@utils/ResponseWrapper'
import { get, update } from '@utils/Query'
import { DiscordBot, getBotReviewLogChannel } from '@utils/DiscordBot'
import { DiscordBot, getBotReviewLogChannel, getOpenBotReviewLogChannel } from '@utils/DiscordBot'
import { BotSubmissionDenyReasonPresetsName, KoreanbotsEndPoints } from '@utils/Constants'
const DenyBotSubmit = RequestHandler()
@ -20,6 +20,9 @@ const DenyBotSubmit = RequestHandler()
const embed = new MessageEmbed().setTitle('거부').setColor('RED').setDescription(`[${submit.id}/${submit.date}](${KoreanbotsEndPoints.URL.submittedBot(submit.id, submit.date)})`).setTimestamp()
if(req.body.reviewer || req.body.reason) embed.addField('📃 정보', `${req.body.reason ? `사유: ${BotSubmissionDenyReasonPresetsName[req.body.reason] || req.body.reason}\n`: ''}${req.body.reviewer ? `심사자: ${req.body.reviewer}` : ''}`)
await getBotReviewLogChannel().send(embed)
const openEmbed = new MessageEmbed().setTitle('거부').setColor('RED').setDescription(`<@${submit.id}> (${submit.id})`).setTimestamp()
if(req.body.reason) openEmbed.addField('📃 사유', `${req.body.reason ? `${BotSubmissionDenyReasonPresetsName[req.body.reason] || req.body.reason}\n`: '없음'}`)
await getOpenBotReviewLogChannel().send(openEmbed)
tracer.trace('botSubmits.deny', span => {
span.setTag('id', submit.id)
span.setTag('date', submit.date)
@ -41,4 +44,4 @@ interface ApiRequest extends NextApiRequest {
}
}
export default DenyBotSubmit
export default DenyBotSubmit

View File

@ -10,6 +10,7 @@ const statsLoggingChannelID = '653227346962153472'
const reviewGuildID = '906537041326637086'
const botReviewLogChannelID = '906551334063439902'
const openBotReviewLogChannelID = '1008376563731013643'
DiscordBot.on('ready', async () => {
console.log('I\'m Ready')
@ -25,9 +26,10 @@ export const getReportChannel = (): Discord.TextChannel => getMainGuild().channe
export const getLoggingChannel = (): Discord.TextChannel => getMainGuild().channels.cache.get(loggingChannelID) as Discord.TextChannel
export const getBotReviewLogChannel = (): Discord.TextChannel => getReviewGuild().channels.cache.get(botReviewLogChannelID) as Discord.TextChannel
export const getStatsLoggingChannel = (): Discord.TextChannel => getMainGuild().channels.cache.get(statsLoggingChannelID) as Discord.TextChannel
export const getOpenBotReviewLogChannel = (): Discord.TextChannel => getMainGuild().channels.cache.get(openBotReviewLogChannelID) as Discord.TextChannel
export const discordLog = async (type: string, issuerID: string, embed?: Discord.MessageEmbed, attachment?: { content: string, format: string}, content?: string): Promise<void> => {
getLoggingChannel().send({
getLoggingChannel().send({
content: `[${type}] <@${issuerID}> (${issuerID})\n${content || ''}`,
embed: embed && embed.setTitle(type).setTimestamp(new Date()),
...(attachment && { files: [
@ -35,4 +37,4 @@ export const discordLog = async (type: string, issuerID: string, embed?: Discord
]
})
})
}
}

View File

@ -66,7 +66,7 @@ async function getBot(id: string, topLevel=true):Promise<Bot> {
}
await knex('bots').update({ name: discordBot.username }).where({ id })
}
return res[0] ?? null
@ -388,12 +388,15 @@ async function voteServer(userID: string, serverID: string): Promise<number|bool
* @returns 2 - Already submitted ID
* @returns 3 - Bot User does not exists
* @returns 4 - Discord not Joined
* @returns 5 - 3 or more denies
* @returns obj - Success
*/
async function submitBot(id: string, data: AddBotSubmit):Promise<1|2|3|4|SubmittedBot> {
async function submitBot(id: string, data: AddBotSubmit):Promise<1|2|3|4|5|SubmittedBot> {
const submits = await knex('submitted').select(['id']).where({ state: 0 }).andWhere('owners', 'LIKE', `%${id}%`)
if(submits.length > 1) return 1
const botId = data.id
const identicalSubmits = await knex('submitted').select(['id']).where({ id: botId, state: 2 }).whereNotIn('reason', ['PRIVATE', 'OFFLINE', 'ABSENT_AT_DISCORD']) // 다음 사유를 제외한 다른 사유의 3회 이상 거부 존재시 봇 등록 제한.
if(identicalSubmits.length >= 3) return 5
const date = Math.round(+new Date()/1000)
const sameID = await knex('submitted').select(['id']).where({ id: botId, state: 0 })
const bot = await get.bot.load(data.id)
@ -417,7 +420,7 @@ async function submitBot(id: string, data: AddBotSubmit):Promise<1|2|3|4|Submitt
discord: data.discord,
state: 0
})
return await getBotSubmit(botId, date)
}
@ -565,8 +568,8 @@ async function getDiscordUser(id: string):Promise<DiscordUser> {
}
/**
*
* @param info
*
* @param info
* @returns 1 - UnVerified
* @returns 2 - Blocked
*/
@ -747,14 +750,14 @@ export const get = {
serverSpec: getServerSpec,
list: {
category: new DataLoader(
async (key: string[]) =>
async (key: string[]) =>
(await Promise.all(key.map(async (k: string) => {
const json = JSON.parse(k)
return await getBotList('CATEGORY', json.page, json.category)
}))).map(row => serialize(row))
, { cacheMap: new TLRU({ maxStoreSize: 50, maxAgeMs: 500000 }) }),
search: new DataLoader(
async (key: string[]) =>
async (key: string[]) =>
(await Promise.all(key.map(async (k: string) => {
const json = JSON.parse(k)
const res = await getBotList('SEARCH', json.page, json.query)
@ -776,14 +779,14 @@ export const get = {
},
serverList: {
category: new DataLoader(
async (key: string[]) =>
async (key: string[]) =>
(await Promise.all(key.map(async (k: string) => {
const json = JSON.parse(k)
return await getServerList('CATEGORY', json.page, json.category)
}))).map(row => serialize(row))
, { cacheMap: new TLRU({ maxStoreSize: 50, maxAgeMs: 500000 }) }),
search: new DataLoader(
async (key: string[]) =>
async (key: string[]) =>
(await Promise.all(key.map(async (k: string) => {
const json = JSON.parse(k)
const res = await getServerList('SEARCH', json.page, json.query)
@ -857,4 +860,4 @@ export const ratelimit = {
addRequest(ip, imageRateLimit)
return imageRateLimit.get(ip)
}
}
}