ChatGPT 选择采用 SSE 协议而非 Websocket 的理由是什么?深入探讨的SSE(Server-Sent Events)技术
在探索 ChatGPT 的使用过程中,我们发现 GPT 采用了流式数据返回的方式。理论上,这种情况可以通过全双工通信协议实现持久化连接,或者依赖于基于 EventStream 的事件流。然而,ChatGPT 选择了后者,也就是本文即将深入探讨的 SSE(Server-Sent Events)技术。要理解这个选择,我们需要关注 ChatGPT 的使用场景。作为一个基于深度学习的大型语言模型,ChatGPT 需要处理大量的自然语言数据,这无疑需要大量的计算资源和时间。相较于普通的读取数据库操作,其响应速度自然会慢许多。对于这种可能需要长时间等待响应的对话场景,ChatGPT 采用了一种巧妙的策略:它会将已经计算出的数据“推送”给用户,并利用 SSE 技术在计算过程中持续返回数据。这样做可以避免用户因等待时间过长而选择关闭页面。
什么是 SSE?SSE(Server-Sent Events)是一种 Web 技术,它允许服务器实时向客户端推送数据。相比于传 ...
工具与效率
1、 js单行替换//[\s\S]*?\n
// 使用 //(?!._.._.).*\n 可以避免将网址等也替换掉
2、 js多行替换/\*(.|\r\n|\n)*?\*/
3、html无换行注释<!--(.*?)-->
4、 html有换行注释<!--([\s\S|\r]*?)-->
也可以匹配到html无换行注释,所以只用这一个也可以
5、编辑器内所有空行^\s*(?=\r?$)\n
部署与运维
查看服务器上所有的 docker 镜像docker images
这个命令会列出所有在本地存在的 Docker 镜像,包括它们的大小和标签信息。如果你想要更详细的信息,可以使用以下命令:
docker images --digests
这会显示每个镜像的摘要信息。如果你想要查看特定仓库的镜像,可以使用–filter 参数来过滤结果:
docker images --filter "reference=<repository-name>"
# 将<repository-name>替换成你想要查看的仓库名称。
查看正在运行的 Docker 容器docker ps
可以使用-a或--all参数来显示所有容器,包括未运行的容器:
docker ps -a
docker ps -a 和 docker images 的区别
docker ps 和 docker images 是两个不同的 Docker 命令,它们显示的信息也有所不同:docker ps:这个命令用于列出容器的信息。docker ps 默认只显示当前正在运行的容器。使用 -a 或 –all 参数可以显示所有容器 ...
前端开发
React核心基础与实践指南React是当今最流行的前端框架之一,它通过组件化的方式让我们能够构建用户界面。本文将系统性地介绍React的核心概念,包括组件、Props、State、生命周期、Hooks等,并通过实际案例展示如何构建React应用。
1. React基础概念1.1 什么是React?React是一个用于构建用户界面的JavaScript库,由Facebook开发并维护。它的主要特点包括:
组件化:将UI拆分为独立的、可复用的组件
虚拟DOM:通过虚拟DOM提高渲染性能
单向数据流:数据从父组件流向子组件
声明式编程:描述UI应该是什么样子,而不是如何操作DOM
1.2 JSX语法JSX是JavaScript的语法扩展,允许我们在JavaScript中编写类似HTML的代码:
// JSX语法示例
const element = <h1>Hello, React!</h1>;
// 在JSX中使用JavaScript表达式
const name = 'React';
const element = <h1>Hello, {name ...
前端开发
移动互联网时代,用户对于网页的打开速度要求越来越高。首屏作为直面用户的第一屏,其重要性不言而喻。优化用户体验更是我们前端开发非常需要 focus 的东西之一。从用户的角度而言,当打开一个网页,往往关心的是从输入完网页地址后到最后展现完整页面这个过程需要的时间,这个时间越短,用户体验越好。所以作为网页的开发者,就从输入 url 到页面渲染呈现这个过程中去提升网页的性能。所以输入 URL 后发生了什么呢?在浏览器中输入 url 会经历域名解析、建立 TCP 连接、发送 http 请求、资源解析等步骤。http 缓存优化是网页性能优化的重要一环,这一部分我会在后续笔记中做一个详细总结,所以本文暂不多做详细整理。本文主要从网页渲染过程、网页交互以及 Vue 应用优化三个角度对性能优化做一个小结。
一、页面加载及渲染过程优化浏览器渲染流程
首先谈谈拿到服务端资源后浏览器渲染的流程:
解析 HTML 文件,构建 DOM 树,同时浏览器主进程负责下载 CSS 文件
CSS 文件下载完成,解析 CSS 文件成树形的数据结构,然后结合 DOM 树合并成 RenderObject 树
布局 Rend ...
大模型与AI
import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
import { z } from "zod";
const NWS_API_BASE = "https://api.weather.gov";
const USER_AGENT = "weather-app/1.0";
// Helper function for making NWS API requests
async function makeNWSRequest<T>(url: string): Promise<T | null> {
const headers = {
"User-Agent": USER_AGENT,
Accept: "application/g ...
前端开发
js 中的事件循环 event loop
所谓单线程,是指在JS引擎中负责解释和执行JavaScript代码的线程只有一个。
事件循环负责收集用事件(包括用户事件以及其他非用户事件等)、对任务进行排队以便在合适的时候执行回调。然后它执行所有处于等待中的 JavaScript 任务(宏任务),然后是微任务,然后在开始下一次循环之前执行一些必要的渲染和绘制操作。
1、同步任务同步任务指的是,在主线程上排队执行的任务,只有前一个任务执行完毕,才能执行后一个任务;
2、异步任务异步任务指的是,不进入主线程、而进入”任务队列”(task queue)的任务。只有等主线程任务执行完毕,"任务队列"开始通知主线程,请求执行任务,该任务才会进入主线程执行。
1)所有同步任务都在主线程上执行,形成一个执行栈(execution context stack)。(2)主线程之外,还存在一个”任务队列”(task queue)。只要异步任务有了运行结果,就在”任务队列”之中放置一个事件。(3)一旦”执行栈”中的所有同步任务执行完毕,系统就会读取”任务队列”,看看里面有哪些事件。那 ...
前端开发
动态引入css(less/sass)文件,在保证功能不变的前提下,适配不同的UI。
代码结构如图所示,我们可以根据配置文件(config.js)内的变量值,动态添加不同文件名的css(less/sass)文件即可
// 核心代码
import { a } from "../../config";
let p = a.project;
if (a.project === "236") {
import("./index_.less")
.then(({ default: style }) => {
console.log("加载 less 成功!");
})
.catch((err) => {
console.log(err, "加载less失败");
});
import("./index2.less")
.then(({ default: style }) => {
consol ...
前端开发
import Vue from 'vue'
import Router from 'vue-router'
// import http from '@/utils/request'
import { isURL } from '@/utils/validate'
import loginHttp from '@/utils/loginRequest'
Vue.use(Router)
// 页面路由(独立页面)
export const pageRoutes = [
{
path: '/404',
component: () => import('@/views/pages/404'),
name: '404',
meta: { title: '404未找到' },
beforeEnter(to, from, next) {
// 拦截处理特殊业务场景
// 如果, 重定向路由包含__双下划线, 为临时添加路由
if (/__.*/.test( ...
前端开发
https://developer.mozilla.org/zh-CN/docs/Web/CSS/border-image-slice
border-image-slice 指定图像的边界向内偏移通过 border-image-source 引用边框图片后,border-image-slice 属性会将图片分割为 9 个区域:四个角,四个边(edges)以及中心区域。四条切片线,从它们各自的侧面设置给定距离,控制区域的大小。
中间的区域将不会被边框使用,但当设置有 fill 关键词时将会被作为 background-image。这个关键词可以被设置在属性的任何一个位置(前面、后面或者两个值之间)
border-image-repeat, border-image-width, border-image-outset 属性则定义这些图片将如何使用。
前端开发
vue项目内
1、插件安装npm install amfe-flexible postcss-px2rem -S
2、引入使用(main.js)import "amfe-flexible";
3、配置(vue.config.js)module.exports = {
css: {
loaderOptions: {
postcss: {
plugins: [
// 设计稿宽度的1/10,一般为192,设计稿为1920
require("postcss-px2rem")({ remUnit: 192 }),
],
},
},
},
};
注意事项:由于是做了适配,那么没有给定大小(默认大小)的元素会发生变化,为了避免这种问题,需要给这类元素一个默认大小
前端开发
npm 会根据 package.lock.json 文件进行包安装cnpm 只会根据 package.json 文件进行包安装