TL;DR:我需要在运行时在服务器和运行 Selenium WebDriver 的多个远程客户端之间分发业务逻辑。
我研究了对象序列化、RMI、即时下载 JAR、通过 Java 和 Selenium Grid 进行的 Selenese。
<小时/>详细信息:多个远程客户端需要通过 Internet 上的 JMS 轮询队列,以获得在给定网站上执行某些工作的命令。每个客户端都将启动 Selenium WebDriver,在客户端运行之前以未预定义(或仅以非常抽象的术语)的方式遍历该网站,然后返回轮询队列直到再次调用.
挑战在于,客户不会提前知道网站和确切的遍历步骤。我可以在服务器上提前定义抽象步骤/方法,但客户端将依赖某种下载的数据来精确获取 Selenium 命令列表。这些步骤中还需要一些循环(重复直到...
)。
例如,如果我们为 example1.com 定义 void login()
:
- 点击“用户名”字段
- 发送 key “用户名”
- 点击“密码”字段
- 发送 key “密码”
- 点击“提交”
而对于 example2.com void login()
则为:
- 点击“登录”框
- 等待“用户名”字段出现
- 点击“用户名”字段
- 点击“继续”
- 等等
研究:
- 序列化:仅传输对象变量,而不传输对象逻辑。
- RMI:对象逻辑在服务器上执行,而不是在客户端上执行,因此无法与客户端的 Selenium 实例交互。
- 即时下载 JAR:可能的解决方案 here不太乐观here 。这些现实吗?
- Selenese:可能无法直接在Java下运行。可能有可能 selenese-runner-java但这似乎只是命令行,这会限制与客户端软件的交互,从而限制功能
- Selenium Grid:节点(客户端)必须始终连接到 Hub(服务器),但无法保证
如何在运行时以这种方式将业务逻辑从服务器分发到客户端?
最佳答案
您可以使用类似的通用 Selenium run 方法声明一个接口(interface)SeleniumRunner
。
public void runSelenium(WebDriver driver);
如 How to provide an interface to JavaCompiler when compiling a source file dynamically? 中所述您可以将源文件传输到客户端并在运行时编译它们。该类必须实现上述接口(interface)。
File sourceFile = new File("SeleniumClass1234.java");
JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();
compiler.run(null, null, null, sourceFile.getPath());
...
SeleniumRunner sr = (SeleniumRunner) Class.forName("SeleniumClass1234").newInstance();
sr.runSelenium(driver);
或者您可以将 jar 文件传输到您的客户端并在运行时加载它们,如第二个链接 How should I load Jars dynamically at runtime? 中所述。 。您还需要此处的界面。否则,您的解决方案将包含大量反射和额外的配置设置,以查找和使用包含您的逻辑的正确方法。
关于Java - 分布式对象逻辑 : server as the store/client as the worker,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55519251/