GLM-4-9B-Chat-1M Chainlit集成教程:WebSocket流式传输+前端Token计数器实现

GLM-4-9B-Chat-1M Chainlit集成教程:WebSocket流式传输+前端Token计数器实现

1. 项目概述与学习目标

今天我们来学习如何将强大的GLM-4-9B-Chat-1M大模型与Chainlit前端框架完美集成,实现WebSocket流式传输和前端Token计数功能。这个教程特别适合想要快速搭建AI对话应用的开发者。

通过本教程,你将学会:

  • 如何部署GLM-4-9B-Chat-1M大模型
  • 如何使用Chainlit构建美观的Web界面
  • 如何实现WebSocket流式传输让回复逐字显示
  • 如何在前端实时统计Token使用情况
  • 如何解决实际部署中的常见问题

不需要深厚的技术背景,只要会基本的Python编程就能跟着做。我们用的GLM-4-9B-Chat-1M支持惊人的100万上下文长度,相当于约200万中文字符,这在长文档处理方面表现非常出色。

2. 环境准备与模型部署

2.1 系统要求与依赖安装

首先确保你的环境满足以下要求:

  • Python 3.8或更高版本
  • 足够的GPU内存(建议至少24GB)
  • 基本的Python包管理知识

安装必要的依赖包:

pip install chainlit transformers torch vllm 

2.2 验证模型部署状态

部署完成后,我们需要确认模型服务是否正常运行。通过以下命令检查部署状态:

cat /root/workspace/llm.log 

如果看到类似下面的输出,说明模型部署成功:

Model loaded successfully Service started on port 8000 Inference engine ready 

这个日志文件会显示模型加载的详细过程,包括内存占用、加载时间等关键信息。如果遇到问题,首先检查这个日志文件。

3. Chainlit前端集成基础

3.1 创建Chainlit应用

Chainlit是一个专门为AI应用设计的Python框架,可以快速构建交互式界面。创建一个基本的app.py文件:

import chainlit as cl from vllm import LLM, SamplingParams # 初始化模型 llm = LLM(model="/path/to/glm-4-9b-chat-1m") @cl.on_chat_start async def start_chat(): # 初始化会话状态 await cl.Message(content="欢迎使用GLM-4-9B聊天助手!").send() @cl.on_message async def main(message: cl.Message): # 处理用户消息 response = "这是模型的回复" await cl.Message(content=response).send() 

3.2 启动Chainlit服务

运行以下命令启动前端服务:

chainlit run app.py -w 

