You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何通过Java(J2SE)解析WSDL并列出服务及参数(含必填/可选)

Absolutely! You’ve got a great question—parsing a WSDL in Java (J2SE) to extract web services, their operations, and parameter requirements (required vs optional) is totally doable, and there are a few solid approaches depending on whether you want to use third-party libraries or stick to pure J2SE. Let’s break them down:

Apache CXF provides a robust, easy-to-use API that handles both WSDL parsing and XSD schema resolution out of the box. This saves you from manually handling namespace complexities and schema lookups.

Step 1: Add Dependencies

If using Maven, include these in your pom.xml:

<dependency>
    <groupId>org.apache.cxf</groupId>
    <artifactId>cxf-core</artifactId>
    <version>3.6.2</version>
</dependency>
<dependency>
    <groupId>org.apache.cxf</groupId>
    <artifactId>cxf-rt-frontend-jaxws</artifactId>
    <version>3.6.2</version>
</dependency>

Step 2: Parse WSDL and Extract Details

Here’s a complete example that lists services, operations, and marks required parameters:

import org.apache.cxf.wsdl.WSDLManager;
import org.apache.ws.commons.schema.XmlSchema;
import org.apache.ws.commons.schema.XmlSchemaElement;
import org.apache.ws.commons.schema.XmlSchemaSequence;
import javax.wsdl.*;
import javax.xml.namespace.QName;
import java.net.URL;
import java.util.Map;

public class CxfWsdlParser {
    public static void main(String[] args) throws Exception {
        String wsdlUrl = "https://com.provider.soap/services/travel?WSDL";
        URL url = new URL(wsdlUrl);

        // Initialize CXF's WSDL manager
        WSDLManager manager = WSDLManager.newInstance();
        Definition wsdlDefinition = manager.getDefinition(url);

        // Iterate over all services in the WSDL
        Map<QName, Service> services = wsdlDefinition.getServices();
        for (Map.Entry<QName, Service> serviceEntry : services.entrySet()) {
            Service service = serviceEntry.getValue();
            System.out.println("\n=== Web Service: " + service.getQName().getLocalPart() + " ===");

            // Iterate over ports in the service
            Map<QName, Port> ports = service.getPorts();
            for (Port port : ports.values()) {
                Binding binding = port.getBinding();
                BindingOperations bindingOperations = binding.getBindingOperations();

                // Iterate over each operation in the port
                for (BindingOperation bindingOp : bindingOperations) {
                    Operation operation = bindingOp.getOperation();
                    System.out.println("\n--- Operation: " + operation.getName() + " ---");

                    // Process input parameters
                    Input input = operation.getInput();
                    if (input != null) {
                        Message inputMessage = input.getMessage();
                        Map<QName, Part> inputParts = inputMessage.getParts();
                        System.out.println("Input Parameters:");

                        for (Part part : inputParts.values()) {
                            if (part.getElementName() != null) {
                                // Resolve the schema element to check requirement status
                                XmlSchema schema = manager.getSchema(wsdlDefinition, part.getElementName().getNamespaceURI());
                                XmlSchemaElement element = schema.getElementByName(part.getElementName());

                                if (element != null) {
                                    // Required if minOccurs is 1 (default) or higher; optional if minOccurs=0
                                    boolean isRequired = element.getMinOccurs() == null || element.getMinOccurs() >= 1;
                                    String status = isRequired ? "*Required*" : "Optional";
                                    System.out.println("- " + part.getName() + ": " + status);

                                    // Parse child elements if the parameter is a complex type
                                    if (element.getSchemaType() instanceof XmlSchemaSequence) {
                                        XmlSchemaSequence sequence = (XmlSchemaSequence) element.getSchemaType();
                                        for (XmlSchemaElement childElement : sequence.getItems()) {
                                            boolean childRequired = childElement.getMinOccurs() == null || childElement.getMinOccurs() >= 1;
                                            String childStatus = childRequired ? "*Required*" : "Optional";
                                            System.out.println("  - " + childElement.getName() + ": " + childStatus);
                                        }
                                    }
                                }
                            }
                        }
                    }

                    // You can add similar logic to process output messages if needed
                }
            }
        }
    }
}
2. Using WSDL4J (Legacy WSDL Parsing Library)

