Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Change additional output type & skip empty optional arguments #104

Merged
merged 2 commits into from
Apr 13, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
66 changes: 49 additions & 17 deletions lib/vix/vips/mutable_operation.ex
Original file line number Diff line number Diff line change
Expand Up @@ -50,19 +50,38 @@ defmodule Vix.Vips.MutableOperation do
#{prepare_doc(desc, in_req_spec, in_opt_spec, out_req_spec, out_opt_spec)}
"""
@spec unquote(func_typespec(func_name, in_req_spec, in_opt_spec, out_req_spec, out_opt_spec))
def unquote(func_name)(unquote_splicing(req_params), optional \\ []) do
[mutable_image | rest_params] = unquote(req_params)

operation_cb = fn image ->
operation_call(
unquote(name),
[image | rest_params],
optional,
unquote(Macro.escape(spec))
)
if in_opt_spec == [] do
# operations without optional arguments
def unquote(func_name)(unquote_splicing(req_params)) do
[mutable_image | rest_params] = unquote(req_params)

operation_cb = fn image ->
operation_call(
unquote(name),
[image | rest_params],
[],
unquote(Macro.escape(spec))
)
end

GenServer.call(mutable_image.pid, {:operation, operation_cb})
end
else
# operations with optional arguments
def unquote(func_name)(unquote_splicing(req_params), optional \\ []) do
[mutable_image | rest_params] = unquote(req_params)

GenServer.call(mutable_image.pid, {:operation, operation_cb})
operation_cb = fn image ->
operation_call(
unquote(name),
[image | rest_params],
optional,
unquote(Macro.escape(spec))
)
end

GenServer.call(mutable_image.pid, {:operation, operation_cb})
end
end

bang_func_name = function_name(String.to_atom(name <> "!"))
Expand All @@ -79,12 +98,25 @@ defmodule Vix.Vips.MutableOperation do
out_opt_spec
)
)
def unquote(bang_func_name)(unquote_splicing(req_params), optional \\ []) do
case __MODULE__.unquote(func_name)(unquote_splicing(req_params), optional) do
:ok -> :ok
{:ok, result} -> result
{:error, reason} when is_binary(reason) -> raise Error, message: reason
{:error, reason} -> raise Error, message: inspect(reason)
if in_opt_spec == [] do
# operations without optional arguments
def unquote(bang_func_name)(unquote_splicing(req_params)) do
case __MODULE__.unquote(func_name)(unquote_splicing(req_params)) do
:ok -> :ok
{:ok, result} -> result
{:error, reason} when is_binary(reason) -> raise Error, message: reason
{:error, reason} -> raise Error, message: inspect(reason)
end
end
else
# operations with optional arguments
def unquote(bang_func_name)(unquote_splicing(req_params), optional \\ []) do
case __MODULE__.unquote(func_name)(unquote_splicing(req_params), optional) do
:ok -> :ok
{:ok, result} -> result
{:error, reason} when is_binary(reason) -> raise Error, message: reason
{:error, reason} -> raise Error, message: inspect(reason)
end
end
end
end)
Expand Down
37 changes: 29 additions & 8 deletions lib/vix/vips/operation.ex
Original file line number Diff line number Diff line change
Expand Up @@ -51,8 +51,16 @@ defmodule Vix.Vips.Operation do
#{prepare_doc(desc, in_req_spec, in_opt_spec, out_req_spec, out_opt_spec)}
"""
@spec unquote(func_typespec(func_name, in_req_spec, in_opt_spec, out_req_spec, out_opt_spec))
def unquote(func_name)(unquote_splicing(req_params), optional \\ []) do
operation_call(unquote(name), unquote(req_params), optional, unquote(Macro.escape(spec)))
if in_opt_spec == [] do
# operations without optional arguments
def unquote(func_name)(unquote_splicing(req_params)) do
operation_call(unquote(name), unquote(req_params), [], unquote(Macro.escape(spec)))
end
else
# operations with optional arguments
def unquote(func_name)(unquote_splicing(req_params), optional \\ []) do
operation_call(unquote(name), unquote(req_params), optional, unquote(Macro.escape(spec)))
end
end

bang_func_name = function_name(String.to_atom(name <> "!"))
Expand All @@ -69,12 +77,25 @@ defmodule Vix.Vips.Operation do
out_opt_spec
)
)
def unquote(bang_func_name)(unquote_splicing(req_params), optional \\ []) do
case __MODULE__.unquote(func_name)(unquote_splicing(req_params), optional) do
:ok -> :ok
{:ok, result} -> result
{:error, reason} when is_binary(reason) -> raise Error, message: reason
{:error, reason} -> raise Error, message: inspect(reason)
if in_opt_spec == [] do
# operations without optional arguments
def unquote(bang_func_name)(unquote_splicing(req_params)) do
case __MODULE__.unquote(func_name)(unquote_splicing(req_params)) do
:ok -> :ok
{:ok, result} -> result
{:error, reason} when is_binary(reason) -> raise Error, message: reason
{:error, reason} -> raise Error, message: inspect(reason)
end
end
else
# operations with optional arguments
def unquote(bang_func_name)(unquote_splicing(req_params), optional \\ []) do
case __MODULE__.unquote(func_name)(unquote_splicing(req_params), optional) do
:ok -> :ok
{:ok, result} -> result
{:error, reason} when is_binary(reason) -> raise Error, message: reason
{:error, reason} -> raise Error, message: inspect(reason)
end
end
end
end)
Expand Down
62 changes: 49 additions & 13 deletions lib/vix/vips/operation_helper.ex
Original file line number Diff line number Diff line change
Expand Up @@ -77,8 +77,11 @@ defmodule Vix.Vips.OperationHelper do
{[term], []} ->
{:ok, term}

