xiongzhu před 2 roky
rodič
revize
c65450a50a

+ 4 - 0
.vscode/settings.json

@@ -0,0 +1,4 @@
+{
+
+    "debug.javascript.autoAttachFilter": "always",
+}

+ 1 - 1
src/auth/jwt.strategy.ts

@@ -33,7 +33,7 @@ export class JwtStrategy extends PassportStrategy(Strategy) {
                 throw new UnauthorizedException('用户身份已过期,请重新登录')
             }
             if (payload.iat < user.iat) {
-                throw new UnauthorizedException('用户身份已过期,请重新登录')
+                //throw new UnauthorizedException('用户身份已过期,请重新登录')
             }
         }
         return {

+ 1 - 1
src/org/entities/org.entity.ts

@@ -33,5 +33,5 @@ export class Org {
     customDomain: string
 
     @Column({ nullable: true })
-    disclaimer: string
+    questionTemplate: string
 }

+ 42 - 45
src/org/org.service.ts

@@ -105,34 +105,54 @@ export class OrgService {
         await this.userService.updateUser(orgUser.userId, { orgId: null })
     }
 
-    async ask(question: string, orgId: number, knowledgeId?: number, fileId?: number) {
+    async buildMessages(question: string, orgId: number, knowledgeId?: number, fileId?: number): Promise<any[]> {
         const org = await this.findById(orgId)
         const context = await this.knowledgeService.askKnowledge(question, orgId, knowledgeId, fileId)
-        let content
-        if (org.contextTemplate) {
-            content = org.contextTemplate.replace('${context}', context.join('\n'))
-        } else {
-            content = dedent`You are a helpful AI article assistant. 
-            The following are the relevant article content fragments found from the article. 
-            The relevance is sorted from high to low. 
-            You can only answer according to the following content:
-            \`\`\`
-            ${context.join('\n')}
-            \`\`\`
-            You need to carefully consider your answer to ensure that it is based on the context. 
-            If the context does not mention the content or it is uncertain whether it is correct, 
-            please answer "Current context cannot provide effective information.
-            You must use Chinese to respond.`
+        if (org.questionTemplate) {
+            question = org.questionTemplate.replace('${question}', question)
+        }
+        const messages = []
+        if (org.systemPrompt) {
+            messages.push({
+                role: 'system',
+                content: org.systemPrompt.replace('${context}', context.join('\n')).replace('${question}', question)
+            })
+        }
+        if (!/\$\{context\}/.test(org.systemPrompt)) {
+            messages.push({
+                role: 'user',
+                content: (
+                    org.contextTemplate ||
+                    dedent`You are a helpful AI article assistant. 
+                    The following are the relevant article content fragments found from the article. 
+                    The relevance is sorted from high to low. 
+                    You can only answer according to the following content:
+                    \`\`\`
+                    ${context}
+                    \`\`\`
+                    You need to carefully consider your answer to ensure that it is based on the context. 
+                    If the context does not mention the content or it is uncertain whether it is correct, 
+                    please answer "Current context cannot provide effective information.
+                    You must use Chinese to respond.`
+                )
+                    .replace('${context}', context.join('\n'))
+                    .replace('${question}', question)
+            })
         }
+        if (!/\$\{question\}/.test('' + org.systemPrompt + org.contextTemplate)) {
+            messages.push({
+                role: 'user',
+                content: question
+            })
+        }
+        return messages
+    }
 
+    async ask(question: string, orgId: number, knowledgeId?: number, fileId?: number) {
         try {
             const response = await this.openai.createChatCompletion({
                 model: 'gpt35',
-                messages: [
-                    { role: 'system', content: org.systemPrompt },
-                    { role: 'user', content },
-                    { role: 'user', content: question }
-                ]
+                messages: await this.buildMessages(question, orgId, knowledgeId, fileId)
             })
             return { answer: response.data.choices[0].message.content }
         } catch (error) {
@@ -147,25 +167,6 @@ export class OrgService {
     async streamAsk(req, res, question: string, orgId: number, knowledgeId?: number, fileId?: number) {
         res.setHeader('Content-type', 'application/octet-stream')
         try {
-            const org = await this.findById(orgId)
-            const context = await this.knowledgeService.askKnowledge(question, orgId, knowledgeId, fileId)
-            let content
-            if (org.contextTemplate) {
-                content = org.contextTemplate.replace('${context}', context.join('\n'))
-            } else {
-                content = dedent`You are a helpful AI article assistant. 
-            The following are the relevant article content fragments found from the article. 
-            The relevance is sorted from high to low. 
-            You can only answer according to the following content:
-            \`\`\`
-            ${context.join('\n')}
-            \`\`\`
-            You need to carefully consider your answer to ensure that it is based on the context. 
-            If the context does not mention the content or it is uncertain whether it is correct, 
-            please answer "Current context cannot provide effective information.
-            You must use Chinese to respond.`
-            }
-
             try {
                 const url = `${process.env.AZURE_OPENAI_ENDPOINT}/openai/deployments/${process.env.AZURE_OPENAI_DEPLOYMENT}/chat/completions?api-version=${process.env.AZURE_OPENAI_VERSION}`
                 let firstChunk = true
@@ -176,11 +177,7 @@ export class OrgService {
                 }
                 await fetchSSE(url, {
                     body: JSON.stringify({
-                        messages: [
-                            { role: 'system', content: org.systemPrompt },
-                            { role: 'user', content },
-                            { role: 'user', content: question }
-                        ],
+                        messages: await this.buildMessages(question, orgId, knowledgeId, fileId),
                         stream: true
                     }),
                     headers: {