-w参数表示自动重新加载,在开发时特别有用。启动后,在浏览器中打开显示的地址(通常是http://localhost:8000)就能看到聊天界面了。

4. WebSocket流式传输实现

4.1 配置流式响应

传统的API调用需要等待完整响应,而流式传输可以让回复逐字显示,用户体验更好。修改之前的代码:

@cl.on_message async def main(message: cl.Message): # 设置采样参数 sampling_params = SamplingParams( temperature=0.7, max_tokens=1024, stream=True ) # 创建消息对象用于流式更新 msg = cl.Message(content="") await msg.send() # 流式生成回复 stream = llm.generate(message.content, sampling_params, stream=True) for chunk in stream: if chunk.text: await msg.stream_token(chunk.text) await msg.update() 

4.2 处理流式数据

流式传输的关键在于逐步发送数据而不是一次性发送完整响应。这种方法有几个好处:

  • 用户不用长时间等待空白屏幕
  • 可以实时看到生成过程
  • 如果生成了不满意的内容,可以提前停止

在实际应用中,你可能会遇到网络延迟或中断的情况,建议添加重试机制和超时处理。

5. 前端Token计数器实现

5.1 Token统计原理

Token是模型处理文本的基本单位,了解Token使用情况有助于控制成本和优化体验。我们需要在前后端都进行统计:

import tiktoken # 用于Token计数 def count_tokens(text): """统计文本的Token数量""" encoding = tiktoken.get_encoding("cl100k_base") return len(encoding.encode(text)) @cl.on_message async def main(message: cl.Message): # 统计输入Token input_tokens = count_tokens(message.content) msg = cl.Message(content="") await msg.send() stream = llm.generate(message.content, sampling_params, stream=True) for chunk in stream: if chunk.text: await msg.stream_token(chunk.text) full_response += chunk.text # 统计输出Token output_tokens = count_tokens(full_response) # 发送Token统计信息 token_info = f"\n\n---\n*输入Token: {input_tokens} | 输出Token: {output_tokens} | 总计: {input_tokens + output_tokens}*" await cl.Message(content=token_info).send() 

5.2 实时显示Token计数

为了让用户实时看到Token使用情况,我们可以创建更高级的显示方式:

@cl.on_message async def main(message: cl.Message): # 创建Token计数显示 token_display = cl.Message(content="计算中...") await token_display.send() input_tokens = count_tokens(message.content) total_tokens = input_tokens # 更新Token显示 await token_display.update(content=f"输入Token: {input_tokens} | 输出Token: 0 | 总计: {total_tokens}") msg = cl.Message(content="") await msg.send() stream = llm.generate(message.content, sampling_params, stream=True) for chunk in stream: if chunk.text: await msg.stream_token(chunk.text) full_response += chunk.text # 实时更新Token计数 output_tokens = count_tokens(full_response) total_tokens = input_tokens + output_tokens await token_display.update(content=f"输入Token: {input_tokens} | 输出Token: {output_tokens} | 总计: {total_tokens}") 

6. 完整集成示例代码

下面是一个完整的集成示例,包含了所有功能:

import chainlit as cl from vllm import LLM, SamplingParams import tiktoken import asyncio # 初始化模型和编码器 llm = LLM(model="/path/to/glm-4-9b-chat-1m") encoding = tiktoken.get_encoding("cl100k_base") def count_tokens(text): """统计文本的Token数量""" return len(encoding.encode(text)) @cl.on_chat_start async def start_chat():"欢迎使用GLM-4-9B-Chat-1M聊天助手! 特性: - 支持100万上下文长度 - 流式响应,逐字显示 - 实时Token计数 - 多语言支持 开始对话吧!""" await cl.Message(content=welcome_msg).send() @cl.on_message async def main(message: cl.Message): # 统计输入Token input_tokens = count_tokens(message.content) # 创建Token计数显示 token_display = cl.Message(content=f"输入Token: {input_tokens} | 输出Token: 0 | 总计: {input_tokens}") await token_display.send() # 创建回复消息 msg = cl.Message(content="") await msg.send() # 设置生成参数 sampling_params = SamplingParams( temperature=0.7, max_tokens=1024, top_p=0.9, stream=True ) # 流式生成回复 try: stream = llm.generate(message.content, sampling_params, stream=True) for chunk in stream: if chunk.text: await msg.stream_token(chunk.text) full_response += chunk.text # 更新Token计数(每秒更新一次,避免过于频繁) output_tokens = count_tokens(full_response) total_tokens = input_tokens + output_tokens await token_display.update(content=f"输入Token: {input_tokens} | 输出Token: {output_tokens} | 总计: {total_tokens}") # 稍微延迟以避免过于频繁的更新 await asyncio.sleep(0.1) except Exception as e: error_msg = f"生成过程中出现错误: {str(e)}" await msg.update(content=error_msg) await msg.update() # 最终更新Token计数 output_tokens = count_tokens(full_response) total_tokens = input_tokens + output_tokens await token_display.update(content=f"输入Token: {input_tokens} | 输出Token: {output_tokens} | 总计: {total_tokens}") # Chainlit配置 cl.integration_settings.auto_scroll = True cl.integration_settings.show_sidebar = True 

7. 部署与优化建议

7.1 性能优化技巧

在实际部署中,可以考虑以下优化措施:

内存优化

# 使用量化模型减少内存占用 llm = LLM( model="/path/to/glm-4-9b-chat-1m", quantization="awq", # 使用AWQ量化 gpu_memory_utilization=0.8 # 控制GPU内存使用率 ) 

响应速度优化

# 调整生成参数平衡速度和质量 sampling_params = SamplingParams( temperature=0.7, max_tokens=512, # 限制生成长度 skip_special_tokens=True, # 跳过特殊Token stop=[".", "!", "?"] # 设置停止条件 ) 

7.2 常见问题解决

模型加载失败

  • 检查模型路径是否正确
  • 确认有足够的GPU内存
  • 查看llm.log获取详细错误信息

流式传输中断

  • 检查网络连接稳定性
  • 增加超时设置
  • 添加重试机制

Token计数不准

  • 确保使用正确的编码器
  • 检查文本预处理步骤

8. 总结

通过这个教程,我们完整实现了GLM-4-9B-Chat-1M模型与Chainlit的集成,包括WebSocket流式传输和前端Token计数器。这种集成方式不仅提升了用户体验,还提供了实用的Token统计功能。

关键收获

  • Chainlit让AI应用前端开发变得简单
  • 流式传输显著改善用户等待体验
  • Token计数帮助监控使用成本和效率
  • GLM-4-9B-Chat-1M的长上下文能力开启了许多新应用场景

下一步建议

  • 尝试添加对话历史管理功能
  • 探索模型的多语言能力
  • 添加自定义工具调用功能
  • 优化前端界面和用户体验

现在你已经掌握了构建现代化AI聊天应用的核心技能,可以在此基础上继续扩展功能,打造更强大的应用了。


获取更多AI镜像

想探索更多AI镜像和应用场景?访问 ZEEKLOG星图镜像广场,提供丰富的预置镜像,覆盖大模型推理、图像生成、视频生成、模型微调等多个领域,支持一键部署。

Read more

GitHub Copilot Pro 学生认证免费订阅及VS Code集成完整教程

GitHub Copilot Pro 学生认证免费订阅及VS Code集成完整教程

GitHub Copilot Pro 学生认证免费订阅及VS Code集成完整教程 一、学生认证资格与前期准备 1.1 认证资格要求 GitHub Copilot Pro 为经官方验证的全日制学生、在职教师及热门开源项目维护者提供免费订阅权限。认证需满足以下核心条件: * 学生需提供有效学籍证明(学生卡/学信网认证) * 教师需提供工作证/教师资格证 * 使用学校官方邮箱(以.edu或.edu.cn结尾) * 账户需通过双重身份认证(2FA) 1.2 账户设置准备 1. 绑定教育邮箱 在GitHub账户设置中添加学校邮箱,并完成验证: * 进入Settings → Emails → Add email address * 输入形如[email protected]的邮箱 * 登录学校邮箱查收验证邮件并确认 2. 完善个人信息 在Profile → Edit profile中填写:

EFSI-DETR:用于无人机图像实时小目标检测的高效频域 - 语义集成方法

EFSI-DETR:用于无人机图像实时小目标检测的高效频域 - 语义集成方法

https://arxiv.org/pdf/2601.18597 作者:Yu Xia, Chang Liu, Tianqi Xiang, Zhigang Tu (IEEE 高级会员) 摘要 由于特征表示有限和多尺度融合效果不佳,无人机(UAV)图像中的实时小目标检测仍然具有挑战性。现有方法未能充分利用频率信息,且依赖于静态卷积操作,这限制了获取丰富特征表示的能力,并阻碍了对深层语义特征的有效利用。为了解决这些问题,我们提出了 EFSI-DETR,这是一种新颖的检测框架,集成了高效的语义特征增强与动态频域 - 空间引导。EFSI-DETR 包含两个主要组件:(1) 动态频域 - 空间统一协同网络(DyFusNet),联合利用频率和空间线索进行鲁棒的多尺度特征融合;(2) 高效语义特征集中器(ESFC),以最小的计算成本实现深层语义提取。此外,采用了细粒度特征保留(FFR)策略,在融合过程中纳入空间丰富的浅层特征,

Stable-Diffusion-v1-5-archive效果展示:高清风格化图像生成作品集(附Prompt)

Stable-Diffusion-v1-5-archive效果展示:高清风格化图像生成作品集(附Prompt) 1. 引言:经典模型的魅力再现 如果你对AI绘画感兴趣,那么“Stable Diffusion”这个名字你一定不陌生。而今天我们要聊的,是它的一个经典版本——Stable Diffusion v1.5 Archive。这个模型就像是AI绘画世界里的“老将”,虽然现在有更新、更强大的模型出现,但它在风格化图像生成上的稳定性和独特的“味道”,依然让很多创作者爱不释手。 简单来说,Stable Diffusion v1.5 Archive是一个专门用来“文生图”的工具。你输入一段文字描述,它就能为你生成一张对应的图片。它的特点在于,对于很多艺术风格——比如油画感、动漫风、赛博朋克——有着非常出色的理解和表现力,生成的作品往往带有一种独特的质感和氛围。 这篇文章,我们不谈复杂的安装和配置,也不讲深奥的原理。我们就来一起看看,这个经典的模型到底能生成出怎样惊艳的图片。我会分享一系列不同风格、不同主题的生成作品,并且把生成每张图所用的“

基于 NSGA-II 的城市密集区无人机多目标路径规划 ——Matlab 实现与核心算法解析

基于 NSGA-II 的城市密集区无人机多目标路径规划 ——Matlab 实现与核心算法解析

城市密集区的无人机路径规划是无人机自主导航领域的经典难题,其核心痛点在于需要同时满足硬约束防撞、动力学极限、多目标性能折中三大核心要求。本文基于非支配排序遗传算法(NSGA-II),实现了城市密集区无人机的多目标路径规划 Matlab 方案,针对建筑避障、雷达威胁、飞行能耗、轨迹平滑等需求完成了全流程建模与开发,通过B 样条轨迹平滑、分层罚函数机制、高阶可视化面板等关键设计,解决了复杂场景下的轨迹穿模、约束违规、多目标权衡等问题。 目录 一、研究背景与问题建模 1.1 城市密集区规划难点 1.2 算法选型与整体设计 二、核心模块详细实现 2.1 复杂场景构建模块(build_Scenario.m) 2.1.1 场景核心要素 2.1.2 关键参数表 2.2 染色体解码与 B 样条轨迹生成