You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用Playwright addScriptTag测试JS库时函数未定义问题求助

问题原因

当你用type="module"加载index_browser.js时,浏览器会按ES模块规则解析代码,其中的import randomFn from './index.js'是基于当前页面URL查找文件的。Playwright默认打开about:blank页面,这个环境下相对路径无法定位到本地的src/index.js,导致模块加载失败,window.randomFn2根本没被赋值,所以evaluate里找不到这个函数。

而直接把函数嵌入index_browser.js时,没有模块依赖的加载问题,代码能正常执行,window.randomFn2就能被正确定义。

解决办法

这里提供两种简单可行的方案:

方案一:内联合并模块内容

读取两个文件的内容,把库函数定义和封装代码合并成一个模块脚本,直接内联到页面中,规避相对路径问题:

修改测试文件tests/index.spec.js:

import fs from 'fs';
import path from 'path';
import { expect, test as it } from '@playwright/test';

const { describe } = it;

// 读取本地文件内容
const libContent = fs.readFileSync(path.resolve(__dirname, '..', 'src', 'index.js'), 'utf8');
const wrapperContent = fs.readFileSync(path.resolve(__dirname, '..', 'src', 'index_browser.js'), 'utf8');

// 替换import语句,合并成完整模块代码
const combinedModule = libContent + '\n' + wrapperContent.replace(/import randomFn from '.\/index.js'/, '');

describe('Example', () => {
  it('should test', async ({ page }) => {
    await page.addScriptTag({
      content: combinedModule,
      type: "module"
    });

    const result = await page.evaluate(() => randomFn2());
    console.log(result); // 输出3
  });
});

方案二:拦截模块请求映射到本地文件

通过Playwright的路由拦截功能,把模块中相对路径的请求映射到本地文件:

修改测试文件tests/index.spec.js:

import fs from 'fs';
import path from 'path';
import { expect, test as it } from '@playwright/test';

const { describe } = it;

const moduleFile = path.resolve(__dirname, '..', 'src', 'index_browser.js');
const libFile = path.resolve(__dirname, '..', 'src', 'index.js');

describe('Example', () => {
  it('should test', async ({ page }) => {
    // 拦截对index.js的请求,返回本地库文件内容
    await page.route('**/index.js', async (route) => {
      const content = fs.readFileSync(libFile, 'utf8');
      await route.fulfill({
        content,
        headers: { 'Content-Type': 'application/javascript' }
      });
    });

    // 跳转到任意可访问URL,确保路由拦截生效
    await page.goto('http://example.com');

    await page.addScriptTag({
      path: moduleFile,
      type: "module"
    });

    const result = await page.evaluate(() => randomFn2());
    console.log(result); // 输出3
  });
});

内容的提问来源于stack exchange,提问作者Justin Dalrymple

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.11 22:00:18