当前位置: 首页 > news >正文

Cucumber + Playwright framework based on javascript

Step 1: Setup new project and playwright+cucumber

Git init and Nodejs init for a new project

cd playwright-cucumber-demo
git init
npm init -y

Install playwright

npm init playwright@latest
# Do you want to use TypeScript or JavaScript? JavaScript (或 TypeScript,本项目以 JS 为例)
# Where to put your end-to-end tests? tests (这个目录之后会被 Cucumber 使用,但先保留)
# Add a GitHub Actions workflow? No (我们将自己创建更定制的流程)
# Install Playwright browsers? Yes

Install cucumber-js

npm install @cucumber/cucumber @cucumber/pretty-formatter
# 如果使用 TypeScript,还需要安装 typescript 和 ts-node

Step 2: Create file structure

playwright-cucumber-demo/
├── features/
│   ├── example.feature       # 用 Gherkin 语言编写的功能文件
│   └── step_definitions/
│       └── example.steps.js  # 步骤定义文件
├── support/
│   ├── world.js             # 自定义 World 对象,用于共享状态
│   └── hooks.js             # 钩子函数 (如 before, after)
├── playwright.config.js     # Playwright 配置文件
├── package.json
└── .github/└── workflows/└── ci.yml           # GitHub Actions 工作流文件 (稍后创建)

Step 3: Cucumber configurations

