前端调用deepseek API 实现与ai助手对话
1.获取apikey
1.1 deepseek API开放平台:DeepSeek 开放平台
1.2 创建API Key
2. 前端调用api
2.1 接口地址
https://platform.deepseek.com/usage --post
2.2 接口封装
import axios from 'axios'; // 封装DeepSeek API接口 interface Message { content: string; role: 'user' | 'assistant' | 'system'; } export const getDeepSeekReply = async (messages: Message[]): Promise => { const apiKey = '***********'; // 替换为你的API密钥 const url = 'https://api.deepseek.com/chat/completions'; // 替换为实际的API端点 const params = { messages: messages, model: "deepseek-chat", max_tokens: 1500, // 增加max_tokens以获得更长的回复 temperature: 0.7, // 调整temperature以获得更自然的回复 top_p: 1, frequency_penalty: 0, presence_penalty: 0, }; try { const response = await axios.post(url, params, { headers: { 'Authorization': `Bearer ${apiKey}`, "Content-Type": "application/json", "Accept": "application/json", } }); return response.data.choices[0].message; } catch (error) { console.error('Axios error:', error); return { content: 'Error occurred while fetching data.', role: 'assistant' }; } }
3. 页面展示
聊天窗口
重新生成 复制
正在加载... 发送 清空消息 停止 继续 import hljs from 'highlight.js'; // import 'highlight.js/styles/default.css'; // import "highlight.js/styles/a11y-dark.css"; import "highlight.js/styles/atom-one-dark-reasonable.css"; import { ref, nextTick, watch, onMounted } from 'vue'; import { getDeepSeekReply, addMessage, getMessageList, deleteHistory } from '../api/deepseekApi'; import { computed } from 'vue'; import { Delete } from '@element-plus/icons-vue'; import { ElMessage } from 'element-plus'; interface Message { content: string; role: 'user' | 'assistant' | 'system'; status?: string; } interface Conversation { title: string; messages: Message[]; status: string; } interface Code { code: string; index: Number; } const messages = ref([]); const newMessage = ref(''); const isLoading = ref(false); const isGenerating = ref(false); const currentMessageIndex = ref(0); const messagesContainer = ref(null); const historyConversations = ref([]); const buton = ref('复制'); const codeList = ref([]); const status = ref(''); const dis = computed(() => { return !newMessage.value.trim(); }); const diss = computed(() => { return !(messages.value.length > 1); }); messages.value.push({ content: '欢迎使用 Deep Seek AI智能助手,请在下方输入您想问的!', role: 'user' }); // 组件挂载之后 onMounted(() => { saveConversation(); }); const highlightCode = (content: string) => { // 使用正则表达式检测是否包含代码块 const codeBlockRegex = /```([\s\S]*?)```/g; // 使用正则表达式检测是否包含单个反引号包裹的文本 const inlineCodeRegex = /`([^`]+)`/g; const inlineCodeRegex1 = /- `([^`]+)`/g; const titleCodeRegex = /\*\*([^\*]+)\*\*/g; // 使用正则表达式检测是否包含以-开头的文本行 const listRegex1 = /- \*\*([^*]+)\*\*/g; const listRegex = /-/g; // 匹配以 `${escapeHtml(p1)}`); // 处理单个反引号包裹的文本 processedContent = processedContent.replace(inlineCodeRegex, (match, p1) => `${escapeHtml(p1)}`); // 处理以-**开头的文本行 processedContent = processedContent.replace(listRegex1, '
• **$1**'); // 处理**引号包裹的文本 processedContent = processedContent.replace(titleCodeRegex, (match, p1) => `${escapeHtml(p1)}`); result.push(`${processedContent}`); } }); return result.join(''); function escapeHtml(unsafe) { return unsafe .replace(/&/g, "&") .replace(//g, ">") .replace(/"/g, """) .replace(/'/g, "'"); } }; // 添加点击事件 const handleButtonClick = () => { codeList.value.forEach((item, index) => { let button = document.getElementById(`code${item.index}`); if (button) { button.addEventListener('click', () => { copyCode(item.code); }); } }); }; // 点击复制代码 const copyCode = (codeContent: string) => { navigator.clipboard.writeText(codeContent).then(() => { console.log('复制成功'); // buton.value = '已复制' ElMessage.success('复制成功'); }).catch((error) => { console.error('复制失败:', error); }); }; // 自动滚动函数 const scrollToBottom = () => { nextTick(() => { if (messagesContainer.value) { messagesContainer.value.scrollTo({ top: messagesContainer.value.scrollHeight, behavior: 'smooth' }); } }); }; const sendMessage = async () => { if (newMessage.value.trim()) { messages.value.push({ content: newMessage.value, role: 'user' }); newMessage.value = ''; isLoading.value = true; isGenerating.value = true; currentMessageIndex.value = messages.value.length - 1; try { const aiReply = await getDeepSeekReply(messages.value); const replyContent = highlightCode(aiReply.content); const newMessage: Message = { content: '', role: 'assistant' }; messages.value.push(newMessage); typeMessage(replyContent, newMessage); } catch (error) { console.error('获取AI回复时出错:', error); messages.value.push({ content: '无法获取AI回复,请稍后再试', role: 'user' }); } finally { isLoading.value = false; scrollToBottom(); // 确保加载完AI回复后滚动到底部 nextTick(() => { handleButtonClick(); }); } } }; // 保存消息到数据库 const saveMessageToDatabase = async (messages: Message[],status:string) => { if (!status){ alert('没有会话id') // 结束程序 return } try { const response = await addMessage({messages,model:'deepseek',status}); console.log('消息保存成功:'); } catch (error) { console.error('消息保存失败:', error); } }; // 使用 requestAnimationFrame 实现更平滑的逐字输出效果 const typeMessage = (text: string, message: Message, index: number = 0) => { if (index { typeMessage(text, message, index + 1); }); setTimeout(() => { scrollToBottom(); // 确保逐字输入后滚动到底部 }, 1000); } else { scrollToBottom(); // 完成逐字输入后滚动到底部 } }; const clearMessages = () => { messages.value = []; messages.value.push({ content: '欢迎使用 Deep Seek AI智能助手,请在下方输入您想问的!', role: 'user' }); }; const stopGenerating = () => { isGenerating.value = false; }; const continueGenerating = () => { if (currentMessageIndex.value >= 0 && currentMessageIndex.value { if (currentMessageIndex.value >= 0 && currentMessageIndex.value { handleButtonClick(); }); } } } }; // 新增: 复制消息内容的方法 const copyMessage = (content: string) => { navigator.clipboard.writeText(content).then(() => { ElMessage.success('复制成功'); }).catch(err => { console.error('复制失败:', err); ElMessage.error('复制失败'); }); }; .new-conversation { width: 95%; } .chat-content { width: 78%; } .indent { text-indent: 2em; /* 使用em单位进行缩进 */ } .chat-window { width: 100%; height: 100%; display: flex; justify-content: space-between; /* flex-direction: column; */ /* align-items: center; */ padding: 20px; background-color: #f9f9f9; position: relative; } .messages { width: 95%; height: 70vh; max-height: 70vh; overflow-y: auto; border: 1px solid #ddd; padding: 10px; margin-bottom: 20px; margin-top: 20px; border-radius: 8px; background-color: #fff; box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1); margin-left: 20px; overflow-y: scroll; } .message { margin-bottom: 10px; display: flex; align-items: flex-start; } .message-content { max-width: 70%; padding: 10px; border-radius: 10px; margin-left: 10px; word-wrap: break-word; } .user-message .message-content { background-color: #e0f7fa; border: 1px solid #b2ebf2; align-self: flex-end; margin-left: auto; margin-right: 10px; } .ai-message .message-content { background-color: #f1f8e9; border: 1px solid #dcedc8; align-self: flex-start; margin-left: 10px; margin-right: auto; } .avatar { width: 30px; height: 30px; border-radius: 50%; margin-right: 10px; } .input-area { width: 95%; display: flex; justify-content: space-between; align-items: center; background-color: #fff; padding: 10px; border-radius: 8px; box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1); position: absolute; bottom: 100px; left: 30px; } input { width: 75%; padding: 10px; border: 1px solid #ddd; border-radius: 5px; transition: border-color 0.3s; } input:focus { border-color: #007bff; outline: none; } button { padding: 10px 20px; border: none; background-color: #007bff; color: white; border-radius: 5px; cursor: pointer; transition: background-color 0.3s; } button:hover { background-color: #0056b3; } .loading { text-align: center; color: #666; margin-top: 10px; } /* 响应式设计 */ @media (max-width: 768px) { .messages { width: 100%; } .input-area { width: 100%; } input { width: 70%; } } .content{ line-height: 30px; font-size: 16px; font-weight: 400; color: #333; word-break: break-all; white-space: pre-wrap; margin-bottom: 5px; }
运行效果如下:
ai生成内容markeddown文本格式转换请参考:Markdown文本格式化显示-CSDN博客
免责声明:我们致力于保护作者版权,注重分享,被刊用文章因无法核实真实出处,未能及时与作者取得联系,或有版权异议的,请联系管理员,我们会立即处理! 部分文章是来自自研大数据AI进行生成,内容摘自(百度百科,百度知道,头条百科,中国民法典,刑法,牛津词典,新华词典,汉语词典,国家院校,科普平台)等数据,内容仅供学习参考,不准确地方联系删除处理! 图片声明:本站部分配图来自人工智能系统AI生成,觅知网授权图片,PxHere摄影无版权图库和百度,360,搜狗等多加搜索引擎自动关键词搜索配图,如有侵权的图片,请第一时间联系我们。