File size: 3,995 Bytes
7c363b0
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
const WebSocket = require('ws')
const axios = require('axios')

class CopilotThink {
    constructor() {
        this.conversationId = null
        this.headers = {
            origin: 'https://copilot.microsoft.com',
            'user-agent': 'Mozilla/5.0 (Linux; Android 15; SM-F958 Build/AP3A.240905.015) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/130.0.6723.86 Mobile Safari/537.36'
        }
    }

    async createConversation() {
        let { data } = await axios.post('https://copilot.microsoft.com/c/api/conversations', null, { headers: this.headers })
        this.conversationId = data.id
        return this.conversationId
    }

    async chat(message) {
        if (!this.conversationId) await this.createConversation()
        return new Promise((resolve, reject) => {
            const ws = new WebSocket(`wss://copilot.microsoft.com/c/api/chat?api-version=2&features=-,ncedge,edgepagecontext&setflight=-,ncedge,edgepagecontext&ncedge=1`, { headers: this.headers })
            const response = { text: '', citations: [] }
            ws.on('open', () => {
                ws.send(JSON.stringify({
                    event: 'setOptions',
                    supportedFeatures: ['partial-generated-images'],
                    supportedCards: ['weather', 'local', 'image', 'sports', 'video', 'ads', 'safetyHelpline', 'quiz', 'finance', 'recipe'],
                    ads: { supportedTypes: ['text', 'product', 'multimedia', 'tourActivity', 'propertyPromotion'] }
                }))
                ws.send(JSON.stringify({
                    event: 'send',
                    mode: 'reasoning',
                    conversationId: this.conversationId,
                    content: [{ type: 'text', text: message }],
                    context: {}
                }))
            })
            ws.on('message', (chunk) => {
                try {
                    const parsed = JSON.parse(chunk.toString())
                    switch (parsed.event) {
                        case 'appendText':
                            response.text += parsed.text || ''
                            break
                        case 'citation':
                            response.citations.push({ title: parsed.title, icon: parsed.iconUrl, url: parsed.url })
                            break
                        case 'done':
                            resolve(response)
                            ws.close()
                            break
                        case 'error':
                            reject(new Error(parsed.message))
                            ws.close()
                            break
                    }
                } catch (error) {
                    reject(error.message)
                }
            })
            ws.on('error', reject)
        })
    }
}

const handler = async (req, res) => {
    try {
        const { text } = req.query

        if (!text) {
            return res.status(400).json({
                author: 'Herza',
                success: false,
                msg: 'Missing required parameter: text'
            })
        }

        const copilot = new CopilotThink()
        const result = await copilot.chat(text)

        res.json({
            author: 'Herza',
            success: true,
            model: 'copilot-think',
            msg: result.text.trim(),
            citations: result.citations
        })

    } catch (error) {
        console.error('Error fetching from Copilot Think:', error)
        res.status(500).json({
            author: 'Herza',
            success: false,
            msg: 'Terjadi kesalahan saat menghubungi AI.'
        })
    }
}

module.exports = {
    name: 'Copilot Think AI',
    description: 'Generate responses using Microsoft Copilot with Reasoning/Think Deeper',
    type: 'GET',
    routes: ['api/AI/copilot-think'],
    tags: ['ai', 'copilot', 'reasoning', 'think-deeper'],
    parameters: ['text'],
    enabled: true,
    main: ['AI'],
    handler
}