个人开发实现AI套壳网站快速搭建(Vue+elementUI+SpringBoot) ...

打印 上一主题 下一主题

主题 566|帖子 566|积分 1698

目录
一、效果展示
二、项目概述
三、手把手快速搭建实现本项目
3.1 前端实现
3.2 后端方向
五、后续开发操持


一、效果展示

默认展示

一般对话展示:

代码对话展示:


二、项目概述

        本项目是一个基于Web的智能对话服务平台,通过后端与第三方AI公司的API接口对接,为前端用户提供了一个简洁、直观的聊天界面。该项目的核心代价在于其便捷性与普适性,让用户可以或许轻松接入高质量的AI对话服务,无论是寻求信息咨询、娱乐互动,还是感情伴随,都能得到即时响应与个性化体验。
技能模块:
1.前端:接纳Vue框架+elementUi框架+HTML本地存储信息
2.后端:接纳SpringBoot框架举行数据响应

三、手把手快速搭建实现本项目

3.1 前端实现

前置预备工作:创建一个新的Vue模板,并导入axios
  1. npm install 'axios'
复制代码
导入elementUI
  1. npm i element-ui -S
复制代码
Vue中main.js 举行配置
  1. import Vue from 'vue'
  2. import App from './App.vue'
  3. import router from './router'
  4. import ElementUI from 'element-ui';
  5. import 'element-ui/lib/theme-chalk/index.css';
  6. Vue.config.productionTip = false
  7. Vue.use(ElementUI);
  8. new Vue({
  9.   router,
  10.   render: h => h(App)
  11. }).$mount('#app')
复制代码
本项目为了简单化,将项目团体仅设置为了一个Vue主视图(App.vue)
template:
  1. <template>
  2.   <div id="Chat">
  3.     <el-container>
  4.       <el-aside width="200px">
  5.         <!-- 添加导航 -->
  6.         <el-row class="tac" >
  7.           <el-col :span="12" style="width: 100%;">
  8.             <h1>个人工具网站</h1>
  9.             <el-menu default-active="2" class="el-menu-vertical-demo" @open="handleOpen" @close="handleClose">
  10.               <el-submenu index="1">
  11.                 <template slot="title">
  12.                   <i class="el-icon-location"></i>
  13.                   <span>人工智能助手</span>
  14.                 </template>
  15.                 <el-menu-item-group>
  16.                   <el-menu-item index="1-1">通义千问</el-menu-item>
  17.                   <el-menu-item index="1-2">文言一心</el-menu-item>
  18.                   <el-menu-item index="1-2">GPT</el-menu-item>
  19.                 </el-menu-item-group>               
  20.               </el-submenu>
  21.               <el-menu-item index="2">
  22.                 <i class="el-icon-menu"></i>
  23.                 <span slot="title">知识星球</span>
  24.               </el-menu-item>
  25.               <el-menu-item index="3" >
  26.                 <i class="el-icon-document"></i>
  27.                 <span slot="title">工具集合</span>
  28.               </el-menu-item>
  29.               <el-menu-item index="4">
  30.                 <i class="el-icon-setting"></i>
  31.                 <span slot="title">素材集合</span>
  32.               </el-menu-item>
  33.             </el-menu>
  34.           </el-col>
  35.         </el-row>
  36.       </el-aside>
  37.       <el-container>
  38.         <el-header>
  39.           <h3>通义千问-API套壳网站</h3>
  40.         </el-header>
  41.         <el-main>
  42.           <div id="ChatLayOut">
  43.             <!-- 对话内容列举 -->
  44.             <div v-for="(msg, index) in messages" :key="index" id="ChatBubble">
  45.               <img :src="getImageUrl(msg.sender)" id="chatImage">
  46.               <!-- <p id="ChatContent">{{ msg.sender }}: {{ msg.content }}</p> -->
  47.               <div class="chat-content-wrap">
  48.                 <!-- 使用预处理后的消息内容 -->
  49.                 <div v-html="preprocessMessageContent(msg.sender+':'+msg.content) "></div>
  50.               </div>
  51.             </div>
  52.           </div>
  53.         </el-main>
  54.         <el-footer>
  55.           <!-- 使用flex布局使元素水平排列 -->
  56.           <div style="display: flex; align-items: center;">
  57.             <!-- 将输入框放入表单中 -->
  58.             <form @submit.prevent="onFormSubmit" style="margin-left: 30%; width: 500px; margin-right: 10px;">
  59.               <el-input id="DialogTextCSS" v-model="message" :placeholder="DialogText" :disabled="flag"
  60.                 style="flex-grow: 1; "></el-input>
  61.             </form>
  62.             <!-- 提交按钮 -->
  63.             <el-button type="primary" @click="sendMessage" style="width:90px ;">提交</el-button>
  64.             <!-- 清空按钮 -->
  65.             <el-button type="danger" @click="deleteMessage">清空本地聊天记录</el-button>
  66.           </div>
  67.           <div>COPYRIGHT: CSDN-ALPHAMILK</div>
  68.           <div>version : 测试版</div>
  69.         </el-footer>
  70.       </el-container>
  71.     </el-container>
  72.   </div>
  73. </template>
