Laravel Dusk 浏览器测试:最佳实践和技巧
发布时间:作者: Eric L. Barnes
我们用于 测试管理 工具 Testmo 的 Laravel Dusk 测试套件目前包含 788 个复杂的浏览器测试。仅针对单个浏览器运行整个测试套件大约需要 2.5 个小时。确保这样的大型测试套件易于维护,避免出现不稳定的测试,并确保它能够稳健地处理未来的应用程序更改,这可能是一项挑战。
有一些最佳实践可以帮助构建和维护 Laravel Dusk 浏览器测试(我们希望在开始使用测试套件时就了解所有这些实践)。在本文中,我们将分享我们学到的经验教训,以便您自己编写更好的 Laravel Dusk 测试。
使用稳健且可维护的选择器
这可能是编写浏览器测试时最关键的一点:在与您的应用程序交互并断言页面状态时,**选择稳健的选择器至关重要**。
这意味着什么?使用 Laravel Dusk 和一般的浏览器测试,您通过 DOM 元素与应用程序交互。例如,您需要告诉浏览器在**哪里**点击以及要填充**哪个**输入字段。您可以使用所谓的 XPaths 来定位元素,指定元素的 ID 属性,使用表单字段名称等。
识别元素最通用和最流行的方式是通过 CSS 选择器。但是,在更改 CSS 类或页面结构时,很容易编写容易失效的选择器。当您使用 Tailwind CSS 或 React 等系统时,情况尤其如此,因为类名对识别元素没有帮助。以下是一些您应该避免使用的选择器示例
// Breaks when you change button order$b->click('.actions button:first-child'); // Breaks when you change app styling$b->click('form button.negative'); // Breaks when you change sorting or add extra rows$b->assertSeeIn('tr:nth-child(5)', 'Admin user');
相反,最好用**标签**标记您的元素,以从测试中唯一识别它们。这使得您的测试在应用程序 UI 更改时更加稳健。例如,如果您想通过单击标记为提交按钮的元素来提交表单,那么无论此元素在视图中以链接、图像还是实际表单按钮的形式实现,都不重要。您可以通过为提交元素添加 [dusk=submitButton]
等属性来标记它。Dusk 有一种方便的方法来选择此类元素,只需在测试中指定以 @ 开头的名称
// In your view:<button dusk="submitButton">Register</button> // Clicks the element with the [dusk=submitButton] attribute$b->click('@submitButton'); // You can also chain selectors to be more specific$b->within('@orderForm', function ($b) { $b->type('@name', 'Gabrielle Baker');}); // You can also add IDs in your views to find elements more reliably$b->assertSeeIn('tr[id=3]', 'Admin user');
避免不稳定的测试并使用更好的等待
不稳定的测试在测试自动化工作中可能是一个大问题。不稳定的测试是指有时通过有时失败的测试,即使您没有更改代码也是如此。不稳定的测试问题在于**它们不可靠、破坏构建且无法信任**。
浏览器测试尤其容易产生不稳定的结果。不稳定的测试通常是由于测试预期之外的计时问题、异步操作或网络延迟造成的。例如,如果您在应用程序中单击一个按钮,然后检查结果文本,但文本有时需要更长的时间才能渲染(例如,因为您的浏览器比断言代码更新得慢),则测试有时会失败。
不稳定的测试不仅令人讨厌,而且通常很难找到也很难修复。以下是我们在 Laravel Dusk 测试中避免、识别和修复不稳定测试的一些策略
-
**等待,不要假设:**在与页面交互或断言页面之前,等待元素出现、DOM 状态准备好并等待更改完成非常重要。Laravel Dusk 提供了许多方法来等待元素、页面更改或文本。确保使用它们!考虑以下示例
// Wrong: not waiting for elements will cause failures$b->click('@addUser'); // Performs network request$b->within('@userDialog', function ($b) { $b->type('@name', 'Gabrielle Baker'); $b->click('@submitButton'); // Performs network request});$this->assertUserExists(1, 'Gabrielle Baker'); // Correct: Wait for updates before interactions or assertions$b->click('@addUser'); // Performs network request$b->whenAvailable('@userDialog', function ($b) { // Wait $b->type('@name', 'Gabrielle Baker'); $b->click('@submitButton'); // Performs network request});$b->waitUntilMissing('@userDialog'); // Wait$this->assertUserExists(1, 'Gabrielle Baker');
-
**从 JavaScript 信号状态:**有时,从 JavaScript 代码信号 DOM 处于可交互状态可能会有所帮助。某些对于用户来说很明显的内容,例如动画,可能会让您的测试感到困惑,导致它与尚未准备好的元素交互。还记得上面提到的标记元素的技巧,例如
[dusk=submitButton]
吗?您可以先不使用此属性输出视图,然后在提交按钮**真正**准备好时从 JavaScript 代码中添加此属性。简单的 Dusk$b->waitFor('@submitButton')
将从您的测试中处理此操作。 -
**针对不同的浏览器测试:**另一个不明显的提示是从一开始就针对不同的 Web 浏览器进行测试。这不仅是确保您的应用程序除了 Chrome 之外还能与其他浏览器一起使用的好主意。这也是检测导致不稳定测试的计时问题的好方法,因为不同的浏览器有时行为略有不同。所以我们的提示:不要只针对默认的 Chrome 浏览器运行 Dusk 测试,而是至少添加 Firefox,甚至可能添加 Edge,以便问题尽早出现。
-
**跟踪和识别不稳定的测试:**要修复问题,首先需要对其进行测量和识别。要找到不稳定的测试,您需要知道哪些测试随机通过和失败。实际上,说起来容易做起来难。大多数测试环境都不便于跟踪或比较一段时间内的结果。这里有两个选项。首先,您可以将测试结果提交到支持不稳定测试检测的 QA 工具。我们的 Testmo 工具允许您查找不稳定的测试(以及缓慢或失败的测试)。使用我们的 测试自动化 支持也很容易提交 PHPUnit 结果,包括来自 CI 管道的结果。另一个选择是您的 CI 工具。如果一些 CI 工具能够跟踪和报告自动化结果,它们也支持不稳定测试检测。无论使用哪个选项,请务必关注不稳定的测试,因为当您扩展和扩展测试套件时,它们会导致很多问题。
错误检测、调试和手动测试
断言在各种测试之后您的应用程序处于您预期状态是您编写测试套件的主要原因。我们的建议:不要只测试 UI 状态**或**数据库状态,请务必**针对页面 DOM 和您的数据模型编写断言**。如果只测试 UI 是否更新正确,可能会导致各种类型的错误检测不到。同样,如果您只是检查表单提交后数据库是否更新,UI 可能不会显示确认消息等。始终测试用户界面和数据库!
我们还发现,在测试中添加一些通用的捕获所有断言和功能非常有帮助。一个被证明非常有价值的做法是在测试结束时获取浏览器日志,并在日志中出现意外警告和错误时引发错误。这是捕获 JavaScript 错误或警告(未触发任何其他断言)的好方法。此外,我们还在失败**和**成功测试之后拍摄浏览器状态的快照。这对于进一步审查或调试测试问题非常有用,尤其是如果测试套件在其他环境(例如 CI 管道)中执行。
最后,我们还要提到手动测试。有了大型测试自动化套件,很容易忘记手动测试在找到您在测试中没有考虑到的问题时仍然很重要。它们对于测试难以自动化的功能(例如付款流程、第三方集成或生产站点)至关重要。
如果您在有专门测试人员的项目中工作,甚至在公司中有完整的 QA 团队,您可能已经熟悉这一点。您的测试人员同事可能已经在类似我们 Testmo 的工具中使用 测试用例管理 或 探索性测试 功能。您也可以从 Excel、Google Docs 或简单的笔记应用程序开始。无论您使用什么工具,健康的自动测试、手动测试和探索性测试组合都能确保您拥有出色的测试覆盖率,从而增加在用户发现错误之前找到错误的机会。
这是由 Testmo 的开发人员之一 Dennis Gurock 发布的客座文章,Testmo 是一款用于管理手动和自动软件测试的 QA 工具。 Testmo 是使用 Laravel 构建的,并大量使用了 Laravel Dusk。 如果你不熟悉 QA 工具,他最近整理了一份 最佳测试管理工具 列表供你尝试。