How to sign outgoing soap request without using wsf/php? - php

I am looking how to sign soap header using PHP.
The soap service is built by apache rampart, which is exactly same as sample 2 in https://axis.apache.org/axis2/java/rampart/samples.html.
Now, I have a soap client develop by using PHP.
I have no idea how to sign the entire headers and body.
I can make my soap request as following
<?xml version="1.0" encoding="UTF-8" ?>
<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:ns1="http://ws.globesteel.com" xmlns:ns2="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd" xmlns:SOAP-ENC="http://schemas.xmlsoap.org/soap/encoding/"
xmlns:ns3="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd">
<SOAP-ENV:Header>
<ns3:Security SOAP-ENV:mustUnderstand="1">
<ns2:Timestamp>
<ns2:Created>2016-07-13T08:16:02Z</ns2:Created>
<ns2:Expires>2016-07-20T06:56:02Z</ns2:Expires>
</ns2:Timestamp>
<ns3:Signature>
<ns3:SignedInfo>
<Signature>
<SignedInfo>
<CanonicalizationMethod>
<Algorithm>http://www.w3.org/2001/10/xml-exc-c14n#</Algorithm>
</CanonicalizationMethod>
<SignatureMethod>
<Algorithm>http://www.w3.org/2000/09/xmldsig#rsa-sha1</Algorithm>
</SignatureMethod>
<Reference>
<SOAP-ENC:Struct>
<Transforms>
<SOAP-ENC:Struct>
<Algorithm>http://www.w3.org/2001/10/xml-exc-c14n#</Algorithm>
</SOAP-ENC:Struct>
</Transforms>
<DigestMethod>
<Algorithm>http://www.w3.org/2000/09/xmldsig#sha1</Algorithm>
</DigestMethod>
<DigestValue>8f6c3a934fc237673e9f1a12793f5507b8103e4a</DigestValue>
<URI>#_body</URI>
<Id/>
</SOAP-ENC:Struct>
<SOAP-ENC:Struct>
<Transforms>
<SOAP-ENC:Struct>
<Algorithm>http://www.w3.org/2001/10/xml-exc-c14n#</Algorithm>
</SOAP-ENC:Struct>
</Transforms>
<DigestMethod>
<Algorithm>http://www.w3.org/2000/09/xmldsig#sha1</Algorithm>
</DigestMethod>
<DigestValue></DigestValue>
<URI>#_control</URI>
<Id/>
</SOAP-ENC:Struct>
</Reference>
</SignedInfo>
<SignatureValue>Yu/DkCbKXAoalySGM2XdieRYhk1rnwhFKNcklXn5l+YgNk3AXEnpr4yDAlReYgU3FGOZh0XGUn8hGWwEs28S+xjrROgb3G/SYKVKbS3EmAU/vLBa+lABn/0NDoGdR/iIv9C7XAr/OBhE++cHA+lktZSS1SUPtfG5BAifN/RtfkE=</SignatureValue>
<KeyInfo>aqePjuZzE1lzwMMtquksvNJsbmI=</KeyInfo>
</Signature>
</ns3:SignedInfo>
</ns3:Signature>
</ns3:Security>
</SOAP-ENV:Header>
<SOAP-ENV:Body>
<ns1:GetAvailableSecurityQuestions/>
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>
But I still get error return "Message is not signed".

After 2 weeks of pain, I finally solved this by using https://github.com/robrichards/xmlseclibs

Related

Sending soap request with attributes using PHP SoapClient