WSDL4J is a lightweight, dedicated library for parsing WSDL files, but it doesn’t handle XSD schema resolution automatically. You’ll need to add extra code to check parameter requirements.

Step 1: Add Dependency

<dependency>
    <groupId>wsdl4j</groupId>
    <artifactId>wsdl4j</artifactId>
    <version>1.6.3</version>
</dependency>

Step 2: Basic WSDL Parsing Example

This code extracts service/operation details, but you’ll need to manually parse associated XSD files to check required parameters:

import javax.wsdl.*;
import javax.wsdl.factory.WSDLFactory;
import javax.wsdl.xml.WSDLReader;
import javax.xml.namespace.QName;
import java.net.URL;
import java.util.Map;

public class Wsdl4jParser {
    public static void main(String[] args) throws Exception {
        String wsdlUrl = "https://com.provider.soap/services/travel?WSDL";
        URL url = new URL(wsdlUrl);

        WSDLFactory factory = WSDLFactory.newInstance();
        WSDLReader reader = factory.newWSDLReader();
        reader.setFeature("javax.wsdl.verbose", false);
        reader.setFeature("javax.wsdl.importDocuments", true);

        Definition definition = reader.readWSDL(null, url.toString());

        // Iterate over services
        Map<QName, Service> services = definition.getServices();
        for (Service service : services.values()) {
            System.out.println("\n=== Web Service: " + service.getQName().getLocalPart() + " ===");

            // Iterate over ports
            Map<QName, Port> ports = service.getPorts();
            for (Port port : ports.values()) {
                Binding binding = port.getBinding();
                BindingOperations bindingOps = binding.getBindingOperations();

                for (BindingOperation bindingOp : bindingOps) {
                    Operation operation = bindingOp.getOperation();
                    System.out.println("\n--- Operation: " + operation.getName() + " ---");

                    // Process input parameters
                    Input input = operation.getInput();
                    if (input != null) {
                        Message inputMsg = input.getMessage();
                        Map<QName, Part> parts = inputMsg.getParts();
                        System.out.println("Input Parameters:");
                        for (Part part : parts.values()) {
                            System.out.println("- " + part.getName() + ": (Check associated XSD for required status)");
                        }
                    }
                }
            }
        }
    }
}
3. Manual XML Parsing (Pure J2SE, No Third-Party Libraries)

If you can’t use external libraries, you can parse the WSDL as a regular XML document using Java’s built-in DOM/SAX/StAX parsers. This requires handling namespaces and schema lookups manually, so it’s more verbose but self-contained.

Example with DOM Parser

import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.NodeList;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import java.net.URL;