复制代码
JavaScript:
  1. <script>
  2. import axios from 'axios';
  3. export default {
  4.   data() {
  5.     return {
  6.       message: '',
  7.       messages: [],
  8.       Identify: '',
  9.       senderType: '', // 新增一个变量来标识发送者类型
  10.       flag:false,
  11.       DialogText:'请您输入内容',
  12.     }
  13.   },
  14.   mounted() {
  15.     // 页面加载时从localStorage读取消息
  16.     const savedMessages = JSON.parse(localStorage.getItem('messages'));
  17.     if(savedMessages===null){
  18.       this.messages.push({sender: "AI", content: "欢迎使用通义千问API的套壳网站,请您通过输入内容到下方的文本框并提交即可开启聊天"});
  19.     }
  20.     if (savedMessages) {
  21.       this.messages = savedMessages;
  22.     }
  23.   },
  24.   methods: {
  25.     scrollToBottom() {
  26.   this.$nextTick(() => {
  27.     // 尝试手动触发一次重绘,看是否有助于解决滚动问题
  28.     const chatLayout = this.$el.querySelector('#ChatLayOut');
  29.     if (chatLayout) {
  30.       // 强制浏览器重绘
  31.       void chatLayout.offsetHeight;
  32.       setTimeout(() => {
  33.         console.log('scrollHeight:', chatLayout.scrollHeight);
  34.         window.scrollTop = chatLayout.scrollHeight;
  35.         console.log('scrollTop after setting:', chatLayout.scrollTop);
  36.       }, 100); // 增加延时时间以确保元素尺寸和内容更新完成
  37.     }
  38.   });
  39. },
  40.     sendMessage() {
  41.       if (this.message.trim() !== '') {
  42.         // 设置身份为用户
  43.         this.senderType = '用户';
  44.         this.messages.push({sender: this.senderType, content: this.message});
  45.         localStorage.setItem('messages', JSON.stringify(this.messages)); // 保存消息到localStorage
  46.         //禁用对话框
  47.         this.flag = true;
  48.         this.DialogText = '请您耐心等待AI的回答';
  49.         // //进行滚动操作,滚动到最新消息
  50.         // this.scrollToBottom();
  51.         // 调用接口获取AI生成的内容
  52.         axios.get('http://localhost:8080/Test/Chat',
  53.           {
  54.             params:{
  55.               message : this.message
  56.             }
  57.           }
  58.         ).then((response) => {
  59.           // 设置身份为AI
  60.           this.senderType = 'AI';
  61.           this.messages.push({sender: this.senderType, content: response.data});
  62.           localStorage.setItem('messages', JSON.stringify(this.messages));
  63.          
  64.           //解除对话框
  65.           this.flag = false;
  66.           this.DialogText = '请您输入内容';
  67.         });
  68.         this.message = ''; // 清空输入框
  69.       }else{
  70.         alert("输入不能为空噢!");
  71.       }
  72.     },
  73.     deleteMessage(){
  74.       localStorage.removeItem("messages");
  75.       this.messages = [];
  76.       this.messages.push({sender: "AI", content: "欢迎使用通义千问API的套壳网站,请您通过输入内容到下方的文本框并提交即可开启聊天"});
  77.     },
  78.     getImageUrl(sender) {
  79.       if (sender === 'AI') {
  80.         return 'https://img.alicdn.com/imgextra/i3/O1CN01sffRIx1nb3dXCKdFC_!!6000000005107-2-tps-1024-1024.png';
  81.       } else {
  82.         return 'https://bpic.51yuansu.com/pic3/cover/00/94/68/58dcd742dd10d_610.jpg?x-oss-process=image/resize,h_360,m_lfit/sharpen,100';
  83.       }
  84.     },
  85.     onFormSubmit() {
  86.       this.sendMessage();
  87.     },
  88. preprocessMessageContent(content) {
  89.   const codeBlockRegex = /```(.*?)```/gs;
  90.   const sortTextRegex = /\*\*(.*?)\*\*/gs;
  91.   let tempContent = content.replace(sortTextRegex, `<p class="sort-text">$1</p>`);
  92.   let processedContent = tempContent.replace(codeBlockRegex, `<pre class="code-block"><code>$1</code></pre>`);
  93.   let segments = processedContent.split(/```.*?```/gs); // 分割代码块
  94.   
  95.   segments = segments.filter(segment => segment.trim());
  96.   
  97.   let finalContent = segments.map((segment) => {
  98.     return `<p class="content-common">${segment}</p>`;
  99.   }).join('');
  100.   return finalContent;
  101. }
  102.   },
  103.   handleOpen(key, keyPath) {
  104.         console.log(key, keyPath);
  105.       },
  106.       handleClose(key, keyPath) {
  107.         console.log(key, keyPath);
  108.       }
  109. }
  110. </script>
