import { AxiosInstance } from 'axios';

interface BotConfig {
    qq: number;
    masterQQ: number;
    settingFile: string;
}

declare class Api {
    adapter: AxiosInstance;
    qq: number;
    verifyKey: string;
    sessionKey: string;
    constructor(qq: number, baseURL: string, verifyKey: string);
    verify(): Promise<{
        code: number;
        session: string;
    }>;
    bind(): Promise<{
        code: number;
        msg: string;
    }>;
    release(): Promise<{
        code: Number;
        msg: string;
    }>;
    fetchMessage(count?: number): Promise<{
        code: number;
        msg: string;
        data: Message[];
    }>;
    sendMessage(target: number, chatroomType: ChatroomType, messageChain: MessageChain, quoteMessage?: number): Promise<{
        code: number;
        msg: string;
        messageId: number;
    }>;
}

declare class Command {
    name: BotCommandName;
    attrs: string[];
    isValid: boolean;
    constructor(commandMessageChain: MessageChain);
}

declare class Context {
    api: Api;
    qq: number;
    messageId: number;
    messageType: MessageType;
    sourceMessage: SourceMessage | undefined;
    contentMessageChain: MessageChain;
    sender: number;
    senderName: string;
    chatroom: number;
    chatroomType: ChatroomType;
    chatroomName: string;
    isQuote: boolean;
    quoteMessage: QuoteMessage;
    isAt: boolean;
    isAtMe: boolean;
    isCommand: boolean;
    command: Command | null;
    constructor(api: Api, qq: number, message: Message);
    reply(message: string | MessageChain): Promise<void>;
    quoteReply(message: string | MessageChain): Promise<void>;
}

declare type Permission = 'OWNER' | 'ADMINISTRATOR' | 'MEMBER';
interface Group {
    id: number;
    name: string;
    permission: Permission;
}
interface Friend {
    id: number;
    nickname: string;
    remark: string;
}
interface GroupMember {
    id: number;
    memberName: string;
    specialTitle: string;
    permission: Permission;
    joinTimestamp: number;
    lastSpeakTimestamp: number;
    muteTimeRemaining: number;
    group: Group;
}

declare type BotSingleMessageType = 'Source' | 'Quote' | 'At' | 'AtAll' | 'Face' | 'Plain' | 'Image' | 'FlashImage' | 'Voice' | 'Xml' | 'Json' | 'App' | 'Poke' | 'Dice' | 'MusicShare' | 'ForwardMessage' | 'File' | 'MiraiCode';
interface BasicSingleMessage {
    type: BotSingleMessageType;
}
interface SourceMessage extends BasicSingleMessage {
    type: 'Source';
    id: number;
    time: number;
}
interface QuoteMessage extends BasicSingleMessage {
    type: 'Quote';
    id: number;
    groupId: number;
    senderId: number;
    targetId: number;
    origin: MessageChain;
}
interface AtMessage extends BasicSingleMessage {
    type: 'At';
    target: number;
    display: string;
}
interface AtAllMessage extends BasicSingleMessage {
    type: 'AtAll';
}
interface FaceMessage extends BasicSingleMessage {
    type: 'Face';
    faceId: number;
    name: string;
}
interface PlainMessage extends BasicSingleMessage {
    type: 'Plain';
    text: string;
}
declare type SingleMessage = SourceMessage | QuoteMessage | AtMessage | AtAllMessage | FaceMessage | PlainMessage;
declare type MessageChain = SingleMessage[];
declare type ReceivedMessageChain = [SourceMessage, ...SingleMessage[]];
declare type ChatroomType = 'Friend' | 'Group';
declare type MessageType = 'FriendMessage' | 'GroupMessage';
interface BasicReceivedMessage {
    type: MessageType;
    messageChain: ReceivedMessageChain;
    sender: Friend | GroupMember;
}
interface ReceivedFriendMessage extends BasicReceivedMessage {
    type: 'FriendMessage';
    sender: Friend;
}
interface ReceivedGroupMessage extends BasicReceivedMessage {
    type: 'GroupMessage';
    sender: GroupMember;
}
declare type Message = ReceivedFriendMessage | ReceivedGroupMessage;

declare type BotMessageType = '*' | 'FriendMessage' | 'GroupMessage' | BotSingleMessageType;
declare type BotCommandName = string;
declare type BotEventName = BotMessageType;
interface BotEventHandler {
    (ctx: Context): any;
}

declare type LoadPluginFunc = (bot: Bot, ...args: any) => string;

declare class Bot {
    qq: number;
    masterQQ: number;
    private api;
    private event;
    private invalidCommandEventKey;
    private invalidCommandHandler;
    private undefinedCommandEventKey;
    private undefinedCommandHandler;
    constructor(config: BotConfig);
    on(eventType: BotEventName, handler: BotEventHandler): void;
    off(eventType: BotEventName): void;
    command(commandName: BotCommandName, handler: BotEventHandler): void;
    offCommand(commandName: BotCommandName): void;
    setInvalidCommandHandler(handler: BotEventHandler): void;
    setUndefinedCommandHandler(handler: BotEventHandler): void;
    use(loadPlugin: LoadPluginFunc, ...args: any): void;
    sendMessage(target: number, chatroomType: ChatroomType, message: string | MessageChain): Promise<{
        code: number;
        msg: string;
        messageId: number;
    }>;
    logToMaster(log: string): Promise<{
        code: number;
        msg: string;
        messageId: number;
    }>;
    start(cb?: () => any): Promise<void>;
    private fetch;
    private resolve;
}

declare function defineConfig(config: BotConfig): BotConfig;

declare function createPlainMessage(message: string | MessageChain): MessageChain;

export { Bot, createPlainMessage, defineConfig };
