一、什么是 GPT-4 及其自动化测试?
1.1 GPT-4 是什么?
GPT-4 是 OpenAI 推出的一种非常强大的人工智能语言模型,它可以用来写文章、翻译语言、回答问题、写代码,甚至陪你聊天。你和它对话的方式就像和真人交流一样,它会根据你说的话来生成合适的回复。
它厉害的原因在于:
-
训练时用了海量的互联网文本数据;
-
它的“大脑”是基于一种叫做 Transformer 的结构,非常适合处理语言;
-
它可以理解上下文,说话前后能连贯、还能“懂你”。
不过,GPT-4 也不是万能的。它有两个比较大的问题:
-
看不见它的内部逻辑:我们只能看到它的输入和输出,不能知道它“为什么这样回答”。
-
每次输出可能不一样:同一个问题,换个提示词(prompt)或者设置,就可能得到不同答案。
所以你不能用传统的软件测试方法(比如“输入 A 就一定输出 B”)来测试它。这时,就需要一种更适合语言模型的测试方式,来判断它的表现好不好。
1.2 为什么要做自动化测试?
如果你正在开发一个用 GPT-4 实现的智能问答系统,或者客服机器人,你可能会遇到这些烦恼:
-
聊天过程中,GPT-4 能不能记住前面的内容?
-
它有没有在一些特殊问题上出错?比如问它不存在的东西,它是不是乱说?
-
换一个提示词,它的表现是变好了,还是变差了?
-
我给它加了知识库,它到底有没有用这些知识来回答问题?
-
我怎么知道它的回答是不是比上一个版本更好?
如果每次都靠人来一个一个问、一个一个比,不但太累,而且不准确。
所以,我们需要一个 自动化的测试框架,来完成这些事:
模拟多轮对话,看上下文是否保持清晰
测试极端输入,比如空问题、乱码,看模型会不会崩
自动对回答进行打分,比如和“标准答案”对比相似度
测试不同的提示词、加不加知识库,效果有什么变化
跑一批问题,统计整体的平均表现
只有这样,才能快速发现问题、反复优化提示词和架构,做出一个真正可靠的 AI 应用。
二、前置
Prompt Engineering(提示词工程)
通过控制输入的 prompt(提示词)来引导大模型生成更优质、更稳定的输出。
常见技巧包括:
-
角色设定(system prompt)
-
模板化结构
-
few-shot 示例
-
chain-of-thought 思维链引导
RAG(检索增强生成,Retrieval-Augmented Generation)
将外部知识库中的内容(如百科、FAQ、数据库等)通过检索系统(如 Elasticsearch)提取出来,注入 prompt 提供背景信息,提升生成质量。
流程如下:
-
用户提问
-
系统检索相关文档
-
将文档注入 prompt 中再交由 GPT-4 回答
RAG 能解决模型“幻觉”、“不知道就瞎说”等问题。
LLM 评估指标
传统分类模型可用准确率等指标,而 LLM 输出是自由文本,评估变得更难。
我们使用以下几种指标:
| 指标 | 用途 | 底层原理 |
|---|---|---|
| BLEU | 机器翻译质量评估 | n-gram 精确匹配 |
| ROUGE | 文本摘要质量评估 | n-gram 召回率 |
| BERTScore | 语义相似度(最贴近人类) | 基于 BERT 的向量相似度 |
实战中,这些指标可以帮助我们判断 prompt 是否优化有效,是否需要引入外部知识(RAG),以及模型是否退化等。
技术栈与前置环境
一、Elasticsearch 是什么?
-
Elasticsearch(简称 ES)是一个开源的搜索引擎,用来快速搜索、筛选、匹配文本信息。它本质上是一个支持全文检索、结构化检索、模糊匹配的数据库系统,特别适合处理大规模的文档/文本数据。
简单来说:当你有很多文章、问答、知识条目时,想从中找到“最相关的那几条” —— 用 Elasticsearch 就对了。
二、本项目中 ES 的作用是什么?
在这个 GPT-4 自动化测试框架中,ES 扮演着**知识检索模块(RAG)**的重要角色:
-
用户输入一个问题
↓ -
系统从 Elasticsearch 中找出几条相关的知识片段(如医学资料)
↓ -
把这些资料“注入”到 Prompt 里再送给 GPT-4
↓ -
GPT 的回答就能更专业、更有依据,而不是“瞎说”
Tip:确保已启动本地 Elasticsearch(默认
http://localhost:9200),并索引了名为medical_docs的文档(字段text存储内容)。
项目结构一览
gpt4_test_framework/
├── prompts/
│ └── rag_template.txt # RAG 模板文件
├── corpus/
│ └── medical_qa.json # 测试用文档占位
├── retriever/
│ └── elastic_search.py # Elasticsearch 检索逻辑
├── generator/
│ └── gpt4_interface.py # GPT‑4 API 封装
├── evaluator/
│ ├── bleu_eval.py # BLEU 评分
│ ├── rouge_eval.py # ROUGE 评分
│ └── bertscore_eval.py # BERTScore 评分
├── testcases/
│ ├── multi_turn_test.py # 多轮对话测试
│ └── rag_test.py # RAG 测试
├── utils/
│ └── logger.py # 日志工具
└── run_tests.py # 评估脚本入口
模块详解
4.1 GPT‑4 接口封装
这个模块负责对 OpenAI 的 Chat API 进行封装,统一调用方式和错误处理。
import openai # 导入 OpenAI 的官方 Python SDK
def call_gpt4(messages, temperature=0.7):
"""
发送多轮消息到 GPT-4 并返回回答内容。
参数:
messages:对话列表,每个元素是 {"role": ..., "content": ...}
temperature:控制回答的随机性(0~1)
返回:
模型生成的文本,或者错误信息。
"""
try:
response = openai.ChatCompletion.create(
model="gpt-4", # 你也可以改为 gpt-4-turbo
messages=messages, # 上下文对话内容
temperature=temperature,
max_tokens=500 # 限制输出长度
)
return response.choices[0].message['content']
except openai.error.OpenAIError as e:
return f"[ERROR] {str(e)}" # 出错时返回错误字符串
4.2 RAG 检索模块
用于 RAG 模式,从 Elasticsearch 检索知识段落,后续注入到 GPT 的 prompt 中。
from elasticsearch import Elasticsearch
es = Elasticsearch("http://localhost:9200") # 连接本地 ES 服务
def retrieve_knowledge(question):
"""
根据问题检索 ES 中最相关的知识片段(Top 3)。
返回:
用换行拼接的三段文本。
"""
query = {
"query": {
"match": {
"text": question # 模糊匹配 text 字段
}
}
}
res = es.search(index="medical_docs", body=query)
top_k = [hit["_source"]["text"] for hit in res["hits"]["hits"][:3]]
return "\n".join(top_k)
4.3 评估指标模块
这里是模型输出质量评估的核心指标模块,包含三种打分方式:
-
BLEU (
evaluator/bleu_eval.py)用于对照参考答案中的词汇重合程度,适合简答题/翻译。from nltk.translate.bleu_score import sentence_bleu def calc_bleu(reference, candidate): """ 计算 BLEU 分数。 """ return sentence_bleu([reference.split()], candidate.split()) -
ROUGE (
evaluator/rouge_eval.py)常用于摘要和问答,衡量“是否答对重点”。 -
from rouge_score import rouge_scorer def calc_rouge(reference, candidate): """ 计算 ROUGE-1 和 ROUGE-L 分数。 """ scorer = rouge_scorer.RougeScorer(['rouge1', 'rougeL'], use_stemmer=True) return scorer.score(reference, candidate) -
BERTScore (
evaluator/bertscore_eval.py)通过深度语义对比,更贴近人类判断。from bert_score import score as bert_score def calc_bertscore(reference, candidate): """ 使用 BERT 模型计算语义相似度。 """ P, R, F1 = bert_score([candidate], [reference], lang="zh", model_type="bert-base-chinese") return F1[0].item()
每个函数都接收「标准答案」ref 和「模型输出」cand,返回对应指标分数。
4.4 测试用例设计
-
多轮对话 (
testcases/multi_turn_test.py)用于测试:上下文是否记得住?回答是否连贯?from generator.gpt4_interface import call_gpt4 def test_multi_turn(): """ 模拟连续提问场景,测试 GPT 的上下文连贯性。 """ # 第一句对话 msg1 = {'role': 'user', 'content': '请介绍一下糖尿病。'} ans1 = call_gpt4([msg1]) # 第二轮提问基于上文 msg2 = {'role': 'user', 'content': '那患者饮食上要注意什么?'} # 多轮对话组合 full_dialogue = [ msg1, {'role': 'assistant', 'content': ans1}, msg2 ] print(call_gpt4(full_dialogue)) -
RAG 测试 (
testcases/rag_test.py)用于测试:模型是否能利用知识回答得更准确?from retriever.elastic_search import retrieve_knowledge from generator.gpt4_interface import call_gpt4 def test_rag_response(): """ 将检索出的知识注入 prompt 进行问答。 """ question = "高血压患者要注意什么?" context = retrieve_knowledge(question) prompt = [ {"role": "system", "content": "你是一位医学专家"}, {"role": "user", "content": f"背景知识:\n{context}\n\n问题:{question}"} ] print(call_gpt4(prompt))
4.5 一键运行脚本
文件:run_tests.py
from evaluator.bleu_eval import calc_bleu
from evaluator.rouge_eval import calc_rouge
from evaluator.bertscore_eval import calc_bertscore
# 模拟参考答案和模型回答
reference = "高血压的常见症状包括头痛、眩晕和心悸。"
candidate = "常见症状有头痛、眩晕、心悸等。"
print("BLEU 分数:", calc_bleu(reference, candidate))
print("ROUGE 分数:", calc_rouge(reference, candidate))
print("BERTScore 分数:", calc_bertscore(reference, candidate))
-
运行即得到三项指标结果,检查评估模块可用性。
五、如何运行框架(附完整命令与运行效果)
下面我们来看如何实际运行这个 GPT-4 测试框架,从配置 API 到运行用例和查看评分结果。
第一步:配置 OpenAI API 密钥
GPT-4 是一个联网的模型服务,使用前你需要有 OpenAI 的 API 密钥。
方法一:在代码中设置(不推荐线上使用)
import openai
openai.api_key = "sk-xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
✅ 第二步:启动 Elasticsearch 检索服务(用于 RAG)
一般来说有本地启动Elasticsearch以及使用docker两种方式,本文使用本地启动
1. 下载 Elasticsearch 安装包
于官网下载自己系统对应的版本即可Download Elasticsearch | Elastic
2. 解压并启动服务
以 Windows 为例:
▶ 解压 zip 包到任意目录,例如:
D:\elasticsearch-8.12.0\
▶ 双击运行启动脚本:
D:\elasticsearch-8.12.0\bin\elasticsearch.bat
3. 测试 Elasticsearch 是否正常运行
打开浏览器访问默认端口:
http://localhost:9200
如果看到类似这样的 JSON 响应,就说明你启动成功了:
{
"name": "your-node-name",
"cluster_name": "elasticsearch",
"version": {
"number": "8.12.0",
...
}
}
4. 关闭安全认证(适合开发环境)
Elasticsearch 8 默认开启了用户名/密码认证和 HTTPS。为了简化本地测试,我们可以关闭它:
编辑文件:config/elasticsearch.yml
在文件末尾添加:
xpack.security.enabled: false
如果你已经打开了Elasticsearch,需要保存后重新启动
5. 导入示例文档
使用 curl 命令导入一条知识文档:
curl -X POST http://localhost:9200/medical_docs/_doc -H "Content-Type: application/json" -d '{
"text": "高血压的常见症状包括头痛、头晕、心悸等。"
}'
或用 Python 代码插入文档(推荐):
from elasticsearch import Elasticsearch
es = Elasticsearch("http://localhost:9200")
doc = {
"text": "高血压是一种以动脉血压升高为特征的慢性病,常见症状有头晕、头痛、心悸。"
}
es.index(index="medical_docs", document=doc)
1010

被折叠的 条评论
为什么被折叠?



