Using Erlang for Comsuming Web Services using SOAP

Luke Gorrie <>
Sat Jan 15 17:56:49 CET 2005


Neil Campbell <> writes:

> Does anyone have experience either using this library for accessing
> (i.e. not hosting) web services or know of any other helpful libraries
> or features that I have missed?

I found it okay to do SOAP the poor man's way, i.e. building it up
with code like:

  encode(SoapMsg) ->
      #soap_msg{headers=Hs, body=Body, related_parts=Related} = SoapMsg,
      XML = {'env:Envelope',
             [{'xmlns:env', "http://schemas.xmlsoap.org/soap/envelope/"}],
             if Hs == [] -> [];
                true     -> [{'env:Header', [], Hs}]
             end ++ [{'env:Body', [], Body}]},
      Z = xmerl_lib:expand(XML),
      Text = xmerl:export_simple(XML, xmerl_xml),
      ....

I decode it from similar tuples, e.g.

  dec_msg({'Envelope', _, Es}) ->
      case xml_util:arrange(Es, ['Header', 'Body']) of
          [{'Header', _, Headers},
           {'Body', _, Body}] ->
              case xml_util:arrange(Body, ['Fault']) of
                  [] ->
                      {ok, #soap_msg{headers=Headers, body=Body}};
                  [{'Fault', _, FBody}] ->
                      case dec_fault(FBody) of
                          {ok, Fault} ->
                              {ok, #soap_msg{headers=Headers, body=Fault}};
                          Err = {error, _} ->
                              Err
                      end
              end;
          _ ->
              {error, {bad_envelope_body, Es}}
      end;
  dec_msg(X) ->
      {error, {bad_envelope, X}}.

(That xml_util:arrange function turned out fairly handy for
pattern-matching on parsed XML that could have elements in a funny
order or include unexpected/not-understood elements:

  %% arrange(Elements, Tags) -> Elements'
  %% Elements = [xml()]
  %% Tags     = [atom()]
  %%
  %% This is a utility to filter and arrange a series of XML elements to
  %% make them easier to pattern match. The returned list:
  %%   Only includes elements whose tag is in Tags;
  %%   Includes at most one of each Tag;
  %%   Returns elements in the same order they appear in Tags
  %%
  %% Example:
  %%   arrange([{bar,_,_},{foo,_,_},{beer,_,_},{baz,_,_}], [foo,bar,baz])
  %%     => [{foo,_,_}, {bar,_,_}, {baz,_,_}]
  arrange(Elems, Spec) ->
      foldr(fun(Tag, Acc) ->
                    case lists:keysearch(Tag, 1, Elems) of
                        {value, X} -> [X|Acc];
                        false      -> Acc
                    end
            end, [], Spec).

Initially I had meant to do it the Right Way by interpreting Schemas
and maybe WSDL but it was all a bit much for me.

For now I attach "the gist", missing the HTTP client part and at least
one xmerl patch. If you want to actually use this then let me know and
I can try to resolve its dependencies and jungerl it when I get a
chance.

-------------- next part --------------
A non-text attachment was scrubbed...
Name: soap.hrl
Type: text/x-erlang-source
Size: 371 bytes
Desc: not available
URL: <http://erlang.org/pipermail/erlang-questions/attachments/20050115/d5ae0009/attachment.bin>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: soap.erl
Type: text/x-erlang-source
Size: 4999 bytes
Desc: not available
URL: <http://erlang.org/pipermail/erlang-questions/attachments/20050115/d5ae0009/attachment-0001.bin>
-------------- next part --------------
A non-text attachment was scrubbed...
Name: xml_util.erl
Type: text/x-erlang-source
Size: 2194 bytes
Desc: not available
URL: <http://erlang.org/pipermail/erlang-questions/attachments/20050115/d5ae0009/attachment-0002.bin>


More information about the erlang-questions mailing list