absinthe - 如何从自定义类型解析嵌套字段
absinthe - how to parse nested field from custom type
我想在我的模式中有一个自定义 GeoPoint 类型,但我在模式类型文件中找不到如何执行此操作的任何示例。我发现的唯一方法是在架构文件中使用 input_object 。是否可以使用 Absinthe.Blueprint.Input.Object 这样做?
这是我的自定义类型:
defmodule MyAppWeb.Schema.Types.GeoPoint do
scalar :geo_point, name: "GeoPoint" do
serialize(&encode/1)
parse(&decode/1)
end
defp encode(value) do
MyApp.JasonEncoders.encode_model(value)
end
defp decode(%Absinthe.Blueprint.Input.String{value: value}) do
with {:ok, decoded} <- Jason.decode(value),
{:ok, point} <- Geo.JSON.decode(decoded) do
{:ok, point}
else
_ -> :error
end
end
defp decode(%Input.Null{}) do
{:ok, nil}
end
end
现在我可以用这个突变创建一个新条目
mutation (
$title: String!,
$geom: GeoPoint!
) {
offer: createOffer(
title: $title,
geom: $geom
)
和这些变量
{
"title": "Point",
"geom": "{\"coordinates\":[1,2],\"type\":\"Point\"}"
}
我更愿意使用类似
的方式来创建
{
"title": "Point",
"geom": {
"lat": 1,
"long": 2
}
}
或
{
"title": "Point",
"lat": 1,
"long": 2
}
你想做的事情不能用标量类型来完成,但你可以使用 input_object:
例如
input_object :geom do
field :lat, non_null(:float)
field :lon, non_null(:float)
end
mutation do
field :create_offer, :offer do
arg :title, non_null(:string)
arg :geom, non_null(:geom)
resolve &create_offer/2
end
end
我想在我的模式中有一个自定义 GeoPoint 类型,但我在模式类型文件中找不到如何执行此操作的任何示例。我发现的唯一方法是在架构文件中使用 input_object 。是否可以使用 Absinthe.Blueprint.Input.Object 这样做?
这是我的自定义类型:
defmodule MyAppWeb.Schema.Types.GeoPoint do
scalar :geo_point, name: "GeoPoint" do
serialize(&encode/1)
parse(&decode/1)
end
defp encode(value) do
MyApp.JasonEncoders.encode_model(value)
end
defp decode(%Absinthe.Blueprint.Input.String{value: value}) do
with {:ok, decoded} <- Jason.decode(value),
{:ok, point} <- Geo.JSON.decode(decoded) do
{:ok, point}
else
_ -> :error
end
end
defp decode(%Input.Null{}) do
{:ok, nil}
end
end
现在我可以用这个突变创建一个新条目
mutation (
$title: String!,
$geom: GeoPoint!
) {
offer: createOffer(
title: $title,
geom: $geom
)
和这些变量
{
"title": "Point",
"geom": "{\"coordinates\":[1,2],\"type\":\"Point\"}"
}
我更愿意使用类似
的方式来创建{
"title": "Point",
"geom": {
"lat": 1,
"long": 2
}
}
或
{
"title": "Point",
"lat": 1,
"long": 2
}
你想做的事情不能用标量类型来完成,但你可以使用 input_object:
例如
input_object :geom do
field :lat, non_null(:float)
field :lon, non_null(:float)
end
mutation do
field :create_offer, :offer do
arg :title, non_null(:string)
arg :geom, non_null(:geom)
resolve &create_offer/2
end
end