// cucumber.config.js
/*  Refer to https://github.com/cucumber/cucumber-js/blob/main/docs/configuration.md for more details
*/
module.exports = {default: {// 显式指定 feature 文件路径paths: ['features/**/*.feature'],require: ['support/world.js','support/hooks.js','support/register-allure.js',  //预留文件,可对allure扩展'features/step_definitions/**/*.js'],format: ['@cucumber/pretty-formatter','html:cucumber-report.html','json:cucumber-report.json'],parallel: 2 // 并行运行的进程数,可根据 CI 环境调整}
}

`npx cucumber-js` execution would trigger below flows:

1.Load the require files in sequence

2.Call setWorldConstructor(CustomWorld) once while it loads world.js

3.Create CustomWorld instance before each scenario execution, so constructor method would be triggered

4.Then Before hook would be triggered

Step 4:Write example feature and step_definition files

# features/example.feature
Feature: 访问 Playwright 官网并搜索Scenario: 在 Playwright 官网搜索Given 我导航到 Playwright 官网When 我在搜索框中输入 "CSS"Then 搜索结果页面应该显示与 "CSS" 相关的内容
// features/step_definitions/example.steps.js
const { Given, When, Then } = require('@cucumber/cucumber');
const { expect } = require('@playwright/test');Given('我导航到 Playwright 官网', async function () {// this.page 来自 World 对象,在 hooks.js 中初始化await this.page.goto('https://playwright.dev');
});When('我在搜索框中输入 {string}', async function (searchTerm) {await this.page.click('button.DocSearch-Button');await this.page.fill('input.DocSearch-Input', searchTerm);
});Then('搜索结果页面应该显示与 {string} 相关的内容', async function (searchTerm) {// 等待搜索结果出现const firstResult = await this.page.waitForSelector('.DocSearch-Hit a');const text = await firstResult.textContent();expect(text).toContain(searchTerm);
});

Step 5: Create support files to integrate Allure

World Extension

Cucumber framework allows a custom World to manage per-scenario state and integrate Allure, so we should define a CustomWorld class to extend World.

Why it's needed: Only when using Cucumber, you need a central place to manage shared state and lifecycles at the scene level (e.g., browser/page and allure operations). Without it, you have to manually create it at each step or manage it through global variables, which is difficult to maintain.

// support/world.js
/*  Refer to https://github.com/cucumber/cucumber-js/blob/db0956e0725e2ef00854c0d52c4392db00bdf307/docs/support_files/world.md for more details
*/
const { setWorldConstructor, World } = require('@cucumber/cucumber');
const { chromium } = require('playwright');
// 根据 allure-cucumberjs legacy.ts 的弃用说明,不再继承 AllureCucumberWorld,直接使用 allure-js-commons API
const {attachment, // 添加附件label,      // 添加自定义或标准标签link,       // 添加链接 (issue / tms)severity,   // 严重级别step        // 自定义步骤包装
} = require('allure-js-commons');class CustomWorld extends World {constructor(options) {super(options);// 可在此处初始化测试上下文数据}async launchBrowser() {this.browser = await chromium.launch({ headless: true });this.context = await this.browser.newContext();this.page = await this.context.newPage();}async closeBrowser() {if (this.browser) await this.browser.close();}// ===== Allure 辅助方法(采用新 API,避免使用已弃用的 AllureCucumberWorld 实例方法) =====async attachScreenshot(name = 'screenshot') {if (!this.page) return;const buf = await this.page.screenshot();attachment(name, buf, { contentType: 'image/png' });}addSeverity(level = 'normal') {severity(level); // e.g. blocker, critical, normal, minor, trivial}addLabel(name, value) {label(name, value);}addIssue(name, url) {link(url, name, 'issue');}addTms(name, url) {link(url, name, 'tms');}async runStep(title, bodyFn) {return step(title, bodyFn); // 在报告中嵌套展示}
}setWorldConstructor(CustomWorld);

Hook function

// support/hooks.js
/*  Refer tohttps://github.com/cucumber/cucumber-js/blob/main/docs/support_files/hooks.mdfor more details
*/
const { Before, After } = require('@cucumber/cucumber');Before(async function () {await this.launchBrowser();
});After(async function () {await this.closeBrowser();
});

Step 6: Add package.json script

"scripts": {"test": "cucumber-js","test:headed": "cucumber-js --world-parameters={\"headed\": true}","test:report": "cucumber-js && open cucumber-report.html"
}

http://www.dtcms.com/a/496513.html

相关文章:

  • 关于电子商务网站建设的论文广告传媒公司介绍
  • 武威建设厅网站建设企业网站进去无法显示
  • 一台网站服务器多少钱网站建设业务员培训
  • 网站建设如何赚钱wordpress主题设置选择
  • SVN 非页面操作 锁定单个cell
  • 布恩网站删除西峡微网站开发
  • 网站后台图片模板wordpress 手机发文
  • 网站建设与用户需求分析国家企业信用信息公示系统查询
  • 李飞飞 world labs最新文章 RTFM: A Real-Time Frame Model 翻译及思考
  • Prism框架核心对象补充:区域上下文与模块化设计
  • 广州那里有学做拼多多网站的天津网站建设市场
  • 福建闽东建设网站设计logo网站 生成器
  • Git合并分支:从命令行到图形化工具
  • 低价建网站wordpress添加友链申请
  • 长沙手机app网站开发哈尔滨网站制作哪里专业
  • 从Backtrader到Freqtrade:搭建自己的全自动量化平台
  • C标准库--类型限制<limits.h>
  • 网页设计新建站点wordpress 数据库设置
  • 外贸机械网站建设域名查询168
  • FFmpeg 基本API avio_write函数内部调用流程分析
  • 怎么优化一个网站关键词wordpress 摄影工作室主题
  • 2025Java高质量面试真题汇总!
  • Edge Wallet数字货币钱包安全可靠吗?浅聊数字钱包
  • 宁波网站建设是哪家便宜如何建个使用自己帐户的网站
  • wordpress视频网站采集器网站设计师和ui设计师
  • 网站后台优化网站建的创新点
  • 网络故障排查:丢包、延迟、MTU 问题诊断与修复方法
  • 公司网站制作怎么弄灵犀科技 高端网站建设
  • 内网搭建邮件服务,打通 IDMP 通知途径
  • 东莞市电商网站建设直播营销策略有哪些