Using XmlSlurper in Groovy / Grails to parse a Pingdom XML response - grails

I have used XmlSlurper successfully before, but am struggling to parse the following XML - it is a response from a call to the Pingdom API. I have tried following the namespace declaration examples, but I just get an error message on the ns1 and ns2 values. Can anybody help point me in the right direction? The xml looks like this:-
<?xml version="1.0" encoding="UTF-8"?>
<SOAP-ENV:Envelope
xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:ns1="urn:methods"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:ns2="urn:PingdomAPI"
xmlns:SOAP-ENC="http://schemas.xmlsoap.org/soap/encoding/"
SOAP-ENV:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/">
<SOAP-ENV:Body>
<ns1:Auth_loginResponse>
<return xsi:type="ns2:Auth_LoginResponse">
<status xsi:type="xsd:int">0</status>
<sessionId xsi:type="xsd:string">mysessionId</sessionId>
</return>
</ns1:Auth_loginResponse>
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>
after using the XmlSlurper it just concatenates the 0 and mysessionId to one string
0mysessionId

Try this, giving your xml is stored in the xml variable :
def records = new XmlSlurper().parseText(xml).declareNamespace(
'SOAP-ENV':'http://schemas.xmlsoap.org/soap/envelope/',
ns1:'urn:methods',
xsd:'http://www.w3.org/2001/XMLSchema',
xsi:'http://www.w3.org/2001/XMLSchema-instance',
ns2:'urn:PingdomAPI'
)
println records.'SOAP-ENV:Body'.'ns1:Auth_loginResponse'.return.status
println records.'SOAP-ENV:Body'.'ns1:Auth_loginResponse'.return.sessionId

Related

NetSuite SuiteTalk ReturnAuthorization

