老婆出轨 发表于 2025-1-10 02:02:54

通过WSDL调用WebService服务的两种方法

1.使用CXF拉代替码到本地(未解决,但是建议先看这一种)

前提:1.你有一个webservice的地点,里面枚举了你想调用的方法。记住这个地点,后面用CXF拉Java代码的时间地点末了加上.wsdl。
即http://xxx:xx/xx/xx.asmx?wsdl
https://i-blog.csdnimg.cn/direct/8c3a8a5ae6d0401cb339aaa5adca461a.png
2.如果你的jdk版本低,可以使用jdk自带的WSDL解析工具,但我的是JDK17,已经移除了,下载使用CXF,我这里下载的是apache-cxf-3.6.4。
https://i-blog.csdnimg.cn/direct/1d43304e013c4c4e9a8ed1c5e0a8627a.png
在bin目录下实行
wsdl2java -encoding utf-8 -d D:\ file:///E:/web_service/xxxxxx.wsdl
到目的路径下拿到代码包,放到你的工程里,它提供了这个wsdl所有的方法,而且会有一个例子(我第一次解析下来的时间没有例子,第二次就有了,可以多试频频),每一个方法都会有一个实例。
https://i-blog.csdnimg.cn/direct/792858aca4b84348bb0ca6b83fd28546.png
添加pom依赖
<dependency>
            <groupId>javax.xml.ws</groupId>
            <artifactId>jaxws-api</artifactId>
            <version>2.3.1</version>
      </dependency>
      <dependency>
            <groupId>com.sun.xml.ws</groupId>
            <artifactId>jaxws-rt</artifactId>
            <version>2.3.3</version>
      </dependency>


      <dependency>
            <groupId>javax.xml.soap</groupId>
            <artifactId>javax.xml.soap-api</artifactId>
            <version>1.4.0</version>
      </dependency>
      <dependency>
            <groupId>org.glassfish.metro</groupId>
            <artifactId>webservices-rt</artifactId>
            <version>2.4.4</version>
      </dependency>

      <dependency>
            <groupId>com.sun.xml.messaging.saaj</groupId>
            <artifactId>saaj-impl</artifactId>
            <version>3.0.3</version>
      </dependency>
      <dependency>
            <groupId>org.glassfish.metro</groupId>
            <artifactId>webservices-api</artifactId>
            <version>2.4.4</version>
      </dependency>
比如我想调用getFieBytes方法
https://i-blog.csdnimg.cn/direct/27cd2fa37eea4425a5762549a2d614e4.png
这样就可以调用乐成了,但我遇到的问题是
OuterServiceSoap port = ss.getOuterServiceSoap();

报错:
Unable to make field private static final jdk.internal.misc.Unsafe jdk.internal.misc.Unsafe.theUnSafe.accessible

照旧jdk的问题,我在测试类里可以运行乐成,但是放到src下报这个错误,网上搜的让添加JVM启动参数,我没试过,放弃了这个方法,去用第二种方法了。一般来说,这种方法就可以调用乐成了。
2.直接通过WSDL调用WebService提供的SOAP接口

比如调用getFileBytes方法,WSDL里的方法是
https://i-blog.csdnimg.cn/direct/077a36809dff4bb59838b4556a92e84d.png
下载SOAPUI测试getFileBytes这个方法是否能够调用乐成。直接复制哀求进去看是否有返回,没有阐明调不通(大概是网络问题,内网访问不到),如果有继承看下面。
不需要加pom依赖
记住这三个东西,我踩了很多坑,少一点或者错一点都报错,还查不到。
先把哀求内容给界说出来
public String getSoapContent(String id, Long fileSize) {
      String content = "<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/\">\n" +
                "<soap:Body>\n" +
                "    <GetFileBytes xmlns=\"http://tempuri.org/\">\n" +
                "      <fileId>" + id + "</fileId>\n" +
                "      <pos>0</pos>\n" +
                "      <length>" + fileSize + "</length>\n" +
                "    </GetFileBytes>\n" +
                "</soap:Body>\n" +
                "</soap:Envelope>";
      return content;
    }
留意:没有"<?xml version="1.0" encoding="utf-8"?>"这一行!!!
如果你加了这一行会报错没有根元素。
然后加上哀求头,发送消息。
//使用SOAP1.1发送消息
    public String doPostSoap(String postUrl, String soapXml, String soapAction) throws Exception {
      String retStr = "";
      // 创建HttpClientBuilder
      HttpClientBuilder httpClientBuilder = HttpClientBuilder.create();
      // HttpClient
      CloseableHttpClient closeableHttpClient = httpClientBuilder.build();
      HttpPost httpPost = new HttpPost(postUrl);
      httpPost.setHeader("Content-Type", "text/xml;charset=UTF-8");
      httpPost.setHeader("SOAPAction", soapAction);
      StringEntity data = new StringEntity(soapXml, Charset.forName("UTF-8"));
      httpPost.setEntity(data);
      CloseableHttpResponse response = closeableHttpClient.execute(httpPost);
      HttpEntity httpEntity = response.getEntity();
      if (httpEntity != null) {
            // 打印响应内容
            retStr = EntityUtils.toString(httpEntity, "UTF-8");
      }
      // 释放资源
      closeableHttpClient.close();
      return retStr;
    }
这里HttpPost.setHeaderI(),就是图片里圈出来的哀求头。
拿到的返回值是一个XML文件,解析这个XML文件,如果是getFileBytes这个方法,它返回的值会放在《GetFileBytesResult》这个标签内,返回的格式是base64Binary,拿到二进制流。
public File SoapResponseParser(String soapResponse, String realName, String extName) throws IOException {
      // 找到JSON数组的开始位置和结束位置
      int startIndex = soapResponse.indexOf("<GetFileBytesResult>");
      int endIndex = soapResponse.indexOf("</GetFileBytesResult>");
      String base64String = soapResponse.substring(startIndex + 20, endIndex);
      byte[] decodedBytes = Base64.getDecoder().decode(base64String);
      // 创建一个临时文件
      Path tempFile = Files.createTempFile();

      // 将字节流写入临时文件
      try (FileOutputStream fos = new FileOutputStream(tempFile.toFile())) {
            fos.write(decodedBytes);
      }
      // 返回一个File对象,指向这个临时文件
      return tempFile.toFile();
    }
哀求头,哀求体,哀求参数都界说好了之后调用方法

private static final String SOAPACTION = "http://tempuri.org/GetFileBytes";
    private static final String SWDLURL = "http://xx:xx/xx/xxService.asmx?wsdl";


String content = getSoapContent(id, fileSize);
            String postSoap = doPostSoap(SWDLURL, content, SOAPACTION);
            File tempFile = SoapResponseParser(postSoap, realName, extName);
拿到文件,接着处置惩罚你本身的逻辑,竣事!

免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!更多信息从访问主页:qidao123.com:ToB企服之家,中国第一个企服评测及商务社交产业平台。
页: [1]
查看完整版本: 通过WSDL调用WebService服务的两种方法