Flex List displays key value pair from Web service - web-services

How to display a list of data in Flex by getting key value pair from a wsdl web service? Please help.

It depends on your web service and data types it provides.
Many web services can return you a response as a list of objects.
Others give you a structured string.
In my example I use a simple public weather web service, which returns its XML as a string.
This is a service description: http://www.webservicex.com/globalweather.asmx?wsdl
This is a test page: http://www.webservicex.com/globalweather.asmx?test
I use the GetCitiesByCountry method to get this list:
//source code
<?xml version="1.0" encoding="utf-8"?>
<s:Application xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx"
minWidth="955" minHeight="600" creationComplete="init()">
<fx:Script>
<![CDATA[
import mx.controls.Alert;
import mx.rpc.CallResponder;
import mx.rpc.events.FaultEvent;
import mx.rpc.events.ResultEvent;
import services.globalweather.Globalweather;
private var ws:Globalweather = new Globalweather();
private var getCitiesByCountryCR:CallResponder;
private function init():void
{
getCitiesByCountryCR = new CallResponder();
getCitiesByCountryCR.addEventListener(ResultEvent.RESULT, onResult);
getCitiesByCountryCR.addEventListener(FaultEvent.FAULT, onFault);
}
private function onResult(evt:ResultEvent):void
{
var xml:XML = new XML(evt.result);
var xmlList:XMLList = xml.Table.City;
taCities.text = "";
for each (var item:XML in xmlList)
{
taCities.text += item.toString() + String.fromCharCode(13);
}
}
private function onFault(evt:FaultEvent):void
{
Alert.show("Fault!");
}
protected function getCities(event:MouseEvent):void
{
getCitiesByCountryCR.token = ws.GetCitiesByCountry(tiCountry.text);
}
]]>
</fx:Script>
<s:VGroup x="20" y="20" width="330" height="200">
<s:HGroup verticalAlign="bottom">
<s:Label text="Enter country name:"/>
<s:TextInput id="tiCountry" text="France"/>
<s:Button x="202" y="10" label="Get cities!" click="getCities(event)"/>
</s:HGroup>
<s:TextArea id="taCities" height="100%" width="100%"/>
</s:VGroup>
</s:Application>

Related

Apache Camel upgrade from 2.13.0 to 2.17.2 route not working