I am trying to create a Return Authorization from a Sales Order but can not determine the required parameters.
I keep receiving an error of:
You must enter at least one line item for this transaction.
If I attempt to include the id of one of the line items in the sales order I receive the following error:
Savon::SOAPFault ((soapenv:Server.userException)
com.netledger.util.schemabean.NLSchemaBeanException: id not found on
{urn:customers_2016_2.transactions.webservices.netsuite.com}
ReturnAuthorizationItem
This is my current request
<?xml version="1.0" encoding="UTF-8"?>
<env:Envelope
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:platformMsgs="urn:messages_2016_2.platform.webservices.netsuite.com" xmlns:platformCore="urn:core_2016_2.platform.webservices.netsuite.com"
xmlns:platformCommon="urn:common_2016_2.platform.webservices.netsuite.com" xmlns:tranSales="urn:sales_2016_2.transactions.webservices.netsuite.com" xmlns:tranCust="urn:customers_2016_2.transactions.webservices.netsuite.com">
<env:Header>
<platformMsgs:tokenPassport>
<platformCore:account>1234_SB1</platformCore:account>
<platformCore:consumerKey>***FILTERED***</platformCore:consumerKey>
<platformCore:token>***FILTERED***</platformCore:token>
<platformCore:nonce>s975gqhodufgodiueroh</platformCore:nonce>
<platformCore:timestamp>1531918396</platformCore:timestamp>
<platformCore:signature algorithm="HMAC-SHA256">p0z56JDUsN+ksjhfe8HEhdEU(WJff7u+0Yee7Axk=
</platformCore:signature>
</platformMsgs:tokenPassport>
<platformMsgs:preferences>
<platformMsgs:ignoreReadOnlyFields>true</platformMsgs:ignoreReadOnlyFields>
</platformMsgs:preferences>
</env:Header>
<env:Body>
<platformMsgs:add>
<platformMsgs:record xsi:type="tranCust:ReturnAuthorization">
<tranCust:entity internalId="173436">
<platformCore:name>C030420 John Thomas</platformCore:name>
</tranCust:entity>
<tranCust:itemList>
<tranCust:item>
<tranCust:id>21354</tranCust:id>
</tranCust:item>
</tranCust:itemList>
</platformMsgs:record>
</platformMsgs:add>
</env:Body>
</env:Envelope>
If anybody could offer any guidance it would be highly appreciated.
Figured it out, its suppose to be.
<?xml version="1.0" encoding="UTF-8"?>
<env:Envelope
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:platformMsgs="urn:messages_2016_2.platform.webservices.netsuite.com" xmlns:platformCore="urn:core_2016_2.platform.webservices.netsuite.com"
xmlns:platformCommon="urn:common_2016_2.platform.webservices.netsuite.com" xmlns:tranSales="urn:sales_2016_2.transactions.webservices.netsuite.com" xmlns:tranCust="urn:customers_2016_2.transactions.webservices.netsuite.com">
<env:Header>
<platformMsgs:tokenPassport>
<platformCore:account>1234_SB1</platformCore:account>
<platformCore:consumerKey>***FILTERED***</platformCore:consumerKey>
<platformCore:token>***FILTERED***</platformCore:token>
<platformCore:nonce>s975gqhodufgodiueroh</platformCore:nonce>
<platformCore:timestamp>1531918396</platformCore:timestamp>
<platformCore:signature algorithm="HMAC-SHA256">p0z56JDUsN+ksjhfe8HEhdEU(WJff7u+0Yee7Axk=
</platformCore:signature>
</platformMsgs:tokenPassport>
<platformMsgs:preferences>
<platformMsgs:ignoreReadOnlyFields>true</platformMsgs:ignoreReadOnlyFields>
</platformMsgs:preferences>
</env:Header>
<env:Body>
<platformMsgs:add>
<platformMsgs:record xsi:type="tranCust:ReturnAuthorization">
<tranCust:entity internalId="173436">
<platformCore:name>C030420 John Thomas</platformCore:name>
</tranCust:entity>
<tranCust:itemList>
<tranCust:item>
<tranCust:item internalId="22138" type="inventoryItem"/>
</tranCust:item>
</tranCust:itemList>
</platformMsgs:record>
</platformMsgs:add>
</env:Body>
</env:Envelope>
You have to create a initialize for the same.
So once the Sales order is created then we can do a Authorization Return on it once it successfully goes through the process.
More info at : https://docs.oracle.com/en/cloud/saas/netsuite/ns-online-help/section_N3508536.html
Make sure the SOAPAction is set to initialize.

wash_out | XML in payload has < > instead of < >

wash_out(0.9.0) has been very helpful for me in implementing a SOAP service in my Rails(3.1) app. One little problem I am facing is that for XML payload in the SOAP body, < > are getting replaced by
< >
Here's my code snippet
render :soap => "<person><firstname>larry</firstname></person>"
Output is
<?xml version="1.0" encoding="UTF-8"?>
<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:tns="http://www.w3.org/2001/12/soap-envelope">
<soap:Body>
<tns:index_response>
<value xsi:type="xsd:string"><person><firstname>larry</firstname></person></value>
</tns:index_response>
</soap:Body>
</soap:Envelope>
Is this a bug or can I fix this by some configuration or additional code.
Kindly help.
Try this (didn't test it):
render :soap => "<person><firstname>larry</firstname></person>".html_safe
I was able to resolve this. There was 1 thing I was doing wrong.
I am using savon client to call my SOAP service. I was doing
client = Savon::Client.new(wsdl: "")
result = client.call(...)
puts result
This was displaying < and >
The right way to access the response content in my case is
result.body[:index_response][:value]
result.body returns a hash
With Nokogiri I could do doc = Nokogiri::XML(result.body.to_xml)
This works well with XML in payload.

Create XML in an iOS app programatically to save it as a string

I was to create XML as below and save it as a string. The values for the XML will be from sqlite database. I want to pass the string value which will be in a xml format through a WebService, so for that reason I want to create XML and save it as a string. Please help me with this.
1st XML:
<?xml version="1.0"?>
<EmployeeHeader xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<EmplID>1001</EmplID>
<EmplName>Jack</EmplName>
<Designation>Manager</Designation>
<Department>Sales</Department>
</EmployeeHeader>
2nd XML:
<?xml version="1.0"?>
<EmployeeDetail xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<Address>
<City>Philadelphia</City>
<State>PA</State>
<Country>USA</Country>
</Address>
</EmployeeDetail>
It's not completely clear what you're asking, but if I'm understanding you correctly, you just want to build an XML string substituting the values you get from a database?
Something like:
NSString *xml = [NSString stringWithFormat:#"<EmployeeDetail><Address><City>%#</City><State>%#</State><Country>%#</Country></Address>", addr.city, addr.state, addr.country];

Using Servicestack WSDL with php

I am trying to use ServiceStack to replace WCF for a self hosted service, accessed with a PHP client that forms its messages from on the WSDL.
The WSDL produced by ServiceStack has "part names" called "par" eg:
<wsdl:message name="GetServiceDetailsIn">
<wsdl:part name="par" element="tns:GetServiceDetails" />
</wsdl:message>
Then the SOAP request produced by PHP looks like this:
<?xml version="1.0" encoding="UTF-8"?>
<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/">
<SOAP-ENV:Body><par/></SOAP-ENV:Body>
</SOAP-ENV:Envelope>
instead of this from the built-in help:
<?xml version="1.0" encoding="utf-8"?>
<soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<soap:Body>
<GetServiceDetails xmlns:i="http://www.w3.org/2001/XMLSchema-instance" xmlns="urn:Shout" />
</soap:Body>
</soap:Envelope>
The PHP client has used a par tag instead of GetServiceDetails and it gets a blank response. Can the "part name" definition can be renamed or removed in ServiceStack?
It seems you can't doing anything about this in ServiceStack and its not designed to work with PHP anyway. However you can get it working if you get PHP to tweak the XML tags with find-and-replace, or XSLTs, before sending it.

Nokogiri::XML not creating xml document

Alright, so the ultimate goal here is to parse the data inside of an xml response. The response comes in the format of a ruby string. The problem is that I'm getting an error when creating the xml file from that string (I know for a fact that response.body.to_s is a valid string of xml:
<?xml version="1.0" encoding="UTF-8"?>
<Response>
<CardTxn>
<authcode>123</authcode>
<card_scheme>Mastercard</card_scheme>
<country>United Kingdom</country>
</CardTxn>
<datacash_reference>XXXX</datacash_reference>
<merchantreference>XX0001</merchantreference>
<mode>TEST</mode>
<reason>ACCEPTED</reason>
<status>1</status>
<time>1286477267</time>
</Response>
Inside the ruby method I try to generate an xml file:
doc = Nokogiri::XML(response.body.to_s)
the output of doc.to_s after the above code executes is:
<?xml version="1.0"?>
Any ideas why the file is not getting generated correctly?
This works for me on 1.9.2. Notice it's Nokogiri::XML.parse().
require 'nokogiri'
asdf = %q{<?xml version="1.0" encoding="UTF-8"?>
<Response>
<CardTxn>
<authcode>123</authcode>
<card_scheme>Mastercard</card_scheme>
<country>United Kingdom</country>
</CardTxn>
<datacash_reference>XXXX</datacash_reference>
<merchantreference>XX0001</merchantreference>
<mode>TEST</mode>
<reason>ACCEPTED</reason>
<status>1</status>
<time>1286477267</time>
</Response>
}
doc = Nokogiri::XML.parse(asdf)
print doc.to_s
This parses the XML into a Nokogiri XML document, but doesn't create a file. doc.to_s only shows you what it would be like if you printed it.
To create a file replace "print doc.to_s" with
File.open('xml.out', 'w') do |fo|
fo.print doc.to_s
end

Resources