
各位读者好。钱币收藏圈一直有个老问题一枚光绪元宝或者袁大头放到网上不同人看边齿、看包浆、看字口往往能得出完全相反的结论。人工鉴定依赖的是长期经验经验又很难复制到系统里。大模型出现之后这类“看图 知识推理”的任务有了新的落地方式也就是把多模态识别和 Agent 工具编排结合起来做一个 AI 钱币鉴定助手。今天这篇文章从一个可运行的工程视角出发完整拆解一个 AI 钱币鉴定 Agent 的实现过程。整体技术组合是Claude Agent 负责任务规划、工具调用与最终报告生成智谱 GLM 大模型负责钱币图片的多模态特征识别。通过这个项目你可以掌握 Agent 工具调用循环的基本写法也能学会如何把商用大模型 API 组合成真实可用的业务应用。无论你是刚接触大模型应用开发还是已经写过一些 API 调用脚本这篇文章都会给你一套能直接照搬的思路和代码骨架。1. 背景为什么大模型可以参与钱币鉴定1.1 钱币鉴定的本质是什么钱币鉴定不是简单地看“花纹清不清楚”而是一个典型的“视觉特征提取 领域知识推理”任务。专业鉴定师拿到一枚钱币通常会做这样几件事看文字与图案的压制效果也就是字口是否挺拔、图案是否立体。看边齿形态机制币的边齿有直齿、橄榄齿、鹰洋齿等不同种类仿品往往做不出自然磨损。看包浆的层次感真币包浆是长期氧化形成的层次自然假币包浆常浮于表面。对比已知版别不同省份、不同年份、不同造币厂生产的同一面值钱币细节差别很大。综合判断历史痕迹比如磕碰、划痕、流通磨损是否符合年代特征。这些判断步骤如果写成代码过去几乎不可能。因为 “自然磨损” 和 “假币做旧” 之间没有固定公式传统图像处理只能提取边缘、颜色、纹理等低层特征很难做语义级别的判断。而多模态大模型正好擅长把图像内容“翻译”成文本描述并且具备一定的版别知识可以作为辅助鉴定工具。1.2 从单次问答到 Agent 协作如果我们只是把一张钱币图片发给一个大模型让它直接判断真伪会遇到两个问题。第一是“幻觉”问题。模型可能没看清图中文字却给出非常笃定的结论。第二是“一次调用”能力有限模型只能基于自己的内部知识回答无法分步思考也无法在回答过程中调用外部工具去补充信息。Agent 的思想是大模型不再只做“输入一句话、输出一句话”的问答机器而是成为一个“规划者”。它可以拆解任务、决定下一步调用什么工具、读取工具返回结果再决定是否需要继续行动最后生成结论。在 AI 钱币鉴定场景下这个思路非常合适。Claude Agent 可以扮演鉴定专家的“大脑”先规划需要观察哪些特征然后调用一个“钱币图片识别工具”这个工具内部交给智谱 GLM 视觉大模型去完成多模态识别。拿到识别结果后Claude Agent 再结合钱币学知识输出完整报告。1.3 为什么选择 Claude Agent 智谱 GLM 的组合选择这个组合更多是出于职责分工的考虑Claude Agent 在工具调用和复杂指令遵循方面表现得比较稳定适合承担 Agent 的规划、循环控制、报告聚合任务。智谱 GLM 是多模态大模型国内可以直接通过开放平台 API 调用延迟相对可控适合承担图片识别任务。把“视觉识别”和“推理规划”分开还能灵活替换模型如果某个视觉模型效果不好只需要改一个工具函数不需要动 Agent 主流程。当然这并不是唯一方案。你也可以用其他支持视觉的大模型替换智谱 GLM用其他支持工具调用的模型替换 Claude。本文的重点是把整个架构和代码流程讲清楚你按需替换即可。2. 系统架构与核心流程2.1 整体架构设计AI 钱币鉴定 Agent 的整体架构可以拆成四层用户输入钱币图片 鉴定问题 | v ----------------------- | Claude Agent 规划层 | | - 理解用户需求 | | - 解析要调用什么工具 | | - 汇总工具结果 | ----------------------- | v ----------------------- | 工具调度层 | | - tool_use 解析 | | - 工具循环执行 | ----------------------- | v ----------------------- | 智谱 GLM 视觉识别层 | | - 图片预处理 | | - 多模态特征提取 | | - 结构文本描述 | ----------------------- | v ----------------------- | 最终鉴定报告 | | - 基本信息 | | - 特征观察 | | - 存疑点 | | - 参考结论 | -----------------------从用户视角来看整个调用过程像一个黑盒用户输入图片路径和问题最终收到一份结构化鉴定报告。从开发者视角来看核心要掌握三个点Agent 工具注册、工具调用循环、多模态图片编码。2.2 Agent 工具调用循环的 4 个步骤目前主流大模型 Agent 的工具调用一般都遵循以下循环将用户问题发送给模型同时在请求中声明可用的工具列表。模型分析问题后返回一个或多个工具调用请求而不是普通文本。开发者解析工具调用在本地真正执行对应函数拿到结果。把工具执行结果返回给模型模型继续生成结论或者发起下一次工具调用。这个循环会一直进行直到模型认为不再需要调用工具直接返回最终答案。为了防止程序无限循环我们要设置最大迭代次数。2.3 为什么图片识别要单独做成工具如果你用过视觉大模型可能会觉得奇怪Claude 本身也支持图片输入为什么还要绕一圈把图片交给智谱 GLM 识别这里的关键是分工和替换成本。实际项目中钱币图片可能来自用户上传、扫描件、拍卖网站截图等不同渠道图片质量参差不齐。如果把这些图片直接全部交给 Claude会占用大量多模态 token而且一旦图片质量差Claude 需要反复重试。更好的方式是单独做一个“图片分析工具”内部统一完成图片压缩、格式转换、Base64 编码再调用智谱 GLM 视觉模型输出结构化描述。这样做的好处是图片预处理逻辑与 Agent 主流程解耦。可以针对钱币场景定制更详细的识别 prompt。后续想换成其他视觉模型时不需要改 Agent 调度逻辑。所以本文的代码里Claude Agent 并不会直接“看见”图片它只能看到一个工具返回的文字识别结果。这种设计看起来多了一层其实是更工程化的做法。3. 环境准备与 API 配置3.1 基础环境说明本文代码使用 Python 编写需要准备以下环境Python 3.10 或更高版本。一个智谱开放平台账号用于获取智谱 GLM API Key。一个 Anthropic 账号用于获取 Claude API Key。本地命令行工具和任意 IDE本文示例使用 VS Code。版本需要根据你的项目实际情况调整本文示例以常见环境为例重点演示配置思路。如果你使用的是 Python 3.9 或更低版本代码中的str | None类型注解需要改成Optional[str]。3.2 创建项目目录与虚拟环境首先创建一个项目目录并进入目录mkdir ai-coin-appraiser cd ai-coin-appraiser然后创建 Python 虚拟环境并激活python -m venv venvWindows 下激活命令是venv\Scripts\activatemacOS 或 Linux 下激活命令是source venv/bin/activate3.3 安装依赖项目需要以下几个 Python 包anthropic zhipuai Pillow python-dotenv将这些依赖写入requirements.txtanthropic0.40.0 zhipuai2.1.0 Pillow10.0.0 python-dotenv1.0.0然后安装pip install -r requirements.txt说明一下每个包的作用anthropicClaude API 官方 SDK用于调用 Claude Agent。zhipuai智谱开放平台 SDK用于调用 GLM 视觉模型。PillowPython 图像处理库用于压缩和转换钱币图片。python-dotenv用于读取.env环境变量文件避免把密钥写死在代码里。3.4 配置 API Key在项目根目录创建.env文件ZHIPU_API_KEY你的智谱APIKey ANTHROPIC_API_KEY你的ClaudeAPIKey需要注意的是API Key 属于敏感信息不要把.env文件提交到 Git 仓库。建议同时在项目根目录创建.gitignore加入以下内容venv/ .env __pycache__/ *.pyc tmp_coin.jpg申请 API Key 的具体入口以对应开放平台控制台为准申请后建议开启调用权限限制只给需要调用的接口授权。3.5 项目文件结构整个项目结构如下ai-coin-appraiser/ ├── .env ├── .gitignore ├── requirements.txt ├── main.py ├── agent/ │ ├── __init__.py │ ├── claude_planner.py │ ├── glm_vision.py │ └── tools.py └── images/ └── sample_coin.jpgagent包存放 Agent 相关模块images目录存放待鉴定的钱币图片。本文后面的代码均以此项目结构为准。4. 核心代码实现4.1 实现智谱 GLM 视觉识别模块首先创建agent/glm_vision.py这个文件负责调用智谱 GLM 视觉模型输入是一张图片的本地路径输出是模型对图片内容的文本描述。# 文件路径agent/glm_vision.py import base64 import os from PIL import Image from zhipuai import ZhipuAI class GlmVision: 基于智谱 GLM 视觉模型的钱币图片识别器。 def __init__(self, api_key: str | None None): self.client ZhipuAI( api_keyapi_key or os.getenv(ZHIPU_API_KEY) ) def preprocess_image(self, image_path: str, max_size: int 1024) - str: 对图片进行缩放、格式转换并返回 Base64 字符串。 之所以先压缩图片是因为大模型视觉接口对图片尺寸和大小有限制 过大的原图会导致请求失败或增加不必要的 token 消耗。 with Image.open(image_path) as img: img.thumbnail((max_size, max_size)) img img.convert(RGB) tmp_path tmp_coin.jpg img.save(tmp_path, JPEG, quality85) with open(tmp_path, rb) as f: return base64.b64encode(f.read()).decode() def analyze_coin(self, image_path: str, prompt: str) - str: 将图片和提示词一起发送给 GLM 视觉模型。 注意model 参数中的模型名以开放平台控制台实际可用的名称为准 不同版本或不同账号可能看到不同的模型列表。 image_base64 self.preprocess_image(image_path) response self.client.chat.completions.create( modelglm-4v-plus, messages[ { role: user, content: [ {type: text, text: prompt}, { type: image_url, image_url: { url: fdata:image/jpeg;base64,{image_base64} }, }, ], } ], temperature0.2, ) return response.choices[0].message.content这个类做的事情很清晰preprocess_image把图片统一压到最长边不超过 1024 像素并转成 JPEG 格式最后编码成 Base64 字符串。analyze_coin把提示词和图片发送给视觉模型temperature设置为 0.2让输出更稳定保守减少随机发挥。返回模型生成的文本内容。有一点要强调视觉模型接口的具体请求格式会随着官方 SDK 升级而变化这里的代码作为一个参考写法。如果你运行时发现模型名或消息格式报错优先去开放平台文档或 SDK 源码里核对。4.2 封装图片分析工具为了让 Claude Agent 能够调用图片识别功能我们需要把GlmVision封装成一个工具函数。创建agent/tools.py# 文件路径agent/tools.py from .glm_vision import GlmVision # 在模块级别初始化视觉识别器避免每次调用都重新建立连接 vision GlmVision() # 针对钱币鉴定场景的专用提示词 COIN_ANALYSIS_PROMPT 你是钱币鉴定助手。请仔细观察图片中的钱币从以下维度输出信息 1. 钱币面额与币种例如“光绪元宝库平七钱二分”或“中华民国三年壹圆”。 2. 钱币文字与图案内容正反面文字、龙纹、嘉禾纹、人像等。 3. 材质与包浆特征颜色、包浆分布、是否有人工作旧痕迹。 4. 铸造工艺特征边齿形态、文字压力感、图案立体感。 5. 瑕疵或异常点划痕、磕碰、修补痕迹、铸缺、沙眼等。 请严格基于图片中能看到的信息回答不要编造细节。 如果你对某个特征不确定请直接写“无法确定”。 def analyze_coin_image(image_path: str, question: str ) - str: 供 Claude Agent 调用的工具函数。 参数 image_path: 钱币图片的本地路径。 question: 用户希望重点观察的鉴定问题。 返回 智谱 GLM 视觉模型对图片的文本描述。 prompt COIN_ANALYSIS_PROMPT if question: prompt f\n用户重点关注的问题{question} return vision.analyze_coin(image_path, prompt)把提示词单独拿出来是因为钱币鉴定的观察维度其实很固定。你可以在不改变工具函数结构的情况下随时调整提示词比如增加“请说明边齿类型”之类的专业要求。4.3 实现 Claude Agent 规划器接下来是 Agent 的核心也就是工具调用循环。创建agent/claude_planner.py# 文件路径agent/claude_planner.py import json import os from anthropic import Anthropic from .tools import analyze_coin_image class ClaudePlanner: 基于 Claude 的 Agent 规划器。 职责理解用户问题 - 决定是否调用图片分析工具 - 把工具结果交给 Claude 汇总 - 输出最终报告。 def __init__(self, api_key: str | None None): self.client Anthropic( api_keyapi_key or os.getenv(ANTHROPIC_API_KEY) ) self.tools [ { name: analyze_coin_image, description: 使用智谱GLM视觉大模型分析一张钱币图片返回钱币的文字图案、工艺特征、包浆特征和瑕疵描述。, input_schema: { type: object, properties: { image_path: { type: string, description: 钱币图片的本地路径, }, question: { type: string, description: 用户希望重点鉴定的问题, }, }, required: [image_path], }, } ] def run(self, user_input: str, image_path: str, max_iters: int 3) - str: 执行 Agent 工具调用循环。 max_iters 用于限制最多调用几轮工具防止模型陷入重复调用。 messages [ { role: user, content: f用户问题{user_input}\n钱币图片路径{image_path}, } ] for _ in range(max_iters): response self.client.messages.create( modelclaude-3-5-sonnet-latest, max_tokens2048, system( 你是一名古钱币鉴定专家。你需要通过图片分析工具采集钱币特征 再结合钱币学常识给出结构化鉴定报告。 不要在没有工具结果时直接下最终结论。 ), toolsself.tools, messagesmessages, ) tool_calls [ block for block in response.content if block.type tool_use ] # 如果没有工具调用请求说明模型已经可以直接回答 if not tool_calls: texts [ block.text for block in response.content if block.type text ] return \n.join(texts) # 把 assistant 返回内容追加到消息历史中 messages.append({role: assistant, content: response.content}) # 依次执行模型请求的工具 for call in tool_calls: if call.name ! analyze_coin_image: continue args ( call.input if isinstance(call.input, dict) else json.loads(call.input) ) result analyze_coin_image( args[image_path], args.get(question, ), ) # 把工具执行结果返回给模型 messages.append( { role: user, content: [ { type: tool_result, tool_use_id: call.id, content: result, } ], } ) return 已达到最大工具调用次数无法生成最终结论。这段代码需要解释几个关键点system提示词里明确要求“不要在没有工具结果时直接下最终结论”这能有效降低模型幻觉概率。run方法使用for循环实现有限次工具调用循环内部先判断模型有没有返回tool_use没有就直接返回文本。每次工具调用的结果都会通过tool_result消息回传给 Claude让模型能够“看到”图片识别结果。如果模型连续多次都要调用工具max_iters会强制停止避免 Agent 死循环和 API 费用失控。4.4 编写主程序入口最后创建main.py把整个流程串起来。# 文件路径main.py import argparse from agent.claude_planner import ClaudePlanner def main(): parser argparse.ArgumentParser(descriptionAI 钱币鉴定 Agent) parser.add_argument(--image, requiredTrue, help钱币图片的本地路径) parser.add_argument( --question, default请帮我看看这枚钱币的基本信息和存疑点。, help用户希望重点鉴定的问题, ) args parser.parse_args() planner ClaudePlanner() report planner.run(args.question, args.image) print( AI 钱币鉴定报告 ) print(report) if __name__ __main__: main()把图片路径和问题都做成命令行参数方便测试。如果你后续要接 Web 后端只需要把这段逻辑封装成一个服务函数不再走命令行即可。4.5 运行与验证先确认.env文件里的两个 API Key 都已经配置好然后在项目根目录执行python main.py \ --image images/sample_coin.jpg \ --question 这枚光绪元宝的大致版本特征是什么有无明显的存疑点注意\换行写法适合 macOS 和 LinuxWindows 命令行建议直接写在一行python main.py --image images\sample_coin.jpg --question 这枚光绪元宝的大致版本特征是什么有无明显的存疑点如果一切正常程序会先调用 Claude Agent 生成工具调用请求然后调用智谱 GLM 分析钱币图片最后 Claude 汇总生成一份类似下面的报告 AI 钱币鉴定报告 基于钱币图片的工具分析结果整理如下 一、基本信息 - 币种机制铜元/银元图中可见“光绪元宝”字样具体面额需结合尺寸判断。 - 版式正面中央为“光绪元宝”上方或左右有铸造省份字样。 二、特征观察 - 文字压力感字口较为清晰部分笔画边缘存在自然流通磨损。 - 包浆状态表面包浆分布不均匀局部颜色偏深未发现明显浮于表面的涂料感。 - 边齿情况图中可见边缘齿形但由于拍摄角度限制无法精确判断齿型类别。 三、存疑点 - 图片分辨率不足以判断币面是否存在砂眼或修补痕迹。 - 无法通过单张图片准确判断材质比重与金属成分。 四、参考结论 该币在现有图片条件下呈现一定自然磨损特征但建议结合边齿微距图、重量和尺寸数据做进一步判断。这只是一个预期输出示例实际运行时的具体内容以模型识别结果为准。不要把示例输出当成真实鉴定结论。5. 常见问题与排查思路在实际运行过程中大概率会遇到下面这些问题。问题现象常见原因解决思路返回 401 认证失败API Key 未配置或配置错误检查.env中是否写入了正确的 Key确认环境变量已加载提示“model not found”或模型不存在视觉模型名写错或账号没有该模型权限登录智谱开放平台控制台查看当前账号可用的视觉模型名称图片读取失败图片路径错误、文件损坏或格式不支持确认路径使用 Pillow 能打开的常见格式例如 jpg、png图片体积过大导致接口报错原始图片尺寸过大调整preprocess_image中的max_size参数进一步压缩图片Agent 循环次数过多模型反复调用工具说明 prompt 或工具定义不够明确检查画像识别 prompt必要时提高max_iters限制但注意控制费用返回结果出现明显幻觉图片质量差或 system 提示词约束不够强降低temperature在提示词中强调“无法确定就写无法确定”请求超时图片识别过程较慢或者网络不稳定增加请求超时时间重试一次同时确认 API 账号没有欠费或限流如果你遇到“Claude 返回空文本”一个常见原因是模型在一次回复中只生成了工具调用没有生成文本内容。这在工具调用循环里是正常现象因为后续拿到工具结果后模型才会继续输出。如果所有迭代都用完了仍然没有文本可以适当调高max_tokens并检查工具返回结果是否太长导致后续上下文空间不足。6. 工程化与安全建议6.1 图片预处理要放在工具内部很多初学者会把图片压缩逻辑写在主流程里这会导致 Agent 每次循环都重复处理图片。更合理的做法是像本文一样把图片预处理放到GlmVision类内部对上层 Agent 完全透明。这样未来如果图片来自 URL、PDF 或本地文件只需要改一个模块。6.2 提示词是“防幻觉”的第一道防线钱币鉴定这类领域模型很容易一本正经地胡说八道。建议在 prompt 中做三层约束系统层明确告诉模型“先调用工具再下结论”。工具层要求视觉模型“只描述图中可见信息”。输出层要求最终报告区分“确定项”“存疑项”“无法判断项”。这样即使模型判断错了用户至少能看出哪些结论是推测不会把推测当确定结果。6.3 不要把 AI 鉴定结果当作最终交易依据需要特别提醒大模型鉴定本质上是辅助工具不能替代专业评级机构的结果。尤其是涉及真伪判断时应该把 AI 输出定位为“参考意见”并给用户明确提示。如果你的应用涉及交易金额最好在界面上加一句免责声明说明 AI 结论不构成交易或投资建议。6.4 安全与合规边界钱币图片本身不算敏感数据但如果你的应用面向普通用户要注意以下几点用户上传的图片可能包含个人信息比如拍摄背景里的桌面文件、地址单据建议服务端对图片做自动脱敏和定期清理。API Key 不要放在前端也不要提交到公开仓库。给 API Key 配置最小权限只允许调用需要的接口避免一个 Key 拥有全部模型权限。调用外部大模型 API 前明确用户是否授权尤其是商业场景下需要遵循平台服务条款。6.5 成本控制与性能优化多模态识别和大模型 Agent 的 token 消耗都不低。生产环境可以考虑这些优化对同一张图片的识别结果做缓存例如计算图片的 MD5如果已经识别过就直接复用结果。压缩图片后再传输既能降低请求耗时也能减少 token。控制 Agent 工具调用次数比如只允许最多两轮工具调用。给不同环节使用不同模型规格区分高精度和低成本场景。6.6 日志与可观测性Agent 应用比普通 API 调用更难排查问题因为每一步都会消耗 token。建议每次工具调用都记录日志至少包含用户原始问题。模型返回了几次工具调用。每条工具调用的参数和耗时。工具返回的内容摘要。最终报告文本。总 token 消耗和费用估算。有了这些日志你才能在模型回答异常时回溯是哪一步出了问题。7. 总结与下一步扩展本文从零实现了一个 AI 钱币鉴定 Agent整体来看你只需要掌握四个关键点多模态模型负责“看图”通过智谱 GLM 视觉模型提取钱币文字、图案、工艺、包浆等特征。Agent 负责“规划”Claude Agent 根据用户问题决定是否调用图片分析工具。工具调用循环是 Agent 的核心机制模型返回工具调用请求代码执行工具并返回结果模型再生成最终报告。工程化重点是“解耦”图片预处理、工具函数、Agent 规划器各自独立便于后续替换模型或扩展功能。你可以基于这套骨架继续扩展的方向有很多。比如把最终报告接入 Web 页面做成一个上传图片即可鉴定的在线小工具也可以增加一个钱币版别知识库让 Agent 在拿到视觉识别结果后再去检索数据库中相似的版别信息做更精确的对比判断还可以增加多图输入能力引导用户拍摄边齿、正面、反面多张图片提升判断准确率。如果你在实际开发中遇到报错建议优先检查 API Key 是否生效、模型名是否与账号权限匹配、图片格式是否被支持这三个因素大部分问题都出在这三处。希望这篇教程对你有所帮助可以先收藏备用也可以根据自己的场景替换模型和提示词做出更符合实际需求的 AI 鉴定工具。