企业防火墙环境下,如何实现EC2上传至S3的测试报告截图可访问?
解决企业防火墙环境下HTML测试报告访问S3私有截图的方案
首先,你提到的在HTML中嵌入JavaScript动态获取截图的思路是完全可行的,但需要配合EC2上的轻量代理服务来实现——毕竟本地浏览器没法直接访问无公网权限的S3桶,得通过有IAM权限的EC2做中转。下面是具体的实现步骤和替代方案:
方案一:JS+EC2代理服务(推荐)
这个方案的核心是让EC2作为S3的代理,本地HTML通过JS请求EC2的接口,由EC2从S3拉取截图后返回给浏览器。
具体步骤:
在EC2上部署轻量HTTP服务
- 用Python的
Flask或者Node.js的Express写个极简接口就行,利用EC2的IAM角色权限调用S3的get_object接口获取截图文件。 - 示例Flask代码片段:
from flask import Flask, send_file import boto3 from io import BytesIO app = Flask(__name__) s3 = boto3.client('s3') BUCKET_NAME = "你的S3桶名称" @app.route('/screenshot/<path:key>') def get_screenshot(key): try: response = s3.get_object(Bucket=BUCKET_NAME, Key=key) return send_file(BytesIO(response['Body'].read()), mimetype='image/png') # 根据截图格式调整mimetype except Exception as e: return str(e), 404 if __name__ == '__main__': app.run(host='0.0.0.0', port=8080) - 记得配置EC2安全组,允许企业内网用户访问这个服务的端口(比如8080)。
- 用Python的
修改HTML报告的截图引用
- 把原来的S3绝对路径替换成EC2代理服务的接口地址,比如原来的
https://s3.amazonaws.com/xxx/screenshot1.png改成http://你的EC2内网IP:8080/screenshot/screenshot1.png。 - 如果需要更灵活的动态加载,用JS批量替换所有图片的
src属性:// 页面加载完成后替换截图地址 document.addEventListener('DOMContentLoaded', function() { const ec2ProxyUrl = 'http://你的EC2内网IP:8080/screenshot/'; document.querySelectorAll('.screenshot-img').forEach(img => { // 假设原src里保存了S3对象键,比如"s3://bucket/screenshot1.png",提取后半段 const s3Key = img.src.split('/').slice(3).join('/'); img.src = ec2ProxyUrl + s3Key; }); });
- 把原来的S3绝对路径替换成EC2代理服务的接口地址,比如原来的
权限控制(可选)
- 如果要限制访问,可以在代理服务里加简单的API Key验证,避免内网无关用户调用。
方案二:生成HTML时直接嵌入截图(Base64)
如果测试报告的截图数量少、体积小,可以在生成报告阶段,直接把S3里的截图转成Base64编码嵌入HTML,这样用户打开本地HTML时完全不需要依赖外部服务。
具体步骤:
- 在EC2生成测试报告的环节,通过IAM权限从S3拉取截图,将文件编码为Base64字符串。
- 在HTML中直接用
data:image/png;base64,xxxxxx作为图片的src属性:<img src="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABAAAAAQAQMAAAAlPW0iAAAABlBMVEUAAAD///+l2Z/dAAAAM0lEQVR4nGP4/5/h/1+G/58ZDrAz3D/McH8yw83NDDeNGe4Ug9C9zwz3gVLMDA/A6P9/AFGGFyjOXZtQAAAAAElFTkSuQmCC" alt="测试步骤截图"> - 注意:如果截图数量多、体积大,会导致HTML文件变得异常庞大,影响打开速度,所以这个方案只适合小体量报告。
为什么不能直接用JS调用S3?
本地浏览器的JS没法复用EC2的IAM角色权限,而且S3没有公网访问的话,浏览器根本连不上S3的端点,所以必须通过EC2中转或者提前嵌入。
内容的提问来源于stack exchange,提问作者mach
相关产品推荐
相关产品推荐

