纯前端调用deepseek v3模型,流式返回,支持md文本、table、代码等

背景

大模型如火如荼,作为公司的边角料,一个不起眼得小渣渣前端切图仔,我们如何在不启动后端服务得情况下,快如入门调用大模型,本文就是来扫盲的,文章末尾有源码可以自行查看

技术栈

我制作的demo比较简陋,也就不到半天时间,基于 react@18 tailwindcss@3 vite ract-marndown等来搞的,代码简单,主要是熟悉流程,先看实现的截图及视频,如果不满足要求,可以直接关闭文章,免得浪费时间

demo功能介绍

  1. 流式调用deeepseek v3
  2. 增加会话历史主页面等布局
  3. 支持md文本展示
  4. 支持table ul link等特殊 md展示
  5. 支持html结构回显
  6. 封装了包括chat-input 用户问答 AI回复 md展示等组件
  7. 优化了支持html的空白间隙问题
  8. 代码的 copy 功能 话不多说,看下面的截图及视频展示

demo展示




实现步骤

注册deepseek api key

deepseek API开放平台

充值至少十块钱

写入api key

clone代码后,将 .env文件 的 VITE_DEEPSEEK_KEY 替换成你自己的

项目启动

js 复制代码
npm i
npm run dev

测试问答

你可以在问答框输入以下问题 看支持的情况如何

  1. 你是什么模型 (测试md纯文本的)
  2. 写一段js去重的代码
  3. 帮我生成一个三行三列的表格,用于计算姓名和成绩

提示

deepseek有提示

,请创建后,很好的保存你得key,不要外泄

核心代码介绍

openai SDK

任何大模型 的接口都兼容 openai的规范,我们可以借助 openai sdk来实现deepseek的模型请求,打开 dangerouslyAllowBrowser属性,可以在浏览器中调用,这种做法仅作demo,后期实际项目需要后端去调用,纯前端调用 api key会暴露

js 复制代码
import OpenAI from "openai";
 const initOpenAI = () => {
        openaiRef.current = new OpenAI({
            baseURL: "https://api.deepseek.com",
            apiKey: GlobalAPI.config?.VITE_DEEPSEEK_KEY,
            dangerouslyAllowBrowser: true,
        });
    };

markdown-ai.tsx组件

js 复制代码
import ReactMarkdown from "react-markdown";
import rehypeRaw from "rehype-raw";
import remarkGfm from "remark-gfm";
import rehypeHighlight from 'rehype-highlight'; // 代码高亮
import 'highlight.js/styles/github.css';

 <ReactMarkdown
        remarkPlugins={[remarkGfm, remarkMath]}
        rehypePlugins={[rehypeRaw, rehypeHighlight, removeExtraWhitespace]}
        components={components as any}
      >
        {markdownstr}
      </ReactMarkdown>

采用react-markdown及配套实现了样式,md文本,table,html标签等支持,详情请看具体代码

代码copy组件

借助react-markdown自定义标签的方式,自定义了<pre>标签,借助 rehype-highlight copy-to-clipboard来实现代码的高亮及复制

js 复制代码
import PreWithCopy from "./copycode.tsx"
// 自定义渲染器
  const components = {
    pre: PreWithCopy,
  };
  
   <ReactMarkdown
        remarkPlugins={[remarkGfm, remarkMath]}
        rehypePlugins={[rehypeRaw, rehypeHighlight, removeExtraWhitespace]}
        components={components as any}
      >
        {markdownstr}
      </ReactMarkdown>
  

html渲染空白行处理

react-markdown开启 rehypePlugins rehypeRaw的时候,大多数情况由于模型返回的\n太多,页面会间距过大,尤其是表格等,我们需要单独空白行处理下

js 复制代码
 // 消除空格的 解决html 渲染的问题
  const removeExtraWhitespace = () => {
    return (tree: any) => {
      const removeWhitespace = (node: any) => {
        if (node.tagName === "pre") {
          return;
        }
        if (node.type === "text") {
          node.value = node.value.replace(/\s+/g, " ");
        }
        if (node.children) {
          node.children = node.children.filter((child: any) => {
            if (child.type === "text") {
              return child.value.trim() !== "";
            }
            removeWhitespace(child);
            return true;
          });
        }
      };
      removeWhitespace(tree);
      return tree;
    };
  };

总结

以上就是demo版本的主要功能和技术实现细节,详情请查看代码 gitee仓库地址

我是基于react写的,如果需要vue版本的,可以留言,抽时间做一套vue的。

相关推荐
EndingCoder几秒前
React从基础入门到高级实战:React 高级主题 - 性能优化:深入探索与实践指南
前端·javascript·react.js·性能优化·前端框架
Sunny_lxm4 分钟前
在 Vue 2中使用 dhtmlxGantt 7.1.13组件,并解决使用时遇到的问题汇总.“dhtmlx-gantt“: “^7.1.13“,
前端·vue.js·甘特图·dhtmlxgantt
江城开朗的豌豆40 分钟前
JavaScript篇:前端兼容性历险记:那些年我们踩过的浏览器坑
前端·javascript·面试
江城开朗的豌豆44 分钟前
JavaScript篇:JS事件冒泡:别让点击事件‘传染’!
前端·javascript·面试
极客密码1 小时前
Cursor,2天,一个小程序!
前端·ai编程·cursor
蓉妹妹1 小时前
React项目在ios和安卓端要做一个渐变色背景,用css不支持,可使用react-native-linear-gradient
android·css·react.js
不知几秋1 小时前
pikachu通关教程-CSRF XSS
前端·xss
lyz2468591 小时前
动态报表筛选多项时的优化处理
javascript·uni-app·view design
1024小神2 小时前
vue3 项目配置多语言支持,如何从服务端拿多语言配置
前端·javascript·vue.js
NoneCoder2 小时前
Symbol、Set 与 Map:新数据结构探秘
前端·javascript·数据结构