You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Crystal specs测试哈希相等性时输出格式不符问题如何解决

Crystal Spec哈希相等性断言失败修复方案

问题现象

编写Crystal specs测试用例验证哈希相等性时,断言失败输出分两种情况:

  • 哈希键为Symbol类型时:
Expected: {text: "Hello World"}
            got: {:text => "Hello World"}
  • 哈希键为String类型时:
Expected: {text: "Hello World"}
            got: {"text" => "Hello World"}

目标是让返回值匹配{text: "Hello World"}格式,顺利通过eq相等性断言。

现有实现代码

  • Symbol键版本:
@output = {} of Symbol => Output
@output[name] = @buffer # name是Symbol类型

language.parse("Hello World").should eq({ text: "Hello World" })
  • String键版本:
@output = {} of String => Output
@output[name.to_s] = @buffer # name是Symbol类型

问题根因

Crystal语法中,{text: "Hello World"}的短写法构造的是NamedTuple(命名元组),不是Hash类型。
无论键是Symbol还是String,Hash的标准字面量格式为{:key => value}或{"key" => value},和NamedTuple属于完全不同的类型,类型不匹配时eq断言必然失败,和输出打印格式无关。

修复方案

根据实际业务需求二选一即可:

方案1:调整业务代码返回NamedTuple(匹配现有测试写法)

如果业务场景不需要动态增删键、键集合固定,直接返回NamedTuple即可通过断言:

# 固定键场景直接构造
@output = {text: @buffer}

# 动态键场景用NamedTuple.new构造
@output = NamedTuple.new(name => @buffer) # name为Symbol类型

language.parse("Hello World").should eq({ text: "Hello World" }) # 断言通过

方案2:调整测试断言匹配Hash类型

如果业务场景必须用Hash(比如需要动态增删键、键集合不固定),修改测试中的预期值为对应类型的Hash字面量即可:

  • 业务代码用Symbol作为Hash键时,测试改为:
language.parse("Hello World").should eq({:text => "Hello World"})
  • 业务代码用String作为Hash键时,测试改为:
language.parse("Hello World").should eq({"text" => "Hello World"})

注意:不要尝试通过修改对象打印格式绕过断言,类型不一致时值比较不会相等。


内容的提问来源于stack exchange,提问作者Dorian

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.31 00:57:14