宏哥微信粉丝群:https://bbs.csdn.net/topics/618423372 有兴趣的可以扫码加入
1.简介
在实际工作中,我们进行web自动化的时候,文件上传是很常见的操作,例如上传用户头像,上传身份证信息等。所以宏哥打算按上传文件的分类对其进行一下讲解和分享。
2.为什么selenium没有提供API?
想必小伙伴们或者童鞋们一定很好奇,既然上传文件在自动化这么常见而且经常用到,那么为什么Selenium的webdriver为什么不提供方法(API),宏哥这里解释一下原因:因为上传文件需要打开window窗口,webdriver是无法对window的控件操作的,换句话说就是:selenium无法识别非web的控件,上传文件窗口为系统自带,无法识别窗口元素。所以没有提供方法,需要我们换个思路去上传文件。
3.上传文件分类
首先,我们要区分出上传按钮的种类,大体上可以分为两种,一种是input框,另外一种就比较复杂,通过js、flash等实现,标签非input。
上传文件有两种场景:input控制上传和非input控件上传。大多数情况都是input控件上传文件,只有非常少数的使用自定义的非input上传文件。今天宏哥这一篇文章就用来介绍非input控件上传文件。
4.非input控件上传文件
非input控件上传文件,我们要引入外部插件上传。这种上传千奇百怪,有用a标签的,有用div的,有用button的,有用object的,我们没有办法通过直接在网页上处理掉这些上传,唯一的办法就是打开OS弹框,去处理弹框。有两种方法一种通过pywin32上传(这种只支持python语言),另一种是通过autoit上传(python和java都支持,其他的没有实践过)。这里我们只会讲到autoit上传文件。
4.1非input控件上传文件
宏哥总结了一下,大体上有以下几种解决方案:
(1)autoIT,借助外力,我们去调用其生成的au3或exe文件。
(2)Python pywin32库,识别对话框句柄,进而操作
(3)SendKeys库
(4)keybd_event,跟3类似,不过是模拟按键,ctrl+a,ctrl+c, ctrl+v…
5.准备工作
关于文件上传,宏哥前边已经介绍过几种方法了,今天这篇介绍一个第三方工具,叫AutoIt,简单来说,这个是一个能支持桌面GUI自动化的工具,它支持脚本语言编写。这里,我们用AutoIt来做文件上传的演示。在Selenium脚本中如果需要AutoIt来协助这个文件上传功能,大概步骤是这样的:
1.Selenium点击web产品上的文件上传按钮,弹窗上传框。
2.执行AutoIt实现准备好的脚本文件,这个脚本文件写了关于上传什么文件的一个.exe文件。
所以,我们先来介绍如何下载和安装AutoIt。
5.1下载和安装AutoIt
文件上传是自动化中棘手的部分,目前selenium并没有提供上传的实现api,所以知道借助外力来完成,如AutoIt、sikuli。
AutoIt , 这是一个使用类似BASIC脚本语言的免费软件,它设计用于Windows GUI(图形用户界面)的自动化操作,利用模拟键盘按键,鼠标移动和窗口/控件的组合来实现自动化任务;
1.打开AutoIt的官网下载
AutoIt下载链接:https://www.autoitscript.com/site/autoit/downloads/ 或者点击下列图标进行下载!
2.点击下载zip
两种下载方法都可以,这里我想下载的是zip,解压出来如下图所示:
5.2上传脚本的编写
1.点击SciTe文件夹,我们打开脚本编辑器。
2.打开百度图片上传窗口,打开AutoIt Windows Info 工具,鼠标移动到Finder Tool,按住鼠标左键拖动到需要识别的windows控件上。拖动元素定位器上那个靶点形状按钮到文件上传弹窗,能够捕获到一些元素信息。用鼠标拖住工具上的Finder Tool的图标(即图中蓝色圈圈部分)到要识别的控件上,控件的唯一标识信息会显示在工具的左侧部分(图中红框标出的部分)。从显示的结果得知,此控件的Title=“打开”,Class为Edit,Instance=1。我们就是利用控件的这些信息,定位控件,编写脚本。
3.打开编辑器,根据控件Finder Tool识别到的信息来调用函数编写脚本;在AutoIt脚本编辑器里输入如下脚本,不要下面我写的备注哈。
我们这里需要知道有以下信息:
1.操作页面的title,用于固定操作的页面。
2.需要填入的信息,在输入框中填入“上传文件的路径及文件名”(windows操作)
3.点击“打开”按钮,实现文件上传。
根据以上所识别的控件信息,利用编辑器SciTE Script Editor,根据AutoIT的语法编写脚本。
实现文件上传需要的几个方法:
ControlFocus ( "窗口标题", "窗口文本", 控件ID)
---->设置输入焦点到指定窗口的某个控件上(即:控件ID“文件名”输入框的id)
WinWait ( "窗口标题" [, "窗口文本" [, 超时时间]] )
---->暂停脚本的执行直至指定窗口存在(出现)为止
ControlSetText ( "窗口标题", "窗口文本", 控件ID, "新文本" )
---->修改指定控件的文本(即:控件ID“文件名”输入框的id)
Sleep ( 延迟 )
---->使脚本暂停指定时间段
ControlClick ( "窗口标题", "窗口文本", 控件ID [, 按钮] [, 点击次数]] )
---->向指定控件发送鼠标点击命令(即:控件ID“打开”按钮的id)
其中,title即AutoIt Window Info识别出的Title字段,controlID即AutoIt Window Info识别出的Class和Instance的拼接,如上图拼接后的结果应为:Button1(即classnameNN)
;ControlFocus(("title","text",controllD)用于识别windows文件上传窗口
ControlFocus("打开","","")
;向文件名输入框输入本地要上传文件的路径
ControlSetText("打开","","Edit1","C:\Users\DELL\Desktop\test\upload\北京宏哥.jpeg")
Sleep(2000)
;点击上传窗口中的“打开“按钮
ControlClick("打开","","Button1")
5.3验证上传脚本是否正确
1.保存脚本文件为ChromFileUpload.au3格式,然后在AutoIt脚本编辑器中点击Tools菜单,tools=>go,执行脚本验证(前提是windows窗口必须是打开状态),验证成功,如下图所示:
5.4上传脚本编译成一个.exe文件
为了这个脚本能被java 程序调用,需要通过Compile Script to .exe (x64)工具生成exe文件(这个是通过.exe安装包安装的AutoIt)
1.AutoIt脚本编辑器中点击Tools菜单,选择compile,会在同路径下生成一个.exe的文件(这个是通过解压包安装的AutoIt)
2.提示Conversion complete转化完成:将ChromeFileUpload.exe拷贝到项目下,待会在Selenium脚本要使用。
5.5java代码执行exe文件
//实现文件上传。通过Runtime的静态方法获取Runtime对象
Runtime runtime = Runtime.getRuntime();
//通过Runtime对象调用exe方法
runtime.exec("C:\Users\DELL\Desktop\test\upload\ChromeFileUpload.exe");
6.项目实战
6.1代码设计
实现文件上传整体代码如下:
6.2参考代码
package lessons;
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.chrome.ChromeDriver;
/**
* @author 北京-宏哥
*
* @公众号:北京宏哥
*
* @《手把手教你》系列技巧篇(五十三)-java+ selenium自动化测试-上传文件-下篇(详细教程)
*
* 2021年12月9日
*/
public class AutoItUpload {
public static void main(String[] args) {
System.setProperty("webdriver.gecko.driver", ".\\Tools\\chromedriver.exe"); //指定驱动路径
WebDriver driver =new ChromeDriver();
try {
driver.get("https://www.baidu.com");
driver.manage().window().maximize();
// 点击照相机这个按钮
driver.findElement(By.xpath("//*/span[@class='soutu-btn']")).click();
// 点击本地上传图片
driver.findElement(By.xpath("//*/input[@class='upload-pic']")).click();
Thread.sleep(3000);
//实现文件上传。通过Runtime的静态方法获取Runtime对象
Runtime runtime = Runtime.getRuntime();
//通过Runtime对象调用exe方法
runtime.exec("C:/Users/DELL/Desktop/test/upload/ChromFileUpload.exe");
Thread.sleep(5000);
}catch (Exception e) {
e.printStackTrace();
}finally {
System.out.println("执行结束,关闭浏览器");
driver.quit();
}
}
}
6.3运行代码
1.运行代码,右键Run AS->Java Appliance,控制台输出,如下图所示:
2.运行代码后电脑端的浏览器的动作,如下小视频所示:
7.小结
这样,我们就实现了利用AutoIt的自动上传功能。好了,今天时间也不是很早了,宏哥今天就讲解和分享到这里,感谢您耐心的阅读!
每天学习一点,今后必成大神-
往期推荐(由于跳转参数丢失了,所有建议选中要访问的右键,在新标签页中打开链接即可访问):
Appium自动化系列,耗时80天打造的从搭建环境到实际应用精品教程测试
Python接口自动化测试教程,熬夜87天整理出这一份上万字的超全学习指南
Python+Selenium自动化系列,通宵700天从无到有搭建一个自动化测试框架
Java+Selenium自动化系列,仿照Python趁热打铁呕心沥血317天搭建价值好几K的自动化测试框架
Jmeter工具从基础->进阶->高级,费时2年多整理出这一份全网超详细的入门到精通教程