复制代码
css:
  1. <style>
  2.   .el-header, .el-footer {
  3.     background-color: #B3C0D1;
  4.     color: #333;
  5.     text-align: center;
  6.     line-height: 60px;
  7.   }
  8.   
  9.   .el-aside {
  10.     background-color: #D3DCE6;
  11.     color: #333;
  12.     text-align: center;
  13.     line-height: 200px;
  14.     box-shadow: 0 2px 4px rgba(0, 0, 0, .12), 0 0 6px rgba(0, 0, 0, .04)
  15.   }
  16.   
  17.   .el-main {
  18.     background-color: #E9EEF3;
  19.     color: #333;
  20.     text-align: center;
  21.     line-height: 160px;
  22.     height: 1000px;
  23.   }
  24.   
  25.   body > .el-container {
  26.     margin-bottom: 40px;
  27.   }
  28.   
  29.   .el-container:nth-child(5) .el-aside,
  30.   .el-container:nth-child(6) .el-aside {
  31.     line-height: 260px;
  32.   }
  33.   
  34.   .el-container:nth-child(7) .el-aside {
  35.     line-height: 320px;
  36.   }
  37. #ChatBubble{
  38.   
  39.   position: relative;
  40.   padding: 10px;
  41.   border-radius: 10px;
  42.   margin-bottom: 30px;
  43.   max-width: 70%;
  44.   background-color: white;
  45.   line-height: normal;
  46. }
  47. /* 用户和AI的不同样式 */
  48. #ChatBubble.user {
  49.   background-color: #E0F2F7; /* 用户气泡颜色 */
  50.   float: left;
  51.   clear: both;
  52.   margin-right: 30px;
  53. }
  54. #ChatBubble.AI {
  55.   background-color: #ECEFF1; /* AI气泡颜色 */
  56.   float: right;
  57.   clear: both;
  58.   margin-left: 30px;
  59. }
  60. /* 指向箭头,这里仅示例用户气泡右边的箭头 */
  61. #ChatBubble.user::after {
  62.   content: "";
  63.   position: absolute;
  64.   top: 50%;
  65.   right: -15px;
  66.   transform: translateY(-50%);
  67.   border-style: solid;
  68.   border-width: 10px 15px 10px 0;
  69.   border-color: transparent #E0F2F7;
  70. }
  71. /* 可能需要清除浮动,避免布局问题 */
  72. #dialog-display::after {
  73.   content: "";
  74.   display: block;
  75.   clear: both;
  76. }
  77. #chatImage{
  78.   float: left;
  79.   margin-top: 17px;
  80.   margin-right: 10px;
  81.   height: 30px;
  82.   width: 30px;
  83.   background-color:#faeeee;
  84. }
  85. #Topic{
  86.   background-color: #f6f6fe;
  87.   border-radius: 10px;
  88.   height: 60px;
  89. }
  90. #chat{
  91. height: 56px;
  92. width: 100%;
  93. background-color: pink;
  94. }
  95. .el-footer{
  96.   background-color: #f7f8fc;
  97. }
  98. .el-main{
  99.   background-color: #f7f8fc;
  100. }
  101. #ChatContent {
  102.   line-height: 1.5; /* 或者根据需要调整 */
  103.    padding: 0; /* 取消内边距 */
  104.   }
  105. #ChatLayOut{
  106.   margin-left: 20%;
  107. }
  108. .el-header{
  109.   background-color: #333;
  110. }
  111. h3{
  112.   color: #E9EEF3;
  113. }
  114. .el-aside{
  115.   background: white;
  116.   box-shadow: 0 2px 4px rgba(0, 0, 0, .12), 0 0 6px rgba(0, 0, 0, .04);
  117.   /* 实现右边border-radi */
  118.   border-top-right-radius: 30px;
  119. }
  120. /* 明亮风格的代码块,文字及行号全部左对齐 */
  121. .code-block {
  122.   background-color: #f8f8f8; /* 明亮背景 */
  123.   color: #333; /* 深色文字 */
  124.   font-family: 'Courier New', monospace; /* 适合代码的字体 */
  125.   white-space: pre-wrap; /* 保留空格和换行 */
  126.   border-radius: 5px; /* 边角圆润 */
  127.   overflow-x: auto; /* 横向滚动条,如果需要 */
  128.   line-height: 1.5;
  129.   padding: 10px;
  130.   position: relative; /* 为行号预留位置 */
  131. }
  132. /* 显示所有行的行号,确保向左对齐 */
  133. .code-block::before {
  134.   content: counter(line);
  135.   counter-increment: line;
  136.   position: absolute; /* 行号绝对定位 */
  137.   left: 0; /* 行号紧贴左侧 */
  138.   margin-left: 15px; /* 与代码内容的距离,可根据需要调整 */
  139.   text-align: left; /* 行号左对齐 */
  140.   width: 30px; /* 行号宽度 */
  141.   color: #666; /* 行号颜色,可调整 */
  142.   display: block; /* 每行前面均显示 */
  143.   line-height: inherit; /* 继承代码块的行高 */
  144. }
  145. /* 确保代码内容也左对齐 */
  146. .code-block code {
  147.   display: block; /* 确保代码块内代码作为独立块显示 */
  148.   padding-left: 45px; /* 为代码内容预留行号和额外的间距 */
  149.   text-align: left; /* 确保代码文本左对齐 */
  150. }
  151. .content-common {
  152.   /* 为普通文本内容定义样式 */
  153.   margin-bottom: 10px; /* 示例:增加段落间距 */
  154.   line-height: 1.5; /* 示例:调整行高 */
  155. }
  156. .el-col-12 {
  157.   width: 100%;
  158. }
  159. .sort-text {
  160.   font-weight: bold; /* 设置为粗体 */
  161.   text-align: left; /* 文本左对齐 */
  162.   line-height: normal; /* 行高设置为正常,确保与未加样式时的文本行高一致 */
  163. }
  164. </style>
