Skip to content

Commit 1834492

Browse files
authored
Allow attributes parse on responses (#119)
* feat: added attributes parse support * feat: improved tests
1 parent 53ff20e commit 1834492

File tree

5 files changed

+42
-5
lines changed

5 files changed

+42
-5
lines changed

lib/soap/response/parser.ex

Lines changed: 27 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -32,8 +32,23 @@ defmodule Soap.Response.Parser do
3232
end
3333

3434
@spec parse_record(tuple()) :: map() | String.t()
35-
defp parse_record({:xmlElement, tag_name, _, _, _, _, _, _, elements, _, _, _}) do
36-
%{tag_name => parse_elements(elements)}
35+
defp parse_record({:xmlElement, tag_name, _, _, _, _, _, attributes, elements, _, _, _}) do
36+
attributes_map = parse_attributes(attributes)
37+
element_content = parse_elements(elements)
38+
39+
case {attributes_map, element_content} do
40+
{attrs, content} when map_size(attrs) == 0 ->
41+
%{tag_name => content}
42+
43+
{attrs, content} when map_size(content) == 0 ->
44+
%{tag_name => attrs}
45+
46+
{attrs, content} when is_map(content) ->
47+
%{tag_name => Map.merge(attrs, content)}
48+
49+
{attrs, content} ->
50+
%{tag_name => %{"_attributes" => attrs, "_value" => content}}
51+
end
3752
end
3853

3954
defp parse_record({:xmlText, _, _, _, value, _}), do: transform_record_value(value)
@@ -42,7 +57,7 @@ defmodule Soap.Response.Parser do
4257
defp transform_record_value(value) when is_list(value), do: value |> to_string() |> String.trim()
4358
defp transform_record_value(value) when is_binary(value), do: value |> String.trim()
4459

45-
@spec parse_elements(list() | tuple()) :: map()
60+
@spec parse_elements(list() | tuple()) :: map() | String.t()
4661
defp parse_elements([]), do: %{}
4762
defp parse_elements(elements) when is_tuple(elements), do: parse_record(elements)
4863

@@ -106,4 +121,13 @@ defmodule Soap.Response.Parser do
106121
defp apply_namespace_to_tag(env_namespace, tag), do: env_namespace <> ":" <> tag
107122

108123
defp soap_version, do: Application.fetch_env!(:soap, :globals)[:version]
124+
125+
@spec parse_attributes(list()) :: map()
126+
defp parse_attributes(attributes) do
127+
attributes
128+
|> Enum.map(fn {:xmlAttribute, name, _, _, _, _, _, _, value, _} ->
129+
{name, transform_record_value(value)}
130+
end)
131+
|> Enum.into(%{})
132+
end
109133
end
Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
<?xml version="1.0" encoding="UTF-8"?><env:Envelope xmlns:env="http://schemas.xmlsoap.org/soap/envelope/" xmlns:tns="com.esendex.ems.soapinterface" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"><env:Header/><env:Body><tns:sendMessage xmlns="com.esendex.ems.soapinterface"><body>BODY</body><date>2018-01-19</date><recipient>WSPB</recipient><type>TYPE</type></tns:sendMessage></env:Body></env:Envelope>
1+
<?xml version="1.0" encoding="UTF-8"?><env:Envelope xmlns:env="http://schemas.xmlsoap.org/soap/envelope/" xmlns:tns="com.esendex.ems.soapinterface" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"><env:Header/><env:Body><tns:sendMessage xmlns="com.esendex.ems.soapinterface"><type>TYPE</type><date>2018-01-19</date><body>BODY</body><recipient>WSPB</recipient></tns:sendMessage></env:Body></env:Envelope>
Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
<?xml version="1.0" encoding="UTF-8"?><env:Envelope xmlns:env="http://www.w3.org/2003/05/soap-envelope" xmlns:tns="com.esendex.ems.soapinterface" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"><env:Header/><env:Body><tns:sendMessage xmlns="com.esendex.ems.soapinterface"><body>BODY</body><date>2018-01-19</date><recipient>WSPB</recipient><type>TYPE</type></tns:sendMessage></env:Body></env:Envelope>
1+
<?xml version="1.0" encoding="UTF-8"?><env:Envelope xmlns:env="http://www.w3.org/2003/05/soap-envelope" xmlns:tns="com.esendex.ems.soapinterface" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"><env:Header/><env:Body><tns:sendMessage xmlns="com.esendex.ems.soapinterface"><type>TYPE</type><date>2018-01-19</date><body>BODY</body><recipient>WSPB</recipient></tns:sendMessage></env:Body></env:Envelope>
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
<env:Envelope xmlns:env="http://schemas.xmlsoap.org/soap/envelope/"><env:Body><response><message id="1234567890" date="2025-03-25"><text lang="en">Hello!</text></message></response></env:Body></env:Envelope>

test/soap/response/parser_test.exs

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,4 +8,16 @@ defmodule Soap.Response.ParserTest do
88

99
assert Parser.parse(xml_body, :success) == correctly_parsed_response
1010
end
11+
12+
test "correct response parsed successful with attributes" do
13+
xml_body = Fixtures.load_xml("send_service/SendMessageResponseComplex.xml")
14+
15+
correctly_parsed_response = %{
16+
response: %{
17+
message: %{date: "2025-03-25", id: "1234567890", text: %{"_attributes" => %{lang: "en"}, "_value" => "Hello!"}}
18+
}
19+
}
20+
21+
assert Parser.parse(xml_body, :success) == correctly_parsed_response
22+
end
1123
end

0 commit comments

Comments
 (0)