public class ManualWsdlParser {
    public static void main(String[] args) throws Exception {
        String wsdlUrl = "https://com.provider.soap/services/travel?WSDL";
        URL url = new URL(wsdlUrl);

        DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
        factory.setNamespaceAware(true);
        DocumentBuilder builder = factory.newDocumentBuilder();
        Document doc = builder.parse(url.openStream());

        // Extract all services
        NodeList serviceNodes = doc.getElementsByTagNameNS("http://schemas.xmlsoap.org/wsdl/", "service");
        for (int i = 0; i < serviceNodes.getLength(); i++) {
            Element serviceElement = (Element) serviceNodes.item(i);
            String serviceName = serviceElement.getAttribute("name");
            System.out.println("\n=== Web Service: " + serviceName + " ===");

            // Extract ports in the service
            NodeList portNodes = serviceElement.getElementsByTagNameNS("http://schemas.xmlsoap.org/wsdl/", "port");
            for (int j = 0; j < portNodes.getLength(); j++) {
                Element portElement = (Element) portNodes.item(j);
                String portName = portElement.getAttribute("name");
                String bindingName = portElement.getAttribute("binding").split(":")[1];
                System.out.println("\nPort: " + portName + " (Binding: " + bindingName + ")");

                // Find matching binding
                NodeList bindingNodes = doc.getElementsByTagNameNS("http://schemas.xmlsoap.org/wsdl/", "binding");
                for (int k = 0; k < bindingNodes.getLength(); k++) {
                    Element bindingElement = (Element) bindingNodes.item(k);
                    if (bindingElement.getAttribute("name").equals(bindingName)) {
                        // Extract operations
                        NodeList operationNodes = bindingElement.getElementsByTagNameNS("http://schemas.xmlsoap.org/wsdl/", "operation");
                        for (int l = 0; l < operationNodes.getLength(); l++) {
                            Element operationElement = (Element) operationNodes.item(l);
                            String operationName = operationElement.getAttribute("name");
                            System.out.println("\n--- Operation: " + operationName + " ---");

                            // Process input parameters
                            Element inputElement = (Element) operationElement.getElementsByTagNameNS("http://schemas.xmlsoap.org/wsdl/", "input").item(0);
                            if (inputElement != null) {
                                String inputMsgName = inputElement.getAttribute("message").split(":")[1];
                                NodeList messageNodes = doc.getElementsByTagNameNS("http://schemas.xmlsoap.org/wsdl/", "message");
                                for (int m = 0; m < messageNodes.getLength(); m++) {
                                    Element messageElement = (Element) messageNodes.item(m);
                                    if (messageElement.getAttribute("name").equals(inputMsgName)) {
                                        NodeList partNodes = messageElement.getElementsByTagNameNS("http://schemas.xmlsoap.org/wsdl/", "part");
                                        System.out.println("Input Parameters:");
                                        for (int n = 0; n < partNodes.getLength(); n++) {
                                            Element partElement = (Element) partNodes.item(n);
                                            String partName = partElement.getAttribute("name");
                                            String elementQName = partElement.getAttribute("element");

                                            if (!elementQName.isEmpty()) {
                                                // Resolve element in embedded XSD schema
                                                NodeList typesNodes = doc.getElementsByTagNameNS("http://schemas.xmlsoap.org/wsdl/", "types");
                                                if (typesNodes.getLength() > 0) {
                                                    Element typesElement = (Element) typesNodes.item(0);
                                                    NodeList schemaNodes = typesElement.getElementsByTagNameNS("http://www.w3.org/2001/XMLSchema", "schema");
                                                    for (int p = 0; p < schemaNodes.getLength(); p++) {
                                                        Element schemaElement = (Element) schemaNodes.item(p);
                                                        String targetNs = schemaElement.getAttribute("targetNamespace");
                                                        String elementName = elementQName.split(":")[1];
                                                        NodeList elementNodes = schemaElement.getElementsByTagNameNS(targetNs, elementName);
                                                        if (elementNodes.getLength() > 0) {
                                                            Element paramElement = (Element) elementNodes.item(0);
                                                            String minOccurs = paramElement.getAttribute("minOccurs");
                                                            boolean isRequired = minOccurs.isEmpty() || Integer.parseInt(minOccurs) >= 1;
                                                            String status = isRequired ? "*Required*" : "Optional";
                                                            System.out.println("- " + partName + ": " + status);
                                                        }
                                                    }
                                                }
                                            } else {
                                                System.out.println("- " + partName + ": (Type-based, check XSD for constraints)");
                                            }
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
            }
        }
    }
}
Key Notes on Required vs Optional Parameters
  • A parameter is required if its XSD element has minOccurs="1" (this is the default if the attribute isn’t specified).
  • A parameter is optional if its XSD element has minOccurs="0".
  • For complex types (parameters with child elements), you’ll need to check each child element’s minOccurs attribute individually, as shown in the CXF example.

Whichever method you choose, Apache CXF is the most efficient and least error-prone option since it handles most of the low-level parsing and schema resolution for you.

内容的提问来源于stack exchange,提问作者Anandhakrishnan

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.27 04:17:54