轉自:http://blessht.iteye.com/blog/1132934
Flex與Java通信的方式有很多種,比較常用的有以下方式:
WebService:一種跨語言的在線服務,只要用特定語言寫好并部署到服務器,其它語言就可以調用
HttpService:通過http請求的形式訪問服務器
RmoteObject:通過AMF協議,以二進制的形式交互數據
Socket:套接字協議,服務器和客戶端以IO的形式交互數據
上面幾種各有個的優勢:WebService常用于跨語言調用,不過解析協議需要花不少時間,運行速度不快;HttpService類似于Ajax;通常RmoteObject是最受歡迎的,因為它的運行效率快,數據解析方便。Socket編碼稍微麻煩點,這里有一個Socket通信的例子,大家可以學習一下:http://blog.csdn.net/as_leon/article/details/5351713
今天針對WebService、HttpService和RmoteObject三種通信分別做一個例子,供大家學習參考。
在Flex頁面上新建三個文本框和按鈕,在文本框中輸入內容再點擊不同按鈕調用不同通信方式,最后將Java返回的數據顯示在界面上。首先看下運行效果:

【Java端代碼】
JDK提供了比較全面的webservice支持,為了簡化開發步驟,我使用了Apache CXF框架實現WebService的開發部署。CXF的使用可以參照這里:http://blessht.iteye.com/blog/1105562
首先創建一個接口:
- package webservice;
-
- import javax.jws.WebService;
-
- @WebService
- public interface HelloWebservice {
- public String getWebservice(String name);
- }
package webservice;
import javax.jws.WebService;
@WebService
public interface HelloWebservice {
public String getWebservice(String name);
}
然后創建該接口的實現類:
- package webservice;
-
- import javax.jws.WebService;
-
- @WebService(endpointInterface="webservice.HelloWebservice",serviceName="hellows",portName="hellowsport")
- public class HelloWebserviceImpl implements HelloWebservice{
- public String getWebservice(String name) {
- return "你好["+name+"]這是來自webservice的信息..."+this;
- }
- }
package webservice;
import javax.jws.WebService;
@WebService(endpointInterface="webservice.HelloWebservice",serviceName="hellows",portName="hellowsport")
public class HelloWebserviceImpl implements HelloWebservice{
public String getWebservice(String name) {
return "你好["+name+"]這是來自webservice的信息..."+this;
}
}
最后創建服務器端啟動代碼,只要運行main方法即可。當前WebService沒有部署在tomcat之類的服務器下,而是通過jetty部署的:
- package webservice;
-
- import javax.xml.ws.Endpoint;
-
- public class WebserviceServer {
- protected WebserviceServer() throws Exception {
-
- System.out.println("Server Starting...");
- HelloWebservice hello = new HelloWebserviceImpl();
- String address = "http://localhost:8888/hellows";
- Endpoint.publish(address, hello);
-
- }
-
- public static void main(String[] args) throws Exception {
-
- new WebserviceServer();
- System.out.println("Server ready...");
- Thread.sleep(5 * 60 * 1000);
- System.out.println("Server exiting...");
- System.exit(0);
- }
- }
package webservice;
import javax.xml.ws.Endpoint;
public class WebserviceServer {
protected WebserviceServer() throws Exception {
// START SNIPPET: publish
System.out.println("Server Starting...");
HelloWebservice hello = new HelloWebserviceImpl();
String address = "http://localhost:8888/hellows";
Endpoint.publish(address, hello);
// END SNIPPET: publish
}
public static void main(String[] args) throws Exception {
//啟動web服務
new WebserviceServer();
System.out.println("Server ready...");
Thread.sleep(5 * 60 * 1000);
System.out.println("Server exiting...");
System.exit(0);
}
}
為了驗證WebService是否啟動成功,可以在瀏覽器下放入如下地址:http://localhost:8888/hellows?wsdl,如果部署成功,則瀏覽器會顯示wsdl的xml配置信息。
【Flex端代碼】
- <fx:Script>
- <![CDATA[
- //WebService調用
- protected function button3_clickHandler(event:MouseEvent):void
- {
- var ws:WebService = new WebService();
- ws.wsdl = "http://localhost:8888/hellows?wsdl";
- ws.loadWSDL();
- ws.getWebservice(webservice_txt.text);
- ws.addEventListener(ResultEvent.RESULT,function callback(e:ResultEvent):void{
- webservice_result.text = e.result.toString()
- });
- }
-
- ]]>
- </fx:Script>
-
- <s:Label x="61" y="215" text="WebService:"/>
- <s:TextInput x="152" y="205" id="webservice_txt"/>
- <s:Button x="289" y="206" label="發送" click="button3_clickHandler(event)"/>
- <s:Label x="383" y="215" id="webservice_result"/>
<fx:Script>
<![CDATA[
//WebService調用
protected function button3_clickHandler(event:MouseEvent):void
{
var ws:WebService = new WebService();
ws.wsdl = "http://localhost:8888/hellows?wsdl";
ws.loadWSDL();
ws.getWebservice(webservice_txt.text);
ws.addEventListener(ResultEvent.RESULT,function callback(e:ResultEvent):void{
webservice_result.text = e.result.toString()
});
}
]]>
</fx:Script>
<s:Label x="61" y="215" text="WebService:"/>
<s:TextInput x="152" y="205" id="webservice_txt"/>
<s:Button x="289" y="206" label="發送" click="button3_clickHandler(event)"/>
<s:Label x="383" y="215" id="webservice_result"/>
注意,WebService,HttpService和RemoteObject發送請求都是異步的,開發人員需要編寫回調函數來獲取返回數據。
最后運行flex,在文本框中輸入內容,點擊發送按鈕就能看到java服務端返回的數據。
【java代碼】
首先創建一個servlet,這里獲取key值為"name"的數據(所以Flex端需要發送一個key為"name"的參數),最后通過PrintWriter.write的形式將結果返回給客戶端。這是一個典型的Ajax請求響應例子。
- public class HelloHttp extends HttpServlet {
- private static final long serialVersionUID = 1L;
-
- protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
- this.doPost(request, response);
- }
-
- protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
- String name = request.getParameter("name");
- response.setCharacterEncoding("UTF-8");
- PrintWriter pw = response.getWriter();
- pw.write("你好["+name+"]這是來自Httpservice的消息...當前Session是:"+request.getSession());
- pw.close();
- }
- }
public class HelloHttp extends HttpServlet {
private static final long serialVersionUID = 1L;
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
this.doPost(request, response);
}
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
String name = request.getParameter("name");
response.setCharacterEncoding("UTF-8");
PrintWriter pw = response.getWriter();
pw.write("你好["+name+"]這是來自Httpservice的消息...當前Session是:"+request.getSession());
pw.close();
}
}
編寫完成后,將java項目部署到服務器中(我使用的是tomcat)。
【Flex代碼】
Flex端需要創建一個HttpService對象來訪問剛才的Servlet:
- <SPAN style="WHITE-SPACE: pre"> </SPAN><fx:Script>
- <![CDATA[
- //HttpService的形式訪問Java服務器
- protected function button2_clickHandler(event:MouseEvent):void
- {
- var http:HTTPService = new HTTPService();
- http.url = "http://localhost:8080/JavaToFlex/HelloHttp?name="+http_txt.text;
- http.send();
- http.addEventListener(ResultEvent.RESULT,function callback(e:ResultEvent):void{
- http_result.text = e.result.toString();
- });
- }
-
- ]]>
- </fx:Script>
-
- <SPAN style="WHITE-SPACE: pre"> </SPAN><s:Label x="61" y="138" text="HttpService:"/>
- <s:TextInput x="152" y="128" id="http_txt"/>
- <s:Button x="289" y="129" label="發送" click="button2_clickHandler(event)"/>
- <s:Label x="383" y="138" id="http_result"/>
<fx:Script>
<![CDATA[
//HttpService的形式訪問Java服務器
protected function button2_clickHandler(event:MouseEvent):void
{
var http:HTTPService = new HTTPService();
http.url = "http://localhost:8080/JavaToFlex/HelloHttp?name="+http_txt.text;
http.send();
http.addEventListener(ResultEvent.RESULT,function callback(e:ResultEvent):void{
http_result.text = e.result.toString();
});
}
]]>
</fx:Script>
<s:Label x="61" y="138" text="HttpService:"/>
<s:TextInput x="152" y="128" id="http_txt"/>
<s:Button x="289" y="129" label="發送" click="button2_clickHandler(event)"/>
<s:Label x="383" y="138" id="http_result"/>
為了實現Flex調用Java代碼,需要引入一個新的插件Blaseds。
把Blaseds項目WEB-INf下的flex文件夾拷貝到Java項目WEB-INF目錄下,再將Blaseds項目下lib目錄的jar文件引入到java項目中(注意jar文件沖突)。
隨后編寫一個Java類:
- package blaseds;
-
- import flex.messaging.FlexContext;
-
- public class RemoteClass {
- public String helloRemote(String name){
- return "你好["+name+"]這是來自JavaRemote的消息...當前Session是:"+FlexContext.getHttpRequest().getSession();
- }
- }
package blaseds;
import flex.messaging.FlexContext;
public class RemoteClass {
public String helloRemote(String name){
return "你好["+name+"]這是來自JavaRemote的消息...當前Session是:"+FlexContext.getHttpRequest().getSession();
}
}
隨后在web.xml中添加如下內容(這些配置在Blaseds文件的web.xml中都能找到):
-
- <listener>
- <listener-class>flex.messaging.HttpFlexSession</listener-class>
- </listener>
-
-
- <servlet>
- <display-name>MessageBrokerServlet</display-name>
- <servlet-name>MessageBrokerServlet</servlet-name>
- <servlet-class>flex.messaging.MessageBrokerServlet</servlet-class>
- <init-param>
- <param-name>services.configuration.file</param-name>
- <param-value>/WEB-INF/flex/services-config.xml</param-value>
- </init-param>
- <load-on-startup>1</load-on-startup>
- </servlet>
-
- <servlet>
- <display-name>RDSDispatchServlet</display-name>
- <servlet-name>RDSDispatchServlet</servlet-name>
- <servlet-class>flex.rds.server.servlet.FrontEndServlet</servlet-class>
- <init-param>
- <param-name>useAppserverSecurity</param-name>
- <param-value>false</param-value>
- </init-param>
- <load-on-startup>10</load-on-startup>
- </servlet>
-
- <servlet-mapping id="RDS_DISPATCH_MAPPING">
- <servlet-name>RDSDispatchServlet</servlet-name>
- <url-pattern>/CFIDE/main/ide.cfm</url-pattern>
- </servlet-mapping>
-
- <servlet-mapping>
- <servlet-name>MessageBrokerServlet</servlet-name>
- <url-pattern>/messagebroker/*</url-pattern>
- </servlet-mapping>
<!-- Http Flex Session attribute and binding listener support -->
<listener>
<listener-class>flex.messaging.HttpFlexSession</listener-class>
</listener>
<!-- MessageBroker Servlet -->
<servlet>
<display-name>MessageBrokerServlet</display-name>
<servlet-name>MessageBrokerServlet</servlet-name>
<servlet-class>flex.messaging.MessageBrokerServlet</servlet-class>
<init-param>
<param-name>services.configuration.file</param-name>
<param-value>/WEB-INF/flex/services-config.xml</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet>
<display-name>RDSDispatchServlet</display-name>
<servlet-name>RDSDispatchServlet</servlet-name>
<servlet-class>flex.rds.server.servlet.FrontEndServlet</servlet-class>
<init-param>
<param-name>useAppserverSecurity</param-name>
<param-value>false</param-value>
</init-param>
<load-on-startup>10</load-on-startup>
</servlet>
<servlet-mapping id="RDS_DISPATCH_MAPPING">
<servlet-name>RDSDispatchServlet</servlet-name>
<url-pattern>/CFIDE/main/ide.cfm</url-pattern>
</servlet-mapping>
<servlet-mapping>
<servlet-name>MessageBrokerServlet</servlet-name>
<url-pattern>/messagebroker/*</url-pattern>
</servlet-mapping>
最后打開Java項目,打開/WEB-INF/flex/remoting-config.xml文件,在文件中添加RemoteClass的遠程支持:
- <service id="remoting-service" class="flex.messaging.services.RemotingService">
-
- <adapters>
- <adapter-definition id="java-object"
- class="flex.messaging.services.remoting.adapters.JavaAdapter"
- default="true" />
- </adapters>
-
- <default-channels>
- <channel ref="my-amf" />
- </default-channels>
-
-
- <destination id="remoteClass">
- <properties>
- <source>blaseds.RemoteClass</source>
- </properties>
- </destination>
- </service>
<service id="remoting-service" class="flex.messaging.services.RemotingService">
<adapters>
<adapter-definition id="java-object"
class="flex.messaging.services.remoting.adapters.JavaAdapter"
default="true" />
</adapters>
<default-channels>
<channel ref="my-amf" />
</default-channels>
<!-- 定義遠程調用的目標名 -->
<destination id="remoteClass">
<properties>
<source>blaseds.RemoteClass</source>
</properties>
</destination>
</service>
隨后將Java項目部署到服務器中。
【Flex端代碼】
Flex端為了調用Java代碼,需要創建一個RemoteObject實例,屬性destination就是在Java端remoting-config.xml文件中定義的<destination id="remoteClass">,這樣你可以把RemoteObject當作一個RemoteClass的實例使用。
- <fx:Script>
- <![CDATA[
-
- //RemoteObject遠程調用Java方法
- protected function button1_clickHandler(event:MouseEvent):void
- {
- var remote:RemoteObject = new RemoteObject();
- remote.destination = "remoteClass";
- remote.helloRemote(remote_txt.text);
- remote.addEventListener(ResultEvent.RESULT,function callback(e:ResultEvent):void{
- remote_result.text = e.result.toString();
- });
- }
-
- ]]>
- </fx:Script>
-
- <s:Label x="61" y="67" text="RemoteObject:"/>
- <s:TextInput x="152" y="57" id="remote_txt"/>
- <s:Button x="289" y="58" label="發送" click="button1_clickHandler(event)"/>
- <s:Label x="383" y="67" id="remote_result"/>