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

Java环境下无头模式Selenium测试录屏方案咨询

无头Chrome下Selenium测试录屏的可行方案

方案1:利用Chrome DevTools Protocol(CDP)原生录屏

无头Chrome支持通过CDP直接捕获页面帧,无需额外第三方工具,适合Java环境集成。

实现步骤:

  1. 初始化无头ChromeDriver时开启CDP会话
  2. 通过CDP的Page.startScreencast命令启动录屏,配置帧率、分辨率等参数
  3. 监听Page.screencastFrame事件接收帧数据
  4. 测试结束后停止录屏,将帧数据合成视频文件

Java代码示例:

import org.openqa.selenium.chrome.ChromeDriver;
import org.openqa.selenium.chrome.ChromeOptions;
import org.openqa.selenium.devtools.DevTools;
import org.openqa.selenium.devtools.v128.page.Page;

import java.util.ArrayList;
import java.util.Base64;
import java.util.List;
import java.util.Optional;
import javax.imageio.ImageIO;
import java.awt.image.BufferedImage;
import java.io.ByteArrayInputStream;
import com.xuggle.xuggler.IMediaWriter;
import com.xuggle.xuggler.ToolFactory;
import java.util.concurrent.TimeUnit;

public class HeadlessRecording {
    public static void main(String[] args) throws Exception {
        // 配置无头Chrome
        ChromeOptions options = new ChromeOptions();
        options.addArguments("--headless=new");
        options.addArguments("--disable-gpu");
        options.addArguments("--window-size=800,600");
        
        ChromeDriver driver = new ChromeDriver(options);
        DevTools devTools = driver.getDevTools();
        devTools.createSession();

        // 启动录屏,设置10fps,800x600分辨率
        devTools.send(Page.startScreencast(
                Optional.empty(), Optional.of(10), Optional.of(800), Optional.of(600), Optional.of(100)
        ));

        List<byte[]> videoFrames = new ArrayList<>();

        // 监听帧数据,解码后存储
        devTools.addListener(Page.screencastFrame(), frame -> {
            byte[] decodedFrame = Base64.getDecoder().decode(frame.getData());
            videoFrames.add(decodedFrame);
            // 确认接收帧,避免CDP停止发送
            devTools.send(Page.screencastFrameAck(frame.getSessionId()));
        });

        // 执行测试逻辑
        driver.get("https://example.com");
        // 这里替换为你的测试步骤
        Thread.sleep(3000);

        // 停止录屏
        devTools.send(Page.stopScreencast());

        // 用Xuggler合成MP4视频(需引入Xuggler依赖)
        IMediaWriter writer = ToolFactory.makeWriter("test-recording.mp4");
        writer.addVideoStream(0, 0, com.xuggle.xuggler.ICodec.ID.CODEC_ID_MPEG4, 800, 600);
        
        long timestamp = 0;
        for (byte[] frameBytes : videoFrames) {
            BufferedImage frame = ImageIO.read(new ByteArrayInputStream(frameBytes));
            writer.encodeVideo(0, frame, timestamp, TimeUnit.MILLISECONDS);
            timestamp += 100; // 对应10fps的时间间隔
        }
        writer.close();

        driver.quit();
    }
}

方案2:使用Monte Media Library录制虚拟显示(跨Windows/Linux)

如果需要录制整个虚拟桌面的内容(适合无法通过CDP捕获的场景),可以用Monte库结合虚拟显示工具:

  • Linux:用Xvfb创建虚拟显示
  • Windows:用VNC或系统自带的虚拟桌面

实现步骤:

  1. 启动虚拟显示(Linux下需提前启动Xvfb)
  2. 配置Chrome在虚拟显示中运行(Linux需设置DISPLAY环境变量)
  3. 用Monte启动屏幕录制
  4. 执行测试后停止录制,保存视频

Java代码示例(Monte):

import org.monte.media.Format;
import org.monte.media.FormatKeys;
import org.monte.media.Registry;
import org.monte.media.math.Rational;
import org.monte.screenrecorder.ScreenRecorder;
import org.openqa.selenium.chrome.ChromeDriver;
import org.openqa.selenium.chrome.ChromeOptions;

import java.awt.*;
import java.io.File;

import static org.monte.media.AudioFormatKeys.*;
import static org.monte.media.VideoFormatKeys.*;

public class MonteScreenRecording {
    public static void main(String[] args) throws Exception {
        // Linux下需先执行:Xvfb :1 -screen 0 800x600x24,然后设置环境变量
        // System.setProperty("DISPLAY", ":1");

        // 配置录制参数
        GraphicsConfiguration gc = GraphicsEnvironment.getLocalGraphicsEnvironment()
                .getDefaultScreenDevice().getDefaultConfiguration();

        ScreenRecorder recorder = new ScreenRecorder(gc,
                new Format(MediaTypeKey, FormatKeys.MediaType.FILE, MimeTypeKey, MIME_AVI),
                new Format(MediaTypeKey, FormatKeys.MediaType.VIDEO, EncodingKey, ENCODING_AVI_TECHSMITH_SCREEN_CAPTURE,
                        CompressorNameKey, ENCODING_AVI_TECHSMITH_SCREEN_CAPTURE,
                        DepthKey, 24, FrameRateKey, Rational.valueOf(15),
                        QualityKey, 1.0f,
                        KeyFrameIntervalKey, 15 * 60),
                new Format(MediaTypeKey, FormatKeys.MediaType.AUDIO, EncodingKey, "PCM",
                        SampleRateKey, 44100,
                        SampleSizeInBitsKey, 16,
                        ChannelsKey, 2),
                null);

        recorder.start();

        // 启动无头Chrome
        ChromeOptions options = new ChromeOptions();
        options.addArguments("--headless=new");
        options.addArguments("--window-size=800,600");
        ChromeDriver driver = new ChromeDriver(options);

        driver.get("https://example.com");
        // 执行测试步骤
        Thread.sleep(3000);

        driver.quit();
        recorder.stop();

        // 录制的视频默认保存在用户目录下的Movies文件夹
        File videoFile = recorder.getCreatedFiles().get(0);
        System.out.println("视频保存路径:" + videoFile.getAbsolutePath());
    }
}

方案3:FFmpeg Java绑定库直接编码帧

如果需要更高效的视频编码,可以用FFmpeg的Java绑定(比如ffmpeg-java)替代Xuggler,结合CDP获取的帧数据直接生成视频,性能和兼容性更好。

核心思路:

  1. 通过CDP获取Base64编码的帧数据
  2. 将帧数据解码为原始图像
  3. 用FFmpeg Java库将图像序列编码为MP4/WebM等格式

关键代码片段(结合CDP):

// 承接方案1的帧数据获取逻辑
// 引入ffmpeg-java依赖后,编码示例:
FFmpeg.atPath()
      .addInput(FrameInput.create()
              .addFrame(videoFrames.stream()
                      .map(frameBytes -> {
                          try {
                              return JavaFrameConverter.toFrame(ImageIO.read(new ByteArrayInputStream(frameBytes)));
                          } catch (IOException e) {
                              throw new RuntimeException(e);
                          }
                      })
                      .collect(Collectors.toList()))
              .setFrameRate(10))
      .addOutput("test-recording.mp4")
      .setVideoCodec("libx264")
      .setPreset("ultrafast")
      .run();

内容的提问来源于stack exchange,提问作者Oriol Julià Torres

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.18 14:22:03