`
lyw985
  • 浏览: 40557 次
  • 性别: Icon_minigender_1
  • 来自: 杭州
社区版块
存档分类
最新评论

如何通过WSDL动态生成HTML,并且提交测试

阅读更多
项目的需求:需要解析WSDL,动态生成对应的HTML,页面上输入对应的参数或者选择文件,打印最后的信息

没有找到对应的Java语言的第三方软件,因此决定自己制作

软件环境:SSH,JSP,Servlet,Mysql

思路:
1.通过配置装载对应的WSDL文件(通过对应的网址解析)
关于这点,鄙人曾经花过时间去查询对应的WSDL装载和解析的方法,有一个WSDL4j,但是这个项目应该是个半成品,所以解析不完善。
因此,我决定自己解析成比较通俗易懂的类包类的方式,虽然暴力,但是易懂

2.动态生成HTML表格
通过已经装载的WSDL,解析成对应的表格
例如:
  <xsd:complexType name="helloWord">
    <xsd:sequence>
      <xsd:element minOccurs="0" name="name" type="xs:string" />
    </xsd:sequence>
  </xsd:complexType>



数组格式
  <xs:complexType name="sum">
    <xs:sequence>
      <xs:element maxOccurs="unbounded" minOccurs="0" name="number" type="xs:int" />
    </xs:sequence>
  </xs:complexType>



其他的不细说了

3.动态解析表单数据,并且测试
这里用到了大量的反射,因为所有的一切都是基于WSDL,全部的东西(类名,属性,方法,参数)都是字符串

主要的代码如下:
//从WSDL和operation上获取key,从request上获得值
Object[] objs = WSDLUtil.getObjects(request, wsdl, operation);
//getWebServiceType(wsdl)获取对应的webService类,反射调用方法
Object obj = ReflectUtil.invoke(getWebServiceType(wsdl),
		operation.getName(), objs);
response.getWriter().println(obj);



普通类型比较简单,直接通过request的提取即可
文本类型稍微有点复杂,因为wsdl里是没有xs:file的,所以需要转化成xs:base64Binary
也就是byte[]
关于文件的解析有两种模式
Action,主要代码如下
if (request instanceof MultiPartRequestWrapper) {
	MultiPartRequestWrapper multiWrapper = (MultiPartRequestWrapper) request;
	File[] files = multiWrapper.getFiles(paramName);
	byte[] param = null;
	for (File file : files) {
		FileInputStream fis = new FileInputStream(file);
		param = new byte[fis.available()];
		fis.read(param);
		fis.close();
	}
	return param;
}

Servlet,主要代码如下
DiskFileItemFactory factory = new DiskFileItemFactory();
ServletFileUpload servletFileUpload = new ServletFileUpload(factory);
List<FileItem> fileItemList = servletFileUpload.parseRequest(request);
List<byte[]> list = new ArrayList<byte[]>();
for (FileItem fileItem : fileItemList) {
	String fileName = fileItem.getFieldName();
	if (fileName.equals(paramName)) {
		InputStream is = fileItem.getInputStream();
		byte[] bs = new byte[is.available()];
		is.read(bs);
		list.add(bs);
		is.close();
		return bs;
	}
}

自定义类型,例如这个
@XmlType
@XmlAccessorType(XmlAccessType.FIELD)
public class User {
	private String username;
	private String password;

	public String getUsername() {
		return username;
	}

	public void setUsername(String username) {
		this.username = username;
	}

	public String getPassword() {
		return password;
	}

	public void setPassword(String password) {
		this.password = password;
	}

}

WSDL上的表述是这样的
  <xs:complexType name="user">
    <xs:sequence>
      <xs:element minOccurs="0" name="username" type="xs:string" />
      <xs:element minOccurs="0" name="password" type="xs:string" />
    </xs:sequence>
  </xs:complexType>
  <xs:element name="login" type="login" />
  <xs:complexType name="login">
    <xs:sequence>
      <xs:element minOccurs="0" name="user" type="user" />
    </xs:sequence>
  </xs:complexType>


通过反射,初始化一个类,从request里提取对应的值,封装参数,反回该类
主要代码
Object newParent = null;
String className = packagePath + element.getType().substring(0, 1).toUpperCase()
		+ element.getType().substring(1);
for (SimpleType simpleType : simpleTypeList) {
	if (simpleType.getName().equals(type)) {
		if (maxOccurs == null) {
			String param = WebUtil.getString(request, paramName);
			if (param == null) {
				return null;
			}
			newParent = ReflectUtil.getFieldObject(Class.forName(className), param);
			return newParent;
		} else {
			String[] strs = WebUtil.getStrings(request, paramName);
			if (strs == null) {
				return null;
			}
			Object[] param = ReflectUtil.getArrayByClassName(className, strs.length);
			for (int i = 0; i < strs.length; i++) {
				param[i] = ReflectUtil
						.getFieldObject(Class.forName(className), strs[i]);
			}
			return param;
		}
	}
}
for (ComplexType complexType : complexTypeList) {
	if (complexType.getName().equals(type)) {
		if (maxOccurs == null) {
			newParent = Class.forName(className).newInstance();
			Object param = null;
			for (com.brightcreek.tradeshow.wsdl.types.schema.complextype.sequence.element.Element e : complexType
					.getSequence().getElementList()) {
				param = getObject(request, e, complexTypeList, simpleTypeList,
						paramName + ".", newParent, packagePath);
				if (null != param) {
					ReflectUtil.setValue(newParent, e.getName(), param);
				} else {
					return null;
				}
			}
			return newParent;
		} else {
			int index = 0;
			Object[] parents = ReflectUtil.getArrayByClassName(className, 0);
			List list = new ArrayList(Arrays.asList(parents));
			Object param = null;
			while (true) {
				newParent = Class.forName(className).newInstance();
				for (com.brightcreek.tradeshow.wsdl.types.schema.complextype.sequence.element.Element e : complexType
						.getSequence().getElementList()) {
					param = getObject(request, e, complexTypeList, simpleTypeList,
							paramName + "[" + index + "].", newParent, packagePath);
					if (null != param) {
						ReflectUtil.setValue(newParent, e.getName(), param);
					} else {
						return list.toArray(ReflectUtil.getArrayByClassName(className,
								list.size()));
					}
				}
				list.add(newParent);
				index++;
			}
		}
	}
}

进行迭代处理,也可以处理类包含类

枚举类型的属性,HTML是通过select展示的
枚举代码
@XmlType
@XmlAccessorType(XmlAccessType.FIELD)
public enum NoteMessage {
	A("A value"), B("B value");
	private final String value;

	public String getValue() {
		return value;
	}

	NoteMessage(String value) {
		this.value = value;
	}
}

反射获取对应值的代码为:
public static Object getEnumerationValue(String className, String fieldName, String methodName)
		throws ClassNotFoundException, SecurityException, NoSuchMethodException,
		NoSuchFieldException, IllegalArgumentException, IllegalAccessException,
		InvocationTargetException {
	Class clazz = Class.forName(className);
	Method method = clazz.getDeclaredMethod(methodName);
	for (Object obj : clazz.getEnumConstants()) {
		if (obj.toString().equals(fieldName)) {
			return method.invoke(obj);
		}
	}
	return null;
}

对应这个枚举的反射方法的调用就是
getEnumerationValue("NoteMessage", "A", "getValue")





分享到:
评论

相关推荐

    Java语言如何通过WSDL动态生成HTML,并且提交测试(附源码)

    本篇将讲解如何利用Java通过WSDL动态生成HTML,并进行测试。首先,我们需要理解WSDL文件的基本结构和用途,它是Web服务客户端和服务提供者之间的桥梁,定义了服务的操作、输入和输出消息格式。 要通过Java动态生成...

    通过webservice提交xml数据以及soap协议的使用

    4. **生成客户端代理**:服务消费者使用WSDL文件生成客户端代理类,这个类提供了调用服务的接口。例如,在Java中,可以使用wsimport工具,而在.NET中,可以使用svcutil.exe。 5. **构建XML请求**:根据服务接口的...

    yavijava_generator:代码生成器可帮助根据 html 文档生成尽可能多的 yavijava

    yavijava_generator 使用用 Groovy 编写的代码生成器,用于解析 VMWare 提供的 HTML 文档,用于为生成代码。为什么yavijava 中的大... 在提交拉取请求之前,请确保先运行测试,以确保所做的更改不会破坏测试。 要运行

    08-Web服务实用技术(Web服务实现技术).ppt

    通过AXIS,开发者可以方便地创建基于SOAP的Web服务,并且能够处理服务的部署、WSDL生成以及客户端的代理类创建。 综上所述,Web服务实现技术涉及服务的开发策略、生命周期管理、运行环境的组件以及辅助工具的使用。...

    2022年优秀-Web服务实用技术.pptx

    1. **自顶向下**:这种开发方式是从服务接口描述(WSDL)开始,先定义服务的行为和消息格式,然后根据WSDL生成服务的实现。例如,从EJB或Java类生成WSDL。 2. **自底向上**:这种方式是先编写服务实现,然后逆向...

    rad开发webservice的例子

    4. **portlet交互**:portlet可以通过动作请求处理用户交互,例如表单提交,也可以通过资源请求获取动态内容。 5. **portlet集成**:在RAD中,可以创建基于JSR 168的portlet项目,进行portlet的开发、测试和部署。 ...

    Java Development with Ant.pdf

    在Ant的构建文件中,可以定义一个任务来运行JUnit测试,并根据测试结果生成HTML格式的报告。 **执行程序** 在Ant中执行Java程序通常是通过`java`任务完成的。这个任务可以设置程序的主类、类路径、系统属性等参数...

    WebServer_Client

    2. 使用gSOAP的工具生成客户端代码,这些代码将解析服务的WSDL(Web服务描述语言)文件,从而知道如何与服务接口进行交互。 3. 在客户端代码中,编写业务逻辑,调用生成的接口函数,发送请求并接收响应。 4. "server...

    J2EE实验.zip

    2. **Servlet和JSP**:作为J2EE的基础,Servlet负责处理HTTP请求,而JSP用于生成动态HTML内容。实验中,你可能需要编写Servlet来处理用户请求,并用JSP展示结果。 3. **EJB(Enterprise JavaBeans)**:EJB是J2EE的...

    C++实现56dxw短信验证码WebService接口--

    (2)项目中添加以下文件:注意,这些文件都是通过gsoap自动生成,无须修改。 stdsoap2.cpp stdsoap2.h soapC.cpp soapH.h WebServiceInterfaceSoap.nsmap.cpp soapWebServiceInterfaceSoapProxy.cpp ...

    php网络开发完全手册

    7.5.6 通过回调函数执行正则表达式 7.5.6 的搜索和替换——preg_replace_ 7.5.6 callback 114 7.5.7 用正则表达式进行字符串分割 7.5.7 ——preg_split 115 7.6 字符操作的注意事项 117 7.7 小结 118 第8章 数组操作...

    JAVA程序开发大全---上半部分

    14.4.2 使用WSDL生成客户端代码 253 14.4.3 创建Web Service客户端测试代码 255 14.5 本章小结 255 第15章 Java EE中EJB的开发 256 15.1 EJB概述 256 15.2 WebLogic服务器的安装与配置 257 15.2.1 WebLogic服务器的...

    Myeclipse的Web开发插件

    1. **Dynamic Web Project**:Myeclipse支持创建动态Web项目,允许开发者构建基于Servlet、JSP、JSF等技术的Web应用。用户只需通过简单的几步操作,即可快速搭建Web项目的结构,包括WEB-INF目录、src目录以及默认的...

    百度2019年最新面试题库

    通过将对象的创建和管理权交给第三方容器(如Spring容器),实现控制反转,使对象不再控制其自身的创建过程,提高代码的可复用性和可测试性。 #### IO和NIO的区别,NIO优点 - **IO(InputStream/OutputStream)**:...

    Python编程入门经典

    14.3.4 使用事务并提交结果 245 14.3.5 检查模块的功能和元 数据 246 14.3.6 处理错误 246 14.4 本章小结 247 14.5 习题 248 第15章 使用Python处理XML 249 15.1 XML的含义 249 15.1.1 层次标记语言 249 15.1.2 一组...

    C#.Net的常见面试试题

    它们可以嵌入到其他ASP.NET页面中,并且能够通过属性进行参数化设置,提高代码的复用性和维护性。 #### 3. 叫应用程序域?什么是受管制的代码?什么是强类型系统?什么是装箱和拆箱?什么是重载?CTS、CLS和CLR分别...

Global site tag (gtag.js) - Google Analytics