Hello Monks

I am working with a 3rd party API and trying to use SOAP::Lite for the first time.

I've figured out how to actually make the request but to use the secure version I essentially need to send an sha1 hash of the message body in a header.

What I've got so far:

#!/usr/bin/env perl use strict; use warnings; use 5.010; use LWP::UserAgent; use SOAP::Lite; my $client = SOAP::Lite->proxy($proxy) ->ns($namespace, 'foo') # I'm not sure I understand this. ->uri($uri) ->on_action(sub { sprintf '%s', $_[0] }) ->on_fault(sub { my($soap, $result) = @_; die ref $result ? "Fault Code: " . $result->faultcode . "\n" . "Fault String: " . $result->faultstring . "\n" : $soap->transport->status, "\n"; }); my $params = { foo => 'bar', biz => 'baz'}; my $result = $client->my_api_method($params);

Essentially, after the xml is generated and before the request is made I need to insert a sha1 hash of the request body. I'm looking at the correct version of the docs now (was looking at 0.55 for some reason...) so hopefully there's something obvious that jumps out.

EDIT: I think I can use SOAP::Data->name($params) somehow...

NOT SOLUTION:

you need to tell it what type of data you're giving it. (I think that's the right vocabulary)

my $data = SOAP::Data->name( %params); #say "Data: $data"; my $serializer = $client->serializer; my $xml = $serializer->envelope(method => 'my_api_call', $data);

now I still call $client->my_api_method(\%params); so I'm doing more work than necessary... right? does it matter? there's probably a way to feed the envelope to the SOAP::Lite->call('my_api_method' => \%params)

EDIT:

Hmm... turns out I was wrong. there are some tags that are added when the request is made. Back to the drawing board.

REAL SOLUTION

So the deal is, you need to hook into the LWP request and get the body from LWP. Anonymous Monk had basically pointed to the answer off the bat :)

#!/usr/bin/env perl use strict; use warnings; use 5.010; use LWP::UserAgent; use SOAP::Lite; my $client = SOAP::Lite->proxy($proxy) ->ns($namespace, 'foo') # I'm not sure I understand this. ->uri($uri) ->on_action(sub { sprintf '%s', $_[0] }) ->on_fault(sub { my($soap, $result) = @_; die ref $result ? "Fault Code: " . $result->faultcode . "\n" . "Fault String: " . $result->faultstring . "\n" : $soap->transport->status, "\n"; }); my $params = { foo => 'bar', biz => 'baz'}; $client->transport->add_handler("request_prepare", \&modify_header ); my $result = $client->my_api_method($params); sub modify_header { my ($request, $ua, $h) = @_; $request->header('some-special-header' => sha1 $request->content); }

In reply to [SOLVED][SOAP::Lite] Obtain request body before request is sent? by three18ti

Title:
Use:  <p> text here (a paragraph) </p>
and:  <code> code here </code>
to format your post, it's "PerlMonks-approved HTML":



  • Posts are HTML formatted. Put <p> </p> tags around your paragraphs. Put <code> </code> tags around your code and data!
  • Titles consisting of a single word are discouraged, and in most cases are disallowed outright.
  • Read Where should I post X? if you're not absolutely sure you're posting in the right place.
  • Please read these before you post! —
  • Posts may use any of the Perl Monks Approved HTML tags:
    a, abbr, b, big, blockquote, br, caption, center, col, colgroup, dd, del, details, div, dl, dt, em, font, h1, h2, h3, h4, h5, h6, hr, i, ins, li, ol, p, pre, readmore, small, span, spoiler, strike, strong, sub, summary, sup, table, tbody, td, tfoot, th, thead, tr, tt, u, ul, wbr
  • You may need to use entities for some characters, as follows. (Exception: Within code tags, you can put the characters literally.)
            For:     Use:
    & &amp;
    < &lt;
    > &gt;
    [ &#91;
    ] &#93;
  • Link using PerlMonks shortcuts! What shortcuts can I use for linking?
  • See Writeup Formatting Tips and other pages linked from there for more info.