after upgrading the Java implementation of Camel from 2.13.0 to 2.17.2 (and cxf-rt-frontend-jaxrs from 2.7.10 to 3.1.5, and spring framework from 3.2.8 to 4.3.2), the webapp that is serving as a proxy stopped working correctly.
The app is supposed to intercept a webservice request, modify fields that are defined in a properties file throught the ContextManager class, and forward the request to the correct endpoint.
After the upgrade, the app is unable to set the missing fields in the original request, thus returning the following message: "REQUEST_MESSAGE_NOT_COMPLIANT_WITH_SCHEMA - Your request message does not comply to the web service schema".
This is of course expected since the missing fields are not being set.
Any help would be greatly appreciated.
UPDATE:
The problem seems to be coming from the xpath method which in the previous version returned the correct node where some information needs to be set and now is returning null.
My Camel route definition is as follows:
CreditLimitRequestServiceRoute.class
public class CreditLimitRequestServiceRoute extends AbstractEHRoute {
#Autowired
private ContextManager contextManager;
#Override
public void configure() throws Exception {
Namespaces ns = new Namespaces("ns1", "http://ehsmartlink/commonError");
onException(SoapFault.class)
.to("consoleflux:message?level=ERROR&text=${exception.message}&content=${exception.detail}")
.setHeader("soapFaultDetail", simple("${exception.detail}"))
.choice()
.when(and(header("soapFaultDetail").isNotNull(), xpath("//ns1:commonError/errorType/text() = 'BusinessError'", ns, "soapFaultDetail")))
.to("consoleflux:finish?ignoreContent=true")
.otherwise()
.to("consoleflux:error?ignoreContent=true");
onException(Exception.class)
.to("consoleflux:error");
from("cxf:bean:creditLimitRequestServiceProxy?dataFormat=PAYLOAD").routeId("creditLimitRequestServiceRoute")
.log(LoggingLevel.INFO, "Invocation du WS").streamCaching()
.to("consoleflux:start?source=SOA&dest=EH&type=CREDIT_LIMIT")
.to("consoleflux:message?ignoreContent=true&text=Affectation du Contexte EH")
.setHeader("context").xpath("//context")
.bean(contextManager, "setContext")
.to("consoleflux:message?ignoreContent=true&text=Invocation du WS EH ${headers.operationName}")
.to("cxf:bean:creditLimitRequestService?dataFormat=PAYLOAD")
.to("consoleflux:finish");
}
}
AbstractEHRoute.class
public abstract class AbstractEHRoute extends RouteBuilder {
protected XPathBuilder xpath(String text, Namespaces namespaces, String headerName) {
XPathBuilder xpath = XPathBuilder.xpath(text).namespaces(namespaces);
xpath.setHeaderName(headerName);
return xpath;
}
}
ContextManager
package com.stef.soa.eh.integration.beans;
import static com.google.common.base.Objects.firstNonNull;
import static com.google.common.base.Strings.isNullOrEmpty;
import java.util.Map;
import java.util.UUID;
import org.apache.camel.Header;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import com.google.common.base.Preconditions;
import com.google.common.collect.Maps;
#Component
public class ContextManager {
private static final String USER_NAME = "userName";
private static final String USER_PASSWORD = "userPassword";
private static final String LANGUAGE_TEXT_IDENTIFIER = "languageTextIdentifier";
private static final String TRANSACTION_IDENTIFIER = "transactionIdentifier";
private static final String POLICIY_IDENTIFIER = "policyIdentifier";
private static final String POLICY_EXTENSION_IDENTIFIER = "policyExtensionIdentifier";
private static final String POLICY_EHBU_IDENTIFIER = "policyEHBUIdentifier";
private static final String IP_ADRESS = "ipAdress";
#Value("${eh.context.userName}")
private String userName;
#Value("${eh.context.userPassword}")
private String userPassword;
#Value("${eh.context.languageTextIdentifier}")
private String languageTextIdentifier;
#Value("${eh.context.policyIdentifier}")
private String policyIdentifier;
#Value("${eh.context.policyExtensionIdentifier}")
private String policyExtensionIdentifier;
#Value("${eh.context.policyEHBUIdentifier}")
private String policyEHBUIdentifier;
#Value("${eh.context.ipAdress}")
private String ipAdress;
public void setContext(#Header("context") Node context) {
Preconditions.checkNotNull(context, "Le contexte doit ĂȘtre renseignĂ©");
// Suppression des noeuds enfants avec sauvegarde les valeurs courantes dans une map
Map<String, String> currentValues = Maps.newHashMap();
NodeList list = context.getChildNodes();
for (int i = list.getLength() - 1; i >= 0; i--) {
Node child = list.item(i);
if (child.getNodeType() == Node.ELEMENT_NODE && !isNullOrEmpty(child.getTextContent())) {
currentValues.put(child.getNodeName(), child.getTextContent());
}
context.removeChild(child);
}
// Ajout des noeuds enfants
appendChild(context, USER_NAME, userName, currentValues);
appendChild(context, USER_PASSWORD, userPassword, currentValues);
appendChild(context, LANGUAGE_TEXT_IDENTIFIER, languageTextIdentifier, currentValues);
appendChild(context, TRANSACTION_IDENTIFIER, UUID.randomUUID().toString(), currentValues);
appendChild(context, POLICIY_IDENTIFIER, policyIdentifier, currentValues);
appendChild(context, POLICY_EXTENSION_IDENTIFIER, policyExtensionIdentifier, currentValues);
appendChild(context, POLICY_EHBU_IDENTIFIER, policyEHBUIdentifier, currentValues);
appendChild(context, IP_ADRESS, ipAdress, currentValues);
}
private void appendChild(Node node, String name, String value, Map<String, String> currentValues) {
Document document = node.getOwnerDocument();
Element child = document.createElement(name);
child.setTextContent(firstNonNull(currentValues.get(name), value));
node.appendChild(child);
}
}
context.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context.xsd">
<context:property-placeholder location="classpath:eh.properties, file:///${eh.home}/conf/eh.properties"
ignore-resource-not-found="true" system-properties-mode="OVERRIDE" />
<context:component-scan base-package="com.stef.soa.eh" />
<context:annotation-config />
<import resource="classpath:META-INF/eh/spring/broker.xml" />
<import resource="classpath:META-INF/eh/spring/camel.xml" />
<import resource="classpath:META-INF/eh/spring/cxf.xml" />
<import resource="classpath:META-INF/soa-console-flux-client/spring/context.xml"/>
</beans>
camel.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans
xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:http="http://cxf.apache.org/transports/http/configuration"
xsi:schemaLocation="
http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://camel.apache.org/schema/spring
http://camel.apache.org/schema/spring/camel-spring.xsd
http://cxf.apache.org/transports/http/configuration
http://cxf.apache.org/schemas/configuration/http-conf.xsd" >
<!-- Camel Context -->
<camelContext xmlns="http://camel.apache.org/schema/spring" id="ehContext">
<properties>
<property key="org.apache.camel.xmlconverter.output.indent" value="yes"/>
<property key="org.apache.camel.xmlconverter.output.{http://xml.apache.org/xslt}indent-amount" value="4"/>
</properties>
<package>com.stef.soa.eh.integration</package>
</camelContext>
</beans>
cxf.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans
xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:cxf="http://camel.apache.org/schema/cxf"
xmlns:http="http://cxf.apache.org/transports/http/configuration"
xmlns:sec="http://cxf.apache.org/configuration/security"
xsi:schemaLocation="
http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://camel.apache.org/schema/cxf
http://camel.apache.org/schema/cxf/camel-cxf.xsd
http://cxf.apache.org/transports/http/configuration
http://cxf.apache.org/schemas/configuration/http-conf.xsd" >
<!-- Serveur Proxy, Certificat -->
<http:conduit name="*.http-conduit">
<http:client ProxyServer="${proxy.host}" ProxyServerPort="${proxy.port}"
ConnectionTimeout="${http.client.connectionTimeout}" ReceiveTimeout="${http.client.receiveTimeout}" />
<http:proxyAuthorization>
<sec:UserName>${proxy.username}</sec:UserName>
<sec:Password>${proxy.password}</sec:Password>
</http:proxyAuthorization>
<http:tlsClientParameters>
<sec:keyManagers keyPassword="${eh.keyStore.password}">
<sec:keyStore type="pkcs12" password="${eh.keyStore.password}" file="${eh.home}/${eh.keyStore.file}" />
</sec:keyManagers>
</http:tlsClientParameters>
</http:conduit>
<!-- Services Proxy et Cible -->
<cxf:cxfEndpoint
id="creditLimitRequestServiceProxy"
address="/creditLimitRequestService"
wsdlURL="META-INF/eh/wsdl/CreditLimitRequestService/EH_SMARTLINK_CreditLimitRequestServiceV4.wsdl"
serviceName="ns:CreditLimitRequestServiceV4"
endpointName="ns:CreditLimitRequestServiceV4"
xmlns:ns="http://ehsmartlink/CreditLimitRequestService/v4"
/>
<cxf:cxfEndpoint
id="creditLimitRequestService"
address="${eh.creditLimitRequestService.url}"
wsdlURL="META-INF/eh/wsdl/CreditLimitRequestService/EH_SMARTLINK_CreditLimitRequestServiceV4.wsdl"
serviceName="ns:CreditLimitRequestServiceV4"
endpointName="ns:CreditLimitRequestServiceV4"
xmlns:ns="http://ehsmartlink/CreditLimitRequestService/v4"
loggingFeatureEnabled="true"
/>
<cxf:cxfEndpoint
id="customerListRetrieveServiceProxy"
address="/customerListRetrieveService"
wsdlURL="META-INF/eh/wsdl/CustomerListRetrieveService/CustomerListRetrieveV2.wsdl"
serviceName="ns:CustomerListRetrieveServiceV2"
endpointName="ns:CustomerListRetrieveServiceV2"
xmlns:ns="http://ehsmartlink/CustomerListRetrieve/v2"
/>
<cxf:cxfEndpoint
id="customerListRetrieveService"
address="${eh.customerListRetrieveService.url}"
wsdlURL="META-INF/eh/wsdl/CustomerListRetrieveService/CustomerListRetrieveV2.wsdl"
serviceName="ns:CustomerListRetrieveServiceV2"
endpointName="ns:CustomerListRetrieveServiceV2"
xmlns:ns="http://ehsmartlink/CustomerListRetrieve/v2"
loggingFeatureEnabled="true"
/>
<cxf:cxfEndpoint
id="firstEuroListRepertoireReadServiceProxy"
address="/firstEuroListRepertoireReadService"
wsdlURL="META-INF/eh/wsdl/FirstEuroListRepertoireReadService/EH_SMARTLINK_FirstEuroListRepertoireReadService-v1.wsdl"
serviceName="ns:FirstEuroListRepertoireReadService-v1"
endpointName="ns:FirstEuroListRepertoireReadServicePort-v1_soap11"
xmlns:ns="http://eulerhermes.com/SMARTLINK/services/FirstEuroListRepertoireReadService/v1"
/>
<cxf:cxfEndpoint
id="firstEuroListRepertoireReadService"
address="${eh.firstEuroListRepertoireReadService.url}"
wsdlURL="META-INF/eh/wsdl/FirstEuroListRepertoireReadService/EH_SMARTLINK_FirstEuroListRepertoireReadService-v1.wsdl"
serviceName="ns:FirstEuroListRepertoireReadService-v1"
endpointName="ns:FirstEuroListRepertoireReadServicePort-v1_soap11"
xmlns:ns="http://eulerhermes.com/SMARTLINK/services/FirstEuroListRepertoireReadService/v1"
loggingFeatureEnabled="true"
/>
<cxf:cxfEndpoint
id="firstEuroListRepertoireUpdateServiceProxy"
address="/firstEuroListRepertoireUpdateService"
wsdlURL="META-INF/eh/wsdl/FirstEuroListRepertoireUpdateService/EH_SMARTLINK_FirstEuroListRepertoireUpdateService-v1.wsdl"
serviceName="ns:FirstEuroListRepertoireUpdateService-v1"
endpointName="ns:FirstEuroListRepertoireUpdateServicePort-v1"
xmlns:ns="http://eulerhermes.com/SMARTLINK/services/FirstEuroListRepertoireUpdateService/v1"
/>
<cxf:cxfEndpoint
id="firstEuroListRepertoireUpdateService"
address="${eh.firstEuroListRepertoireUpdateService.url}"
wsdlURL="META-INF/eh/wsdl/FirstEuroListRepertoireUpdateService/EH_SMARTLINK_FirstEuroListRepertoireUpdateService-v1.wsdl"
serviceName="ns:FirstEuroListRepertoireUpdateService-v1"
endpointName="ns:FirstEuroListRepertoireUpdateServicePort-v1"
xmlns:ns="http://eulerhermes.com/SMARTLINK/services/FirstEuroListRepertoireUpdateService/v1"
loggingFeatureEnabled="true"
/>
<cxf:cxfEndpoint
id="limitDetailReadServiceProxy"
address="/limitDetailReadService"
wsdlURL="META-INF/eh/wsdl/LimitDetailReadService/EH_SMARTLINK_LimitDetailReadService-v2.wsdl"
serviceName="ns:LimitDetailReadService-v2"
endpointName="ns:LimitDetailReadServicePort-v2"
xmlns:ns="http://eulerhermes.com/SMARTLINK/services/LimitDetailReadService/v2"
/>
<cxf:cxfEndpoint
id="limitDetailReadService"
address="${eh.limitDetailReadService.url}"
wsdlURL="META-INF/eh/wsdl/LimitDetailReadService/EH_SMARTLINK_LimitDetailReadService-v2.wsdl"
serviceName="ns:LimitDetailReadService-v2"
endpointName="ns:LimitDetailReadServicePort-v2"
xmlns:ns="http://eulerhermes.com/SMARTLINK/services/LimitDetailReadService/v2"
loggingFeatureEnabled="true"
/>
</beans>

