编写合成测试
编辑编写合成测试编辑
在设置项目后,您可以开始编写合成测试,以检查最终用户可能在您的站点上执行的关键操作和请求。
语法概述编辑
要为您的应用程序编写合成测试,您需要了解基本的 JavaScript 和 Playwright 语法。
Playwright 是由 Microsoft 开发的浏览器测试库。它速度快、可靠性高,并具有现代 API,可以自动等待页面元素准备就绪。
合成代理公开了一个用于创建和运行测试的 API,包括
|
测试一个离散的功能单元。采用两个参数: |
|
旅程中应按特定顺序完成的操作。采用两个参数: |
|
检查值是否满足特定条件。支持多种检查。在进行断言中了解更多信息。 |
|
在任何 |
|
在单个 |
|
在所有 |
|
在单个 |
|
|
创建旅程编辑
使用 .journey.ts
或 .journey.js
文件扩展名创建一个新文件,或编辑其中一个示例旅程文件。
旅程测试一个离散的功能单元。例如,登录网站、将商品添加到购物车或加入邮件列表。
journey 函数采用两个参数:name
和 callback
。name
帮助您识别单个旅程。callback
参数是一个函数,它封装了旅程的功能。回调函数提供对新的 Playwright page
、params
、browser
和 context
实例的访问。
journey('Journey name', ({ page, browser, context, params, request }) => { // Add steps here });
参数编辑
|
用户定义的字符串,用于描述旅程。 |
|
您将在其中添加步骤的函数。 实例:
|
添加步骤编辑
旅程由一个或多个步骤组成。步骤是应按特定顺序完成的操作。步骤在 Synthetics 应用程序中单独显示,并附带屏幕截图,以便于调试和错误跟踪。
一个基本的包含两个步骤的旅程如下所示
journey('Journey name', ({ page, browser, client, params, request }) => { step('Step 1 name', () => { // Do something here }); step('Step 2 name', () => { // Do something else here }); });
步骤可以根据您的需要简单或复杂。例如,一个基本的第一步可能是加载网页
step('Load the demo page', () => { await page.goto('https://elastic.github.io/synthetics-demo/'); });
有关更多信息,请转到 |
参数编辑
|
用户定义的字符串,用于描述旅程。 |
|
一个函数,您可以在其中使用 Synthetics 和 Playwright 语法模拟用户工作流程。 |
如果您想通过直接与网页交互来生成代码,可以使用Synthetics 记录器。
记录器会启动一个 Chromium 浏览器,该浏览器会监听您与网页的每次交互,并使用 Playwright 在内部记录它们。当您完成与浏览器的交互后,记录器会将记录的操作转换为 JavaScript 代码,您可以将该代码与 Elastic Synthetics 或 Heartbeat 一起使用。
有关 Synthetics 记录器入门的更多详细信息,请参阅使用 Synthetics 记录器。
Playwright 语法编辑
在每个步骤的回调函数中,您可能会使用很多 Playwright 语法。使用 Playwright 模拟和验证用户工作流程,包括
有关信息,请访问 Playwright 文档。
在通过 Elastic 的全球托管测试基础设施或私有位置运行时,请勿尝试在有头模式下运行(使用 headless:false
),因为不支持此功能。
但是,并非所有 Playwright 功能都应与 Elastic Synthetics 一起使用。在某些情况下,Elastic Synthetics 库中内置了 Playwright 功能的替代方案。这些替代方案旨在更好地用于合成监控。请勿使用 Playwright 语法来
-
发出 API 请求。 请改用 Elastic Synthetic 的
request
参数。在发出 API 请求中了解更多信息。
还有一些 Playwright 功能在 Elastic Synthetics 中默认不受支持,包括
通过 screenshot
或 video
以编程方式完成的捕获不会被存储,也不会显示在 Synthetics 应用程序中。提供 path
可能会导致监视器因缺少写入本地文件的权限而失败。
进行断言编辑
更复杂的 step
可能会等待页面元素被选中,然后确保它与预期值匹配。
Elastic Synthetics 使用 @playwright/test
的 expect
函数进行断言,并支持大多数 Playwright 断言。Elastic Synthetics 不支持 toHaveScreenshot
或任何 快照断言。
例如,在使用以下 HTML 的页面上
<header class="header"> <h1>todos</h1> <input class="new-todo" autofocus autocomplete="off" placeholder="What needs to be done?"> </header>
您可以使用以下测试来验证类为 new-todo
的 input
元素是否具有预期的 placeholder
值(input
元素的提示文本)
step('Assert placeholder text', async () => { const input = await page.locator('input.new-todo'); expect(await input.getAttribute('placeholder')).toBe( 'What needs to be done?' ); });
发出 API 请求编辑
您可以使用 request
参数独立于浏览器交互发出 API 请求。例如,您可以从 HTTP 端点检索令牌,并在后续网页请求中使用它。
step('make an API request', async () => { const response = await request.get(params.url); // Do something with the response })
Elastic Synthetics request
参数类似于Playwright 公开的其他请求对象,但有一些关键区别
- Elastic Synthetics
request
参数内置于库中,因此无需单独导入,这减少了所需的代码量,并允许您在内联旅程中发出 API 请求。 - 与 Playwright 的
context.request
和page.request
(与相应的BrowserContext
共享 Cookie 存储)不同,Elastic Synthetics 公开的顶级request
对象具有其自己的隔离 Cookie 存储。 - 如果您想控制
request
对象的创建,可以通过--playwright-options
或在synthetics.config.ts
文件中传递选项来实现。
有关显示如何使用 request
对象的完整示例,请参阅Elastic Synthetics 演示存储库。
request
参数并非用于编写纯 API 测试。相反,它是一种支持在基于浏览器的测试中编写普通 HTTP 请求的方法。
设置和删除全局状态编辑
如果在旅程之前或之后有任何操作需要执行,可以使用 before
、beforeAll
、after
或 afterAll
。
例如,要设置将用于单个 journey
的全局状态或服务器,请使用 before
钩子。要在所有旅程之前执行一次此设置,请使用 beforeAll
钩子。
before(({ params }) => { // Actions to take }); beforeAll(({ params }) => { // Actions to take });
您可以使用 after
钩子清理用于单个 journey
的全局状态或关闭服务器。要在所有旅程之后执行一次此清理,请使用 afterAll
钩子。
after(({ params }) => { // Actions to take }); afterAll(({ params }) => { // Actions to take });
导入 NPM 包编辑
您可以在旅程代码中导入和使用其他 NPM 包。请参阅以下使用外部 NPM 包 is-positive
的示例
import { journey, step, monitor, expect } from '@elastic/synthetics'; import isPositive from 'is-positive'; journey('bundle test', ({ page, params }) => { step('check if positive', () => { expect(isPositive(4)).toBe(true); }); });
当您从使用外部 NPM 包的旅程创建监视器时,在调用 push
命令时,这些包将与旅程代码一起捆绑。
但是,使用外部包时存在一些限制
- 压缩后的捆绑旅程不应超过 800 KB。
- 由于平台不一致,原生节点模块将无法按预期工作。
示例合成测试编辑
一个完整的基本合成测试示例可能如下所示
import { journey, step, expect } from '@elastic/synthetics'; journey('Ensure placeholder is correct', ({ page }) => { step('Load the demo page', async () => { await page.goto('https://elastic.github.io/synthetics-demo/'); }); step('Assert placeholder text', async () => { const placeholderValue = await page.getAttribute( 'input.new-todo', 'placeholder' ); expect(placeholderValue).toBe('What needs to be done?'); }); });
您可以在Elastic Synthetics 演示存储库中找到更复杂的示例。
本地测试编辑
在编写旅程时,您可以在本地运行它们以验证它们是否按预期工作。然后,您可以创建监视器以定期运行您的旅程。
要测试项目中的所有旅程,请导航到包含 Synthetics 项目的目录并在其中运行旅程。默认情况下,@elastic/synthetics
运行器将仅运行与文件名 *.journey.(ts|js)*
匹配的文件。
# Run tests on the current directory. The dot `.` indicates # that it should run all tests in the current directory. npx @elastic/synthetics .
测试内联监视器编辑
要在本地测试内联监视器的旅程,请将内联旅程通过管道传递到 npx @elastic/synthetics
命令。
例如,假设您的内联监视器包含以下代码
step('load homepage', async () => { await page.goto('https://elastic.ac.cn'); }); step('hover over products menu', async () => { await page.hover('css=[data-nav-item=products]'); });
要在本地运行该旅程,您可以将该代码保存到文件中,并将文件的内容通过管道传递到 @elastic-synthetics
cat path/to/sample.js | npx @elastic/synthetics --inline
您将收到如下响应
Journey: inline ✓ Step: 'load homepage' succeeded (1831 ms) ✓ Step: 'hover over products menu' succeeded (97 ms) 2 passed (2511 ms)