Skip to content

Commit

Permalink
feat(core): emit before-send event; sender.sendMsg()
Browse files Browse the repository at this point in the history
  • Loading branch information
shigma committed Jan 23, 2020
1 parent ba28276 commit 1c3cfee
Show file tree
Hide file tree
Showing 4 changed files with 70 additions and 7 deletions.
3 changes: 2 additions & 1 deletion packages/koishi-core/src/meta.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,10 @@
import { User, Group } from './database'

export type PostType = 'message' | 'notice' | 'request' | 'meta_event' | 'send'
export type MessageType = 'private' | 'group' | 'discuss'

export interface MetaTypeMap {
message: 'private' | 'group' | 'discuss'
message: MessageType
notice: 'group_upload' | 'group_admin' | 'group_increase' | 'group_decrease' | 'group_ban' | 'friend_add'
request: 'friend' | 'group'
// eslint-disable-next-line camelcase
Expand Down
41 changes: 36 additions & 5 deletions packages/koishi-core/src/sender.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ import {
VipInfo,
GroupNoticeInfo,
ContextType,
MessageType,
} from './meta'

export class SenderError extends Error {
Expand Down Expand Up @@ -102,8 +103,7 @@ export class Sender {
}
}

_createSendMeta ($ctxType: ContextType, $ctxId: number, message: string) {
const sendType = $ctxType === 'user' ? 'private' : $ctxType as any
_createSendMeta (sendType: MessageType, $ctxType: ContextType, $ctxId: number, message: string) {
return {
$ctxId,
$ctxType,
Expand All @@ -115,10 +115,35 @@ export class Sender {
} as Meta<'send'>
}

async sendMsg (type: MessageType, ctxId: number, message: string, autoEscape = false) {
this._assertElement('type', type, ['private', 'group', 'discuss'])
const ctxType = type === 'private' ? 'user' : type
const ctxIdKey = ctxType + 'Id'
this._assertInteger(ctxIdKey, ctxId)
if (!message) return
const meta = this._createSendMeta(type, ctxType, ctxId, message)
this.app.emitEvent(meta, 'before-send', meta)
const { messageId } = await this.get<MessageResponse>('send_msg', { [ctxIdKey]: ctxId, message, autoEscape })
meta.messageId = messageId
this.app.emitEvent(meta, 'send', meta)
return messageId
}

async sendMsgAsync (type: MessageType, ctxId: number, message: string, autoEscape = false) {
this._assertElement('type', type, ['private', 'group', 'discuss'])
const ctxType = type === 'private' ? 'user' : type
const ctxIdKey = ctxType + 'Id'
this._assertInteger(ctxIdKey, ctxId)
if (!message) return
const meta = this._createSendMeta(type, ctxType, ctxId, message)
this.app.emitEvent(meta, 'before-send', meta)
await this.get('send_msg_async', { [ctxIdKey]: ctxId, message, autoEscape })
}

async sendGroupMsg (groupId: number, message: string, autoEscape = false) {
this._assertInteger('groupId', groupId)
if (!message) return
const meta = this._createSendMeta('group', groupId, message)
const meta = this._createSendMeta('group', 'group', groupId, message)
this.app.emitEvent(meta, 'before-send', meta)
const { messageId } = await this.get<MessageResponse>('send_group_msg', { groupId, message, autoEscape })
meta.messageId = messageId
Expand All @@ -129,13 +154,15 @@ export class Sender {
async sendGroupMsgAsync (groupId: number, message: string, autoEscape = false) {
this._assertInteger('groupId', groupId)
if (!message) return
const meta = this._createSendMeta('group', 'group', groupId, message)
this.app.emitEvent(meta, 'before-send', meta)
await this.get('send_group_msg_async', { groupId, message, autoEscape })
}

async sendDiscussMsg (discussId: number, message: string, autoEscape = false) {
this._assertInteger('discussId', discussId)
if (!message) return
const meta = this._createSendMeta('discuss', discussId, message)
const meta = this._createSendMeta('discuss', 'discuss', discussId, message)
this.app.emitEvent(meta, 'before-send', meta)
const { messageId } = await this.get<MessageResponse>('send_discuss_msg', { discussId, message, autoEscape })
meta.messageId = messageId
Expand All @@ -146,13 +173,15 @@ export class Sender {
async sendDiscussMsgAsync (discussId: number, message: string, autoEscape = false) {
this._assertInteger('discussId', discussId)
if (!message) return
const meta = this._createSendMeta('discuss', 'discuss', discussId, message)
this.app.emitEvent(meta, 'before-send', meta)
await this.get('send_discuss_msg_async', { discussId, message, autoEscape })
}

async sendPrivateMsg (userId: number, message: string, autoEscape = false) {
this._assertInteger('userId', userId)
if (!message) return
const meta = this._createSendMeta('user', userId, message)
const meta = this._createSendMeta('private', 'user', userId, message)
this.app.emitEvent(meta, 'before-send', meta)
const { messageId } = await this.get<MessageResponse>('send_private_msg', { userId, message, autoEscape })
meta.messageId = messageId
Expand All @@ -163,6 +192,8 @@ export class Sender {
async sendPrivateMsgAsync (userId: number, message: string, autoEscape = false) {
this._assertInteger('userId', userId)
if (!message) return
const meta = this._createSendMeta('private', 'user', userId, message)
this.app.emitEvent(meta, 'before-send', meta)
await this.get('send_private_msg_async', { userId, message, autoEscape })
}

Expand Down
2 changes: 1 addition & 1 deletion packages/koishi-core/src/server.ts
Original file line number Diff line number Diff line change
Expand Up @@ -124,7 +124,7 @@ export abstract class Server {
}
meta.$send = async (message, autoEscape = false) => {
if (meta.$response) {
app.emitEvent(meta, 'before-send', app.sender._createSendMeta(ctxType, ctxId, message))
app.emitEvent(meta, 'before-send', app.sender._createSendMeta(meta.messageType, ctxType, ctxId, message))
return meta.$response({ reply: message, autoEscape, atSender: false })
}
return app.sender[`send${capitalize(meta.messageType)}MsgAsync`](ctxId, message, autoEscape)
Expand Down
31 changes: 31 additions & 0 deletions packages/koishi-core/tests/sender.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -53,6 +53,37 @@ describe('Sender API', () => {

const messageId = 456

test('sendMsg', async () => {
await expect(sender.sendMsg(undefined, undefined, undefined)).rejects.toHaveProperty('message', 'missing argument: type')
await expect(sender.sendMsg('foo' as any, undefined, undefined)).rejects.toHaveProperty('message', 'invalid argument: type')
await expect(sender.sendMsg('private', undefined, undefined)).rejects.toHaveProperty('message', 'missing argument: userId')
await expect(sender.sendMsg('group', undefined, undefined)).rejects.toHaveProperty('message', 'missing argument: groupId')
await expect(sender.sendMsg('discuss', undefined, undefined)).rejects.toHaveProperty('message', 'missing argument: discussId')
await expect(sender.sendMsgAsync(undefined, undefined, undefined)).rejects.toHaveProperty('message', 'missing argument: type')
await expect(sender.sendMsgAsync('foo' as any, undefined, undefined)).rejects.toHaveProperty('message', 'invalid argument: type')
await expect(sender.sendMsgAsync('private', undefined, undefined)).rejects.toHaveProperty('message', 'missing argument: userId')
await expect(sender.sendMsgAsync('group', undefined, undefined)).rejects.toHaveProperty('message', 'missing argument: groupId')
await expect(sender.sendMsgAsync('discuss', undefined, undefined)).rejects.toHaveProperty('message', 'missing argument: discussId')

server.setResponse('send_msg', { messageId })
await expect(sender.sendMsg('group', 123, '')).resolves.toBeUndefined()
server.shouldHaveNoRequests()
await expect(sender.sendMsg('group', 123, 'foo')).resolves.toBe(messageId)
server.shouldHaveLastRequest('send_msg', { groupId: '123', message: 'foo' })
await expect(sender.sendMsg('private', 123, 'foo')).resolves.toBe(messageId)
server.shouldHaveLastRequest('send_msg', { userId: '123', message: 'foo' })
await expect(sender.sendMsg('private', 123, 'foo', true)).resolves.toBe(messageId)
server.shouldHaveLastRequest('send_msg', { userId: '123', message: 'foo', autoEscape: 'true' })
await expect(sender.sendMsgAsync('group', 123, '')).resolves.toBeUndefined()
server.shouldHaveNoRequests()
await expect(sender.sendMsgAsync('group', 123, 'foo')).resolves.toBeUndefined()
server.shouldHaveLastRequest('send_msg_async', { groupId: '123', message: 'foo' })
await expect(sender.sendMsgAsync('private', 123, 'foo')).resolves.toBeUndefined()
server.shouldHaveLastRequest('send_msg_async', { userId: '123', message: 'foo' })
await expect(sender.sendMsgAsync('private', 123, 'foo', true)).resolves.toBeUndefined()
server.shouldHaveLastRequest('send_msg_async', { userId: '123', message: 'foo', autoEscape: 'true' })
})

test('sendGroupMsg', async () => {
await expect(sender.sendGroupMsg(undefined, undefined)).rejects.toHaveProperty('message', 'missing argument: groupId')
await expect(sender.sendGroupMsgAsync(undefined, undefined)).rejects.toHaveProperty('message', 'missing argument: groupId')
Expand Down

0 comments on commit 1c3cfee

Please sign in to comment.