从 API 获取数据并使用 Poison 解码时出现参数错误
Getting argument error when fetching data from API and decoding with Poison
我是 Elixir/Phoenix 的新手,正在尝试通过构建一个小应用程序来学习。
我正在从第 3 方获取数据 API 并不断收到以下错误。
(ArgumentError) argument error :erlang.iolist_to_binary([%{"24h_volume" => "1000", "name" => "some_name"},{...}])
我的控制器中有:
HTTPoison.start
%HTTPoison.Response{body: body} = HTTPoison.get!(url)
body = body
|> Poison.decode!(keys: :atoms!)
这不起作用。我使用了 Poison 文档中不鼓励使用的 (keys: :atoms)。
这是我的架构:
schema "things" do
field :name, :string
field :volume_24h, :float
timestamps()
end
@doc false
def changeset(%Thing{} = thing, attrs) do
thing
|> cast(attrs, [:volume_24h, :name])
|> validate_not_nil([:volume_24h, :name])
end
def validate_not_nil(changeset, fields) do
Enum.reduce(fields, changeset, fn field, changeset ->
if get_field(changeset, field) == nil do
add_error(changeset, field, "nil")
else
changeset
end
end)
end
我正在尝试为“24h_volume”使用不同的字段名称,但出现此错误:
(ArgumentError) argument error :erlang.binary_to_existing_atom("24h_volume", :utf8)
我显然在这里遗漏了一些东西。
有没有办法将所需的字段名称传递给 Poison,因为“24h_volume”不是有效原子?
我该如何修复这些错误?
你已经定义了你的 atom 如下,因为你的 atom 通常以数字开头是非法的,但你可以通过用 "
包装它来解决这个问题
所以改变你的原子如下:
:"24_volume"
你的 volume_24h
参数一团糟。
Note that keys: :atoms!
reuses existing atoms, i.e. if :name
was not allocated before the call, you will encounter an argument error message.
这正是发生的事情。应用程序期望 :volume_24h
键来自请求,但它(出于某种原因,可能是由于 like 的表单配置错误)收到了 24h_volume
。通过使用宽松的 atoms
调用而不是 atoms!
你没有解决任何问题,你 隐藏了问题 。实际发生的是,24h_volume
键出现, 被调用 cast
.
有效丢弃
您需要的是修复 fronend/request 发送器以发送 volume_24h
密钥,或者修复控制器以接受 :"24h_volume"
密钥。
不鼓励 atoms
使用的原因有两个。 Poison
文档中描述了一个:所谓的“atoms DOS 攻击”是可能的,随后发出具有随机密钥的随机请求,溢出 atom 存储。第二个是通过使用 banged 版本 atoms!
来保护自己免受 typos/misconfiguration 的影响,就像上面的那样。
FWIW,正确键的原子正在模式定义中分配。
我是 Elixir/Phoenix 的新手,正在尝试通过构建一个小应用程序来学习。
我正在从第 3 方获取数据 API 并不断收到以下错误。
(ArgumentError) argument error :erlang.iolist_to_binary([%{"24h_volume" => "1000", "name" => "some_name"},{...}])
我的控制器中有:
HTTPoison.start
%HTTPoison.Response{body: body} = HTTPoison.get!(url)
body = body
|> Poison.decode!(keys: :atoms!)
这不起作用。我使用了 Poison 文档中不鼓励使用的 (keys: :atoms)。
这是我的架构:
schema "things" do
field :name, :string
field :volume_24h, :float
timestamps()
end
@doc false
def changeset(%Thing{} = thing, attrs) do
thing
|> cast(attrs, [:volume_24h, :name])
|> validate_not_nil([:volume_24h, :name])
end
def validate_not_nil(changeset, fields) do
Enum.reduce(fields, changeset, fn field, changeset ->
if get_field(changeset, field) == nil do
add_error(changeset, field, "nil")
else
changeset
end
end)
end
我正在尝试为“24h_volume”使用不同的字段名称,但出现此错误:
(ArgumentError) argument error :erlang.binary_to_existing_atom("24h_volume", :utf8)
我显然在这里遗漏了一些东西。
有没有办法将所需的字段名称传递给 Poison,因为“24h_volume”不是有效原子? 我该如何修复这些错误?
你已经定义了你的 atom 如下,因为你的 atom 通常以数字开头是非法的,但你可以通过用 "
所以改变你的原子如下:
:"24_volume"
你的 volume_24h
参数一团糟。
Note that
keys: :atoms!
reuses existing atoms, i.e. if:name
was not allocated before the call, you will encounter an argument error message.
这正是发生的事情。应用程序期望 :volume_24h
键来自请求,但它(出于某种原因,可能是由于 like 的表单配置错误)收到了 24h_volume
。通过使用宽松的 atoms
调用而不是 atoms!
你没有解决任何问题,你 隐藏了问题 。实际发生的是,24h_volume
键出现, 被调用 cast
.
您需要的是修复 fronend/request 发送器以发送 volume_24h
密钥,或者修复控制器以接受 :"24h_volume"
密钥。
不鼓励 atoms
使用的原因有两个。 Poison
文档中描述了一个:所谓的“atoms DOS 攻击”是可能的,随后发出具有随机密钥的随机请求,溢出 atom 存储。第二个是通过使用 banged 版本 atoms!
来保护自己免受 typos/misconfiguration 的影响,就像上面的那样。
FWIW,正确键的原子正在模式定义中分配。