有人说学测试底层原理只是为应付面试?真怪不得你只能拿10K
Posted 程序员小濠
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了有人说学测试底层原理只是为应付面试?真怪不得你只能拿10K相关的知识,希望对你有一定的参考价值。
前言
金三银四,是纵多互联网企业面试招聘的黄金季。尤其是互联网大厂,每月都要吸纳十几名自动化测试,对我们普通技术人来说,这可是几十张通往财务自由的船票,装满了数不清的财富和机遇。自动
大厂对 测试中高测试工程师者经验要求一般都是 3 年起,但很多 3 年经验的自动化测试,却在一面就挂得很惨。 这究竟是为什么呢?耐心看完,一定对你有帮助。
技术岗,不是只靠工作年限吃饭的岗位。在我们互联网技术行业,经验其实是个幌子,我整理过一份详细的大厂岗位需求表,里面显示很多 15K 以上的自动化测试岗,基本都要求具备的相关经验。老练的面试官知道,对于一个 中高级测试工程师而言,如果对ui自动化底层原理、源码有全面而深入的了解,那说明技术功底足够扎实。
大家好,我是小濠,今天整理了一些软件测试资料,希望能对你有帮助!
这里赠送一套软件测试相关资源:
- 软件测试相关工具
- 软件测试练习集
- 深入自动化测试
- Python学习手册
- Python编码规范
- 大厂面试题和简历模板
关注我公众号:【程序员小濠】即可免费领取!
UI自动化测试底层原理
底层原理如下:
1.在自动化测试过程中,存在三部分组件:客户端脚本+驱动+浏览器终端。
2.驱动文件,以geckodriver.exe为例,这个可执行的驱动文件启动后,相当于一个暴露了一系列接口的服务器,监听某一端口,例如:89890。
3.客户端的操作(访问页面,定位元素,输入数据,点击按钮等)都是封装成了接口请求(eg:/session/xx/yy),然后提交到驱动服务器。
4.驱动服务器接收到客户端的请求后,再跟终端浏览器交互。
5.终端浏览器做出相应操作。
下图描述了整个交互过程:
以定位元素为例,定位搜索框,我们来看底下这行代码在执行的时候底层到底经历了些什么:
WebElement searchInputBox = driver.findElement(By.id("js_keyword"));
实际,底层请求时,每个请求会被封装为一个command,然后根据不同的commannd封装得到不同的HttpRequest对象:
根据此命令,得到接口地址:
拿到此接口地址封装为一个HttpRequest请求。
client.execute(httpRequest,true),执行接口调用:
至于其他操作:往输入框输入数据,点击按钮等,都是对应一个接口地址,通过调用接口,请求驱动来处理,最后驱动同浏览器进行交互,浏览器按照指示做出对应操作。
Selenium有一个类AbstractHttpCommandCodec,此类中维护了众多自动化操作对应的接口地址:
public AbstractHttpCommandCodec() { defineCommand(STATUS, get("/status")); defineCommand(GET_ALL_SESSIONS, get("/sessions")); defineCommand(NEW_SESSION, post("/session")); defineCommand(GET_CAPABILITIES, get("/session/:sessionId")); defineCommand(QUIT, delete("/session/:sessionId")); defineCommand(GET_SESSION_LOGS, post("/logs")); defineCommand(GET_LOG, post("/session/:sessionId/log")); defineCommand(GET_AVAILABLE_LOG_TYPES, get("/session/:sessionId/log/types")); defineCommand(SWITCH_TO_FRAME, post("/session/:sessionId/frame")); defineCommand(SWITCH_TO_PARENT_FRAME, post("/session/:sessionId/frame/parent")); defineCommand(CLOSE, delete("/session/:sessionId/window")); defineCommand(SWITCH_TO_WINDOW, post("/session/:sessionId/window")); defineCommand(FULLSCREEN_CURRENT_WINDOW, post("/session/:sessionId/window/fullscreen")); defineCommand(GET_CURRENT_URL, get("/session/:sessionId/url")); defineCommand(GET, post("/session/:sessionId/url")); defineCommand(GO_BACK, post("/session/:sessionId/back")); defineCommand(GO_FORWARD, post("/session/:sessionId/forward")); defineCommand(REFRESH, post("/session/:sessionId/refresh")); defineCommand(SET_ALERT_CREDENTIALS, post("/session/:sessionId/alert/credentials")); defineCommand(UPLOAD_FILE, post("/session/:sessionId/file")); defineCommand(SCREENSHOT, get("/session/:sessionId/screenshot")); defineCommand(ELEMENT_SCREENSHOT, get("/session/:sessionId/screenshot/:id")); defineCommand(GET_TITLE, get("/session/:sessionId/title")); defineCommand(FIND_ELEMENT, post("/session/:sessionId/element")); defineCommand(FIND_ELEMENTS, post("/session/:sessionId/elements")); defineCommand(GET_ELEMENT_PROPERTY, get("/session/:sessionId/element/:id/property/:name")); defineCommand(CLICK_ELEMENT, post("/session/:sessionId/element/:id/click")); defineCommand(CLEAR_ELEMENT, post("/session/:sessionId/element/:id/clear")); defineCommand( GET_ELEMENT_VALUE_OF_CSS_PROPERTY, get("/session/:sessionId/element/:id/css/:propertyName")); defineCommand(FIND_CHILD_ELEMENT, post("/session/:sessionId/element/:id/element")); defineCommand(FIND_CHILD_ELEMENTS, post("/session/:sessionId/element/:id/elements")); defineCommand(IS_ELEMENT_ENABLED, get("/session/:sessionId/element/:id/enabled")); defineCommand(ELEMENT_EQUALS, get("/session/:sessionId/element/:id/equals/:other")); defineCommand(GET_ELEMENT_RECT, get("/session/:sessionId/element/:id/rect")); defineCommand(GET_ELEMENT_LOCATION, get("/session/:sessionId/element/:id/location")); defineCommand(GET_ELEMENT_TAG_NAME, get("/session/:sessionId/element/:id/name")); defineCommand(IS_ELEMENT_SELECTED, get("/session/:sessionId/element/:id/selected")); defineCommand(GET_ELEMENT_SIZE, get("/session/:sessionId/element/:id/size")); defineCommand(GET_ELEMENT_TEXT, get("/session/:sessionId/element/:id/text")); defineCommand(SEND_KEYS_TO_ELEMENT, post("/session/:sessionId/element/:id/value")); defineCommand(GET_ALL_COOKIES, get("/session/:sessionId/cookie")); defineCommand(GET_COOKIE, get("/session/:sessionId/cookie/:name")); defineCommand(ADD_COOKIE, post("/session/:sessionId/cookie")); defineCommand(DELETE_ALL_COOKIES, delete("/session/:sessionId/cookie")); defineCommand(DELETE_COOKIE, delete("/session/:sessionId/cookie/:name")); defineCommand(SET_TIMEOUT, post("/session/:sessionId/timeouts")); defineCommand(SET_SCRIPT_TIMEOUT, post("/session/:sessionId/timeouts/async_script")); defineCommand(IMPLICITLY_WAIT, post("/session/:sessionId/timeouts/implicit_wait")); defineCommand(GET_APP_CACHE_STATUS, get("/session/:sessionId/application_cache/status")); defineCommand(IS_BROWSER_ONLINE, get("/session/:sessionId/browser_connection")); defineCommand(SET_BROWSER_ONLINE, post("/session/:sessionId/browser_connection")); defineCommand(GET_LOCATION, get("/session/:sessionId/location")); defineCommand(SET_LOCATION, post("/session/:sessionId/location")); defineCommand(GET_SCREEN_ORIENTATION, get("/session/:sessionId/orientation")); defineCommand(SET_SCREEN_ORIENTATION, post("/session/:sessionId/orientation")); defineCommand(GET_SCREEN_ROTATION, get("/session/:sessionId/rotation")); defineCommand(SET_SCREEN_ROTATION, post("/session/:sessionId/rotation")); defineCommand(IME_GET_AVAILABLE_ENGINES, get("/session/:sessionId/ime/available_engines")); defineCommand(IME_GET_ACTIVE_ENGINE, get("/session/:sessionId/ime/active_engine")); defineCommand(IME_IS_ACTIVATED, get("/session/:sessionId/ime/activated")); defineCommand(IME_DEACTIVATE, post("/session/:sessionId/ime/deactivate")); defineCommand(IME_ACTIVATE_ENGINE, post("/session/:sessionId/ime/activate")); // Mobile Spec defineCommand(GET_NETWORK_CONNECTION, get("/session/:sessionId/network_connection")); defineCommand(SET_NETWORK_CONNECTION, post("/session/:sessionId/network_connection")); defineCommand(SWITCH_TO_CONTEXT, post("/session/:sessionId/context")); defineCommand(GET_CURRENT_CONTEXT_HANDLE, get("/session/:sessionId/context")); defineCommand(GET_CONTEXT_HANDLES, get("/session/:sessionId/contexts")); }
另外,可能会有人好奇,驱动服务器是何时启动的服务。其实是在执行下面这行代码的时候启动的,大家可执行去debug调试selenium的底层代码:
//创建火狐驱动对象 WebDriver driver = new FirefoxDriver();
当上面这行代码执行完,可以发现eclipse的控制台显示了如下信息:
1531911173760 geckodriver INFO geckodriver 0.19.0 1531911173772 geckodriver INFO Listening on 127.0.0.1:21984
说明此驱动服务器成功启动了,并且监听了本机的21984端口,等待客户端发起请求,并处理。
最后,为方便大家自学软件测试,特意给大家准备了一份13G的超实用干货学习资源,涉及的内容非常全面。
包括,软件学习路线图,50多天的上课视频、16个突击实战项目,80余个软件测试用软件,37份测试文档,70个软件测试相关问题,40篇测试经验级文章,上千份测试真题分享,还有2021软件测试面试宝典,还有软件测试求职的各类精选简历,希望对大家有所帮助……
关注我公众号:【程序员小濠】即可获取这份资料了!
送上一句话:
世界的模样取决于你凝视它的目光,自己的价值取决于你的追求和心态,一切美好的愿望,不在等待中拥有,而是在奋斗中争取。
我的学习交流群:175317069 群里有技术大牛一起交流分享~群内有不定期的学习视频资料发放
以上是关于有人说学测试底层原理只是为应付面试?真怪不得你只能拿10K的主要内容,如果未能解决你的问题,请参考以下文章
前端面试题总结(这里不得不总结,我是后台,但是经常有人问我前台的问题,不得不了解一下前台的基础原理知识)