I`m having remote wsdl API that requires some xml attributes in request.
Integration of this API must be made usind PHP (and possibly SoapClient).
I`m creating SimpleXMLElement() object like
<?xml version="1.0" encoding="UTF-8"?>
<Body>
<FlightMatrixRequest xmlns="http://www.somesite.com/webservices">
<flightMatrixRQ Target="Test" Version="1.0">
<AirItinerary DirectionInd="OneWay">
<OriginDestinationOptions>
<OriginDestinationOption>
<FlightSegment DepartureDateTime="2022-05-30T00:00:00+11:00"
ArrivalDateTime="2022-05-30T00:00:00+11:00" RPH="1">
<DepartureAirport LocationCode="BKK"/>
<ArrivalAirport LocationCode="CNX"/>
<MarketingAirline Code="SL"/>
</FlightSegment>
</OriginDestinationOption>
</OriginDestinationOptions>
</AirItinerary>
<TravelerInfoSummary>
<AirTravelerAvail>
<AirTraveler>
<PassengerTypeQuantity Code="ADT" Quantity="1"/>
</AirTraveler>
</AirTravelerAvail>
<AirTravelerAvail>
<AirTraveler>
<PassengerTypeQuantity Code="CNN" Quantity="1"/>
</AirTraveler>
</AirTravelerAvail>
<AirTravelerAvail>
<AirTraveler>
<PassengerTypeQuantity Code="INF" Quantity="1"/>
</AirTraveler>
</AirTravelerAvail>
</TravelerInfoSummary>
</flightMatrixRQ>
</FlightMatrixRequest>
</Body>
Converting it to array using
$array = json_decode(json_encode($xml), true);
Then requesting
$soapClient->__soapCall($method, $array)
And getting errors from API
$soapClient->__getLastRequest() returns
<?xml version="1.0" encoding="UTF-8"?>
<env:Envelope xmlns:env="http://www.w3.org/2003/05/soap-envelope" xmlns:ns1="http://www.somesite.com/webservices"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
<env:Body>
<ns1:FlightMatrixRequest>
<ns1:flightMatrixRQ>
<ns1:AirItinerary>
<ns1:OriginDestinationOptions>
<ns1:OriginDestinationOption>
<ns1:FlightSegment>
<ns1:DepartureAirport/>
<ns1:ArrivalAirport/>
<ns1:MarketingAirline/>
</ns1:FlightSegment>
</ns1:OriginDestinationOption>
</ns1:OriginDestinationOptions>
</ns1:AirItinerary>
<ns1:TravelerInfoSummary>
<ns1:AirTravelerAvail>
<ns1:AirTraveler>
<ns1:PassengerTypeQuantity/>
<ns1:PassengerIdentificationDocument xsi:nil="true"/>
</ns1:AirTraveler>
</ns1:AirTravelerAvail>
<ns1:AirTravelerAvail>
<ns1:AirTraveler>
<ns1:PassengerTypeQuantity/>
<ns1:PassengerIdentificationDocument xsi:nil="true"/>
</ns1:AirTraveler>
</ns1:AirTravelerAvail>
<ns1:AirTravelerAvail>
<ns1:AirTraveler>
<ns1:PassengerTypeQuantity/>
<ns1:PassengerIdentificationDocument xsi:nil="true"/>
</ns1:AirTraveler>
</ns1:AirTravelerAvail>
</ns1:TravelerInfoSummary>
</ns1:flightMatrixRQ>
</ns1:FlightMatrixRequest>
</env:Body>
</env:Envelope>
As you may see there is no attribute`s data, like DepartureDateTime/LocationCode etc.
Could not find any solution for this case. Possible it may be fixed by using regular curl request with prepared body/headers but it does not look like a good idea.
Any ideas?

Reading soap response in php using nusoap_client

How do I read this soap response and echo the values of subid and points.
Here is the response
<?xml version="1.0" encoding="ISO-8859-1"?>
<SOAP-ENV:Envelope SOAP-ENV:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:SOAP-ENC="http://schemas.xmlsoap.org/soap/encoding/" xmlns:tns="urn:zuku">
<SOAP-ENV:Body>
<ns1:showloyaltypointsResponse xmlns:ns1="http://tempuri.org">
<return xsi:type="SOAP-ENC:Array" SOAP-ENC:arrayType="tns:subpoints[1]">
<item xsi:type="tns:subpoints">
<subid xsi:type="xsd:integer">618341</subid>
<points xsi:type="xsd:string">0</points>
</item>
</return>
</ns1:showloyaltypointsResponse>
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>
And here is my php code
$result = $client ->call('showloyaltypoints',array("subid" =>$subid,"username" =>"$username", "password" =>"$password"));
echo $client->response;
I found out the solution by converting it to an array first.
https://stackoverflow.com/a/42311833/7042343

Prestashop webservice API creating cart rules

Have been trying to create a cart rule using Prestashop web-service with no luck.
Tried this https://github.com/PrestaShop/PrestaShop-webservice-lib/blob/master/examples/Create.php (with cart_rules value replaced away from customers).
But I always get the same error: Property CartRule->name is empty.
Request:
<?xml version="1.0" encoding="UTF-8"?>
<prestashop xmlns:xlink="http://www.w3.org/1999/xlink">
<cart_rule>
<id></id>
<id_customer>1</id_customer>
<date_from>2017-09-05 13:00:00</date_from>
<date_to>2020-06-30 13:00:00</date_to>
<description>1</description>
<quantity>1</quantity>
<quantity_per_user>1</quantity_per_user>
<priority>1</priority>
<partial_use>1</partial_use>
<code>11111111111111111111111111111111111111111111111111</code>
<minimum_amount>1</minimum_amount>
<minimum_amount_tax>1</minimum_amount_tax>
<minimum_amount_currency>1</minimum_amount_currency>
<minimum_amount_shipping>1</minimum_amount_shipping>
<country_restriction>1</country_restriction>
<carrier_restriction>1</carrier_restriction>
<group_restriction>1</group_restriction>
<cart_rule_restriction>1</cart_rule_restriction>
<product_restriction>1</product_restriction>
<shop_restriction>1</shop_restriction>
<free_shipping>1</free_shipping>
<reduction_percent>151</reduction_percent>
<reduction_amount>1</reduction_amount>
<reduction_tax>1</reduction_tax>
<reduction_currency>1</reduction_currency>
<reduction_product>1</reduction_product>
<reduction_exclude_special>1</reduction_exclude_special>
<gift_product>1</gift_product>
<gift_product_attribute>1</gift_product_attribute>
<highlight>1</highlight>
<active>1</active>
<date_add>1</date_add>
<date_upd>1</date_upd>
<name>TEST NAME</name>
</cart_rule>
</prestashop>
Response:
<?xml version="1.0" encoding="UTF-8"?>
<prestashop xmlns:xlink="http://www.w3.org/1999/xlink">
<errors>
<error>
<code><![CDATA[84]]></code>
<message><![CDATA[Validation error: "Property CartRule->name is empty."]]></message>
</error>
</errors>
</prestashop>
The cart rule name is a multi-language field, so you have to specify the language id.
Try this:
<cart_rule>
...
<name>
<language id="1">TEST NAME</language>
</name>
...
</cart_rule>
Obviously you have to use the right ID language

Get Value from given XML using simple load string

Hi I want to get value from given XML using simple_xml_string but its not working. XML is given below:
<soap-env:Envelope xmlns:soap-env="http://schemas.xmlsoap.org/soap/envelope/">
<soap-env:Header>
<eb:MessageHeader xmlns:eb="http://www.ebxml.org/namespaces/messageHeader" eb:version="1.0" soap-env:mustUnderstand="1">
<eb:From><eb:PartyId eb:type="urn:x12.org.IO5:01">webservices.sabre.com</eb:PartyId></eb:From>
<eb:To><eb:PartyId eb:type="urn:x12.org.IO5:01">info#gandakiintl.com</eb:PartyId></eb:To>
<eb:CPAId>T198</eb:CPAId>
<eb:ConversationId>111#gandakiintl.com</eb:ConversationId>
<eb:Service eb:type="SabreXML">Enhanced Air Book Request</eb:Service>
<eb:Action>ErrorRS</eb:Action>
<eb:MessageData>
<eb:MessageId>1522435489615361760</eb:MessageId>
<eb:Timestamp>2017-01-11T13:36:01</eb:Timestamp>
<eb:RefToMessageId>mid:11110info#gandakiintl.com</eb:RefToMessageId>
</eb:MessageData>
</eb:MessageHeader>
<wsse:Security xmlns:wsse="http://schemas.xmlsoap.org/ws/2002/12/secext">
<wsse:BinarySecurityToken valueType="String" EncodingType="wsse:Base64Binary">
Shared/IDL:IceSess\/SessMgr:1\.0.IDL/Common/!ICESMS\/ACPCRTC!ICESMSLB\/CRT.LB!-3319706757025363837!367706!0
</wsse:BinarySecurityToken>
</wsse:Security>
</soap-env:Header>
<soap-env:Body>
<soap-env:Fault>
<faultcode>soap-env:Client.InvalidSecurityToken</faultcode>
<faultstring>Invalid or Expired binary security token: Shared/IDL:IceSess\/SessMgr:1\.0.IDL/Common/!ICESMS\/ACPCRTC!ICESMSLB\/CRT.LB!-3319706757025363837!367706!0</faultstring>
<detail>
<StackTrace>
com.sabre.universalservices.base.session.SessionException: errors.session.USG_INVALID_SECURITY_TOKEN
</StackTrace>
</detail>
</soap-env:Fault>
</soap-env:Body>
</soap-env:Envelope>
From above xml I want to get faultCode node value But I am not able to get. Please help. I tried doing it but its not working.
$feed = simplexml_load_string($response);
$a = $feed->children('http://schemas.xmlsoap.org/soap/envelope/');
var_dump($a->Fault->children('http://schemas.xmlsoap.org/soap/envelope/'));
Edited:
Output I get is: Node no longer exists. But I want to get "soap-env:Client.InvalidSecurityToken" value.

Authorize.net Update recurrent billing using ARB

Does Authorize.net ARP API accept XML data if the data field is empty ? Do we need to have the data on all the XML elements ?
I used the following XML for updating the subscription.
<?xml version="1.0" encoding="utf-8"?>
<ARBUpdateSubscriptionRequest xmlns="AnetApi/xml/v1/schema/AnetApiSchema.xsd">
<merchantAuthentication>
<name>435345345345</name>
<transactionKey>sdfsdfsdfsdf</transactionKey>
</merchantAuthentication>
<refId>155969e50PGj</refId>
<subscriptionId>234324</subscriptionId>
<subscription>
<amount>75</amount>
<customer>
<id>155969</id>
<email></email>
<phoneNumber></phoneNumber>
</customer>
<billTo>
<firstName></firstName>
<lastName></lastName>
<company></company>
<address></address>
<city></city>
<state></state>
<zip></zip>
<country></country>
</billTo>
<shipTo>
<firstName></firstName>
<lastName></lastName>
<company></company>
<address></address>
<city></city>
<state></state>
<zip></zip>
<country></country>
</shipTo>
</subscription>
</ARBUpdateSubscriptionRequest>
I got the following error :
<?xml version="1.0" encoding="utf-8"?>
<ARBUpdateSubscriptionResponse xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns="AnetApi/xml/v1/schema/AnetApiSchema.xsd">
<refId>155969e50PGj</refId>
<messages>
<resultCode>Error</resultCode>
<message>
<code>E00014</code>
<text>Bill-To First Name is required.</text>
</message>
<message>
<code>E00014</code>
<text>Bill-To Last Name is required.</text>
</message>
</messages>
</ARBUpdateSubscriptionResponse>
ARBUpdateSubscriptionRequest is required other XML in request
<?xml version="1.0" encoding="utf-8"?>
<ARBUpdateSubscriptionRequest xmlns="AnetApi/xml/v1/schema/AnetApiSchema.xsd">
<merchantAuthentication>
<name>mytestacct</name>
<transactionKey>112223344</transactionKey>
</merchantAuthentication>
<refId>Sample</refId>
<subscriptionId>100748</subscriptionId>
<subscription>
<payment>
<creditCard>
<cardNumber>4111111111111111</cardNumber>
<expirationDate>2010-08</expirationDate>
</creditCard>
</payment>
</subscription>
</ARBUpdateSubscriptionRequest>

Categories