复制代码
末了配置端口为8081(在vue.config.js文件下):
  1. const { defineConfig } = require('@vue/cli-service')
  2. module.exports = {
  3.   devServer: {
  4.     port: 8081, // 将端口设置为你想要的端口号
  5.   },
  6. };
复制代码
运行:在控制台启动步调
  1. npm run serve
复制代码
打开欣赏器:前端的配置改为(localhost:8081)


3.2 后端方向

创建一个SpringBoot项目


在项目pom.xml文件导入以下依靠:
  1.         <!-- https://mvnrepository.com/artifact/com.alibaba/dashscope-sdk-java -->
  2.         <dependency>
  3.             <groupId>com.alibaba</groupId>
  4.             <artifactId>dashscope-sdk-java</artifactId>
  5.             <version>2.8.2</version>
  6.         </dependency>
  7.         <!--okhttp3 依赖-->
  8.         <dependency>
  9.             <groupId>com.squareup.okhttp3</groupId>
  10.             <artifactId>okhttp</artifactId>
  11.             <version>4.9.3</version>
  12.         </dependency>
复制代码
由于后端功能十分简单,仅需要一个Utils和一个Controller即可
Utils:(留意:这里要填自己申请的APIKey(十分简单,一毛钱就能开通))
  1. @Component
  2. public class AICHAT {
  3.     public static String callWithMessage(String message)
  4.             throws NoApiKeyException, ApiException, InputRequiredException {
  5.         Generation gen = new Generation();
  6.         Constants.apiKey="xxxxxx";//TODO:这里填写自己申请的APIKEY
  7.         MessageManager msgManager = new MessageManager(10);
  8.         Message systemMsg =
  9.                 Message.builder().role(Role.SYSTEM.getValue()).content("You are a helpful assistant.").build();
  10.         Message userMsg = Message.builder().role(Role.USER.getValue()).content(message).build();//这里填写对话内容
  11.         msgManager.add(systemMsg);
  12.         msgManager.add(userMsg);
  13.         QwenParam param =
  14.                 QwenParam.builder().model(Generation.Models.QWEN_TURBO).messages(msgManager.get())
  15.                         .resultFormat(QwenParam.ResultFormat.MESSAGE)
  16.                         .topP(0.8)
  17.                         .enableSearch(true)
  18.                         .build();
  19.         GenerationResult result = gen.call(param);
  20.         String Message = extractContentFromResult(result);
  21.         System.out.println(Message);
  22.         return Message;
  23.     }
  24. //    仅获取JSON结果中message字段的信息
  25.     public static String extractContentFromResult(GenerationResult result) {
  26.         if (result != null && result.getOutput() != null && !result.getOutput().getChoices().isEmpty()) {
  27.             Message message = result.getOutput().getChoices().get(0).getMessage();
  28.             return message.getContent();
  29.         }
  30.         return null; // 或者返回一个默认值
  31.     }
  32. }