Customize SOAP request send from Windows 8 application

I am consuming a WSDL in a Windows 8 app. I need to customize the SOAP request like
New SOAP Request:
</ns0:Header>
<ns0:Body>
<ns0:Request xmlns:ns0="http://www.ABC.co.il/2004/01/RetrieveEntityDetails/EntityDetailsRequest">
</ns0:Request></ns0:Body></ns0:Envelope>
Current SOAP Request:
<s:Envelope xmlns:s="http://schemas.xmlsoap.org/soap/envelope/">
<s:Header>
</s:Header>
<s:Body>
<RetrieveEntityDetailsXPOP_XmlRequest xmlns="http://tempuri.org/">
<RetrieveEntityDetailsXPOP_Xml xmlns:i="http://www.w3.org/2001/XMLSchema-instance">
<requestDoc>
</requestDoc>
</RetrieveEntityDetailsXPOP_Xml>
</RetrieveEntityDetailsXPOP_XmlRequest>
</s:Body>
</s:Envelope>
How will I change the namespace and set a request tag inside the body tag.
Code:
Client = new EAI_RetrieveEntityDetailsXP_ServiceSoapClient();
Client.RetrieveEntityDetailsXPOP_XmlCompleted += Client_RetrieveEntityDetailsXPOP_XmlCompleted;
XElement requestData = GetRequestData();
using (new OperationContextScope(Client.InnerChannel))
{
// Create a custom soap header
var msgHeader = MessageHeader.CreateHeader("myCustomHeader", string.Empty, "myValue");
// Add the header into request message
OperationContext.Current.OutgoingMessageHeaders.Add(msgHeader);
Client.RetrieveEntityDetailsXPOP_XmlAsync(requestData);
}
I have actually used HttpCleint to call this service by using following code. Using this we can generate the SOAP request as desired.
string soapString = ConstructSoapRequest();
using (var client = new HttpClient())
{
client.DefaultRequestHeaders.Add("SOAPAction", SOAPActionUri);
var content = new StringContent(soapString, Encoding.UTF8, "text/xml");
using (var response = await client.PostAsync(Uri, content))
{
var soapResponse = await response.Content.ReadAsStringAsync();
return soapResponse;
}
}
private string ConstructSoapRequest()
{
return String.Format(#"<ns0:Envelope xmlns:ns0='http://www.cellcom.co.il/2004/01/std-headers'>
<ns0:Header>
</ns0:Header>
<ns0:Body>
<ns0:Request xmlns:ns0='http://www.cellcom.co.il/2004/01/RetrieveEntityDetails/EntityDetailsRequest'>
</ns0:Request></ns0:Body></ns0:Envelope>", 100);
}

How do I run multiple Selenium tests with different required capabilties

I want to run the same test code:
e.g.
WebElement element = driver.findElement(By.name("q"));
element.sendKeys("mysql excel 2013");
element.submit();
// Check the title of the page
System.out.println("Page title is: " + driver.getTitle());
// Google's search is rendered dynamically with JavaScript.
// Wait for the page to load, timeout after 10 seconds
(new WebDriverWait(driver, 10)).until(new ExpectedCondition<Boolean>() {
public Boolean apply(WebDriver d) {
return d.getTitle().toLowerCase().startsWith("mysql");
}
});
// Should see: "cheese! - Google Search"
System.out.println("Page title is: " + driver.getTitle());
// Close the browser
With different capability configurations
DesiredCapabilities capability = DesiredCapabilities.firefox();
capability.setVersion("15");
capability.setCapability("flash", "11-4");
RemoteWebDriver driver = new RemoteWebDriver(new URL("http://192.168.1.22:4444/wd/hub"), capability);
Chrome
DesiredCapabilities capability = DesiredCapabilities.chrome();
capability.setVersion("21");
capability.setCapability("flash", "11-4");
RemoteWebDriver driver = new RemoteWebDriver(new URL("http://192.168.1.22:4444/wd/hub"), capability);
What is the best way to do this without just creating multiple instances with different capabilitilies? Is there a concept provided by Selenium for doing this ?
Or would I "simply" use some kind of looping construct to loop over?
For achieving this you should go for parameter passing concept using testng
TestNg Suite
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE suite SYSTEM "http://testng.org/testng-1.0.dtd">
<suite thread-count="2" name=MyTestSuite" parallel="tests">
<test name="RunInFirefox" preserve-order="false">
<parameter name="version" value="8"/>
<parameter name="browser" value="firefox"/>
<parameter name="flashVersion" value="11.2"/>
<classes preserve-order="true">
<class name="com.test.TestCase1"/>
<class name="com.test.TestCase2"/>
<class name="com.test.TestCase3"/>
</classes>
</test>
<test name="RunInChrome" preserve-order="false">
<parameter name="version" value="21"/>
<parameter name="browser" value="chrome"/>
<parameter name="flashVersion" value="11.2"/>
<classes preserve-order="true">
<class name="com.test.TestCase1"/>
<class name="com.test.TestCase2"/>
<class name="com.test.TestCase3"/>
</classes>
</test>
</suite>
TestNg TestCase
import org.openqa.selenium.WebDriver;
import org.testng.annotations.Parameters;
import org.testng.annotations.Test;
import org.testng.annotations.BeforeMethod;
import org.testng.annotations.AfterMethod;
import org.testng.annotations.BeforeClass;
import org.testng.annotations.AfterClass;
import org.testng.annotations.BeforeTest;
import org.testng.annotations.AfterTest;
public class ExampleTestCase {
private static WebDriver driver;
#Parameters({"browser,version,flashVersion"})
#BeforeClass
public void beforeClass(String browser,String version,String flashVersion)
{
driver=getDriverInstance(browser,version,flashVersion);
}
#BeforeTest
public void beforeTest()
{
}
#Test
public void f()
{
//your test code here
}
#AfterTest
public void afterTest()
{
}
#AfterClass
public void afterClass()
{
}
}
getDriverInstance method implimentation
public static WebDriver getDriverInstance(String browser,String version,String flashVersion)
{
WebDriver driver=null;
if(browser.equals("firefox"))
{
DesiredCapabilities capability = DesiredCapabilities.firefox();
capability.setVersion(version);
capability.setCapability("flash", flashVersion);
driver = new RemoteWebDriver(new URL("http://192.168.1.22:4444/wd/hub"), capability);
}
else if(browser.equals("chrome"))
{
DesiredCapabilities capability = DesiredCapabilities.chrome();
capability.setVersion(version);
capability.setCapability("flash", flashVersion);
driver = new RemoteWebDriver(new URL("http://192.168.1.22:4444/wd/hub"), capability);
}
return driver;
}

My flex code does not parse the soap response properly

My code is supposed to parse a SOAP response and populate the dropdown list. When I manually add the xml code it works but when I try to parse the SOAP response it runs into following error:
TypeError: Error #1009: Cannot access a property or method of a null object reference.
at ex1_02_starter/dropDownList_creationCompleteHandler()[C:\Users\jack\Adobe Flash Builder 4.5\Workspace\Starter 1_02\src\ex1_02_starter.mxml:26]
at ex1_02_starter/___ex1_02_starter_Operation1_result()[C:\Users\jack\Adobe Flash Builder 4.5\Workspace\Starter 1_02\src\ex1_02_starter.mxml:41]
at flash.events::EventDispatcher/dispatchEventFunction()
at flash.events::EventDispatcher/dispatchEvent()
at mx.rpc::AbstractOperation/http://www.adobe.com/2006/flex/mx/internal::dispatchRpcEvent()[E:\dev\4.5.1\frameworks\projects\rpc\src\mx\rpc\AbstractOperation.as:249]
at mx.rpc::AbstractInvoker/http://www.adobe.com/2006/flex/mx/internal::resultHandler()[E:\dev\4.5.1\frameworks\projects\rpc\src\mx\rpc\AbstractInvoker.as:318]
at mx.rpc::Responder/result()[E:\dev\4.5.1\frameworks\projects\rpc\src\mx\rpc\Responder.as:56]
at mx.rpc::AsyncRequest/acknowledge()[E:\dev\4.5.1\frameworks\projects\rpc\src\mx\rpc\AsyncRequest.as:84]
at DirectHTTPMessageResponder/completeHandler()[E:\dev\4.5.1\frameworks\projects\rpc\src\mx\messaging\channels\DirectHTTPChannel.as:451]
at flash.events::EventDispatcher/dispatchEventFunction()
at flash.events::EventDispatcher/dispatchEvent()
at flash.net::URLLoader/onComplete()
The SOAP Response that I am receiving
<?xml version="1.0" encoding="UTF-8"?>
<soapenv:Envelope
xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<soapenv:Body>
<mycustomersResponse xmlns="http://Services.com">
<mycustomersReturn>
<age>28</age>
<name>Alex</name>
</mycustomersReturn>
<mycustomersReturn>
<age>29</age>
<name>Jack</name>
</mycustomersReturn>
<mycustomersReturn>
<age>30</age>
<name>Johny</name>
</mycustomersReturn>
</mycustomersResponse>
</soapenv:Body>
</soapenv:Envelope>
My Flex code
<?xml version="1.0" encoding="utf-8"?>
<s:Application xmlns:fx="http://ns.adobe.com/mxml/2009"
xmlns:s="library://ns.adobe.com/flex/spark"
xmlns:mx="library://ns.adobe.com/flex/mx"
xmlns:components="components.*"
xmlns:hellos="services.hellos.*"
height="957" creationComplete="initApp()" >
<fx:Style source="Styles.css"/>
<fx:Script>
<![CDATA[
import mx.collections.XMLListCollection;
import mx.events.FlexEvent;
import mx.messaging.messages.SOAPMessage;
import mx.rpc.events.ResultEvent;
[Bindable]
var _result:*;
private function initApp():void
{
mywebservice.mycustomers();
}
protected function
dropDownList_creationCompleteHandler(event:ResultEvent):void
{
var xml:XML = event.result as XML;
var xmlString:String = xml.toXMLString();
var patt:RegExp = new RegExp("xmlns[^\"]*\"[^\"]*\"", "gi");
var newXmlString:String = xmlString.replace(patt, "");
xml = new XML(newXmlString);
_result = new XMLListCollection(xml.mycustomersResponse.mycustomersReturn);
}
]]>
</fx:Script>
<fx:Declarations>
<s:WebService id="mywebservice"
wsdl="http://localhost:8081/WebServiceTest/services/Hellos?wsdl">
<s:operation name="mycustomers"
resultFormat="object"
result="dropDownList_creationCompleteHandler(event);"
/>
</s:WebService>
</fx:Declarations>
<s:FormItem label="Label">
<s:DropDownList id="dropDownList"
labelField="name">
<s:AsyncListView list="{_result}"/>
</s:DropDownList>
</s:FormItem>
</s:Application>
coming from here dropdown list does not show its values I slightly modified my example. There are two opportunities:
Strip namespace from xml
Utilize namespace
Those are shown in dropDownList and dropDownList2 code respectively.
Note, that you can not utilize namespace still using labelField property(at least I couldn't find a way). You have to use labelFunction to extract label.
<?xml version="1.0" encoding="utf-8"?>
<![CDATA[
import mx.collections.XMLListCollection;
import mx.events.FlexEvent;
import mx.messaging.messages.SOAPMessage;
[Bindable]
var _result:*;
[Bindable]
var _result2:*;
protected function
dropDownList_creationCompleteHandler(event:FlexEvent):void
{
var xml:XML = <Body>
<myusersResponse xmlns="http://Services.com">
<myusersReturn>
<name>Nicole</name>
<age>50</age>
</myusersReturn>
<myusersReturn>
<name>Jayne</name>
<age>40</age>
</myusersReturn>
<myusersReturn>
<name>Alex</name>
<age>33</age>
</myusersReturn>
</myusersResponse>
</Body>;
var xmlString:String = xml.toXMLString();
var patt:RegExp = new RegExp("xmlns[^\"]*\"[^\"]*\"", "gi");
var newXmlString:String = xmlString.replace(patt, "");
xml = new XML(newXmlString);
_result = new XMLListCollection(xml.myusersResponse.myusersReturn);
}
protected function dropDownList2_creationCompleteHandler(event:FlexEvent):void
{
var xml:XML = <Body>
<myusersResponse xmlns="http://Services.com">
<myusersReturn>
<name>Nicole</name>
<age>50</age>
</myusersReturn>
<myusersReturn>
<name>Jayne</name>
<age>40</age>
</myusersReturn>
<myusersReturn>
<name>Alex</name>
<age>33</age>
</myusersReturn>
</myusersResponse>
</Body>;
var ns:Namespace = new Namespace("http://Services.com");
_result2 = new XMLListCollection(xml.ns::myusersResponse.ns::myusersReturn);
}
private function dropDownList2_labelFunction(item:Object):String{
var itemXml:XML = item as XML;
var ns:Namespace = new Namespace("http://Services.com");
return item.ns::name;
}
]]>
</fx:Script>
<fx:Declarations>
</fx:Declarations>
<s:FormItem label="Label">
<s:DropDownList id="dropDownList"
creationComplete="dropDownList_creationCompleteHandler(event)"
labelField="name">
<s:AsyncListView list="{_result}"/>
</s:DropDownList>
<s:DropDownList id="dropDownList2"
creationComplete="dropDownList2_creationCompleteHandler(event)"
labelFunction="dropDownList2_labelFunction">
<s:AsyncListView list="{_result2}"/>
</s:DropDownList>
</s:FormItem>
I think you should use event.result..mycustomersReturn. That will return an XMLList with two items that you can then convert and use in your dropdown.
Use xml parsing with namespace definition:
protected function dropDownList_creationCompleteHandler(event:ResultEvent):void
{
namespace ns = "http://Services.com";
use namespace ns;
namespace ns_soapenv = "http://schemas.xmlsoap.org/soap/envelope/";
use namespace ns_soapenv;
var xml:XML = event.result as XML;
_result = xml.Body.mycustomersResponse.mycustomersReturn;
}

JBoss 7.1.1 Webservice programatic JAAS authentication

I have a simple POJO as a webservice that is mapped to, lets say /public/authenticate :
WebService
#SOAPBinding(style = SOAPBinding.Style.DOCUMENT)
public class AuthWS{
#WebMethod
public boolean doAuthenticate(String securityToken) {
....
}
}
This webservice doesn't requre authentication and is not a protected resource.
I do have other private webservices mapped to path : /private/ws/*;
For the moment I use a security-domain that has a Database login module setup. It works fine, but user first needs to authenticate trought a web form based that makes a post request to /j_security_check. Only after this step user can use other private webservices.
I want to perform a programatically authentication after client calls this doAuthenticate method. So that client to be able to invoke other /private/ws/* webservice methods.
I'll type what I want to achieve:
#WebService
#SOAPBinding(style = SOAPBinding.Style.DOCUMENT)
public class AuthWS{
#WebMethod
public boolean doAuthenticate(String securityToken) {
SomeSecurityManager manager= SomeSecurityManager.getDefaultManager()
Map<String,Object> map = new HashMap<String, Object>();
map.put("MY_CUSTOM_SECURITY_TOKEN",securityToken);
manager.doLogin(map);
// after webservice method returns, client should now be able to invoke other private webservice
// this means that the manager should associate with this session an authenticated user.
// in order that authorization to work.
}
}
And my CustomLoginModule :
class CustomLogModule implements LoginModule {
...
public void initialize(Subject subject, CallbackHandler callbackHandler, Map<String, ?> sharedState, Map<String, ?> options) {
// store what's needed
}
public boolean login(){
// get securityToken send from the SomeSecurityManager and validate it.
// get user information from that token and store into Subject object.
}
}
And in my CustomLoginModule that implements JAAS LoginModule to check that securityToken with a custom logic, verify if it right signed with a public key for example. That securityToken contains information about principal.
If you need more details, feel free to ask.
Thanks.
EDITED
1.) Created custom-login-module.jar together with module.xml
<module xmlns="urn:jboss:module:1.1" name="custom.login.module">
<resources>
<resource-root path="custom-login-module.jar"/>
</resources>
<dependencies>
<module name="org.picketbox"/>
<module name="javax.api"/>
<module name="org.slf4j"/>
</dependencies>
</module>
2.) Added custom-login-module.jar and module.xml into jboss-as-7.1.1.Final\modules\custom\login\module
3.) custom-login-module.jar contains :
public class CustomCallbackHandler implements CallbackHandler {
private static final Logger LOGGER = LoggerFactory.getLogger(CustomCallbackHandler.class);
private String token;
public CustomCallbackHandler(String token) {
this.token= token;
}
public String getToken() {
return token;
}
#Override
public void handle(Callback[] callbacks) throws IOException, UnsupportedCallbackException {
for (Callback callback : callbacks) {
if (callback instanceof TokenCallback) {
((TokenCallback) callback).setToken(token);
}
}
}
}
public class TokenCallback implements Callback {
private static final Logger LOGGER = LoggerFactory.getLogger(TokenCallback.class);
private String token;
public TokenCallback() {
}
public String getToken() {
return token;
}
public void setToken(String token) {
LOGGER.info("Setting token = " + token);
this.token = token;
}
}
public class CustomLoginModule extends AbstractServerLoginModule {
private static final Logger LOGGER = LoggerFactory.getLogger(CustomLoginModule.class);
#Override
public boolean login() throws LoginException {
LOGGER.info("Doing login()");
boolean login = super.login();
super.loginOk = true;
return login;
}
#Override
protected Principal getIdentity() {
return new UserPrincipal("some user");
}
#Override
protected Group[] getRoleSets() throws LoginException {
return new Group[]{new MyGroup()}; // that and has name 'dummy'
}
}
These are only dummy implementations.
My web application is deployed from within a .war archive. And it Contains following :
jboss-web.xml
<?xml version='1.0' encoding='UTF-8' ?>
<!DOCTYPE jboss-web
PUBLIC -//JBoss//DTD Web Application 2.3V2//EN
http://www.jboss.org/j2ee/dtd/jboss-web_3_2.dtd>
<jboss-web>
<security-domain>custom-auth</security-domain>
</jboss-web>
web.xml
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee"
xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
id="WebApp_ID" version="2.5">
<display-name>WebApp</display-name>
<session-config>
<session-timeout>120</session-timeout>
</session-config>
<security-constraint>
<web-resource-collection>
<web-resource-name>All resources</web-resource-name>
<description>Protects all private resources</description>
<url-pattern>/private/*</url-pattern>
</web-resource-collection>
<auth-constraint>
<role-name>dummy</role-name>
</auth-constraint>
<user-data-constraint>
<transport-guarantee>CONFIDENTIAL</transport-guarantee>
</user-data-constraint>
</security-constraint>
<security-role>
<role-name>dummy</role-name>
</security-role>
<servlet>
<servlet-name>Private</servlet-name>
<servlet-class>com.company.private.PrivateWs</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>Private</servlet-name>
<url-pattern>/private/PrivateWs</url-pattern>
</servlet-mapping>
<servlet>
<servlet-name>AuthWS</servlet-name>
<servlet-class>com.company.auth.AuthWS</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>AuthWS</servlet-name>
<url-pattern>/AuthWS</url-pattern>
</servlet-mapping>
</web-app>
#WebService
#SOAPBinding(style = SOAPBinding.Style.DOCUMENT)
public class AuthWS{
private static final Logger LOGGER = LoggerFactory.getLogger(AuthWS.class);
#WebMethod
public boolean doAuthenticate(String token) {
tryProgrammaticLogin(token);
return true;
}
private void tryProgrammaticLogin(String token) {
LoginContext loginContext = null;
try {
loginContext = new LoginContext("custom-auth", new CustomCallbackHandler(token));
loginContext.login();
} catch (LoginException e) {
LOGGER.info("Some problem occured when trying to custom login.", e);
}
}
}
The call to doAuthenticate from my ws client works but the problem is that after try ProgrammaticLogin an exception occurs. And the PrivateWS is not accesible by client.
17:33:40,901 INFO [com.mycompany.AuthWS] (http--0.0.0.0-8080-1) Some problem occured when trying to custom login.: javax.security.auth.login.LoginException: Login Failure: all modules ignored
at javax.security.auth.login.LoginContext.invoke(LoginContext.java:921) [rt.jar:1.6.0_26]
at javax.security.auth.login.LoginContext.access$000(LoginContext.java:186) [rt.jar:1.6.0_26]
at javax.security.auth.login.LoginContext$4.run(LoginContext.java:683) [rt.jar:1.6.0_26]
at java.security.AccessController.doPrivileged(Native Method) [rt.jar:1.6.0_26]
at javax.security.auth.login.LoginContext.invokePriv(LoginContext.java:680) [rt.jar:1.6.0_26]
at javax.security.auth.login.LoginContext.login(LoginContext.java:579) [rt.jar:1.6.0_26]
standalone.xml from jboss configuration directory contains:
<security-domain name="custom-auth">
<authentication>
<login-module code="com.mycompany.CustomLoginModule" flag="required" module="custom.login.module"/>
</authentication>
</security-domain>
Please tell me if the way of doing authentication with creating a new LoginContext object is the right way of doing. I can't understand why this problem occurs.