WebSerive免费视频教程http://edu.51cto.com/course/course_id-1373.html
http://www.icoolxue.com/album/show/225
WebService文档WSDL结构(发布WebService服务后wsdl文档自动生成)
JDK和CXF的区别:
JDK有些局限,CXF是对JDK原生WebService的包装和扩展
JDK不支持Map数据结构,CXF支持
一、WebService基于JDK(1.6以上)运行的开发
1、WebService-Server端:
1)创建java工程
2)编写接口和实现类的业务代码(接口和接口实现类用JDK的注解@WebService标注,接口方法用@WebMethod)
3)发布WebService-Server:Endpoint(终端,发布WebService)
在main方法中:
String address="http://192.168.10.16:8989/day_ws/hellows";
Endpoint.publish(address,new 实现类)
运行main方法(启动)
2、WebService-Client端(远程调用wsdl文件生成):
1)创建java工程
2)终端进入准备存放代码的目录
3)用JDK包工具wsimport远程调用WebService服务端wsdl文件生成客户端代码
"wsimport -keep http://192.168.10.16:8989/day_ws/hellows?wsdl"
在main方法中:
创建起始类实例(起始类在wsdl文件中“<wsdl:service name="ChinaStockWebService">”),调用对应的方法
3、WebService-Client端(通过本地wsdl文件生成):
1)创建java工程
2)终端进入准备存放代码的目录
3)浏览器中“http://192.168.10.16:8989/day_ws/hellows?wsdl”保存为本地文件
4)用JDK包工具wsimport调用本地保存的wsdl文件生成客户端代码
"wsimport -keep E:\...."
在main方法中:
创建起始类实例(起始类在wsdl文件中“<wsdl:service name="ChinaStockWebService">”),调用对应的方法
二、WebService基于CXF框架开发
1、WebService-CXF-Server端:
1)创建java工程
2)在基于JDK运行的java工程上导入CXF框架(集成了各种架包,Jetty)即导入CXF的架包
3)编写接口和实现类的业务代码(接口和接口实现类用JDK的注解@WebService标注,接口方法用@WebMethod)
4)发布WebService-Server:Endpoint(终端,发布WebService)
在main方法中:
String address="http://192.168.10.16:8989/day_ws/hellows";
Endpoint.publish(address,new 实现类)
运行main方法(启动)
注意:该方法和基于JDK的几乎没什么区别但导入架包后项目运行在了jetty(和tomcat类似是个servlet/jsp容器)中
2、WebService-CXF-Client端
1)将cxf框架bin/wsdl2java.bat工具放入操作系统path路径中
2)创建java工程
3)终端进入准备存放代码的目录
4)执行wsdl2java命令生成代码
“wsdl2java xxx?wsdl”(可以是本地或网络上的wsdl文件)
5)新建main方法类,根据wsdl文档查看WebService的起始类<wsdl:service name="ChinaStockWebService">,在main方法中创建调用服务端的起始类实例
AbstractPhaseInterceptor(自定义拦截器从此继承)
LoggingInInterceptor(系统日志入拦截器类)
LoggingOutInterceptor(系统日志出拦截器类)
三、CXF基于编码形式引入拦截器发布、访问(WebService服务端,WebService客户端)
/*
* 自定义拦截器--客户端
*/
public class UserDefinedInterceptor extends AbstractPhaseInterceptor<SoapMessage> {
private String name;
private String password;
public UserDefinedInterceptor(String name, String password) {
super(Phase.PRE_PROTOCOL);//准备协议化时拦截
this.name = name;
this.password = password;
}
/*
* <Envelope>
* <head>
* <atguigu>
* <name>xfzhang</name>
* <password>123456</password>
* </atguigu>
* </head>
* <Body>
* <sayHello>
* <arg0>BOB</arg0>
* </sayHello>
* </Body>
* </Envelope>
*/
public void handleMessage(SoapMessage msg) throws Fault {
List<Header> header msg.getHeaders();
/*
* <atguigu>
* <name>xfzhang</name>
* <password>123456</password>
* </atguigu>
*/
Document document =DOMHelper.createDocument();
Element rootEle=document.createElement("atguigu");
Element nameEle=document.createElement("name");
nameEle.setTextContent(name);
rootEle.appendChild(nameEle);
Element passwordEle=document.createElement("password");
passwordEle.setTextContent(password);
rootEle.appendChild(passwordEle);
headers.add(new Header(new QName("atguigu"),rootEle));
System.out.println("client handleMessage()...");
}
}
/*
* 自定义拦截器--服务器端
*/
public class CheckUserDefinedInterceptor extends AbstractPhaseInterceptor<SoapMessage> {
public CheckUserDefinedInterceptor() {
super(Phase.PRE_PROTOCOL);//准备协议化时拦截
}
/*
* <Envelope>
* <head>
* <atguigu>
* <name>xfzhang</name>
* <password>123456</password>
* </atguigu>
* </head>
* <Body>
* <sayHello>
* <arg0>BOB</arg0>
* </sayHello>
* </Body>
* </Envelope>
*/
public void handleMessage(SoapMessage msg) throws Fault {
Header header=msg.getHeader(new QName("atguigu"));
if(header!=null){
Element atguiguEle=(Element)header.getObject();
String name=atguiguEle.getElementsByTagName("name").item(0).getTextContent();
String password=atguiguEle.getElementsByTagName("password").item(0).getTextContent();
if("xfzhang".equals(name)&&"123456".equals(password)){
System.out.println("server 通过拦截器...");
return ;
}
}
System.out.println("server 没有通过拦截器...");
throw new Fault(new RuntimeException("请求需要一个正确的用户名和密码"));
}
}
/*
* 服务器端
*/
public static void main(String[] args) {
String address = "http://192.168.10.165:8888/day01_ws_server/datatypews";
Endpoint endpoint = Endpoint.publish(address, new HelloWSImpl());
EndpointImpl endpointImpl = (EndpointImpl) endpoint;
//服务器端日志入拦截器
List<Interceptor<? extends Message>> inInterceptors=endpointImpl.getInInterceptors();
inInterceptors.add(new LoggingInInterceptor());
//接收客户端数据(根据数据格式通过拦截器解析数据)
inInterceptors.add(new CheckUserDefinedInterceptor());
//服务器端日志出拦截器
List<Interceptor<? extends Message>> outInterceptors=endpointImpl.getOutInterceptors();
outInterceptors.add(new LoggingOutInterceptor());
System.out.println("发布WebService成功");
}
/**
* 客户端
*/
public static void main(String[] args) {
HelloWSImplService factory=new HelloWSImplService();
HelloWS hellWS=factory.getHelloWSImplPort();
//发送请求的客户端对象
Client client ClientProxy.getClient(hellWS);
//客户端日志出拦截器
List<Interceptor<? extends Message>> outInterceptors=client.getOutInterceptors();
outInterceptors.add(new LoggingOutInterceptor());
//向服务器端发送数据(根据数据格式通过拦截器封装数据)
outInterceptors.add(new UserDefinedInterceptor("xfzhang","123456"));
//客户端日志入拦截器
List<Interceptor<? extends Message>> inInterceptors=client.getInInterceptors();
inInterceptors.add(new LoggingInInterceptor());
Strign result=hellWS.sayHello("BOB");
System.out.println("client"+result);
}
四、CXF基于Spring配置形式引入拦截器发布、访问(WebService服务端,WebService客户端)
五、CXF基于Spring注解形式引入拦截器发布、访问(WebService服务端,WebService客户端)
六、Ajax、JQuery访问(WebService服务端,浏览器客户端)
1、服务端不变
2、客户端是以浏览器形式访问
1)请求数据以Webservice的wsdl定义的格式组装
2)Ajax、JQuery正常方式访问
注意:JS访问有跨域问题,java编码客户端不存在,所以可以利用这一特性,将“JS访问-->WebService服务”变通为“JS访问-->后端应用(HttpUrlConnection)-->WebService服务”
七、HttpClient访问(WebService服务端,HttpUrlConnection客户端)
public class HttpURLConnectionServlet extends HttpServlet {
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException,
IOException {
String name = req.getParameter("name");
System.out.println("doPost" + name);
String data = "<soap:Envelope xmlns:soap='http://schemas.xmlsoap.org/soap/envelope/'><soap:Body><ns2:sayHello xmlns:ns2='http://ws.day01_ws.atguigu.com/'><arg0>'+name+'</arg0></ns2:sayHello></soap:Body></soap:Envelope";
URL url = new URL("http://192.168.10.165:8888/day01_ws/datatypews");
HttpURLConnection connection = (HttpURLConnection) url.openConnection();
connection.setRequestMethod("POST");
connection.setDoOutput(true);
connection.setDoInput(true);
connection.setRequestProperty("Content-Type", "text/xml;charset=utf-8");
OutputStream os = connection.getOutputStream();
os.write(data.getBytes("utf-8"));
int respCode = connection.getResponseCode();
if (respCode == 200) {
InputStream is = connection.getInputStream();
System.out.println("return" + is.available());
resp.setContentType("text/xml;charset=utf-8");
ServletOutputStream outputStream = resp.getOutputStream();
byte[] buffer = new byte[1024];
int len = 0;
while ((len = is.read(buffer)) > 0) {
outputStream.write(buffer, 0, len);
}
outputStream.flush();
}
}
}
CXF WebService 开发文档-目录索引http://www.cnblogs.com/hoojo/archive/2011/03/30/1999587.html
java 实现WebService 以及不同的调用方式http://www.cnblogs.com/siqi/archive/2013/12/15/3475222.html