复制代码
ChatController:
  1. @RestController
  2. @RequestMapping("/Test")
  3. @CrossOrigin
  4. public class ChatController {
  5.     @Autowired
  6.     AICHAT aichat;
  7.     @GetMapping("/Chat")
  8.     public String GetParameter(String message) {
  9.         try {
  10.             if (message != null) {
  11.                 String AiResponse = null;
  12.                 try {
  13.                     AiResponse = aichat.callWithMessage(message);
  14.                 } catch (ApiException | NoApiKeyException | InputRequiredException e) {
  15.                     System.out.println(e.getMessage());
  16.                 }
  17.                 return AiResponse;
  18.             }
  19.         } catch (Exception e) {
  20.             return "出错了>_<"+e.getMessage();
  21.         }
  22.         return  null;
  23.     }
  24.    
  25. }
复制代码
 启动(Application):

前后端联调测试:



五、后续开发操持

后续改进操持:
后续将会修改许多的bug,并加入许多新的功能,一步步将其打造成一个可以或许实现贸易化的,满意平凡人可以使用的通用网站。关注后即可获取最新的动态
1.加入多个可用个人免费的API,让切换AI模型可以或许方便快捷
2.加入用户管理,满意以后实现贸易化的一步
3.加入动画效果,让聊天更生动
4.加入语音输入功能,与语音输出功能。实现外语教师功能
5.将项目通过nginx部署到服务器上
 .......


免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!更多信息从访问主页:qidao123.com:ToB企服之家,中国第一个企服评测及商务社交产业平台。
回复

使用道具 举报

0 个回复

倒序浏览

快速回复

您需要登录后才可以回帖 登录 or 立即注册

本版积分规则

卖不甜枣

金牌会员
这个人很懒什么都没写!

标签云

快速回复 返回顶部 返回列表