{required, []} ->
{:ok, List.to_tuple(required)}

{required, optional} ->
{:ok, List.to_tuple(required ++ [optional])}
{:ok, List.to_tuple(required ++ [Map.new(optional)])}
end
end

Expand Down Expand Up @@ -167,11 +170,19 @@ defmodule Vix.Vips.OperationHelper do
{:ok, unquote(typespec(pspec))} | {:error, term()}
end

{pspec_list, []} ->
quote do
{:ok, {unquote_splicing(required_args_typespec(pspec_list))}}
| {:error, term()}
end

{pspec_list, optional} ->
optional_out = optional_args_typespec(optional)

quote do
{:ok, {unquote_splicing(required_args_typespec(pspec_list)), unquote(optional_out)}}
{:ok,
{unquote_splicing(required_args_typespec(pspec_list)),
%{unquote_splicing(optional_out)}}}
| {:error, term()}
end
end
Expand All @@ -189,11 +200,18 @@ defmodule Vix.Vips.OperationHelper do
unquote(typespec(pspec)) | no_return()
end

{pspec_list, []} ->
quote do
{unquote_splicing(required_args_typespec(pspec_list))}
| no_return()
end

{pspec_list, optional} ->
optional_out = optional_args_typespec(optional)

quote do
{unquote_splicing(required_args_typespec(pspec_list)), unquote(optional_out)}
{unquote_splicing(required_args_typespec(pspec_list)),
%{unquote_splicing(optional_out)}}
| no_return()
end
end
Expand All @@ -202,8 +220,13 @@ defmodule Vix.Vips.OperationHelper do
def func_typespec(func_name, required_in, optional_in, required_out, optional_out) do
quote do
unquote(func_name)(
unquote_splicing(required_args_typespec(required_in)),
unquote(optional_args_typespec(optional_in))
unquote_splicing(
if optional_in == [] do
required_args_typespec(required_in)
else
required_args_typespec(required_in) ++ [optional_args_typespec(optional_in)]
end
)
) ::
unquote(output_typespec(required_out, optional_out))
end
Expand All @@ -212,8 +235,13 @@ defmodule Vix.Vips.OperationHelper do
def bang_func_typespec(func_name, required_in, optional_in, required_out, optional_out) do
quote do
unquote(func_name)(
unquote_splicing(required_args_typespec(required_in)),
unquote(optional_args_typespec(optional_in))
unquote_splicing(
if optional_in == [] do
required_args_typespec(required_in)
else
required_args_typespec(required_in) ++ [optional_args_typespec(optional_in)]
end
)
) ::
unquote(bang_output_typespec(required_out, optional_out))
end
Expand Down Expand Up @@ -341,18 +369,26 @@ defmodule Vix.Vips.OperationHelper do
"* #{pspec.param_name} - #{pspec.desc}. (`#{Macro.to_string(typespec(pspec))}`)"
end)

"""
## Returns
Operation returns a tuple

#{required_out_values}

#{optional_out_doc(optional_out)}
"""
end

defp optional_out_doc([]), do: ""

defp optional_out_doc(optional_out) do
optional_out_values =
Enum.map_join(optional_out, "\n", fn pspec ->
"* #{pspec.param_name} - #{pspec.desc}. (`#{Macro.to_string(typespec(pspec))}`)"
end)

"""
## Returns
Ordered values in the returned tuple
#{required_out_values}

## Additional
Last value of the the output tuple is a keyword list of additional optional output values
Last value of the tuple is a map of additional output values as key-value pair.
#{optional_out_values}
"""
end
Expand Down
4 changes: 2 additions & 2 deletions test/vix/vips/operation_test.exs
Original file line number Diff line number Diff line change
Expand Up @@ -61,13 +61,13 @@ defmodule Vix.Vips.OperationTest do
test "additional return values", %{dir: _dir} do
{:ok, im} = Image.new_from_file(img_path("black_on_white.jpg"))

assert {:ok, {0.0, [x: _, y: _, "out-array": [0.0], "x-array": [_ | _], "y-array": [_ | _]]}} =
assert {:ok, {0.0, %{x: _, y: _, "out-array": [0.0], "x-array": [_ | _], "y-array": [_ | _]}}} =
Operation.min(im)
end

test "required output order", %{dir: _dir} do
{:ok, im} = Image.new_from_file(img_path("black_on_white.jpg"))
assert Operation.find_trim(im) == {:ok, {41, 44, 45, 45, []}}
assert Operation.find_trim(im) == {:ok, {41, 44, 45, 45}}
end

test "when unsupported argument is passed", %{dir: _dir} do
Expand Down